com php-src: Fix #72482: Ilegal write/read access caused by gdImageAALine overflow: ext/gd/libgd/gd.c ext/gd/tests/bug72482.phpt
ext/gd/tests/bug72482_2.phpt ext/gd/tests/bug 72482_2.png
| From: | Anatol Belski | Date: | Tue, 01 Nov 2016 12:03:41 +0000 |
| Subject: | com php-src: Fix #72482: Ilegal write/read access caused by gdImageAALine overflow: ext/gd/libgd/gd.c ext/gd/tests/bug72482.phpt ext/gd/tests/bug72482_2.phpt ext/gd/tests/bug 72482_2.png |
||
| Groups: | php.cvs | ||
| Request: | Send a blank email to php-cvs+get-95438@lists.php.net to get a copy of this message | ||
Commit: 1b5543b8ab22b85c14546649057475fce2083fbd
Author: Christoph M. Becker <cmbecker69@gmx.de> Tue, 25 Oct 2016 15:14:22 +0200
Committer: Anatol Belski <ab@php.net> Tue, 1 Nov 2016 13:03:41 +0100
Parents: 7cf7920055d44da72529b4277e6890c99cf1932e
Branches: PHP-7.0 PHP-7.1 master
Link: http://git.php.net/?p=php-src.git;a=commitdiff;h=1b5543b8ab22b85c14546649057475fce2083fbd
Log:
Fix #72482: Ilegal write/read access caused by gdImageAALine overflow
Instead of rolling our own bounds check we use clip_1d() as it's done
in gdImageLine() and in external libgd. We must not pass the image
width and height, respectively, but rather the largest ordinate value
that is allowed to be accessed, i.e. width-1 and height-1,
respectively.
(cherry picked from commit 6499581af76cfe986e12330faabb3a7c36d45ffc)
Bugs:
https://bugs.php.net/72482
Changed paths:
M ext/gd/libgd/gd.c
A ext/gd/tests/bug72482.phpt
A ext/gd/tests/bug72482_2.phpt
A ext/gd/tests/bug72482_2.png
Diff:
diff --git a/ext/gd/libgd/gd.c b/ext/gd/libgd/gd.c
index 99cbdde..0673a8d 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;
diff --git a/ext/gd/tests/bug72482.phpt b/ext/gd/tests/bug72482.phpt
new file mode 100644
index 0000000..548921d
--- /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 0000000..a8a08fa
--- /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
new file mode 100644
index 0000000..da90b2a
Binary files /dev/null and b/ext/gd/tests/bug72482_2.png differ