mirror of
https://github.com/php/php-src.git
synced 2024-11-28 04:14:26 +08:00
Proper fix for bug #37707 ("clone $x" must call __clone() enven if result value is not used)
This commit is contained in:
parent
6e24feb80d
commit
2a7d16f8fd
@ -2,10 +2,15 @@
|
||||
Bug #37707 (clone without assigning leaks memory)
|
||||
--FILE--
|
||||
<?php
|
||||
class testme {}
|
||||
class testme {
|
||||
function __clone() {
|
||||
echo "clonned\n";
|
||||
}
|
||||
}
|
||||
clone new testme();
|
||||
echo "NO LEAK\n";
|
||||
?>
|
||||
--EXPECT--
|
||||
clonned
|
||||
NO LEAK
|
||||
|
||||
|
@ -2506,12 +2506,15 @@ ZEND_VM_HANDLER(110, ZEND_CLONE, CONST|TMP|VAR|UNUSED|CV, ANY)
|
||||
}
|
||||
|
||||
EX_T(opline->result.u.var).var.ptr_ptr = &EX_T(opline->result.u.var).var.ptr;
|
||||
if (!EG(exception) && RETURN_VALUE_USED(opline)) {
|
||||
if (!EG(exception)) {
|
||||
ALLOC_ZVAL(EX_T(opline->result.u.var).var.ptr);
|
||||
Z_OBJVAL_P(EX_T(opline->result.u.var).var.ptr) = clone_call(obj TSRMLS_CC);
|
||||
Z_TYPE_P(EX_T(opline->result.u.var).var.ptr) = IS_OBJECT;
|
||||
EX_T(opline->result.u.var).var.ptr->refcount=1;
|
||||
EX_T(opline->result.u.var).var.ptr->is_ref=1;
|
||||
if (!RETURN_VALUE_USED(opline)) {
|
||||
zval_ptr_dtor(&EX_T(opline->result.u.var).var.ptr);
|
||||
}
|
||||
}
|
||||
FREE_OP1_IF_VAR();
|
||||
ZEND_VM_NEXT_OPCODE();
|
||||
|
@ -1831,12 +1831,15 @@ static int ZEND_CLONE_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
|
||||
}
|
||||
|
||||
EX_T(opline->result.u.var).var.ptr_ptr = &EX_T(opline->result.u.var).var.ptr;
|
||||
if (!EG(exception) && RETURN_VALUE_USED(opline)) {
|
||||
if (!EG(exception)) {
|
||||
ALLOC_ZVAL(EX_T(opline->result.u.var).var.ptr);
|
||||
Z_OBJVAL_P(EX_T(opline->result.u.var).var.ptr) = clone_call(obj TSRMLS_CC);
|
||||
Z_TYPE_P(EX_T(opline->result.u.var).var.ptr) = IS_OBJECT;
|
||||
EX_T(opline->result.u.var).var.ptr->refcount=1;
|
||||
EX_T(opline->result.u.var).var.ptr->is_ref=1;
|
||||
if (!RETURN_VALUE_USED(opline)) {
|
||||
zval_ptr_dtor(&EX_T(opline->result.u.var).var.ptr);
|
||||
}
|
||||
}
|
||||
|
||||
ZEND_VM_NEXT_OPCODE();
|
||||
@ -4328,12 +4331,15 @@ static int ZEND_CLONE_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
|
||||
}
|
||||
|
||||
EX_T(opline->result.u.var).var.ptr_ptr = &EX_T(opline->result.u.var).var.ptr;
|
||||
if (!EG(exception) && RETURN_VALUE_USED(opline)) {
|
||||
if (!EG(exception)) {
|
||||
ALLOC_ZVAL(EX_T(opline->result.u.var).var.ptr);
|
||||
Z_OBJVAL_P(EX_T(opline->result.u.var).var.ptr) = clone_call(obj TSRMLS_CC);
|
||||
Z_TYPE_P(EX_T(opline->result.u.var).var.ptr) = IS_OBJECT;
|
||||
EX_T(opline->result.u.var).var.ptr->refcount=1;
|
||||
EX_T(opline->result.u.var).var.ptr->is_ref=1;
|
||||
if (!RETURN_VALUE_USED(opline)) {
|
||||
zval_ptr_dtor(&EX_T(opline->result.u.var).var.ptr);
|
||||
}
|
||||
}
|
||||
|
||||
ZEND_VM_NEXT_OPCODE();
|
||||
@ -7407,12 +7413,15 @@ static int ZEND_CLONE_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
|
||||
}
|
||||
|
||||
EX_T(opline->result.u.var).var.ptr_ptr = &EX_T(opline->result.u.var).var.ptr;
|
||||
if (!EG(exception) && RETURN_VALUE_USED(opline)) {
|
||||
if (!EG(exception)) {
|
||||
ALLOC_ZVAL(EX_T(opline->result.u.var).var.ptr);
|
||||
Z_OBJVAL_P(EX_T(opline->result.u.var).var.ptr) = clone_call(obj TSRMLS_CC);
|
||||
Z_TYPE_P(EX_T(opline->result.u.var).var.ptr) = IS_OBJECT;
|
||||
EX_T(opline->result.u.var).var.ptr->refcount=1;
|
||||
EX_T(opline->result.u.var).var.ptr->is_ref=1;
|
||||
if (!RETURN_VALUE_USED(opline)) {
|
||||
zval_ptr_dtor(&EX_T(opline->result.u.var).var.ptr);
|
||||
}
|
||||
}
|
||||
if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
|
||||
ZEND_VM_NEXT_OPCODE();
|
||||
@ -14295,12 +14304,15 @@ static int ZEND_CLONE_SPEC_UNUSED_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
|
||||
}
|
||||
|
||||
EX_T(opline->result.u.var).var.ptr_ptr = &EX_T(opline->result.u.var).var.ptr;
|
||||
if (!EG(exception) && RETURN_VALUE_USED(opline)) {
|
||||
if (!EG(exception)) {
|
||||
ALLOC_ZVAL(EX_T(opline->result.u.var).var.ptr);
|
||||
Z_OBJVAL_P(EX_T(opline->result.u.var).var.ptr) = clone_call(obj TSRMLS_CC);
|
||||
Z_TYPE_P(EX_T(opline->result.u.var).var.ptr) = IS_OBJECT;
|
||||
EX_T(opline->result.u.var).var.ptr->refcount=1;
|
||||
EX_T(opline->result.u.var).var.ptr->is_ref=1;
|
||||
if (!RETURN_VALUE_USED(opline)) {
|
||||
zval_ptr_dtor(&EX_T(opline->result.u.var).var.ptr);
|
||||
}
|
||||
}
|
||||
|
||||
ZEND_VM_NEXT_OPCODE();
|
||||
@ -19623,12 +19635,15 @@ static int ZEND_CLONE_SPEC_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
|
||||
}
|
||||
|
||||
EX_T(opline->result.u.var).var.ptr_ptr = &EX_T(opline->result.u.var).var.ptr;
|
||||
if (!EG(exception) && RETURN_VALUE_USED(opline)) {
|
||||
if (!EG(exception)) {
|
||||
ALLOC_ZVAL(EX_T(opline->result.u.var).var.ptr);
|
||||
Z_OBJVAL_P(EX_T(opline->result.u.var).var.ptr) = clone_call(obj TSRMLS_CC);
|
||||
Z_TYPE_P(EX_T(opline->result.u.var).var.ptr) = IS_OBJECT;
|
||||
EX_T(opline->result.u.var).var.ptr->refcount=1;
|
||||
EX_T(opline->result.u.var).var.ptr->is_ref=1;
|
||||
if (!RETURN_VALUE_USED(opline)) {
|
||||
zval_ptr_dtor(&EX_T(opline->result.u.var).var.ptr);
|
||||
}
|
||||
}
|
||||
|
||||
ZEND_VM_NEXT_OPCODE();
|
||||
|
Loading…
Reference in New Issue
Block a user