Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions NEWS
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,8 @@ PHP NEWS
with no other live PDO handle. (iliaal)

- Standard:
. Fixed a segfault when a stream filter callback unsets StreamBucket::$data
before re-attaching the bucket. (iliaal)
. Fixed a memory leak in array_merge_recursive() when the recursive merge of
an object converted to an array fails. (David Carlier)

Expand Down
27 changes: 27 additions & 0 deletions ext/standard/tests/filters/bucket_data_unset.phpt
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
--TEST--
unset(StreamBucket::$data) in filter callback must not crash when bucket is re-attached
--FILE--
<?php
class MyFilter extends php_user_filter {
public function filter($in, $out, &$consumed, bool $closing): int {
while ($bucket = stream_bucket_make_writeable($in)) {
unset($bucket->data);
stream_bucket_prepend($out, $bucket);
}
return PSFS_PASS_ON;
}
}
stream_filter_register("myfilter", "MyFilter");
$fp = fopen("php://temp", "w+");
fwrite($fp, str_repeat("A", 100));
rewind($fp);
stream_filter_append($fp, "myfilter");
try {
var_dump(stream_get_contents($fp));
} catch (Throwable $e) {
echo $e::class, ': ', $e->getMessage(), "\n";
}
echo "DONE\n";
--EXPECT--
Error: Typed property StreamBucket::$data must not be accessed before initialization
DONE
4 changes: 4 additions & 0 deletions ext/standard/user_filters.c
Original file line number Diff line number Diff line change
Expand Up @@ -424,6 +424,10 @@ static void php_stream_bucket_attach(int append, INTERNAL_FUNCTION_PARAMETERS)

if (NULL != (pzdata = zend_read_property(NULL, Z_OBJ_P(zobject), "data", sizeof("data")-1, false, &rv))) {

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

note: not from your change but seems to me zend_read_property does not return NULL ?

@iliaal iliaal Aug 26, 2026

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Correct, std read_property returns &EG(uninitialized_zval). Pre-existing.

ZVAL_DEREF(pzdata);
if (EG(exception)) {
RETURN_THROWS();
}
ZEND_ASSERT(Z_TYPE_P(pzdata) == IS_STRING);
if (!bucket->own_buf) {
bucket = php_stream_bucket_make_writeable(bucket);
}
Expand Down
Loading