mirror of
https://github.com/php/php-src.git
synced 2026-03-24 00:02:20 +01:00
Emit EXT_STMT after each pipe stage, and attach the TMP var that holds the intermediary result (#19377)
* Emit EXT_STMT after each pipe stage, and attach the TMP var that holds the intermediary result * Add ZEND_EXT_STMT to keeps_op1_alive as per review * Fix leak with EXT_STMT when pipe result is unused Co-authored-by: Ilija Tovilo <ilija.tovilo@me.com>
This commit is contained in:
@@ -420,6 +420,14 @@ static void zend_optimize_block(zend_basic_block *block, zend_op_array *op_array
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case ZEND_EXT_STMT:
|
||||||
|
if (opline->op1_type & (IS_TMP_VAR|IS_VAR)) {
|
||||||
|
/* Variable will be deleted later by FREE, so we can't optimize it */
|
||||||
|
Tsource[VAR_NUM(opline->op1.var)] = NULL;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
case ZEND_CASE:
|
case ZEND_CASE:
|
||||||
case ZEND_CASE_STRICT:
|
case ZEND_CASE_STRICT:
|
||||||
case ZEND_COPY_TMP:
|
case ZEND_COPY_TMP:
|
||||||
|
|||||||
@@ -821,7 +821,8 @@ static void zend_do_free(znode *op1) /* {{{ */
|
|||||||
} else {
|
} else {
|
||||||
while (opline >= CG(active_op_array)->opcodes) {
|
while (opline >= CG(active_op_array)->opcodes) {
|
||||||
if ((opline->opcode == ZEND_FETCH_LIST_R ||
|
if ((opline->opcode == ZEND_FETCH_LIST_R ||
|
||||||
opline->opcode == ZEND_FETCH_LIST_W) &&
|
opline->opcode == ZEND_FETCH_LIST_W ||
|
||||||
|
opline->opcode == ZEND_EXT_STMT) &&
|
||||||
opline->op1_type == IS_VAR &&
|
opline->op1_type == IS_VAR &&
|
||||||
opline->op1.var == op1->u.op.var) {
|
opline->op1.var == op1->u.op.var) {
|
||||||
zend_emit_op(NULL, ZEND_FREE, op1, NULL);
|
zend_emit_op(NULL, ZEND_FREE, op1, NULL);
|
||||||
@@ -1920,7 +1921,7 @@ static void zend_add_to_list(void *result, void *item) /* {{{ */
|
|||||||
}
|
}
|
||||||
/* }}} */
|
/* }}} */
|
||||||
|
|
||||||
static void zend_do_extended_stmt(void) /* {{{ */
|
static void zend_do_extended_stmt(znode* result) /* {{{ */
|
||||||
{
|
{
|
||||||
zend_op *opline;
|
zend_op *opline;
|
||||||
|
|
||||||
@@ -1931,6 +1932,9 @@ static void zend_do_extended_stmt(void) /* {{{ */
|
|||||||
opline = get_next_op();
|
opline = get_next_op();
|
||||||
|
|
||||||
opline->opcode = ZEND_EXT_STMT;
|
opline->opcode = ZEND_EXT_STMT;
|
||||||
|
if (result) {
|
||||||
|
SET_NODE(opline->op1, result);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
/* }}} */
|
/* }}} */
|
||||||
|
|
||||||
@@ -6050,7 +6054,7 @@ static void zend_compile_for(zend_ast *ast) /* {{{ */
|
|||||||
|
|
||||||
zend_update_jump_target_to_next(opnum_jmp);
|
zend_update_jump_target_to_next(opnum_jmp);
|
||||||
zend_compile_for_expr_list(&result, cond_ast);
|
zend_compile_for_expr_list(&result, cond_ast);
|
||||||
zend_do_extended_stmt();
|
zend_do_extended_stmt(NULL);
|
||||||
|
|
||||||
zend_emit_cond_jump(ZEND_JMPNZ, &result, opnum_start);
|
zend_emit_cond_jump(ZEND_JMPNZ, &result, opnum_start);
|
||||||
|
|
||||||
@@ -6171,7 +6175,7 @@ static void zend_compile_if(zend_ast *ast) /* {{{ */
|
|||||||
|
|
||||||
if (i > 0) {
|
if (i > 0) {
|
||||||
CG(zend_lineno) = cond_ast->lineno;
|
CG(zend_lineno) = cond_ast->lineno;
|
||||||
zend_do_extended_stmt();
|
zend_do_extended_stmt(NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
zend_compile_expr(&cond_node, cond_ast);
|
zend_compile_expr(&cond_node, cond_ast);
|
||||||
@@ -6505,6 +6509,8 @@ static void zend_compile_pipe(znode *result, zend_ast *ast)
|
|||||||
}
|
}
|
||||||
|
|
||||||
zend_compile_expr(result, fcall_ast);
|
zend_compile_expr(result, fcall_ast);
|
||||||
|
CG(zend_lineno) = fcall_ast->lineno;
|
||||||
|
zend_do_extended_stmt(result);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void zend_compile_match(znode *result, zend_ast *ast)
|
static void zend_compile_match(znode *result, zend_ast *ast)
|
||||||
@@ -8537,7 +8543,7 @@ static zend_op_array *zend_compile_func_decl_ex(
|
|||||||
/* put the implicit return on the really last line */
|
/* put the implicit return on the really last line */
|
||||||
CG(zend_lineno) = decl->end_lineno;
|
CG(zend_lineno) = decl->end_lineno;
|
||||||
|
|
||||||
zend_do_extended_stmt();
|
zend_do_extended_stmt(NULL);
|
||||||
zend_emit_final_return(0);
|
zend_emit_final_return(0);
|
||||||
|
|
||||||
pass_two(CG(active_op_array));
|
pass_two(CG(active_op_array));
|
||||||
@@ -11607,7 +11613,7 @@ static void zend_compile_stmt(zend_ast *ast) /* {{{ */
|
|||||||
CG(zend_lineno) = ast->lineno;
|
CG(zend_lineno) = ast->lineno;
|
||||||
|
|
||||||
if ((CG(compiler_options) & ZEND_COMPILE_EXTENDED_STMT) && !zend_is_unticked_stmt(ast)) {
|
if ((CG(compiler_options) & ZEND_COMPILE_EXTENDED_STMT) && !zend_is_unticked_stmt(ast)) {
|
||||||
zend_do_extended_stmt();
|
zend_do_extended_stmt(NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
switch (ast->kind) {
|
switch (ast->kind) {
|
||||||
|
|||||||
@@ -903,7 +903,8 @@ static bool keeps_op1_alive(zend_op *opline) {
|
|||||||
|| opline->opcode == ZEND_MATCH_ERROR
|
|| opline->opcode == ZEND_MATCH_ERROR
|
||||||
|| opline->opcode == ZEND_FETCH_LIST_R
|
|| opline->opcode == ZEND_FETCH_LIST_R
|
||||||
|| opline->opcode == ZEND_FETCH_LIST_W
|
|| opline->opcode == ZEND_FETCH_LIST_W
|
||||||
|| opline->opcode == ZEND_COPY_TMP) {
|
|| opline->opcode == ZEND_COPY_TMP
|
||||||
|
|| opline->opcode == ZEND_EXT_STMT) {
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
ZEND_ASSERT(opline->opcode != ZEND_FE_FETCH_R
|
ZEND_ASSERT(opline->opcode != ZEND_FE_FETCH_R
|
||||||
|
|||||||
Reference in New Issue
Block a user