From: Dmitry Stogov Date: Mon, 12 May 2008 09:09:28 +0000 (+0000) Subject: Fixed bug #44952 (isset() does not checks correctly variable variable) X-Git-Tag: RELEASE_2_0_0b1~12 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=25aaecc64dd9d28710aa07a5a9f0c0ab597087a6;p=php Fixed bug #44952 (isset() does not checks correctly variable variable) --- diff --git a/Zend/zend_compile.c b/Zend/zend_compile.c index b090bc6d9e..c5f46469b7 100644 --- a/Zend/zend_compile.c +++ b/Zend/zend_compile.c @@ -4442,6 +4442,7 @@ void zend_do_unset(znode *variable TSRMLS_DC) /* {{{ */ SET_UNUSED(opline->op2); opline->op2.u.EA.type = ZEND_FETCH_LOCAL; SET_UNUSED(opline->result); + opline->extended_value = ZEND_QUICK_SET; } else { last_op = &CG(active_op_array)->opcodes[get_next_op_number(CG(active_op_array))-1]; @@ -4476,6 +4477,7 @@ void zend_do_isset_or_isempty(int type, znode *result, znode *variable TSRMLS_DC SET_UNUSED(last_op->op2); last_op->op2.u.EA.type = ZEND_FETCH_LOCAL; last_op->result.u.var = get_temporary_variable(CG(active_op_array)); + last_op->extended_value = ZEND_QUICK_SET; } else { last_op = &CG(active_op_array)->opcodes[get_next_op_number(CG(active_op_array))-1]; @@ -4490,9 +4492,10 @@ void zend_do_isset_or_isempty(int type, znode *result, znode *variable TSRMLS_DC last_op->opcode = ZEND_ISSET_ISEMPTY_PROP_OBJ; break; } + last_op->extended_value = 0; } last_op->result.op_type = IS_TMP_VAR; - last_op->extended_value = type; + last_op->extended_value |= type; *result = last_op->result; } diff --git a/Zend/zend_compile.h b/Zend/zend_compile.h index 1c1ed444ee..675018413b 100644 --- a/Zend/zend_compile.h +++ b/Zend/zend_compile.h @@ -691,6 +691,8 @@ int zendlex(znode *zendlval TSRMLS_DC); #define ZEND_ISSET (1<<0) #define ZEND_ISEMPTY (1<<1) +#define ZEND_ISSET_ISEMPTY_MASK (ZEND_ISSET | ZEND_ISEMPTY) +#define ZEND_QUICK_SET (1<<2) #define ZEND_CT (1<<0) #define ZEND_RT (1<<1) diff --git a/Zend/zend_vm_def.h b/Zend/zend_vm_def.h index 6ee4697ac9..446a7a881e 100644 --- a/Zend/zend_vm_def.h +++ b/Zend/zend_vm_def.h @@ -3258,7 +3258,7 @@ ZEND_VM_HANDLER(74, ZEND_UNSET_VAR, CONST|TMP|VAR|CV, ANY) HashTable *target_symbol_table; zend_free_op free_op1; - if (OP1_TYPE == IS_CV) { + if (OP1_TYPE == IS_CV && (opline->extended_value & ZEND_QUICK_SET)) { if (EG(active_symbol_table)) { zend_execute_data *ex = EX(prev_execute_data); zend_compiled_variable *cv = &CV_DEF_OF(opline->op1.u.var); @@ -3295,7 +3295,7 @@ ZEND_VM_HANDLER(74, ZEND_UNSET_VAR, CONST|TMP|VAR|CV, ANY) zval_copy_ctor(&tmp); convert_to_text(&tmp); varname = &tmp; - } else if (OP1_TYPE == IS_VAR) { + } else if (OP1_TYPE == IS_VAR || OP1_TYPE == IS_CV) { Z_ADDREF_P(varname); } @@ -3332,7 +3332,7 @@ ZEND_VM_HANDLER(74, ZEND_UNSET_VAR, CONST|TMP|VAR|CV, ANY) if (varname == &tmp) { zval_dtor(&tmp); - } else if (OP1_TYPE == IS_VAR) { + } else if (OP1_TYPE == IS_VAR || OP1_TYPE == IS_CV) { zval_ptr_dtor(&varname); } FREE_OP1(); @@ -3802,7 +3802,7 @@ ZEND_VM_HANDLER(114, ZEND_ISSET_ISEMPTY_VAR, CONST|TMP|VAR|CV, ANY) zval **value; zend_bool isset = 1; - if (OP1_TYPE == IS_CV) { + if (OP1_TYPE == IS_CV && (opline->extended_value & ZEND_QUICK_SET)) { if (EX(CVs)[opline->op1.u.var]) { value = EX(CVs)[opline->op1.u.var]; } else if (EG(active_symbol_table)) { @@ -3846,7 +3846,7 @@ ZEND_VM_HANDLER(114, ZEND_ISSET_ISEMPTY_VAR, CONST|TMP|VAR|CV, ANY) Z_TYPE(EX_T(opline->result.u.var).tmp_var) = IS_BOOL; - switch (opline->extended_value) { + switch (opline->extended_value & ZEND_ISSET_ISEMPTY_MASK) { case ZEND_ISSET: if (isset && Z_TYPE_PP(value) == IS_NULL) { Z_LVAL(EX_T(opline->result.u.var).tmp_var) = 0; diff --git a/Zend/zend_vm_execute.h b/Zend/zend_vm_execute.h index 56dbeedab7..ea2dcdbcbc 100644 --- a/Zend/zend_vm_execute.h +++ b/Zend/zend_vm_execute.h @@ -1819,7 +1819,7 @@ static int ZEND_UNSET_VAR_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS) HashTable *target_symbol_table; - if (IS_CONST == IS_CV) { + if (IS_CONST == IS_CV && (opline->extended_value & ZEND_QUICK_SET)) { if (EG(active_symbol_table)) { zend_execute_data *ex = EX(prev_execute_data); zend_compiled_variable *cv = &CV_DEF_OF(opline->op1.u.var); @@ -1856,7 +1856,7 @@ static int ZEND_UNSET_VAR_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS) zval_copy_ctor(&tmp); convert_to_text(&tmp); varname = &tmp; - } else if (IS_CONST == IS_VAR) { + } else if (IS_CONST == IS_VAR || IS_CONST == IS_CV) { Z_ADDREF_P(varname); } @@ -1893,7 +1893,7 @@ static int ZEND_UNSET_VAR_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS) if (varname == &tmp) { zval_dtor(&tmp); - } else if (IS_CONST == IS_VAR) { + } else if (IS_CONST == IS_VAR || IS_CONST == IS_CV) { zval_ptr_dtor(&varname); } @@ -2058,7 +2058,7 @@ static int ZEND_ISSET_ISEMPTY_VAR_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS) zval **value; zend_bool isset = 1; - if (IS_CONST == IS_CV) { + if (IS_CONST == IS_CV && (opline->extended_value & ZEND_QUICK_SET)) { if (EX(CVs)[opline->op1.u.var]) { value = EX(CVs)[opline->op1.u.var]; } else if (EG(active_symbol_table)) { @@ -2102,7 +2102,7 @@ static int ZEND_ISSET_ISEMPTY_VAR_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS) Z_TYPE(EX_T(opline->result.u.var).tmp_var) = IS_BOOL; - switch (opline->extended_value) { + switch (opline->extended_value & ZEND_ISSET_ISEMPTY_MASK) { case ZEND_ISSET: if (isset && Z_TYPE_PP(value) == IS_NULL) { Z_LVAL(EX_T(opline->result.u.var).tmp_var) = 0; @@ -5172,7 +5172,7 @@ static int ZEND_UNSET_VAR_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS) HashTable *target_symbol_table; zend_free_op free_op1; - if (IS_TMP_VAR == IS_CV) { + if (IS_TMP_VAR == IS_CV && (opline->extended_value & ZEND_QUICK_SET)) { if (EG(active_symbol_table)) { zend_execute_data *ex = EX(prev_execute_data); zend_compiled_variable *cv = &CV_DEF_OF(opline->op1.u.var); @@ -5209,7 +5209,7 @@ static int ZEND_UNSET_VAR_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS) zval_copy_ctor(&tmp); convert_to_text(&tmp); varname = &tmp; - } else if (IS_TMP_VAR == IS_VAR) { + } else if (IS_TMP_VAR == IS_VAR || IS_TMP_VAR == IS_CV) { Z_ADDREF_P(varname); } @@ -5246,7 +5246,7 @@ static int ZEND_UNSET_VAR_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS) if (varname == &tmp) { zval_dtor(&tmp); - } else if (IS_TMP_VAR == IS_VAR) { + } else if (IS_TMP_VAR == IS_VAR || IS_TMP_VAR == IS_CV) { zval_ptr_dtor(&varname); } zval_dtor(free_op1.var); @@ -5411,7 +5411,7 @@ static int ZEND_ISSET_ISEMPTY_VAR_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS) zval **value; zend_bool isset = 1; - if (IS_TMP_VAR == IS_CV) { + if (IS_TMP_VAR == IS_CV && (opline->extended_value & ZEND_QUICK_SET)) { if (EX(CVs)[opline->op1.u.var]) { value = EX(CVs)[opline->op1.u.var]; } else if (EG(active_symbol_table)) { @@ -5455,7 +5455,7 @@ static int ZEND_ISSET_ISEMPTY_VAR_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS) Z_TYPE(EX_T(opline->result.u.var).tmp_var) = IS_BOOL; - switch (opline->extended_value) { + switch (opline->extended_value & ZEND_ISSET_ISEMPTY_MASK) { case ZEND_ISSET: if (isset && Z_TYPE_PP(value) == IS_NULL) { Z_LVAL(EX_T(opline->result.u.var).tmp_var) = 0; @@ -8566,7 +8566,7 @@ static int ZEND_UNSET_VAR_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS) HashTable *target_symbol_table; zend_free_op free_op1; - if (IS_VAR == IS_CV) { + if (IS_VAR == IS_CV && (opline->extended_value & ZEND_QUICK_SET)) { if (EG(active_symbol_table)) { zend_execute_data *ex = EX(prev_execute_data); zend_compiled_variable *cv = &CV_DEF_OF(opline->op1.u.var); @@ -8603,7 +8603,7 @@ static int ZEND_UNSET_VAR_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS) zval_copy_ctor(&tmp); convert_to_text(&tmp); varname = &tmp; - } else if (IS_VAR == IS_VAR) { + } else if (IS_VAR == IS_VAR || IS_VAR == IS_CV) { Z_ADDREF_P(varname); } @@ -8640,7 +8640,7 @@ static int ZEND_UNSET_VAR_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS) if (varname == &tmp) { zval_dtor(&tmp); - } else if (IS_VAR == IS_VAR) { + } else if (IS_VAR == IS_VAR || IS_VAR == IS_CV) { zval_ptr_dtor(&varname); } if (free_op1.var) {zval_ptr_dtor(&free_op1.var);}; @@ -8961,7 +8961,7 @@ static int ZEND_ISSET_ISEMPTY_VAR_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS) zval **value; zend_bool isset = 1; - if (IS_VAR == IS_CV) { + if (IS_VAR == IS_CV && (opline->extended_value & ZEND_QUICK_SET)) { if (EX(CVs)[opline->op1.u.var]) { value = EX(CVs)[opline->op1.u.var]; } else if (EG(active_symbol_table)) { @@ -9005,7 +9005,7 @@ static int ZEND_ISSET_ISEMPTY_VAR_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS) Z_TYPE(EX_T(opline->result.u.var).tmp_var) = IS_BOOL; - switch (opline->extended_value) { + switch (opline->extended_value & ZEND_ISSET_ISEMPTY_MASK) { case ZEND_ISSET: if (isset && Z_TYPE_PP(value) == IS_NULL) { Z_LVAL(EX_T(opline->result.u.var).tmp_var) = 0; @@ -22875,7 +22875,7 @@ static int ZEND_UNSET_VAR_SPEC_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS) HashTable *target_symbol_table; - if (IS_CV == IS_CV) { + if (IS_CV == IS_CV && (opline->extended_value & ZEND_QUICK_SET)) { if (EG(active_symbol_table)) { zend_execute_data *ex = EX(prev_execute_data); zend_compiled_variable *cv = &CV_DEF_OF(opline->op1.u.var); @@ -22912,7 +22912,7 @@ static int ZEND_UNSET_VAR_SPEC_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS) zval_copy_ctor(&tmp); convert_to_text(&tmp); varname = &tmp; - } else if (IS_CV == IS_VAR) { + } else if (IS_CV == IS_VAR || IS_CV == IS_CV) { Z_ADDREF_P(varname); } @@ -22949,7 +22949,7 @@ static int ZEND_UNSET_VAR_SPEC_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS) if (varname == &tmp) { zval_dtor(&tmp); - } else if (IS_CV == IS_VAR) { + } else if (IS_CV == IS_VAR || IS_CV == IS_CV) { zval_ptr_dtor(&varname); } @@ -23114,7 +23114,7 @@ static int ZEND_ISSET_ISEMPTY_VAR_SPEC_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS) zval **value; zend_bool isset = 1; - if (IS_CV == IS_CV) { + if (IS_CV == IS_CV && (opline->extended_value & ZEND_QUICK_SET)) { if (EX(CVs)[opline->op1.u.var]) { value = EX(CVs)[opline->op1.u.var]; } else if (EG(active_symbol_table)) { @@ -23158,7 +23158,7 @@ static int ZEND_ISSET_ISEMPTY_VAR_SPEC_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS) Z_TYPE(EX_T(opline->result.u.var).tmp_var) = IS_BOOL; - switch (opline->extended_value) { + switch (opline->extended_value & ZEND_ISSET_ISEMPTY_MASK) { case ZEND_ISSET: if (isset && Z_TYPE_PP(value) == IS_NULL) { Z_LVAL(EX_T(opline->result.u.var).tmp_var) = 0;