Commit 22aaa20dab6 for php.net
commit 22aaa20dab657f43c309dbfbad0123674477c2ee
Author: Niels Dossche <7771979+ndossche@users.noreply.github.com>
Date: Fri Dec 19 18:21:45 2025 +0100
Fix GH-20732: Phar::LoadPhar undefined behavior when loading directory
The size of `got` was incorrect: it being unsigned means that the error
return codes are converted from -1 to SIZE_MAX. We should use ssize_t
instead.
Closes GH-20735.
diff --git a/NEWS b/NEWS
index 2c6bab631e6..d96969b286f 100644
--- a/NEWS
+++ b/NEWS
@@ -29,6 +29,10 @@ PHP NEWS
. Fixed bug GH-20674 (Fix GH-20674 mb_decode_mimeheader does not handle
separator). (Yuya Hamada)
+- Phar:
+ . Fixed bug GH-20732 (Phar::LoadPhar undefined behavior when reading fails).
+ (ndossche)
+
- SPL:
. Fixed bug GH-20678 (resource created by GlobIterator crashes with fclose()).
(David Carlier)
diff --git a/ext/phar/phar.c b/ext/phar/phar.c
index a63a8dd8eb6..4c2cab27dce 100644
--- a/ext/phar/phar.c
+++ b/ext/phar/phar.c
@@ -1609,7 +1609,7 @@ static int phar_open_from_fp(php_stream* fp, char *fname, size_t fname_len, char
const zend_long readsize = sizeof(buffer) - sizeof(token);
const zend_long tokenlen = sizeof(token) - 1;
zend_long halt_offset;
- size_t got;
+ ssize_t got;
uint32_t compression = PHAR_FILE_COMPRESSED_NONE;
if (error) {
@@ -1627,7 +1627,7 @@ static int phar_open_from_fp(php_stream* fp, char *fname, size_t fname_len, char
/* Maybe it's better to compile the file instead of just searching, */
/* but we only want the offset. So we want a .re scanner to find it. */
while(!php_stream_eof(fp)) {
- if ((got = php_stream_read(fp, buffer+tokenlen, readsize)) < (size_t) tokenlen) {
+ if ((got = php_stream_read(fp, buffer+tokenlen, readsize)) < tokenlen) {
MAPPHAR_ALLOC_FAIL("internal corruption of phar \"%s\" (truncated entry)")
}
diff --git a/ext/phar/tests/gh20732.phpt b/ext/phar/tests/gh20732.phpt
new file mode 100644
index 00000000000..b938d16d42c
--- /dev/null
+++ b/ext/phar/tests/gh20732.phpt
@@ -0,0 +1,14 @@
+--TEST--
+GH-20732 (Phar::LoadPhar undefined behavior when loading directory)
+--EXTENSIONS--
+phar
+--FILE--
+<?php
+try {
+ @Phar::LoadPhar('.');
+} catch (PharException $e) {
+ echo $e->getMessage(), "\n";
+}
+?>
+--EXPECTF--
+%r(internal corruption of phar "%s" \(truncated entry\)|unable to open phar for reading ".")%r