Commit cb3dc62fd90 for php.net

commit cb3dc62fd90dc2660296d9261c022cd7de52253f
Author: David Carlier <devnexen@gmail.com>
Date:   Thu Apr 30 19:17:42 2026 +0100

    ext/spl: Fix SplFixedArray::setSize leak when destructor grows during clear.

    close GH-21920

diff --git a/NEWS b/NEWS
index 3dbfb272495..35f34920e62 100644
--- a/NEWS
+++ b/NEWS
@@ -9,6 +9,10 @@ PHP                                                                        NEWS
 - OpenSSL:
   . Fix compatibility issues with OpenSSL 4.0. (jordikroon, Remi)

+- SPL:
+  . Fix SplFixedArray::setSize leak when destructor grows during clear.
+    (David Carlier)
+
 - Standard:
   . Fixed bug GH-21689 (version_compare() incorrectly handles versions ending
     with a dot). (timwolla)
diff --git a/ext/spl/spl_fixedarray.c b/ext/spl/spl_fixedarray.c
index 84adbe2233b..8f8108e2f90 100644
--- a/ext/spl/spl_fixedarray.c
+++ b/ext/spl/spl_fixedarray.c
@@ -172,18 +172,18 @@ static void spl_fixedarray_resize(spl_fixedarray *array, zend_long size)
 		return;
 	}

-	/* first initialization */
-	if (array->size == 0) {
-		spl_fixedarray_init(array, size);
-		return;
-	}
-
 	if (UNEXPECTED(array->cached_resize >= 0)) {
 		/* We're already resizing, so just remember the desired size.
 		 * The resize will happen later. */
 		array->cached_resize = size;
 		return;
 	}
+	/* first initialization */
+	if (array->size == 0) {
+		spl_fixedarray_init(array, size);
+		return;
+	}
+
 	array->cached_resize = size;

 	/* clearing the array */
diff --git a/ext/spl/tests/SplFixedArray_setSize_destruct_grow_during_clear.phpt b/ext/spl/tests/SplFixedArray_setSize_destruct_grow_during_clear.phpt
new file mode 100644
index 00000000000..f0982364afa
--- /dev/null
+++ b/ext/spl/tests/SplFixedArray_setSize_destruct_grow_during_clear.phpt
@@ -0,0 +1,28 @@
+--TEST--
+SplFixedArray::setSize: grow re-entrantly during clear (setSize(0))
+--FILE--
+<?php
+class Reentrant {
+    public ?SplFixedArray $arr = null;
+    public function __destruct() {
+        if ($this->arr !== null) {
+            $this->arr->setSize(5);
+        }
+    }
+}
+
+$arr = new SplFixedArray(2);
+$r = new Reentrant();
+$r->arr = $arr;
+$arr[0] = $r;
+unset($r);
+$arr[1] = "tail";
+
+$arr->setSize(0);
+echo "size: ", $arr->getSize(), "\n";
+$arr[0] = "ok";
+var_dump($arr[0]);
+?>
+--EXPECT--
+size: 5
+string(2) "ok"