diff --git a/NEWS b/NEWS index 478ac3e78e7..756b66b33aa 100644 --- a/NEWS +++ b/NEWS @@ -11,6 +11,10 @@ PHP NEWS ReflectionClass). (Nikita) . Fixed bug #81474 (Make ReflectionEnum and related class non-final). (Nikita) +- SPL: + . Fixed bug #80663 (Recursive SplFixedArray::setSize() may cause double-free). + (cmb, Nikita, Tyson Andre) + - XML: . Fixed bug #70962 (XML_OPTION_SKIP_WHITE strips embedded whitespace). (Aliaksandr Bystry, cmb) diff --git a/ext/spl/spl_fixedarray.c b/ext/spl/spl_fixedarray.c index 0fd5717224b..f5a60607c73 100644 --- a/ext/spl/spl_fixedarray.c +++ b/ext/spl/spl_fixedarray.c @@ -156,10 +156,14 @@ static void spl_fixedarray_dtor_range(spl_fixedarray *array, zend_long from, zen */ static void spl_fixedarray_dtor(spl_fixedarray *array) { - zend_long size = array->size; if (!spl_fixedarray_empty(array)) { - spl_fixedarray_dtor_range(array, 0, size); - efree(array->elements); + zval *begin = array->elements, *end = array->elements + array->size; + array->elements = NULL; + array->size = 0; + while (begin != end) { + zval_ptr_dtor(--end); + } + efree(begin); } } diff --git a/ext/spl/tests/bug80663.phpt b/ext/spl/tests/bug80663.phpt new file mode 100644 index 00000000000..9e359cc60ef --- /dev/null +++ b/ext/spl/tests/bug80663.phpt @@ -0,0 +1,15 @@ +--TEST-- +Bug #80663 (Recursive SplFixedArray::setSize() may cause double-free) +--FILE-- +setSize(0); + } +} + +$obj = new SplFixedArray(1000); +$obj[0] = new InvalidDestructor(); +$obj->setSize(0); +?> +--EXPECT--