summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChristoph M. Becker <cmbecker69@gmx.de>2016-12-17 17:06:58 +0100
committerAnatol Belski <ab@php.net>2017-01-17 09:42:45 +0100
commit761cc2b766e040452f026a3b4c3b2c71bcbfb3dd (patch)
treed73d324624968305b1cfa44d5ed10b1a1d68da1d
parent564a161258e53c05e1d0b02a16568e24d4da3b51 (diff)
downloadphp-git-761cc2b766e040452f026a3b4c3b2c71bcbfb3dd.tar.gz
Fix #73869: Signed Integer Overflow gd_io.c
GD2 stores the number of horizontal and vertical chunks as words (i.e. 2 byte unsigned). These values are multiplied and assigned to an int when reading the image, what can cause integer overflows. We have to avoid that, and also make sure that either chunk count is actually greater than zero. If illegal chunk counts are detected, we bail out from reading the image. (cherry picked from commit 5b5d9db3988b829e0b121b74bb3947f01c2796a1) (cherry picked from commit d2274b01cbbadf5516b3ea87ad76fbae18834007)
-rw-r--r--ext/gd/libgd/gd_gd2.c4
-rw-r--r--ext/gd/tests/bug73869.phpt19
-rw-r--r--ext/gd/tests/bug73869a.gd2bin0 -> 92 bytes
-rw-r--r--ext/gd/tests/bug73869b.gd2bin0 -> 18 bytes
4 files changed, 23 insertions, 0 deletions
diff --git a/ext/gd/libgd/gd_gd2.c b/ext/gd/libgd/gd_gd2.c
index d06f328425..83eaaa3d6c 100644
--- a/ext/gd/libgd/gd_gd2.c
+++ b/ext/gd/libgd/gd_gd2.c
@@ -136,6 +136,10 @@ static int _gd2GetHeader(gdIOCtxPtr in, int *sx, int *sy, int *cs, int *vers, in
GD2_DBG(php_gd_error("%d Chunks vertically", *ncy));
if (gd2_compressed(*fmt)) {
+ if (*ncx <= 0 || *ncy <= 0 || *ncx > INT_MAX / *ncy) {
+ GD2_DBG(printf ("Illegal chunk counts: %d * %d\n", *ncx, *ncy));
+ goto fail1;
+ }
nc = (*ncx) * (*ncy);
GD2_DBG(php_gd_error("Reading %d chunk index entries", nc));
if (overflow2(sizeof(t_chunk_info), nc)) {
diff --git a/ext/gd/tests/bug73869.phpt b/ext/gd/tests/bug73869.phpt
new file mode 100644
index 0000000000..3cc10a4201
--- /dev/null
+++ b/ext/gd/tests/bug73869.phpt
@@ -0,0 +1,19 @@
+--TEST--
+Bug #73869 (Signed Integer Overflow gd_io.c)
+--SKIPIF--
+<?php
+if (!extension_loaded('gd')) die('skip gd extension not available');
+?>
+--FILE--
+<?php
+var_dump(imagecreatefromgd2(__DIR__ . DIRECTORY_SEPARATOR . 'bug73869a.gd2'));
+var_dump(imagecreatefromgd2(__DIR__ . DIRECTORY_SEPARATOR . 'bug73869b.gd2'));
+?>
+===DONE===
+--EXPECTF--
+Warning: imagecreatefromgd2(): '%s' is not a valid GD2 file in %s on line %d
+bool(false)
+
+Warning: imagecreatefromgd2(): '%s' is not a valid GD2 file in %s on line %d
+bool(false)
+===DONE=== \ No newline at end of file
diff --git a/ext/gd/tests/bug73869a.gd2 b/ext/gd/tests/bug73869a.gd2
new file mode 100644
index 0000000000..5060bfde3a
--- /dev/null
+++ b/ext/gd/tests/bug73869a.gd2
Binary files differ
diff --git a/ext/gd/tests/bug73869b.gd2 b/ext/gd/tests/bug73869b.gd2
new file mode 100644
index 0000000000..8600126bec
--- /dev/null
+++ b/ext/gd/tests/bug73869b.gd2
Binary files differ