diff options
| author | Anatol Belski <ab@php.net> | 2016-11-08 11:13:29 +0100 |
|---|---|---|
| committer | Anatol Belski <ab@php.net> | 2016-11-08 11:13:29 +0100 |
| commit | 2b30b542750a917932fed29cafac83d40a045ffe (patch) | |
| tree | 93730bf6b1787772a50d3ac9d2ff96674e697a24 | |
| parent | 5faaf76bd51818fb5954a12643a2de8f76120fcd (diff) | |
| parent | de643586dee986ff16c0a6be44813687786aa781 (diff) | |
| download | php-git-2b30b542750a917932fed29cafac83d40a045ffe.tar.gz | |
Merge remote-tracking branch 'phpsec/PHP-7.0.13' into PHP-7.0
* phpsec/PHP-7.0.13:
Fixed bug #73418 Integer Overflow in "_php_imap_mail" leads to crash
Fix #72696: imagefilltoborder stackoverflow on truecolor images
Fix #72482: Ilegal write/read access caused by gdImageAALine overflow
Fix bug #73144 and bug #73341 - remove extra dtor
remove unreferenced var came in with merge
Fix bug #73331 - do not try to serialize/unserialize objects wddx can not handle
fix version
set versions
| -rw-r--r-- | ext/gd/libgd/gd.c | 53 | ||||
| -rw-r--r-- | ext/gd/tests/bug72482.phpt | 19 | ||||
| -rw-r--r-- | ext/gd/tests/bug72482_2.phpt | 21 | ||||
| -rw-r--r-- | ext/gd/tests/bug72482_2.png | bin | 0 -> 118 bytes | |||
| -rw-r--r-- | ext/gd/tests/bug72696.phpt | 14 | ||||
| -rw-r--r-- | ext/imap/php_imap.c | 2 | ||||
| -rw-r--r-- | ext/pdo/pdo_stmt.c | 1 | ||||
| -rw-r--r-- | ext/standard/tests/serialize/bug73341.phpt | 24 | ||||
| -rw-r--r-- | ext/wddx/tests/bug45901.phpt | 4 | ||||
| -rw-r--r-- | ext/wddx/tests/bug72790.phpt | 2 | ||||
| -rw-r--r-- | ext/wddx/tests/bug73331.phpt | 15 | ||||
| -rw-r--r-- | ext/wddx/wddx.c | 51 |
12 files changed, 133 insertions, 73 deletions
diff --git a/ext/gd/libgd/gd.c b/ext/gd/libgd/gd.c index 99cbdde776..8d1e48dce5 100644 --- a/ext/gd/libgd/gd.c +++ b/ext/gd/libgd/gd.c @@ -1115,7 +1115,7 @@ void gdImageLine (gdImagePtr im, int x1, int y1, int x2, int y2, int color) } /* 2.0.10: Nick Atty: clip to edges of drawing rectangle, return if no points need to be drawn */ - if (!clip_1d(&x1,&y1,&x2,&y2,gdImageSX(im)) || !clip_1d(&y1,&x1,&y2,&x2,gdImageSY(im))) { + if (!clip_1d(&x1,&y1,&x2,&y2,gdImageSX(im)-1) || !clip_1d(&y1,&x1,&y2,&x2,gdImageSY(im)-1)) { return; } @@ -1299,55 +1299,10 @@ void gdImageAALine (gdImagePtr im, int x1, int y1, int x2, int y2, int col) long x, y, inc, frac; long dx, dy,tmp; - if (y1 < 0 && y2 < 0) { - return; - } - if (y1 < 0) { - x1 += (y1 * (x1 - x2)) / (y2 - y1); - y1 = 0; - } - if (y2 < 0) { - x2 += (y2 * (x1 - x2)) / (y2 - y1); - y2 = 0; - } - - /* bottom edge */ - if (y1 >= im->sy && y2 >= im->sy) { - return; - } - if (y1 >= im->sy) { - x1 -= ((im->sy - y1) * (x1 - x2)) / (y2 - y1); - y1 = im->sy - 1; - } - if (y2 >= im->sy) { - x2 -= ((im->sy - y2) * (x1 - x2)) / (y2 - y1); - y2 = im->sy - 1; - } - - /* left edge */ - if (x1 < 0 && x2 < 0) { - return; - } - if (x1 < 0) { - y1 += (x1 * (y1 - y2)) / (x2 - x1); - x1 = 0; - } - if (x2 < 0) { - y2 += (x2 * (y1 - y2)) / (x2 - x1); - x2 = 0; - } - /* right edge */ - if (x1 >= im->sx && x2 >= im->sx) { + /* 2.0.10: Nick Atty: clip to edges of drawing rectangle, return if no points need to be drawn */ + if (!clip_1d(&x1,&y1,&x2,&y2,gdImageSX(im)-1) || !clip_1d(&y1,&x1,&y2,&x2,gdImageSY(im)-1)) { return; } - if (x1 >= im->sx) { - y1 -= ((im->sx - x1) * (y1 - y2)) / (x2 - x1); - x1 = im->sx - 1; - } - if (x2 >= im->sx) { - y2 -= ((im->sx - x2) * (y1 - y2)) / (x2 - x1); - x2 = im->sx - 1; - } dx = x2 - x1; dy = y2 - y1; @@ -1790,7 +1745,7 @@ void gdImageFillToBorder (gdImagePtr im, int x, int y, int border, int color) int leftLimit = -1, rightLimit; int i, restoreAlphaBlending = 0; - if (border < 0) { + if (border < 0 || color < 0) { /* Refuse to fill to a non-solid border */ return; } diff --git a/ext/gd/tests/bug72482.phpt b/ext/gd/tests/bug72482.phpt new file mode 100644 index 0000000000..548921d559 --- /dev/null +++ b/ext/gd/tests/bug72482.phpt @@ -0,0 +1,19 @@ +--TEST-- +Bug #72482 (Ilegal write/read access caused by gdImageAALine overflow) +--SKIPIF-- +<?php +if (!extension_loaded('gd')) die('skip gd extension not available'); +?> +--FILE-- +<?php +$img = imagecreatetruecolor(13, 1007); +imageantialias($img, true); +imageline($img, 0, 0, 1073745919, 1073745919, 4096); + +$img = imagecreatetruecolor(100, 100); +imageantialias($img, true); +imageline($img, 1094795585, 0, 2147483647, 255, 0xff); +?> +===DONE=== +--EXPECT-- +===DONE=== diff --git a/ext/gd/tests/bug72482_2.phpt b/ext/gd/tests/bug72482_2.phpt new file mode 100644 index 0000000000..a8a08faa53 --- /dev/null +++ b/ext/gd/tests/bug72482_2.phpt @@ -0,0 +1,21 @@ +--TEST-- +Bug 72482 (Ilegal write/read access caused by gdImageAALine overflow) +--SKIPIF-- +<?php +if (!extension_loaded('gd')) die('skip gd extension not available'); +?> +--FILE-- +<?php +require_once __DIR__ . DIRECTORY_SEPARATOR . 'func.inc'; + +$im = imagecreatetruecolor(10, 10); +imagefilledrectangle($im, 0, 0, 9, 9, imagecolorallocate($im, 255, 255, 255)); +imageantialias($im, true); +imageline($im, 0, 0, 10, 10, imagecolorallocate($im, 0, 0, 0)); + +test_image_equals_file(__DIR__ . DIRECTORY_SEPARATOR . 'bug72482_2.png', $im); +?> +===DONE=== +--EXPECT-- +The images are equal. +===DONE=== diff --git a/ext/gd/tests/bug72482_2.png b/ext/gd/tests/bug72482_2.png Binary files differnew file mode 100644 index 0000000000..da90b2a267 --- /dev/null +++ b/ext/gd/tests/bug72482_2.png diff --git a/ext/gd/tests/bug72696.phpt b/ext/gd/tests/bug72696.phpt new file mode 100644 index 0000000000..4f0d9e7f1d --- /dev/null +++ b/ext/gd/tests/bug72696.phpt @@ -0,0 +1,14 @@ +--TEST-- +Bug #72696 (imagefilltoborder stackoverflow on truecolor images) +--SKIPIF-- +<?php +if (!extension_loaded('gd')) die('skip gd extension not available'); +?> +--FILE-- +<?php +$im = imagecreatetruecolor(10, 10); +imagefilltoborder($im, 0, 0, 1, -2); +?> +===DONE=== +--EXPECT-- +===DONE=== diff --git a/ext/imap/php_imap.c b/ext/imap/php_imap.c index a8eae27b0e..8ac5ed4150 100644 --- a/ext/imap/php_imap.c +++ b/ext/imap/php_imap.c @@ -3934,7 +3934,7 @@ int _php_imap_mail(char *to, char *subject, char *message, char *headers, char * char *tsm_errmsg = NULL; ADDRESS *addr; char *bufferTo = NULL, *bufferCc = NULL, *bufferBcc = NULL, *bufferHeader = NULL; - int offset, bufferLen = 0; + size_t offset, bufferLen = 0; size_t bt_len; if (headers) { diff --git a/ext/pdo/pdo_stmt.c b/ext/pdo/pdo_stmt.c index d135467192..0ff8a04000 100644 --- a/ext/pdo/pdo_stmt.c +++ b/ext/pdo/pdo_stmt.c @@ -2299,6 +2299,7 @@ void pdo_stmt_init(void) pdo_row_ce->ce_flags |= ZEND_ACC_FINAL; /* when removing this a lot of handlers need to be redone */ pdo_row_ce->create_object = pdo_row_new; pdo_row_ce->serialize = pdo_row_serialize; + pdo_row_ce->unserialize = zend_class_unserialize_deny; } PDO_API void php_pdo_free_statement(pdo_stmt_t *stmt) diff --git a/ext/standard/tests/serialize/bug73341.phpt b/ext/standard/tests/serialize/bug73341.phpt new file mode 100644 index 0000000000..55423217c3 --- /dev/null +++ b/ext/standard/tests/serialize/bug73341.phpt @@ -0,0 +1,24 @@ +--TEST-- +Bug #73144 (Use-afte-free in ArrayObject Deserialization) +--FILE-- +<?php +try { +$token = 'a:2:{i:0;O:1:"0":2:0s:1:"0";i:0;s:1:"0";a:1:{i:0;C:11:"ArrayObject":7:0x:i:0;r0'; +$obj = unserialize($token); +} catch(Exception $e) { + echo $e->getMessage()."\n"; +} + +try { +$inner = 'x:i:1;O:8:"stdClass":1:{};m:a:0:{}'; +$exploit = 'C:11:"ArrayObject":'.strlen($inner).':{'.$inner.'}'; +unserialize($exploit); +} catch(Exception $e) { + echo $e->getMessage()."\n"; +} +?> +--EXPECTF-- +Error at offset 6 of 7 bytes + +Notice: ArrayObject::unserialize(): Unexpected end of serialized data in %sbug73341.php on line %d +Error at offset 24 of 34 bytes
\ No newline at end of file diff --git a/ext/wddx/tests/bug45901.phpt b/ext/wddx/tests/bug45901.phpt index 4084ccbf20..e76e47eab7 100644 --- a/ext/wddx/tests/bug45901.phpt +++ b/ext/wddx/tests/bug45901.phpt @@ -14,5 +14,7 @@ echo wddx_serialize_value($xml, 'Variables') . "\n"; echo "DONE"; ?> --EXPECTF-- -<wddxPacket version='1.0'><header><comment>Variables</comment></header><data><struct><var name='php_class_name'><string>SimpleXMLElement</string></var><var name='test'><struct><var name='php_class_name'><string>SimpleXMLElement</string></var></struct></var></struct></data></wddxPacket> + +Warning: wddx_serialize_value(): Class SimpleXMLElement can not be serialized in %sbug45901.php on line %d +<wddxPacket version='1.0'><header><comment>Variables</comment></header><data></data></wddxPacket> DONE
\ No newline at end of file diff --git a/ext/wddx/tests/bug72790.phpt b/ext/wddx/tests/bug72790.phpt index a60524bdaf..3b08e58cc6 100644 --- a/ext/wddx/tests/bug72790.phpt +++ b/ext/wddx/tests/bug72790.phpt @@ -1,5 +1,5 @@ --TEST-- -Bug 72790: wddx_deserialize null dereference with invalid xml +Bug #72790: wddx_deserialize null dereference with invalid xml --SKIPIF-- <?php if (!extension_loaded('wddx')) { diff --git a/ext/wddx/tests/bug73331.phpt b/ext/wddx/tests/bug73331.phpt new file mode 100644 index 0000000000..7e4cda1ea1 --- /dev/null +++ b/ext/wddx/tests/bug73331.phpt @@ -0,0 +1,15 @@ +--TEST-- +Bug #73331 (NULL Pointer Dereference in WDDX Packet Deserialization with PDORow) +--SKIPIF-- +<?php if (!extension_loaded("wddx") || !extension_loaded("pdo")) print "skip"; ?> +--FILE-- +<?php + +$wddx = "<wddxPacket version='1.0'><header/><data><struct><var name='php_class_name'><string>PDORow</string></var></struct></data></wddxPacket>"; +var_dump(wddx_deserialize($wddx)); +?> +--EXPECTF-- + +Warning: wddx_deserialize(): Class pdorow can not be unserialized in %s73331.php on line %d +NULL + diff --git a/ext/wddx/wddx.c b/ext/wddx/wddx.c index 7d805e484f..e21d178edf 100644 --- a/ext/wddx/wddx.c +++ b/ext/wddx/wddx.c @@ -453,6 +453,16 @@ static void php_wddx_serialize_object(wddx_packet *packet, zval *obj) zend_ulong idx; char tmp_buf[WDDX_BUF_LEN]; HashTable *objhash, *sleephash; + zend_class_entry *ce; + PHP_CLASS_ATTRIBUTES; + + PHP_SET_CLASS_ATTRIBUTES(obj); + ce = Z_OBJCE_P(obj); + if (!ce || ce->serialize || ce->unserialize) { + php_error_docref(NULL, E_WARNING, "Class %s can not be serialized", ZSTR_VAL(class_name)); + PHP_CLEANUP_CLASS_ATTRIBUTES(); + return; + } ZVAL_STRING(&fname, "__sleep"); /* @@ -473,8 +483,6 @@ static void php_wddx_serialize_object(wddx_packet *packet, zval *obj) php_wddx_add_chunk_static(packet, WDDX_STRING_E); php_wddx_add_chunk_static(packet, WDDX_VAR_E); - PHP_CLEANUP_CLASS_ATTRIBUTES(); - objhash = Z_OBJPROP_P(obj); ZEND_HASH_FOREACH_VAL(sleephash, varname) { @@ -491,10 +499,6 @@ static void php_wddx_serialize_object(wddx_packet *packet, zval *obj) php_wddx_add_chunk_static(packet, WDDX_STRUCT_E); } } else { - PHP_CLASS_ATTRIBUTES; - - PHP_SET_CLASS_ATTRIBUTES(obj); - php_wddx_add_chunk_static(packet, WDDX_STRUCT_S); snprintf(tmp_buf, WDDX_BUF_LEN, WDDX_VAR_S, PHP_CLASS_NAME_VAR); php_wddx_add_chunk(packet, tmp_buf); @@ -503,8 +507,6 @@ static void php_wddx_serialize_object(wddx_packet *packet, zval *obj) php_wddx_add_chunk_static(packet, WDDX_STRING_E); php_wddx_add_chunk_static(packet, WDDX_VAR_E); - PHP_CLEANUP_CLASS_ATTRIBUTES(); - objhash = Z_OBJPROP_P(obj); ZEND_HASH_FOREACH_KEY_VAL(objhash, idx, key, ent) { if (ent == obj) { @@ -528,6 +530,8 @@ static void php_wddx_serialize_object(wddx_packet *packet, zval *obj) php_wddx_add_chunk_static(packet, WDDX_STRUCT_E); } + PHP_CLEANUP_CLASS_ATTRIBUTES(); + zval_ptr_dtor(&fname); zval_ptr_dtor(&retval); } @@ -947,23 +951,28 @@ static void php_wddx_pop_element(void *user_data, const XML_Char *name) pce = PHP_IC_ENTRY; } - /* Initialize target object */ - object_init_ex(&obj, pce); + if (pce != PHP_IC_ENTRY && (pce->serialize || pce->unserialize)) { + ZVAL_UNDEF(&ent2->data); + php_error_docref(NULL, E_WARNING, "Class %s can not be unserialized", Z_STRVAL(ent1->data)); + } else { + /* Initialize target object */ + object_init_ex(&obj, pce); - /* Merge current hashtable with object's default properties */ - zend_hash_merge(Z_OBJPROP(obj), - Z_ARRVAL(ent2->data), - zval_add_ref, 0); + /* Merge current hashtable with object's default properties */ + zend_hash_merge(Z_OBJPROP(obj), + Z_ARRVAL(ent2->data), + zval_add_ref, 0); - if (incomplete_class) { - php_store_class_name(&obj, Z_STRVAL(ent1->data), Z_STRLEN(ent1->data)); - } + if (incomplete_class) { + php_store_class_name(&obj, Z_STRVAL(ent1->data), Z_STRLEN(ent1->data)); + } - /* Clean up old array entry */ - zval_ptr_dtor(&ent2->data); + /* Clean up old array entry */ + zval_ptr_dtor(&ent2->data); - /* Set stack entry to point to the newly created object */ - ZVAL_COPY_VALUE(&ent2->data, &obj); + /* Set stack entry to point to the newly created object */ + ZVAL_COPY_VALUE(&ent2->data, &obj); + } /* Clean up class name var entry */ zval_ptr_dtor(&ent1->data); |
