Stefan Fritsch wrote: > Package: freeciv > Severity: grave > Tags: security > Justification: user security hole > > CVE-2006-3913: > "Buffer overflow in Freeciv 2.1.0-beta1 and earlier, and SVN 15 Jul > 2006 and earlier, allows remote attackers to cause a denial of service > (crash) and possibly execute arbitrary code via a (1) negative > chunk_length or a (2) large chunk->offset value in a > PACKET_PLAYER_ATTRIBUTE_CHUNK packet in the > generic_handle_player_attribute_chunk function in common/packets.c, > and (3) a large packet->length value in the handle_unit_orders > function in server/unithand.c." > > Please mention the CVE-id in the changelog.
Attached please find the patch sent to the maintainer already. Regards, Joey -- In the beginning was the word, and the word was content-type: text/plain Please always Cc to me when replying to me on the lists.
#! /bin/sh /usr/share/dpatch/dpatch-run ## 04_CVE-2006-3913.dpatch by Joey Schulze <[EMAIL PROTECTED]> ## ## All lines beginning with `## DP:' are a description of the patch. ## DP: Fix DoS due to missing boundary checks @DPATCH@ diff -u -p -Nr --exclude CVS freeciv-2.0.1.orig/common/packets.c freeciv-2.0.1/common/packets.c --- freeciv-2.0.1.orig/common/packets.c 2006-07-28 16:48:40.000000000 +0200 +++ freeciv-2.0.1/common/packets.c 2006-07-28 16:55:23.000000000 +0200 @@ -573,6 +573,8 @@ void generic_handle_player_attribute_chu packet_player_attribute_chunk *chunk) { + if (chunk->total_length < 0) + return; /* first one in a row */ if (chunk->offset == 0) { if (pplayer->attribute_block.data) { diff -u -p -Nr --exclude CVS freeciv-2.0.1.orig/server/unithand.c freeciv-2.0.1/server/unithand.c --- freeciv-2.0.1.orig/server/unithand.c 2005-04-01 06:19:35.000000000 +0200 +++ freeciv-2.0.1/server/unithand.c 2006-07-28 17:03:29.000000000 +0200 @@ -1602,7 +1602,7 @@ void handle_unit_orders(struct player *p struct unit *punit = player_find_unit_by_id(pplayer, packet->unit_id); int i; - if (!punit || packet->length < 0 || punit->activity != ACTIVITY_IDLE) { + if (!punit || packet->length < 0 || packet->length > MAX_LEN_ROUTE || punit->activity != ACTIVITY_IDLE) { return; }