]> granicus.if.org Git - php/commitdiff
Fixed bug #35017 (Exception thrown in error handler may cause unexpected behavior)
authorDmitry Stogov <dmitry@php.net>
Mon, 31 Oct 2005 19:25:14 +0000 (19:25 +0000)
committerDmitry Stogov <dmitry@php.net>
Mon, 31 Oct 2005 19:25:14 +0000 (19:25 +0000)
NEWS
Zend/tests/bug35017.phpt [new file with mode: 0755]
Zend/zend_execute.c
Zend/zend_vm_def.h
Zend/zend_vm_execute.h

diff --git a/NEWS b/NEWS
index 40d6eb90d5f36f2790025b32bbbe31028e9584e5..6d542bf18702c5cb1026accea075094c7f52906b 100644 (file)
--- a/NEWS
+++ b/NEWS
@@ -3,6 +3,8 @@ PHP                                                                        NEWS
 ?? Nov 2005, PHP 5.1
 - Fixed bugs #35022, #35019 (Regression in the behavior of key() and current()
   functions). (Ilia)
+- Fixed bug #35017 (Exception thrown in error handler may cause unexpected
+  behavior). (Dmitry)
 - Fixed bug #35014 (array_product() always returns 0). (Ilia)
 
 28 Oct 2005, PHP 5.1 Release Candidate 4
diff --git a/Zend/tests/bug35017.phpt b/Zend/tests/bug35017.phpt
new file mode 100755 (executable)
index 0000000..0a89d23
--- /dev/null
@@ -0,0 +1,21 @@
+--TEST--
+Bug #35017 (Exception thrown in error handler may cause unexpected behavior)
+--FILE--
+<?php
+set_error_handler('errorHandler');
+try {
+       if ($a) {
+               echo "1\n";
+       } else {
+               echo "0\n";
+       }
+       echo "?\n";
+} catch(Exception $e) { 
+  echo "This Exception should be catched\n";
+}
+function errorHandler($errno, $errstr, $errfile, $errline, $vars) {
+       throw new Exception('Some Exception');
+}
+?>
+--EXPECT--
+This Exception should be catched
index 401a344b0a33d30c3b84cd43288b5c651b351ba3..bbe056457aa120c6d63de8dfe7b5e5e9628d3fd0 100644 (file)
@@ -1371,6 +1371,11 @@ ZEND_API void execute_internal(zend_execute_data *execute_data_ptr, int return_v
      CHECK_SYMBOL_TABLES() \
      EX(opline) = new_op
 
+#define ZEND_VM_JMP(new_op) \
+     CHECK_SYMBOL_TABLES() \
+          EX(opline) = EG(exception)?EX(opline)+1:new_op; \
+     ZEND_VM_CONTINUE()
+
 #define ZEND_VM_INC_OPCODE() \
      if (!EG(exception)) { \
        CHECK_SYMBOL_TABLES() \
@@ -1388,9 +1393,6 @@ ZEND_API void execute_internal(zend_execute_data *execute_data_ptr, int return_v
      EG(current_execute_data) = EX(prev_execute_data); \
      ZEND_VM_RETURN()
 
-#define ZEND_VM_CONTINUE_JMP() \
-     ZEND_VM_CONTINUE()    
-
 #include "zend_vm_execute.h"
 
 ZEND_API int zend_set_user_opcode_handler(zend_uchar opcode, opcode_handler_t handler)
index 7a290d1fa28d8f983841226903e5d0e432d08d0e..08983deeb8f59c56278358856cbbe09eed47266e 100644 (file)
@@ -1438,8 +1438,7 @@ ZEND_VM_HANDLER(43, ZEND_JMPZ, CONST|TMP|VAR|CV, ANY)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(opline->op2.u.jmp_addr);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(opline->op2.u.jmp_addr);
        }
 
        ZEND_VM_NEXT_OPCODE();
@@ -1456,8 +1455,7 @@ ZEND_VM_HANDLER(44, ZEND_JMPNZ, CONST|TMP|VAR|CV, ANY)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(opline->op2.u.jmp_addr);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(opline->op2.u.jmp_addr);
        }
 
        ZEND_VM_NEXT_OPCODE();
@@ -1474,14 +1472,12 @@ ZEND_VM_HANDLER(45, ZEND_JMPZNZ, CONST|TMP|VAR|CV, ANY)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp on true to %d\n", opline->extended_value);
 #endif
-               ZEND_VM_SET_OPCODE(&EX(op_array)->opcodes[opline->extended_value]);
-               ZEND_VM_CONTINUE(); /* CHECK_ME */
+               ZEND_VM_JMP(&EX(op_array)->opcodes[opline->extended_value]);
        } else {
 #if DEBUG_ZEND>=2
                printf("Conditional jmp on false to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(&EX(op_array)->opcodes[opline->op2.u.opline_num]);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(&EX(op_array)->opcodes[opline->op2.u.opline_num]);
        }
 }
 
@@ -1498,8 +1494,7 @@ ZEND_VM_HANDLER(46, ZEND_JMPZ_EX, CONST|TMP|VAR|CV, ANY)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(opline->op2.u.jmp_addr);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(opline->op2.u.jmp_addr);
        }
        ZEND_VM_NEXT_OPCODE();
 }
@@ -1517,8 +1512,7 @@ ZEND_VM_HANDLER(47, ZEND_JMPNZ_EX, CONST|TMP|VAR|CV, ANY)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(opline->op2.u.jmp_addr);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(opline->op2.u.jmp_addr);
        }
        ZEND_VM_NEXT_OPCODE();
 }
@@ -2339,26 +2333,24 @@ ZEND_VM_HANDLER(50, ZEND_BRK, ANY, CONST|TMP|VAR|CV)
 {
        zend_op *opline = EX(opline);
        zend_free_op free_op2;
+       zend_brk_cont_element *el;
 
-       ZEND_VM_SET_OPCODE(EX(op_array)->opcodes +
-         zend_brk_cont(GET_OP2_ZVAL_PTR(BP_VAR_R),
-           opline->op1.u.opline_num,
-           EX(op_array), EX(Ts) TSRMLS_CC)->brk);
+       el = zend_brk_cont(GET_OP2_ZVAL_PTR(BP_VAR_R), opline->op1.u.opline_num,
+                          EX(op_array), EX(Ts) TSRMLS_CC);
        FREE_OP2();
-       ZEND_VM_CONTINUE(); /* CHECK_ME */
+       ZEND_VM_JMP(EX(op_array)->opcodes + el->brk);
 }
 
 ZEND_VM_HANDLER(51, ZEND_CONT, ANY, CONST|TMP|VAR|CV)
 {
        zend_op *opline = EX(opline);
        zend_free_op free_op2;
+       zend_brk_cont_element *el;
 
-       ZEND_VM_SET_OPCODE(EX(op_array)->opcodes +
-         zend_brk_cont(GET_OP2_ZVAL_PTR(BP_VAR_R),
-           opline->op1.u.opline_num,
-           EX(op_array), EX(Ts) TSRMLS_CC)->cont);
+       el = zend_brk_cont(GET_OP2_ZVAL_PTR(BP_VAR_R), opline->op1.u.opline_num,
+                          EX(op_array), EX(Ts) TSRMLS_CC);
        FREE_OP2();
-       ZEND_VM_CONTINUE(); /* CHECK_ME */
+       ZEND_VM_JMP(EX(op_array)->opcodes + el->cont);
 }
 
 ZEND_VM_HANDLER(48, ZEND_CASE, CONST|TMP|VAR|CV, CONST|TMP|VAR|CV)
@@ -2428,8 +2420,7 @@ ZEND_VM_HANDLER(68, ZEND_NEW, ANY, ANY)
                } else {
                        zval_ptr_dtor(&object_zval);
                }
-               ZEND_VM_SET_OPCODE(EX(op_array)->opcodes + opline->op2.u.opline_num);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(EX(op_array)->opcodes + opline->op2.u.opline_num);
        } else {
                SELECTIVE_PZVAL_LOCK(object_zval, &opline->result);
                EX_T(opline->result.u.var).var.ptr_ptr = &EX_T(opline->result.u.var).var.ptr;
@@ -2976,8 +2967,7 @@ ZEND_VM_HANDLER(77, ZEND_FE_RESET, CONST|TMP|VAR|CV, ANY)
                } else if (Z_TYPE_PP(array_ptr_ptr) == IS_OBJECT) {
                        if(Z_OBJ_HT_PP(array_ptr_ptr)->get_class_entry == NULL) {
                                zend_error(E_WARNING, "foreach() can not iterate over objects without PHP class");
-                               ZEND_VM_SET_OPCODE(EX(op_array)->opcodes+opline->op2.u.opline_num);
-                               ZEND_VM_CONTINUE_JMP();
+                               ZEND_VM_JMP(EX(op_array)->opcodes+opline->op2.u.opline_num);
                        }
                        
                        ce = Z_OBJCE_PP(array_ptr_ptr);
@@ -3072,8 +3062,7 @@ ZEND_VM_HANDLER(77, ZEND_FE_RESET, CONST|TMP|VAR|CV, ANY)
                FREE_OP1_IF_VAR();
        }
        if (is_empty) {
-               ZEND_VM_SET_OPCODE(EX(op_array)->opcodes+opline->op2.u.opline_num);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(EX(op_array)->opcodes+opline->op2.u.opline_num);
        } else {
                ZEND_VM_NEXT_OPCODE();
        }
@@ -3099,8 +3088,7 @@ ZEND_VM_HANDLER(78, ZEND_FE_FETCH, VAR, ANY)
                default:
                case ZEND_ITER_INVALID:
                        zend_error(E_WARNING, "Invalid argument supplied for foreach()");
-                       ZEND_VM_SET_OPCODE(EX(op_array)->opcodes+opline->op2.u.opline_num);
-                       ZEND_VM_CONTINUE_JMP();
+                       ZEND_VM_JMP(EX(op_array)->opcodes+opline->op2.u.opline_num);
 
                case ZEND_ITER_PLAIN_OBJECT: {
                        char *class_name, *prop_name;
@@ -3110,8 +3098,7 @@ ZEND_VM_HANDLER(78, ZEND_FE_FETCH, VAR, ANY)
                        do {
                                if (zend_hash_get_current_data(fe_ht, (void **) &value)==FAILURE) {
                                        /* reached end of iteration */
-                                       ZEND_VM_SET_OPCODE(EX(op_array)->opcodes+opline->op2.u.opline_num);
-                                       ZEND_VM_CONTINUE_JMP();
+                                       ZEND_VM_JMP(EX(op_array)->opcodes+opline->op2.u.opline_num);
                                }
                                key_type = zend_hash_get_current_key_ex(fe_ht, &str_key, &str_key_len, &int_key, 0, NULL);
 
@@ -3130,8 +3117,7 @@ ZEND_VM_HANDLER(78, ZEND_FE_FETCH, VAR, ANY)
                        fe_ht = HASH_OF(array);
                        if (zend_hash_get_current_data(fe_ht, (void **) &value)==FAILURE) {
                                /* reached end of iteration */
-                               ZEND_VM_SET_OPCODE(EX(op_array)->opcodes+opline->op2.u.opline_num);
-                               ZEND_VM_CONTINUE_JMP();
+                               ZEND_VM_JMP(EX(op_array)->opcodes+opline->op2.u.opline_num);
                        }
                        if (use_key) {
                                key_type = zend_hash_get_current_key_ex(fe_ht, &str_key, &str_key_len, &int_key, 1, NULL);
@@ -3158,8 +3144,7 @@ ZEND_VM_HANDLER(78, ZEND_FE_FETCH, VAR, ANY)
                                        zval_ptr_dtor(&array);
                                        ZEND_VM_NEXT_OPCODE();
                                }
-                               ZEND_VM_SET_OPCODE(EX(op_array)->opcodes+opline->op2.u.opline_num);
-                               ZEND_VM_CONTINUE_JMP();
+                               ZEND_VM_JMP(EX(op_array)->opcodes+opline->op2.u.opline_num);
                        }
                        iter->funcs->get_current_data(iter, &value TSRMLS_CC);
                        if (EG(exception)) {
@@ -3169,8 +3154,7 @@ ZEND_VM_HANDLER(78, ZEND_FE_FETCH, VAR, ANY)
                        }
                        if (!value) {
                                /* failure in get_current_data */
-                               ZEND_VM_SET_OPCODE(EX(op_array)->opcodes+opline->op2.u.opline_num);
-                               ZEND_VM_CONTINUE_JMP();
+                               ZEND_VM_JMP(EX(op_array)->opcodes+opline->op2.u.opline_num);
                        }
                        if (use_key) {
                                if (iter->funcs->get_current_key) {
index c637e31fc946dde2923509fd1272dd6a092f8605..d3affc42dd7e61ea5d59ba21a88984e2dc2de747 100644 (file)
@@ -403,8 +403,7 @@ static int ZEND_NEW_SPEC_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
                } else {
                        zval_ptr_dtor(&object_zval);
                }
-               ZEND_VM_SET_OPCODE(EX(op_array)->opcodes + opline->op2.u.opline_num);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(EX(op_array)->opcodes + opline->op2.u.opline_num);
        } else {
                SELECTIVE_PZVAL_LOCK(object_zval, &opline->result);
                EX_T(opline->result.u.var).var.ptr_ptr = &EX_T(opline->result.u.var).var.ptr;
@@ -765,26 +764,24 @@ static int ZEND_BRK_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 {
        zend_op *opline = EX(opline);
        
+       zend_brk_cont_element *el;
 
-       ZEND_VM_SET_OPCODE(EX(op_array)->opcodes +
-         zend_brk_cont(&opline->op2.u.constant,
-           opline->op1.u.opline_num,
-           EX(op_array), EX(Ts) TSRMLS_CC)->brk);
+       el = zend_brk_cont(&opline->op2.u.constant, opline->op1.u.opline_num,
+                          EX(op_array), EX(Ts) TSRMLS_CC);
 
-       ZEND_VM_CONTINUE(); /* CHECK_ME */
+       ZEND_VM_JMP(EX(op_array)->opcodes + el->brk);
 }
 
 static int ZEND_CONT_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 {
        zend_op *opline = EX(opline);
        
+       zend_brk_cont_element *el;
 
-       ZEND_VM_SET_OPCODE(EX(op_array)->opcodes +
-         zend_brk_cont(&opline->op2.u.constant,
-           opline->op1.u.opline_num,
-           EX(op_array), EX(Ts) TSRMLS_CC)->cont);
+       el = zend_brk_cont(&opline->op2.u.constant, opline->op1.u.opline_num,
+                          EX(op_array), EX(Ts) TSRMLS_CC);
 
-       ZEND_VM_CONTINUE(); /* CHECK_ME */
+       ZEND_VM_JMP(EX(op_array)->opcodes + el->cont);
 }
 
 static int ZEND_FETCH_CLASS_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
@@ -916,26 +913,24 @@ static int ZEND_BRK_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 {
        zend_op *opline = EX(opline);
        zend_free_op free_op2;
+       zend_brk_cont_element *el;
 
-       ZEND_VM_SET_OPCODE(EX(op_array)->opcodes +
-         zend_brk_cont(_get_zval_ptr_tmp(&opline->op2, EX(Ts), &free_op2 TSRMLS_CC),
-           opline->op1.u.opline_num,
-           EX(op_array), EX(Ts) TSRMLS_CC)->brk);
+       el = zend_brk_cont(_get_zval_ptr_tmp(&opline->op2, EX(Ts), &free_op2 TSRMLS_CC), opline->op1.u.opline_num,
+                          EX(op_array), EX(Ts) TSRMLS_CC);
        zval_dtor(free_op2.var);
-       ZEND_VM_CONTINUE(); /* CHECK_ME */
+       ZEND_VM_JMP(EX(op_array)->opcodes + el->brk);
 }
 
 static int ZEND_CONT_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 {
        zend_op *opline = EX(opline);
        zend_free_op free_op2;
+       zend_brk_cont_element *el;
 
-       ZEND_VM_SET_OPCODE(EX(op_array)->opcodes +
-         zend_brk_cont(_get_zval_ptr_tmp(&opline->op2, EX(Ts), &free_op2 TSRMLS_CC),
-           opline->op1.u.opline_num,
-           EX(op_array), EX(Ts) TSRMLS_CC)->cont);
+       el = zend_brk_cont(_get_zval_ptr_tmp(&opline->op2, EX(Ts), &free_op2 TSRMLS_CC), opline->op1.u.opline_num,
+                          EX(op_array), EX(Ts) TSRMLS_CC);
        zval_dtor(free_op2.var);
-       ZEND_VM_CONTINUE(); /* CHECK_ME */
+       ZEND_VM_JMP(EX(op_array)->opcodes + el->cont);
 }
 
 static int ZEND_FETCH_CLASS_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
@@ -1067,26 +1062,24 @@ static int ZEND_BRK_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 {
        zend_op *opline = EX(opline);
        zend_free_op free_op2;
+       zend_brk_cont_element *el;
 
-       ZEND_VM_SET_OPCODE(EX(op_array)->opcodes +
-         zend_brk_cont(_get_zval_ptr_var(&opline->op2, EX(Ts), &free_op2 TSRMLS_CC),
-           opline->op1.u.opline_num,
-           EX(op_array), EX(Ts) TSRMLS_CC)->brk);
+       el = zend_brk_cont(_get_zval_ptr_var(&opline->op2, EX(Ts), &free_op2 TSRMLS_CC), opline->op1.u.opline_num,
+                          EX(op_array), EX(Ts) TSRMLS_CC);
        if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
-       ZEND_VM_CONTINUE(); /* CHECK_ME */
+       ZEND_VM_JMP(EX(op_array)->opcodes + el->brk);
 }
 
 static int ZEND_CONT_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 {
        zend_op *opline = EX(opline);
        zend_free_op free_op2;
+       zend_brk_cont_element *el;
 
-       ZEND_VM_SET_OPCODE(EX(op_array)->opcodes +
-         zend_brk_cont(_get_zval_ptr_var(&opline->op2, EX(Ts), &free_op2 TSRMLS_CC),
-           opline->op1.u.opline_num,
-           EX(op_array), EX(Ts) TSRMLS_CC)->cont);
+       el = zend_brk_cont(_get_zval_ptr_var(&opline->op2, EX(Ts), &free_op2 TSRMLS_CC), opline->op1.u.opline_num,
+                          EX(op_array), EX(Ts) TSRMLS_CC);
        if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
-       ZEND_VM_CONTINUE(); /* CHECK_ME */
+       ZEND_VM_JMP(EX(op_array)->opcodes + el->cont);
 }
 
 static int ZEND_FETCH_CLASS_SPEC_UNUSED_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
@@ -1298,26 +1291,24 @@ static int ZEND_BRK_SPEC_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 {
        zend_op *opline = EX(opline);
        
+       zend_brk_cont_element *el;
 
-       ZEND_VM_SET_OPCODE(EX(op_array)->opcodes +
-         zend_brk_cont(_get_zval_ptr_cv(&opline->op2, EX(Ts), BP_VAR_R TSRMLS_CC),
-           opline->op1.u.opline_num,
-           EX(op_array), EX(Ts) TSRMLS_CC)->brk);
+       el = zend_brk_cont(_get_zval_ptr_cv(&opline->op2, EX(Ts), BP_VAR_R TSRMLS_CC), opline->op1.u.opline_num,
+                          EX(op_array), EX(Ts) TSRMLS_CC);
 
-       ZEND_VM_CONTINUE(); /* CHECK_ME */
+       ZEND_VM_JMP(EX(op_array)->opcodes + el->brk);
 }
 
 static int ZEND_CONT_SPEC_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 {
        zend_op *opline = EX(opline);
        
+       zend_brk_cont_element *el;
 
-       ZEND_VM_SET_OPCODE(EX(op_array)->opcodes +
-         zend_brk_cont(_get_zval_ptr_cv(&opline->op2, EX(Ts), BP_VAR_R TSRMLS_CC),
-           opline->op1.u.opline_num,
-           EX(op_array), EX(Ts) TSRMLS_CC)->cont);
+       el = zend_brk_cont(_get_zval_ptr_cv(&opline->op2, EX(Ts), BP_VAR_R TSRMLS_CC), opline->op1.u.opline_num,
+                          EX(op_array), EX(Ts) TSRMLS_CC);
 
-       ZEND_VM_CONTINUE(); /* CHECK_ME */
+       ZEND_VM_JMP(EX(op_array)->opcodes + el->cont);
 }
 
 static int ZEND_BW_NOT_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
@@ -1496,8 +1487,7 @@ static int ZEND_JMPZ_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(opline->op2.u.jmp_addr);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(opline->op2.u.jmp_addr);
        }
 
        ZEND_VM_NEXT_OPCODE();
@@ -1513,8 +1503,7 @@ static int ZEND_JMPNZ_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(opline->op2.u.jmp_addr);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(opline->op2.u.jmp_addr);
        }
 
        ZEND_VM_NEXT_OPCODE();
@@ -1530,14 +1519,12 @@ static int ZEND_JMPZNZ_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp on true to %d\n", opline->extended_value);
 #endif
-               ZEND_VM_SET_OPCODE(&EX(op_array)->opcodes[opline->extended_value]);
-               ZEND_VM_CONTINUE(); /* CHECK_ME */
+               ZEND_VM_JMP(&EX(op_array)->opcodes[opline->extended_value]);
        } else {
 #if DEBUG_ZEND>=2
                printf("Conditional jmp on false to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(&EX(op_array)->opcodes[opline->op2.u.opline_num]);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(&EX(op_array)->opcodes[opline->op2.u.opline_num]);
        }
 }
 
@@ -1553,8 +1540,7 @@ static int ZEND_JMPZ_EX_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(opline->op2.u.jmp_addr);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(opline->op2.u.jmp_addr);
        }
        ZEND_VM_NEXT_OPCODE();
 }
@@ -1571,8 +1557,7 @@ static int ZEND_JMPNZ_EX_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(opline->op2.u.jmp_addr);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(opline->op2.u.jmp_addr);
        }
        ZEND_VM_NEXT_OPCODE();
 }
@@ -2026,8 +2011,7 @@ static int ZEND_FE_RESET_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
                } else if (Z_TYPE_PP(array_ptr_ptr) == IS_OBJECT) {
                        if(Z_OBJ_HT_PP(array_ptr_ptr)->get_class_entry == NULL) {
                                zend_error(E_WARNING, "foreach() can not iterate over objects without PHP class");
-                               ZEND_VM_SET_OPCODE(EX(op_array)->opcodes+opline->op2.u.opline_num);
-                               ZEND_VM_CONTINUE_JMP();
+                               ZEND_VM_JMP(EX(op_array)->opcodes+opline->op2.u.opline_num);
                        }
                        
                        ce = Z_OBJCE_PP(array_ptr_ptr);
@@ -2122,8 +2106,7 @@ static int ZEND_FE_RESET_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 
        }
        if (is_empty) {
-               ZEND_VM_SET_OPCODE(EX(op_array)->opcodes+opline->op2.u.opline_num);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(EX(op_array)->opcodes+opline->op2.u.opline_num);
        } else {
                ZEND_VM_NEXT_OPCODE();
        }
@@ -3914,8 +3897,7 @@ static int ZEND_JMPZ_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(opline->op2.u.jmp_addr);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(opline->op2.u.jmp_addr);
        }
 
        ZEND_VM_NEXT_OPCODE();
@@ -3932,8 +3914,7 @@ static int ZEND_JMPNZ_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(opline->op2.u.jmp_addr);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(opline->op2.u.jmp_addr);
        }
 
        ZEND_VM_NEXT_OPCODE();
@@ -3950,14 +3931,12 @@ static int ZEND_JMPZNZ_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp on true to %d\n", opline->extended_value);
 #endif
-               ZEND_VM_SET_OPCODE(&EX(op_array)->opcodes[opline->extended_value]);
-               ZEND_VM_CONTINUE(); /* CHECK_ME */
+               ZEND_VM_JMP(&EX(op_array)->opcodes[opline->extended_value]);
        } else {
 #if DEBUG_ZEND>=2
                printf("Conditional jmp on false to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(&EX(op_array)->opcodes[opline->op2.u.opline_num]);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(&EX(op_array)->opcodes[opline->op2.u.opline_num]);
        }
 }
 
@@ -3974,8 +3953,7 @@ static int ZEND_JMPZ_EX_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(opline->op2.u.jmp_addr);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(opline->op2.u.jmp_addr);
        }
        ZEND_VM_NEXT_OPCODE();
 }
@@ -3993,8 +3971,7 @@ static int ZEND_JMPNZ_EX_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(opline->op2.u.jmp_addr);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(opline->op2.u.jmp_addr);
        }
        ZEND_VM_NEXT_OPCODE();
 }
@@ -4445,8 +4422,7 @@ static int ZEND_FE_RESET_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
                } else if (Z_TYPE_PP(array_ptr_ptr) == IS_OBJECT) {
                        if(Z_OBJ_HT_PP(array_ptr_ptr)->get_class_entry == NULL) {
                                zend_error(E_WARNING, "foreach() can not iterate over objects without PHP class");
-                               ZEND_VM_SET_OPCODE(EX(op_array)->opcodes+opline->op2.u.opline_num);
-                               ZEND_VM_CONTINUE_JMP();
+                               ZEND_VM_JMP(EX(op_array)->opcodes+opline->op2.u.opline_num);
                        }
                        
                        ce = Z_OBJCE_PP(array_ptr_ptr);
@@ -4541,8 +4517,7 @@ static int ZEND_FE_RESET_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 
        }
        if (is_empty) {
-               ZEND_VM_SET_OPCODE(EX(op_array)->opcodes+opline->op2.u.opline_num);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(EX(op_array)->opcodes+opline->op2.u.opline_num);
        } else {
                ZEND_VM_NEXT_OPCODE();
        }
@@ -6824,8 +6799,7 @@ static int ZEND_JMPZ_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(opline->op2.u.jmp_addr);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(opline->op2.u.jmp_addr);
        }
 
        ZEND_VM_NEXT_OPCODE();
@@ -6842,8 +6816,7 @@ static int ZEND_JMPNZ_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(opline->op2.u.jmp_addr);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(opline->op2.u.jmp_addr);
        }
 
        ZEND_VM_NEXT_OPCODE();
@@ -6860,14 +6833,12 @@ static int ZEND_JMPZNZ_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp on true to %d\n", opline->extended_value);
 #endif
-               ZEND_VM_SET_OPCODE(&EX(op_array)->opcodes[opline->extended_value]);
-               ZEND_VM_CONTINUE(); /* CHECK_ME */
+               ZEND_VM_JMP(&EX(op_array)->opcodes[opline->extended_value]);
        } else {
 #if DEBUG_ZEND>=2
                printf("Conditional jmp on false to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(&EX(op_array)->opcodes[opline->op2.u.opline_num]);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(&EX(op_array)->opcodes[opline->op2.u.opline_num]);
        }
 }
 
@@ -6884,8 +6855,7 @@ static int ZEND_JMPZ_EX_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(opline->op2.u.jmp_addr);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(opline->op2.u.jmp_addr);
        }
        ZEND_VM_NEXT_OPCODE();
 }
@@ -6903,8 +6873,7 @@ static int ZEND_JMPNZ_EX_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(opline->op2.u.jmp_addr);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(opline->op2.u.jmp_addr);
        }
        ZEND_VM_NEXT_OPCODE();
 }
@@ -7445,8 +7414,7 @@ static int ZEND_FE_RESET_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
                } else if (Z_TYPE_PP(array_ptr_ptr) == IS_OBJECT) {
                        if(Z_OBJ_HT_PP(array_ptr_ptr)->get_class_entry == NULL) {
                                zend_error(E_WARNING, "foreach() can not iterate over objects without PHP class");
-                               ZEND_VM_SET_OPCODE(EX(op_array)->opcodes+opline->op2.u.opline_num);
-                               ZEND_VM_CONTINUE_JMP();
+                               ZEND_VM_JMP(EX(op_array)->opcodes+opline->op2.u.opline_num);
                        }
                        
                        ce = Z_OBJCE_PP(array_ptr_ptr);
@@ -7541,8 +7509,7 @@ static int ZEND_FE_RESET_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
                if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
        }
        if (is_empty) {
-               ZEND_VM_SET_OPCODE(EX(op_array)->opcodes+opline->op2.u.opline_num);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(EX(op_array)->opcodes+opline->op2.u.opline_num);
        } else {
                ZEND_VM_NEXT_OPCODE();
        }
@@ -7568,8 +7535,7 @@ static int ZEND_FE_FETCH_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
                default:
                case ZEND_ITER_INVALID:
                        zend_error(E_WARNING, "Invalid argument supplied for foreach()");
-                       ZEND_VM_SET_OPCODE(EX(op_array)->opcodes+opline->op2.u.opline_num);
-                       ZEND_VM_CONTINUE_JMP();
+                       ZEND_VM_JMP(EX(op_array)->opcodes+opline->op2.u.opline_num);
 
                case ZEND_ITER_PLAIN_OBJECT: {
                        char *class_name, *prop_name;
@@ -7579,8 +7545,7 @@ static int ZEND_FE_FETCH_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
                        do {
                                if (zend_hash_get_current_data(fe_ht, (void **) &value)==FAILURE) {
                                        /* reached end of iteration */
-                                       ZEND_VM_SET_OPCODE(EX(op_array)->opcodes+opline->op2.u.opline_num);
-                                       ZEND_VM_CONTINUE_JMP();
+                                       ZEND_VM_JMP(EX(op_array)->opcodes+opline->op2.u.opline_num);
                                }
                                key_type = zend_hash_get_current_key_ex(fe_ht, &str_key, &str_key_len, &int_key, 0, NULL);
 
@@ -7599,8 +7564,7 @@ static int ZEND_FE_FETCH_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
                        fe_ht = HASH_OF(array);
                        if (zend_hash_get_current_data(fe_ht, (void **) &value)==FAILURE) {
                                /* reached end of iteration */
-                               ZEND_VM_SET_OPCODE(EX(op_array)->opcodes+opline->op2.u.opline_num);
-                               ZEND_VM_CONTINUE_JMP();
+                               ZEND_VM_JMP(EX(op_array)->opcodes+opline->op2.u.opline_num);
                        }
                        if (use_key) {
                                key_type = zend_hash_get_current_key_ex(fe_ht, &str_key, &str_key_len, &int_key, 1, NULL);
@@ -7627,8 +7591,7 @@ static int ZEND_FE_FETCH_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
                                        zval_ptr_dtor(&array);
                                        ZEND_VM_NEXT_OPCODE();
                                }
-                               ZEND_VM_SET_OPCODE(EX(op_array)->opcodes+opline->op2.u.opline_num);
-                               ZEND_VM_CONTINUE_JMP();
+                               ZEND_VM_JMP(EX(op_array)->opcodes+opline->op2.u.opline_num);
                        }
                        iter->funcs->get_current_data(iter, &value TSRMLS_CC);
                        if (EG(exception)) {
@@ -7638,8 +7601,7 @@ static int ZEND_FE_FETCH_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
                        }
                        if (!value) {
                                /* failure in get_current_data */
-                               ZEND_VM_SET_OPCODE(EX(op_array)->opcodes+opline->op2.u.opline_num);
-                               ZEND_VM_CONTINUE_JMP();
+                               ZEND_VM_JMP(EX(op_array)->opcodes+opline->op2.u.opline_num);
                        }
                        if (use_key) {
                                if (iter->funcs->get_current_key) {
@@ -18938,8 +18900,7 @@ static int ZEND_JMPZ_SPEC_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(opline->op2.u.jmp_addr);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(opline->op2.u.jmp_addr);
        }
 
        ZEND_VM_NEXT_OPCODE();
@@ -18955,8 +18916,7 @@ static int ZEND_JMPNZ_SPEC_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(opline->op2.u.jmp_addr);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(opline->op2.u.jmp_addr);
        }
 
        ZEND_VM_NEXT_OPCODE();
@@ -18972,14 +18932,12 @@ static int ZEND_JMPZNZ_SPEC_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp on true to %d\n", opline->extended_value);
 #endif
-               ZEND_VM_SET_OPCODE(&EX(op_array)->opcodes[opline->extended_value]);
-               ZEND_VM_CONTINUE(); /* CHECK_ME */
+               ZEND_VM_JMP(&EX(op_array)->opcodes[opline->extended_value]);
        } else {
 #if DEBUG_ZEND>=2
                printf("Conditional jmp on false to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(&EX(op_array)->opcodes[opline->op2.u.opline_num]);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(&EX(op_array)->opcodes[opline->op2.u.opline_num]);
        }
 }
 
@@ -18995,8 +18953,7 @@ static int ZEND_JMPZ_EX_SPEC_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(opline->op2.u.jmp_addr);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(opline->op2.u.jmp_addr);
        }
        ZEND_VM_NEXT_OPCODE();
 }
@@ -19013,8 +18970,7 @@ static int ZEND_JMPNZ_EX_SPEC_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 #if DEBUG_ZEND>=2
                printf("Conditional jmp to %d\n", opline->op2.u.opline_num);
 #endif
-               ZEND_VM_SET_OPCODE(opline->op2.u.jmp_addr);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(opline->op2.u.jmp_addr);
        }
        ZEND_VM_NEXT_OPCODE();
 }
@@ -19547,8 +19503,7 @@ static int ZEND_FE_RESET_SPEC_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
                } else if (Z_TYPE_PP(array_ptr_ptr) == IS_OBJECT) {
                        if(Z_OBJ_HT_PP(array_ptr_ptr)->get_class_entry == NULL) {
                                zend_error(E_WARNING, "foreach() can not iterate over objects without PHP class");
-                               ZEND_VM_SET_OPCODE(EX(op_array)->opcodes+opline->op2.u.opline_num);
-                               ZEND_VM_CONTINUE_JMP();
+                               ZEND_VM_JMP(EX(op_array)->opcodes+opline->op2.u.opline_num);
                        }
                        
                        ce = Z_OBJCE_PP(array_ptr_ptr);
@@ -19643,8 +19598,7 @@ static int ZEND_FE_RESET_SPEC_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 
        }
        if (is_empty) {
-               ZEND_VM_SET_OPCODE(EX(op_array)->opcodes+opline->op2.u.opline_num);
-               ZEND_VM_CONTINUE_JMP();
+               ZEND_VM_JMP(EX(op_array)->opcodes+opline->op2.u.opline_num);
        } else {
                ZEND_VM_NEXT_OPCODE();
        }