Commit dfdae429ca0 for php.net

commit dfdae429ca0933169ff7e79fb9a5bacd89f56d43
Author: Louis-Arnaud <la.catoire@gmail.com>
Date:   Sun Sep 6 14:58:17 2026 +0200

    Fix wrong argument number and UB in fsockopen timeout error (#23431)

    php_fsockopen_stream() called zend_argument_value_error(6, ...) for the
    $timeout parameter, but $timeout is the 5th argument. This caused the
    error message to show "Argument #6" with no parameter name, since
    get_function_arg_name() returns NULL when arg_num exceeds the actual
    argument count.

    The format string also contained ZEND_ULONG_FMT (which expects a zend_ulong)
    but received a double expression, causing undefined behavior.
    This is fixed by casting to uint64_t instead.

diff --git a/NEWS b/NEWS
index 41b26e5d094..ab8e20c7507 100644
--- a/NEWS
+++ b/NEWS
@@ -104,6 +104,8 @@ PHP                                                                        NEWS
   . Fixed read buffer compaction in php_stream_filter_flush(). (crystarm)
   . Fixed bug GH-22410 (Incorrect float behavior with large numbers).
     (arshidkv12)
+  . Fixed GH-23338 (fsockopen()/pfsockopen() ValueError reported wrong
+    argument number for $timeout). (lacatoire)

 - SimpleXML:
   . Fixed writing to a dimension of the object returned by attributes() not
diff --git a/ext/standard/fsock.c b/ext/standard/fsock.c
index c8e6ed08e4c..bf60f610f84 100644
--- a/ext/standard/fsock.c
+++ b/ext/standard/fsock.c
@@ -107,7 +107,7 @@ static void php_fsockopen_stream(INTERNAL_FUNCTION_PARAMETERS, int persistent)
 			efree(hashkey);
 		}

-		zend_argument_value_error(6, "must be -1 or between 0 and " ZEND_ULONG_FMT, ((double) PHP_TIMEOUT_ULL_MAX / 1000000.0));
+		zend_argument_value_error(5, "must be -1 or between 0 and %" PRIu64, (uint64_t) ((double) PHP_TIMEOUT_ULL_MAX / 1000000.0));
 		RETURN_THROWS();
 	} else {
 #ifndef PHP_WIN32
diff --git a/ext/standard/tests/network/fsockopen_timeout_out_of_range.phpt b/ext/standard/tests/network/fsockopen_timeout_out_of_range.phpt
new file mode 100644
index 00000000000..575db4690fb
--- /dev/null
+++ b/ext/standard/tests/network/fsockopen_timeout_out_of_range.phpt
@@ -0,0 +1,19 @@
+--TEST--
+fsockopen() and pfsockopen(): ValueError for $timeout reports correct argument number and name
+--FILE--
+<?php
+try {
+    fsockopen('localhost', 80, $errno, $errstr, -2.0);
+} catch (Throwable $e) {
+    echo $e::class, ': ', $e->getMessage(), "\n";
+}
+
+try {
+    pfsockopen('localhost', 80, $errno, $errstr, -2.0);
+} catch (Throwable $e) {
+    echo $e::class, ': ', $e->getMessage(), "\n";
+}
+?>
+--EXPECTF--
+ValueError: fsockopen(): Argument #5 ($timeout) must be -1 or between 0 and %s
+ValueError: pfsockopen(): Argument #5 ($timeout) must be -1 or between 0 and %s
diff --git a/ext/standard/tests/streams/gh14780.phpt b/ext/standard/tests/streams/gh14780.phpt
index 064e496b175..c0fc4e621a9 100644
--- a/ext/standard/tests/streams/gh14780.phpt
+++ b/ext/standard/tests/streams/gh14780.phpt
@@ -31,8 +31,8 @@
 }
 ?>
 --EXPECTF--
-pfsockopen(): Argument #6 must be -1 or between 0 and %s
-pfsockopen(): Argument #6 must be -1 or between 0 and %s
+pfsockopen(): Argument #5 ($timeout) must be -1 or between 0 and %s
+pfsockopen(): Argument #5 ($timeout) must be -1 or between 0 and %s
 resource(%d) of type (persistent stream)
-pfsockopen(): Argument #6 must be -1 or between 0 and %s
-pfsockopen(): Argument #6 must be -1 or between 0 and %s
+pfsockopen(): Argument #5 ($timeout) must be -1 or between 0 and %s
+pfsockopen(): Argument #5 ($timeout) must be -1 or between 0 and %s