Commit 45766b7ec6c for php

commit 45766b7ec6c3a0c32a252bf0990e33c193fe7627
Author: Gina Peter Banyard <girgias@php.net>
Date:   Tue Oct 20 17:35:13 2026 +0100

    std: throw ValueError on invalid INI scanner mode (#24429)

    Follow-up to #23893 using the https://wiki.php.net/rfc/policy-exempt-type-value-error-bc-policy policy.

diff --git a/Zend/tests/bug61087.phpt b/Zend/tests/bug61087.phpt
deleted file mode 100644
index 124497c657c..00000000000
--- a/Zend/tests/bug61087.phpt
+++ /dev/null
@@ -1,10 +0,0 @@
---TEST--
-Bug #61087 (Memory leak in parse_ini_file when specifying invalid scanner mode)
---FILE--
-<?php
-// the used file is actually irrelevant, so just use this file
-// even though it's not an .ini
-parse_ini_file(__FILE__, false, 100);
-?>
---EXPECTF--
-Warning: parse_ini_file(): Invalid scanner mode in %s on line %d
diff --git a/ext/standard/basic_functions.c b/ext/standard/basic_functions.c
index 93e2025da8a..b76149d2bfa 100644
--- a/ext/standard/basic_functions.c
+++ b/ext/standard/basic_functions.c
@@ -2515,10 +2515,9 @@ PHP_FUNCTION(parse_ini_file)
 		RETURN_THROWS();
 	}

-	/* Sanity check */
 	if (UNEXPECTED(scanner_mode != ZEND_INI_SCANNER_NORMAL && scanner_mode != ZEND_INI_SCANNER_RAW && scanner_mode != ZEND_INI_SCANNER_TYPED)) {
-		php_error_docref(NULL, E_WARNING, "Invalid scanner mode");
-		RETURN_FALSE;
+		zend_argument_value_error(3, "must be one of INI_SCANNER_NORMAL, INI_SCANNER_RAW, or INI_SCANNER_TYPED");
+		RETURN_THROWS();
 	}

 	/* Set callback function */
@@ -2557,10 +2556,9 @@ PHP_FUNCTION(parse_ini_string)
 		Z_PARAM_LONG(scanner_mode)
 	ZEND_PARSE_PARAMETERS_END();

-	/* Sanity check */
 	if (UNEXPECTED(scanner_mode != ZEND_INI_SCANNER_NORMAL && scanner_mode != ZEND_INI_SCANNER_RAW && scanner_mode != ZEND_INI_SCANNER_TYPED)) {
-		php_error_docref(NULL, E_WARNING, "Invalid scanner mode");
-		RETURN_FALSE;
+		zend_argument_value_error(3, "must be one of INI_SCANNER_NORMAL, INI_SCANNER_RAW, or INI_SCANNER_TYPED");
+		RETURN_THROWS();
 	}

 	if (INT_MAX - str_len < ZEND_MMAP_AHEAD) {
diff --git a/ext/standard/tests/file/parse_ini_file_error.phpt b/ext/standard/tests/file/parse_ini_file_error.phpt
index 6c519c1e5fe..be4456202d4 100644
--- a/ext/standard/tests/file/parse_ini_file_error.phpt
+++ b/ext/standard/tests/file/parse_ini_file_error.phpt
@@ -8,8 +8,13 @@
 echo "\n-- Testing parse_ini_file() function with invalid scanner mode --\n";
 $filename = 'string_val';
 $process_sections = true;
-$scanner_mode = 10;
-var_dump( parse_ini_file($filename, $process_sections, $scanner_mode) );
+
+try {
+	$scanner_mode = 10;
+	var_dump( parse_ini_file($filename, $process_sections, $scanner_mode) );
+} catch (Throwable $e) {
+    echo $e::class, ': ', $e->getMessage(), "\n";
+}

 echo "\n-- Testing parse_ini_file() function with a non-existent file --\n";
 $filename = __FILE__ . 'invalidfilename';
@@ -21,9 +26,7 @@
 *** Testing parse_ini_file() : error conditions ***

 -- Testing parse_ini_file() function with invalid scanner mode --
-
-Warning: parse_ini_file(): Invalid scanner mode in %s on line %d
-bool(false)
+ValueError: parse_ini_file(): Argument #3 ($scanner_mode) must be one of INI_SCANNER_NORMAL, INI_SCANNER_RAW, or INI_SCANNER_TYPED

 -- Testing parse_ini_file() function with a non-existent file --