Skip to content

Commit 773f980

Browse files
committed
Backport of a partial fix for bug Bug #76982 (memory leak declaring closure in included file).
1 parent 5733f11 commit 773f980

File tree

3 files changed

+4
-19
lines changed

3 files changed

+4
-19
lines changed

Zend/zend_closures.c

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -666,6 +666,7 @@ ZEND_API void zend_create_closure(zval *res, zend_function *func, zend_class_ent
666666
if (func->type == ZEND_USER_FUNCTION) {
667667
memcpy(&closure->func, func, sizeof(zend_op_array));
668668
closure->func.common.fn_flags |= ZEND_ACC_CLOSURE;
669+
closure->func.common.fn_flags &= ~ZEND_ACC_IMMUTABLE;
669670
if (closure->func.op_array.static_variables) {
670671
closure->func.op_array.static_variables =
671672
zend_array_dup(closure->func.op_array.static_variables);
@@ -676,7 +677,9 @@ ZEND_API void zend_create_closure(zval *res, zend_function *func, zend_class_ent
676677
|| func->common.scope != scope
677678
|| (func->common.fn_flags & ZEND_ACC_NO_RT_ARENA)
678679
) {
679-
if (!func->op_array.run_time_cache && (func->common.fn_flags & ZEND_ACC_CLOSURE)) {
680+
if (!func->op_array.run_time_cache
681+
&& (func->common.fn_flags & ZEND_ACC_CLOSURE)
682+
&& !(func->common.fn_flags & ZEND_ACC_IMMUTABLE)) {
680683
/* If a real closure is used for the first time, we create a shared runtime cache
681684
* and remember which scope it is for. */
682685
func->common.scope = scope;

Zend/zend_vm_def.h

Lines changed: 0 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -7097,15 +7097,6 @@ ZEND_VM_HANDLER(153, ZEND_DECLARE_LAMBDA_FUNCTION, CONST, UNUSED)
70977097
zfunc = zend_hash_find_ex(EG(function_table), Z_STR_P(RT_CONSTANT(opline, opline->op1)), 1);
70987098
ZEND_ASSERT(zfunc != NULL && Z_FUNC_P(zfunc)->type == ZEND_USER_FUNCTION);
70997099

7100-
fbc = Z_PTR_P(zfunc);
7101-
if (fbc->common.fn_flags & ZEND_ACC_IMMUTABLE) {
7102-
zend_function *new_func = zend_arena_alloc(&CG(arena), sizeof(zend_op_array));
7103-
7104-
memcpy(new_func, fbc, sizeof(zend_op_array));
7105-
new_func->common.fn_flags &= ~ZEND_ACC_IMMUTABLE;
7106-
Z_PTR_P(zfunc) = fbc = new_func;
7107-
}
7108-
71097100
if (Z_TYPE(EX(This)) == IS_OBJECT) {
71107101
called_scope = Z_OBJCE(EX(This));
71117102
if (UNEXPECTED((Z_FUNC_P(zfunc)->common.fn_flags & ZEND_ACC_STATIC) ||

Zend/zend_vm_execute.h

Lines changed: 0 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -9209,15 +9209,6 @@ static ZEND_OPCODE_HANDLER_RET ZEND_FASTCALL ZEND_DECLARE_LAMBDA_FUNCTION_SPEC_C
92099209
zfunc = zend_hash_find_ex(EG(function_table), Z_STR_P(RT_CONSTANT(opline, opline->op1)), 1);
92109210
ZEND_ASSERT(zfunc != NULL && Z_FUNC_P(zfunc)->type == ZEND_USER_FUNCTION);
92119211

9212-
fbc = Z_PTR_P(zfunc);
9213-
if (fbc->common.fn_flags & ZEND_ACC_IMMUTABLE) {
9214-
zend_function *new_func = zend_arena_alloc(&CG(arena), sizeof(zend_op_array));
9215-
9216-
memcpy(new_func, fbc, sizeof(zend_op_array));
9217-
new_func->common.fn_flags &= ~ZEND_ACC_IMMUTABLE;
9218-
Z_PTR_P(zfunc) = fbc = new_func;
9219-
}
9220-
92219212
if (Z_TYPE(EX(This)) == IS_OBJECT) {
92229213
called_scope = Z_OBJCE(EX(This));
92239214
if (UNEXPECTED((Z_FUNC_P(zfunc)->common.fn_flags & ZEND_ACC_STATIC) ||

0 commit comments

Comments
 (0)