[ioquake3] 01/02: Add patch from upstream for CVE-2017-11721

Simon McVittie smcv at debian.org
Fri Sep 8 10:33:15 UTC 2017


This is an automated email from the git hooks/post-receive script.

smcv pushed a commit to annotated tag debian/1.36+u20161101+dfsg1-2+deb9u1
in repository ioquake3.

commit 10ddd267dc17b0dac4167422beb327f379764cf4
Author: Simon McVittie <smcv at debian.org>
Date:   Mon Aug 7 17:43:23 2017 -0400

    Add patch from upstream for CVE-2017-11721
    
      + Address read buffer overflow in
        MSG_ReadBits (CVE-2017-11721) (Closes: #870725)
      + Check buffer boundary exactly in MSG_WriteBits, instead of
        potentially failing with a few bytes still available
---
 debian/changelog                                   |   5 +
 ...al-vmMagic-that-causes-equivalent-native-.patch |  10 +-
 ...-a-window-by-default-on-new-installations.patch |   4 +-
 ...er-overflow-in-MSG_ReadBits-MSG_WriteBits.patch | 213 +++++++++++++++++++++
 debian/patches/series                              |   1 +
 5 files changed, 226 insertions(+), 7 deletions(-)

diff --git a/debian/changelog b/debian/changelog
index 1c64d99..d225dac 100644
--- a/debian/changelog
+++ b/debian/changelog
@@ -1,6 +1,11 @@
 ioquake3 (1.36+u20161101+dfsg1-3) UNRELEASED; urgency=medium
 
   * Reference CVE-2017-6903 in previous changelog entry
+  * Add patch from upstream:
+    + Address read buffer overflow in
+      MSG_ReadBits (CVE-2017-11721) (Closes: #870725)
+    + Check buffer boundary exactly in MSG_WriteBits, instead of
+      potentially failing with a few bytes still available
 
  -- Simon McVittie <smcv at debian.org>  Tue, 14 Mar 2017 22:38:25 +0000
 
diff --git a/debian/patches/debian/Add-a-special-vmMagic-that-causes-equivalent-native-.patch b/debian/patches/debian/Add-a-special-vmMagic-that-causes-equivalent-native-.patch
index 067c7fe..0b10826 100644
--- a/debian/patches/debian/Add-a-special-vmMagic-that-causes-equivalent-native-.patch
+++ b/debian/patches/debian/Add-a-special-vmMagic-that-causes-equivalent-native-.patch
@@ -26,10 +26,10 @@ Forwarded: no
  4 files changed, 64 insertions(+), 5 deletions(-)
 
 diff --git a/code/qcommon/files.c b/code/qcommon/files.c
-index 3b4a8ae..3fcb125 100644
+index 27f5713..dc9b504 100644
 --- a/code/qcommon/files.c
 +++ b/code/qcommon/files.c
-@@ -1418,7 +1418,7 @@ Return the searchpath in "startSearch".
+@@ -1426,7 +1426,7 @@ Return the searchpath in "startSearch".
  =================
  */
  
@@ -38,7 +38,7 @@ index 3b4a8ae..3fcb125 100644
  {
  	searchpath_t *search, *lastSearch;
  	directory_t *dir;
-@@ -1442,7 +1442,7 @@ int FS_FindVM(void **startSearch, char *found, int foundlen, const char *name, i
+@@ -1450,7 +1450,7 @@ int FS_FindVM(void **startSearch, char *found, int foundlen, const char *name, i
  
  	while(search)
  	{
@@ -47,7 +47,7 @@ index 3b4a8ae..3fcb125 100644
  		{
  			dir = search->dir;
  
-@@ -1465,7 +1465,7 @@ int FS_FindVM(void **startSearch, char *found, int foundlen, const char *name, i
+@@ -1473,7 +1473,7 @@ int FS_FindVM(void **startSearch, char *found, int foundlen, const char *name, i
  				return VMI_COMPILED;
  			}
  		}
@@ -57,7 +57,7 @@ index 3b4a8ae..3fcb125 100644
  			pack = search->pack;
  
 diff --git a/code/qcommon/qcommon.h b/code/qcommon/qcommon.h
-index b965690..6847ee1 100644
+index da89f15..8648afe 100644
 --- a/code/qcommon/qcommon.h
 +++ b/code/qcommon/qcommon.h
 @@ -627,7 +627,7 @@ qboolean FS_FileExists( const char *file );
diff --git a/debian/patches/debian/Run-in-a-window-by-default-on-new-installations.patch b/debian/patches/debian/Run-in-a-window-by-default-on-new-installations.patch
index 7dd5735..2d9b3fc 100644
--- a/debian/patches/debian/Run-in-a-window-by-default-on-new-installations.patch
+++ b/debian/patches/debian/Run-in-a-window-by-default-on-new-installations.patch
@@ -33,10 +33,10 @@ index 15e7972..701c182 100644
  	r_customwidth = ri.Cvar_Get( "r_customwidth", "1600", CVAR_ARCHIVE | CVAR_LATCH );
  	r_customheight = ri.Cvar_Get( "r_customheight", "1024", CVAR_ARCHIVE | CVAR_LATCH );
 diff --git a/code/renderergl2/tr_init.c b/code/renderergl2/tr_init.c
-index 30803e2..c60ad40 100644
+index 7b9c21a..035e02c 100644
 --- a/code/renderergl2/tr_init.c
 +++ b/code/renderergl2/tr_init.c
-@@ -1186,8 +1186,8 @@ void R_Register( void )
+@@ -1182,8 +1182,8 @@ void R_Register( void )
  	ri.Cvar_CheckRange( r_ext_multisample, 0, 4, qtrue );
  	r_overBrightBits = ri.Cvar_Get ("r_overBrightBits", "1", CVAR_ARCHIVE | CVAR_LATCH );
  	r_ignorehwgamma = ri.Cvar_Get( "r_ignorehwgamma", "0", CVAR_ARCHIVE | CVAR_LATCH);
diff --git a/debian/patches/security/Fix-improve-buffer-overflow-in-MSG_ReadBits-MSG_WriteBits.patch b/debian/patches/security/Fix-improve-buffer-overflow-in-MSG_ReadBits-MSG_WriteBits.patch
new file mode 100644
index 0000000..f44bc70
--- /dev/null
+++ b/debian/patches/security/Fix-improve-buffer-overflow-in-MSG_ReadBits-MSG_WriteBits.patch
@@ -0,0 +1,213 @@
+From: Zack Middleton <zack at cloemail.com>
+Date: Wed, 2 Aug 2017 14:55:10 -0500
+Subject: Fix/improve buffer overflow in MSG_ReadBits/MSG_WriteBits
+
+Prevent reading past end of message in MSG_ReadBits. If read past
+end of msg->data buffer (16348 bytes) the engine could SEGFAULT.
+Make MSG_WriteBits use an exact buffer overflow check instead of
+possibly failing with a few bytes left.
+
+Origin: upstream, commit:d2b1d124d4055c2fcbe5126863487c52fd58cca1
+Bug-CVE: CVE-2017-11721
+Bug-Debian: https://bugs.debian.org/870725
+---
+ code/qcommon/huffman.c | 27 ++++++++++++++++++---------
+ code/qcommon/msg.c     | 40 +++++++++++++++++++++++++++++++++++-----
+ code/qcommon/qcommon.h |  6 +++---
+ 3 files changed, 56 insertions(+), 17 deletions(-)
+
+diff --git a/code/qcommon/huffman.c b/code/qcommon/huffman.c
+index c1b9f24..1f42498 100644
+--- a/code/qcommon/huffman.c
++++ b/code/qcommon/huffman.c
+@@ -279,9 +279,14 @@ int Huff_Receive (node_t *node, int *ch, byte *fin) {
+ }
+ 
+ /* Get a symbol */
+-void Huff_offsetReceive (node_t *node, int *ch, byte *fin, int *offset) {
++void Huff_offsetReceive (node_t *node, int *ch, byte *fin, int *offset, int maxoffset) {
+ 	bloc = *offset;
+ 	while (node && node->symbol == INTERNAL_NODE) {
++		if (bloc >= maxoffset) {
++			*ch = 0;
++			*offset = maxoffset + 1;
++			return;
++		}
+ 		if (get_bit(fin)) {
+ 			node = node->right;
+ 		} else {
+@@ -298,11 +303,15 @@ void Huff_offsetReceive (node_t *node, int *ch, byte *fin, int *offset) {
+ }
+ 
+ /* Send the prefix code for this node */
+-static void send(node_t *node, node_t *child, byte *fout) {
++static void send(node_t *node, node_t *child, byte *fout, int maxoffset) {
+ 	if (node->parent) {
+-		send(node->parent, node, fout);
++		send(node->parent, node, fout, maxoffset);
+ 	}
+ 	if (child) {
++		if (bloc >= maxoffset) {
++			bloc = maxoffset + 1;
++			return;
++		}
+ 		if (node->right == child) {
+ 			add_bit(1, fout);
+ 		} else {
+@@ -312,22 +321,22 @@ static void send(node_t *node, node_t *child, byte *fout) {
+ }
+ 
+ /* Send a symbol */
+-void Huff_transmit (huff_t *huff, int ch, byte *fout) {
++void Huff_transmit (huff_t *huff, int ch, byte *fout, int maxoffset) {
+ 	int i;
+ 	if (huff->loc[ch] == NULL) { 
+ 		/* node_t hasn't been transmitted, send a NYT, then the symbol */
+-		Huff_transmit(huff, NYT, fout);
++		Huff_transmit(huff, NYT, fout, maxoffset);
+ 		for (i = 7; i >= 0; i--) {
+ 			add_bit((char)((ch >> i) & 0x1), fout);
+ 		}
+ 	} else {
+-		send(huff->loc[ch], NULL, fout);
++		send(huff->loc[ch], NULL, fout, maxoffset);
+ 	}
+ }
+ 
+-void Huff_offsetTransmit (huff_t *huff, int ch, byte *fout, int *offset) {
++void Huff_offsetTransmit (huff_t *huff, int ch, byte *fout, int *offset, int maxoffset) {
+ 	bloc = *offset;
+-	send(huff->loc[ch], NULL, fout);
++	send(huff->loc[ch], NULL, fout, maxoffset);
+ 	*offset = bloc;
+ }
+ 
+@@ -413,7 +422,7 @@ void Huff_Compress(msg_t *mbuf, int offset) {
+ 
+ 	for (i=0; i<size; i++ ) {
+ 		ch = buffer[i];
+-		Huff_transmit(&huff, ch, seq);						/* Transmit symbol */
++		Huff_transmit(&huff, ch, seq, size<<3);						/* Transmit symbol */
+ 		Huff_addRef(&huff, (byte)ch);								/* Do update */
+ 	}
+ 
+diff --git a/code/qcommon/msg.c b/code/qcommon/msg.c
+index 20dec91..eb767be 100644
+--- a/code/qcommon/msg.c
++++ b/code/qcommon/msg.c
+@@ -107,9 +107,7 @@ void MSG_WriteBits( msg_t *msg, int value, int bits ) {
+ 
+ 	oldsize += bits;
+ 
+-	// this isn't an exact overflow check, but close enough
+-	if ( msg->maxsize - msg->cursize < 4 ) {
+-		msg->overflowed = qtrue;
++	if ( msg->overflowed ) {
+ 		return;
+ 	}
+ 
+@@ -122,6 +120,11 @@ void MSG_WriteBits( msg_t *msg, int value, int bits ) {
+ 	}
+ 
+ 	if ( msg->oob ) {
++		if ( msg->cursize + ( bits >> 3 ) > msg->maxsize ) {
++			msg->overflowed = qtrue;
++			return;
++		}
++
+ 		if ( bits == 8 ) {
+ 			msg->data[msg->cursize] = value;
+ 			msg->cursize += 1;
+@@ -144,6 +147,10 @@ void MSG_WriteBits( msg_t *msg, int value, int bits ) {
+ 		if ( bits&7 ) {
+ 			int nbits;
+ 			nbits = bits&7;
++			if ( msg->bit + nbits > msg->maxsize << 3 ) {
++				msg->overflowed = qtrue;
++				return;
++			}
+ 			for( i = 0; i < nbits; i++ ) {
+ 				Huff_putBit( (value & 1), msg->data, &msg->bit );
+ 				value = (value >> 1);
+@@ -152,8 +159,13 @@ void MSG_WriteBits( msg_t *msg, int value, int bits ) {
+ 		}
+ 		if ( bits ) {
+ 			for( i = 0; i < bits; i += 8 ) {
+-				Huff_offsetTransmit( &msgHuff.compressor, (value & 0xff), msg->data, &msg->bit );
++				Huff_offsetTransmit( &msgHuff.compressor, (value & 0xff), msg->data, &msg->bit, msg->maxsize << 3 );
+ 				value = (value >> 8);
++
++				if ( msg->bit > msg->maxsize << 3 ) {
++					msg->overflowed = qtrue;
++					return;
++				}
+ 			}
+ 		}
+ 		msg->cursize = (msg->bit >> 3) + 1;
+@@ -167,6 +179,10 @@ int MSG_ReadBits( msg_t *msg, int bits ) {
+ 	int			i, nbits;
+ //	FILE*	fp;
+ 
++	if ( msg->readcount > msg->cursize ) {
++		return 0;
++	}
++
+ 	value = 0;
+ 
+ 	if ( bits < 0 ) {
+@@ -177,6 +193,11 @@ int MSG_ReadBits( msg_t *msg, int bits ) {
+ 	}
+ 
+ 	if (msg->oob) {
++		if (msg->readcount + (bits>>3) > msg->cursize) {
++			msg->readcount = msg->cursize + 1;
++			return 0;
++		}
++
+ 		if(bits==8)
+ 		{
+ 			value = msg->data[msg->readcount];
+@@ -204,6 +225,10 @@ int MSG_ReadBits( msg_t *msg, int bits ) {
+ 		nbits = 0;
+ 		if (bits&7) {
+ 			nbits = bits&7;
++			if (msg->bit + nbits > msg->cursize << 3) {
++				msg->readcount = msg->cursize + 1;
++				return 0;
++			}
+ 			for(i=0;i<nbits;i++) {
+ 				value |= (Huff_getBit(msg->data, &msg->bit)<<i);
+ 			}
+@@ -212,9 +237,14 @@ int MSG_ReadBits( msg_t *msg, int bits ) {
+ 		if (bits) {
+ //			fp = fopen("c:\\netchan.bin", "a");
+ 			for(i=0;i<bits;i+=8) {
+-				Huff_offsetReceive (msgHuff.decompressor.tree, &get, msg->data, &msg->bit);
++				Huff_offsetReceive (msgHuff.decompressor.tree, &get, msg->data, &msg->bit, msg->cursize<<3);
+ //				fwrite(&get, 1, 1, fp);
+ 				value |= (get<<(i+nbits));
++
++				if (msg->bit > msg->cursize<<3) {
++					msg->readcount = msg->cursize + 1;
++					return 0;
++				}
+ 			}
+ //			fclose(fp);
+ 		}
+diff --git a/code/qcommon/qcommon.h b/code/qcommon/qcommon.h
+index f8cd035..da89f15 100644
+--- a/code/qcommon/qcommon.h
++++ b/code/qcommon/qcommon.h
+@@ -1191,9 +1191,9 @@ void	Huff_Decompress(msg_t *buf, int offset);
+ void	Huff_Init(huffman_t *huff);
+ void	Huff_addRef(huff_t* huff, byte ch);
+ int		Huff_Receive (node_t *node, int *ch, byte *fin);
+-void	Huff_transmit (huff_t *huff, int ch, byte *fout);
+-void	Huff_offsetReceive (node_t *node, int *ch, byte *fin, int *offset);
+-void	Huff_offsetTransmit (huff_t *huff, int ch, byte *fout, int *offset);
++void	Huff_transmit (huff_t *huff, int ch, byte *fout, int maxoffset);
++void	Huff_offsetReceive (node_t *node, int *ch, byte *fin, int *offset, int maxoffset);
++void	Huff_offsetTransmit (huff_t *huff, int ch, byte *fout, int *offset, int maxoffset);
+ void	Huff_putBit( int bit, byte *fout, int *offset);
+ int		Huff_getBit( byte *fout, int *offset);
+ 
diff --git a/debian/patches/series b/debian/patches/series
index 5be9dd2..63af1e9 100644
--- a/debian/patches/series
+++ b/debian/patches/series
@@ -1,6 +1,7 @@
 security/Don-t-load-.pk3s-as-.dlls-and-don-t-load-user-config-file.patch
 security/Don-t-open-.pk3-files-as-OpenAL-drivers.patch
 security/Merge-some-file-writing-extension-checks-from-OpenJK.patch
+security/Fix-improve-buffer-overflow-in-MSG_ReadBits-MSG_WriteBits.patch
 debian/Add-sv_dorestart-which-can-be-set-by-game-code-to-re.patch
 debian/Let-servers-set-sv_fps-too.patch
 debian/Add-a-special-vmMagic-that-causes-equivalent-native-.patch

-- 
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/pkg-games/ioquake3.git



More information about the Pkg-games-commits mailing list