]> granicus.if.org Git - php/commitdiff
Fully fix typed generator returns
authorBob Weinand <bobwei9@hotmail.com>
Fri, 24 Jul 2015 20:03:05 +0000 (22:03 +0200)
committerBob Weinand <bobwei9@hotmail.com>
Fri, 24 Jul 2015 20:04:05 +0000 (22:04 +0200)
Zend/tests/generators/generator_return_return_type.phpt
Zend/zend_compile.c
Zend/zend_opcode.c

index 804542285f5391845bcf9e8153f893aba11aa6da..345e0065c2970322effdd5a04fdb2f1b838efada 100644 (file)
@@ -4,8 +4,9 @@ Generators must return a valid variable with return type specified
 <?php
 
 $gen = (function (): Generator {
-    return true;
-    yield;
+       1 + $a = 1; // force a temporary
+       return true;
+       yield;
 })();
 
 var_dump($gen->valid());
index 64ad77d4a74b0ca4900f04c936eeb9f6686b1837..f0ddbd478b3dea08bfdf89529efa3898e59870dc 100644 (file)
@@ -3610,7 +3610,7 @@ void zend_resolve_goto_label(zend_op_array *op_array, znode *label_node, zend_op
        znode *loop_var = NULL;
 
        if (pass2_opline) {
-               label = RT_CONSTANT(op_array, pass2_opline->op2);
+               label = CT_CONSTANT_EX(op_array, pass2_opline->op2.constant);
        } else {
                label = &label_node->u.constant;
        }
index c42f3807e4d5b76e0cf5bd1f4a2f7f411ed7d14f..da401e17b9f7946ef1f79802fdcbc7e19fc3fc4c 100644 (file)
@@ -693,7 +693,6 @@ static void zend_resolve_finally_calls(zend_op_array *op_array)
                                break;
                        case ZEND_GOTO:
                                if (Z_TYPE_P(CT_CONSTANT_EX(op_array, opline->op2.constant)) != IS_LONG) {
-                                       ZEND_PASS_TWO_UPDATE_CONSTANT(op_array, opline->op2);
                                        zend_resolve_goto_label(op_array, NULL, opline);
                                }
                                /* break omitted intentionally */
@@ -744,19 +743,6 @@ ZEND_API int pass_two(zend_op_array *op_array)
        opline = op_array->opcodes;
        end = opline + op_array->last;
        while (opline < end) {
-               if (opline->op1_type == IS_CONST) {
-                       ZEND_PASS_TWO_UPDATE_CONSTANT(op_array, opline->op1);
-               } else if (opline->op1_type & (IS_VAR|IS_TMP_VAR)) {
-                       opline->op1.var = (uint32_t)(zend_intptr_t)ZEND_CALL_VAR_NUM(NULL, op_array->last_var + opline->op1.var);
-               }
-               if (opline->op2_type == IS_CONST) {
-                       ZEND_PASS_TWO_UPDATE_CONSTANT(op_array, opline->op2);
-               } else if (opline->op2_type & (IS_VAR|IS_TMP_VAR)) {
-                       opline->op2.var = (uint32_t)(zend_intptr_t)ZEND_CALL_VAR_NUM(NULL, op_array->last_var + opline->op2.var);
-               }
-               if (opline->result_type & (IS_VAR|IS_TMP_VAR)) {
-                       opline->result.var = (uint32_t)(zend_intptr_t)ZEND_CALL_VAR_NUM(NULL, op_array->last_var + opline->result.var);
-               }
                switch (opline->opcode) {
                        case ZEND_DECLARE_ANON_INHERITED_CLASS:
                                ZEND_PASS_TWO_UPDATE_JMP_TARGET(op_array, opline, opline->op1);
@@ -776,7 +762,7 @@ ZEND_API int pass_two(zend_op_array *op_array)
                                }
                                break;
                        case ZEND_GOTO:
-                               if (Z_TYPE_P(RT_CONSTANT(op_array, opline->op2)) != IS_LONG) {
+                               if (Z_TYPE_P(CT_CONSTANT_EX(op_array, opline->op2.constant)) != IS_LONG) {
                                        zend_resolve_goto_label(op_array, NULL, opline);
                                }
                                /* break omitted intentionally */
@@ -821,6 +807,19 @@ ZEND_API int pass_two(zend_op_array *op_array)
                                }
                                break;
                }
+               if (opline->op1_type == IS_CONST) {
+                       ZEND_PASS_TWO_UPDATE_CONSTANT(op_array, opline->op1);
+               } else if (opline->op1_type & (IS_VAR|IS_TMP_VAR)) {
+                       opline->op1.var = (uint32_t)(zend_intptr_t)ZEND_CALL_VAR_NUM(NULL, op_array->last_var + opline->op1.var);
+               }
+               if (opline->op2_type == IS_CONST) {
+                       ZEND_PASS_TWO_UPDATE_CONSTANT(op_array, opline->op2);
+               } else if (opline->op2_type & (IS_VAR|IS_TMP_VAR)) {
+                       opline->op2.var = (uint32_t)(zend_intptr_t)ZEND_CALL_VAR_NUM(NULL, op_array->last_var + opline->op2.var);
+               }
+               if (opline->result_type & (IS_VAR|IS_TMP_VAR)) {
+                       opline->result.var = (uint32_t)(zend_intptr_t)ZEND_CALL_VAR_NUM(NULL, op_array->last_var + opline->result.var);
+               }
                ZEND_VM_SET_OPCODE_HANDLER(opline);
                opline++;
        }