Skip to content

Commit cc876c0

Browse files
committed
Fix too early terminated temporary range with break/cont/goto
I have no crashing or leaking reproduce script, only valgrind invalid reads for that one; hence no phpt here
1 parent 9591b1c commit cc876c0

File tree

5 files changed

+10
-10
lines changed

5 files changed

+10
-10
lines changed

Zend/zend_compile.c

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3482,7 +3482,7 @@ void zend_compile_return(zend_ast *ast) /* {{{ */
34823482
zend_emit_return_type_check(expr_ast ? &expr_node : NULL, CG(active_op_array)->arg_info - 1);
34833483
}
34843484

3485-
zend_free_foreach_and_switch_variables(ZEND_FREE_ON_RETURN);
3485+
zend_free_foreach_and_switch_variables(ZEND_FREE_ON_JUMP);
34863486

34873487
if (CG(context).in_finally) {
34883488
opline = zend_emit_op(NULL, ZEND_DISCARD_EXCEPTION, NULL, NULL);
@@ -3567,7 +3567,7 @@ void zend_compile_break_continue(zend_ast *ast) /* {{{ */
35673567
}
35683568

35693569
if (nest_level > 1) {
3570-
generate_free_loop_var(&CG(context).brk_cont_array[array_offset].loop_var);
3570+
generate_free_loop_var_ex(&CG(context).brk_cont_array[array_offset].loop_var, ZEND_FREE_ON_JUMP);
35713571
}
35723572

35733573
array_offset = CG(context).brk_cont_array[array_offset].parent;
@@ -3637,7 +3637,7 @@ void zend_resolve_goto_label(zend_op_array *op_array, znode *label_node, zend_op
36373637
if (pass2_opline) {
36383638
free_vars++;
36393639
} else {
3640-
generate_free_loop_var(&CG(context).brk_cont_array[current].loop_var);
3640+
generate_free_loop_var_ex(&CG(context).brk_cont_array[current].loop_var, ZEND_FREE_ON_JUMP);
36413641
}
36423642
}
36433643
current = CG(context).brk_cont_array[current].parent;

Zend/zend_compile.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -882,7 +882,7 @@ ZEND_API void zend_assert_valid_class_name(const zend_string *const_name);
882882

883883
#define ZEND_FETCH_ARG_MASK 0x000fffff
884884

885-
#define ZEND_FREE_ON_RETURN (1<<0)
885+
#define ZEND_FREE_ON_JUMP (1<<0)
886886

887887
#define ZEND_MEMBER_FUNC_CALL (1<<0)
888888

Zend/zend_opcode.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -994,8 +994,8 @@ static zend_always_inline uint32_t *generate_var_liveliness_info_ex(zend_op_arra
994994
&& opline->opcode != ZEND_FE_FETCH_RW
995995
/* the following opcodes are parts of "return" statement */
996996
&& opline->opcode != ZEND_VERIFY_RETURN_TYPE
997-
&& (opline->opcode != ZEND_FREE || !(opline->extended_value & ZEND_FREE_ON_RETURN))
998-
&& (opline->opcode != ZEND_FE_FREE || !(opline->extended_value & ZEND_FREE_ON_RETURN))
997+
&& (opline->opcode != ZEND_FREE || !(opline->extended_value & ZEND_FREE_ON_JUMP))
998+
&& (opline->opcode != ZEND_FE_FREE || !(opline->extended_value & ZEND_FREE_ON_JUMP))
999999
) {
10001000
op_live_total += liveliness_kill_var(op_array, opline, var, Tstart, opTs);
10011001
}

Zend/zend_vm_def.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7084,8 +7084,8 @@ ZEND_VM_HANDLER(149, ZEND_HANDLE_EXCEPTION, ANY, ANY)
70847084

70857085
if (catch_op_num || finally_op_num) {
70867086
if (EX(func)->op_array.opcodes[op_num].opcode == ZEND_VERIFY_RETURN_TYPE
7087-
|| (EX(func)->op_array.opcodes[op_num].opcode == ZEND_FREE && (EX(func)->op_array.opcodes[op_num].extended_value & ZEND_FREE_ON_RETURN))
7088-
|| (EX(func)->op_array.opcodes[op_num].opcode == ZEND_FE_FREE && (EX(func)->op_array.opcodes[op_num].extended_value & ZEND_FREE_ON_RETURN))
7087+
|| (EX(func)->op_array.opcodes[op_num].opcode == ZEND_FREE && (EX(func)->op_array.opcodes[op_num].extended_value & ZEND_FREE_ON_JUMP))
7088+
|| (EX(func)->op_array.opcodes[op_num].opcode == ZEND_FE_FREE && (EX(func)->op_array.opcodes[op_num].extended_value & ZEND_FREE_ON_JUMP))
70897089
) {
70907090
catch_op_num = finally_op_num = 0;
70917091
}

Zend/zend_vm_execute.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1502,8 +1502,8 @@ static ZEND_OPCODE_HANDLER_RET ZEND_FASTCALL ZEND_HANDLE_EXCEPTION_SPEC_HANDLER(
15021502

15031503
if (catch_op_num || finally_op_num) {
15041504
if (EX(func)->op_array.opcodes[op_num].opcode == ZEND_VERIFY_RETURN_TYPE
1505-
|| (EX(func)->op_array.opcodes[op_num].opcode == ZEND_FREE && (EX(func)->op_array.opcodes[op_num].extended_value & ZEND_FREE_ON_RETURN))
1506-
|| (EX(func)->op_array.opcodes[op_num].opcode == ZEND_FE_FREE && (EX(func)->op_array.opcodes[op_num].extended_value & ZEND_FREE_ON_RETURN))
1505+
|| (EX(func)->op_array.opcodes[op_num].opcode == ZEND_FREE && (EX(func)->op_array.opcodes[op_num].extended_value & ZEND_FREE_ON_JUMP))
1506+
|| (EX(func)->op_array.opcodes[op_num].opcode == ZEND_FE_FREE && (EX(func)->op_array.opcodes[op_num].extended_value & ZEND_FREE_ON_JUMP))
15071507
) {
15081508
catch_op_num = finally_op_num = 0;
15091509
}

0 commit comments

Comments
 (0)