Skip to content

Commit 5177db1

Browse files
committed
Merge branch 'PHP-7.3'
* PHP-7.3: Fix #75273: php_zlib_inflate_filter() may not update bytes_consumed
2 parents 5df4955 + 58e2f5e commit 5177db1

File tree

2 files changed

+60
-10
lines changed

2 files changed

+60
-10
lines changed

ext/zlib/tests/bug75273.phpt

Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
--TEST--
2+
Bug #75273 (php_zlib_inflate_filter() may not update bytes_consumed)
3+
--SKIPIF--
4+
<?php
5+
if (!extension_loaded('zlib')) die('skip zlib extension not available');
6+
?>
7+
--FILE--
8+
<?php
9+
function non_repeating_str($len = 8192) {
10+
$ret = '';
11+
mt_srand(1);
12+
$iterations = (int) ($len / 256) + 1;
13+
for ($i = 0; $i < $iterations; $i++) {
14+
$haves = array();
15+
$cnt = 0;
16+
while ($cnt < 256) {
17+
$j = mt_rand(0, 255);
18+
if (!isset($haves[$j])) {
19+
$haves[$j] = $j;
20+
$cnt++;
21+
$ret .= chr($j);
22+
}
23+
}
24+
}
25+
return substr($ret, 0, $len);
26+
}
27+
28+
$base_len = 32768 - 23 /*overhead*/;
29+
30+
$stream = fopen('php://memory', 'rb+');
31+
32+
for ($i = 1; $i <= 8; $i++) {
33+
$in_data = non_repeating_str($base_len + $i);
34+
35+
$deflate_filter = stream_filter_append($stream, 'zlib.deflate', STREAM_FILTER_WRITE, ['window' => 16 + 15]);
36+
rewind($stream);
37+
fwrite($stream, $in_data);
38+
stream_filter_remove($deflate_filter);
39+
40+
rewind($stream);
41+
$out_data = stream_get_contents($stream);
42+
$out_data_len = strlen($out_data);
43+
44+
$inflate_filter = stream_filter_prepend($stream, 'zlib.inflate', STREAM_FILTER_WRITE, ['window' => 16 + 15]);
45+
rewind($stream);
46+
$fwrite_len = fwrite($stream, $out_data);
47+
stream_filter_remove($inflate_filter);
48+
49+
if ($out_data_len !== $fwrite_len) {
50+
echo "bug i=$i out_data_len=$out_data_len fwrite_len=$fwrite_len\n";
51+
}
52+
}
53+
54+
fclose($stream);
55+
?>
56+
===DONE===
57+
--EXPECT--
58+
===DONE===

ext/zlib/zlib_filter.c

Lines changed: 2 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -76,12 +76,7 @@ static php_stream_filter_status_t php_zlib_inflate_filter(
7676

7777
bucket = php_stream_bucket_make_writeable(buckets_in->head);
7878

79-
while (bin < (unsigned int) bucket->buflen) {
80-
81-
if (data->finished) {
82-
consumed += bucket->buflen;
83-
break;
84-
}
79+
while (bin < (unsigned int) bucket->buflen && !data->finished) {
8580

8681
desired = bucket->buflen - bin;
8782
if (desired > data->inbuf_len) {
@@ -94,6 +89,7 @@ static php_stream_filter_status_t php_zlib_inflate_filter(
9489
if (status == Z_STREAM_END) {
9590
inflateEnd(&(data->strm));
9691
data->finished = '\1';
92+
exit_status = PSFS_PASS_ON;
9793
} else if (status != Z_OK) {
9894
/* Something bad happened */
9995
php_stream_bucket_delref(bucket);
@@ -116,10 +112,6 @@ static php_stream_filter_status_t php_zlib_inflate_filter(
116112
data->strm.avail_out = data->outbuf_len;
117113
data->strm.next_out = data->outbuf;
118114
exit_status = PSFS_PASS_ON;
119-
} else if (status == Z_STREAM_END && data->strm.avail_out >= data->outbuf_len) {
120-
/* no more data to decompress, and nothing was spat out */
121-
php_stream_bucket_delref(bucket);
122-
return PSFS_PASS_ON;
123115
}
124116

125117
}

0 commit comments

Comments
 (0)