mirror of
https://github.com/php/php-src.git
synced 2025-08-18 23:18:56 +02:00
Merge branch 'PHP-7.1'
This commit is contained in:
commit
976d72a3bd
4 changed files with 77 additions and 76 deletions
|
@ -1647,8 +1647,12 @@ static void zend_t_usage(zend_cfg *cfg, zend_op_array *op_array, zend_bitset use
|
||||||
case ZEND_QM_ASSIGN:
|
case ZEND_QM_ASSIGN:
|
||||||
case ZEND_BOOL:
|
case ZEND_BOOL:
|
||||||
case ZEND_BOOL_NOT:
|
case ZEND_BOOL_NOT:
|
||||||
if (ZEND_OP1_TYPE(opline) == IS_TMP_VAR) {
|
if (ZEND_OP1_TYPE(opline) == IS_CV) {
|
||||||
|
opline->opcode = ZEND_CHECK_VAR;
|
||||||
|
SET_UNUSED(opline->result);
|
||||||
|
} else if (ZEND_OP1_TYPE(opline) == IS_TMP_VAR) {
|
||||||
opline->opcode = ZEND_FREE;
|
opline->opcode = ZEND_FREE;
|
||||||
|
SET_UNUSED(opline->result);
|
||||||
} else {
|
} else {
|
||||||
if (ZEND_OP1_TYPE(opline) == IS_CONST) {
|
if (ZEND_OP1_TYPE(opline) == IS_CONST) {
|
||||||
literal_dtor(&ZEND_OP1_LITERAL(opline));
|
literal_dtor(&ZEND_OP1_LITERAL(opline));
|
||||||
|
|
|
@ -1145,13 +1145,13 @@ static const func_info_t func_infos[] = {
|
||||||
F0("xml_set_external_entity_ref_handler", MAY_BE_NULL | MAY_BE_FALSE | MAY_BE_TRUE),
|
F0("xml_set_external_entity_ref_handler", MAY_BE_NULL | MAY_BE_FALSE | MAY_BE_TRUE),
|
||||||
F0("xml_set_start_namespace_decl_handler", MAY_BE_NULL | MAY_BE_FALSE | MAY_BE_TRUE),
|
F0("xml_set_start_namespace_decl_handler", MAY_BE_NULL | MAY_BE_FALSE | MAY_BE_TRUE),
|
||||||
F0("xml_set_end_namespace_decl_handler", MAY_BE_NULL | MAY_BE_FALSE | MAY_BE_TRUE),
|
F0("xml_set_end_namespace_decl_handler", MAY_BE_NULL | MAY_BE_FALSE | MAY_BE_TRUE),
|
||||||
F0("xml_parse", MAY_BE_NULL | MAY_BE_LONG),
|
F0("xml_parse", MAY_BE_NULL | MAY_BE_FALSE | MAY_BE_LONG),
|
||||||
F0("xml_parse_into_struct", MAY_BE_NULL | MAY_BE_LONG),
|
F0("xml_parse_into_struct", MAY_BE_NULL | MAY_BE_FALSE | MAY_BE_LONG),
|
||||||
F0("xml_get_error_code", MAY_BE_NULL | MAY_BE_LONG),
|
F0("xml_get_error_code", MAY_BE_NULL | MAY_BE_FALSE | MAY_BE_LONG),
|
||||||
F1("xml_error_string", MAY_BE_NULL | MAY_BE_STRING),
|
F1("xml_error_string", MAY_BE_NULL | MAY_BE_STRING),
|
||||||
F0("xml_get_current_line_number", MAY_BE_NULL | MAY_BE_LONG),
|
F0("xml_get_current_line_number", MAY_BE_NULL | MAY_BE_FALSE | MAY_BE_LONG),
|
||||||
F0("xml_get_current_column_number", MAY_BE_NULL | MAY_BE_LONG),
|
F0("xml_get_current_column_number", MAY_BE_NULL | MAY_BE_FALSE | MAY_BE_LONG),
|
||||||
F0("xml_get_current_byte_index", MAY_BE_NULL | MAY_BE_LONG),
|
F0("xml_get_current_byte_index", MAY_BE_NULL | MAY_BE_FALSE | MAY_BE_LONG),
|
||||||
F0("xml_parser_free", MAY_BE_NULL | MAY_BE_FALSE | MAY_BE_TRUE),
|
F0("xml_parser_free", MAY_BE_NULL | MAY_BE_FALSE | MAY_BE_TRUE),
|
||||||
F0("xml_parser_set_option", MAY_BE_NULL | MAY_BE_FALSE | MAY_BE_TRUE),
|
F0("xml_parser_set_option", MAY_BE_NULL | MAY_BE_FALSE | MAY_BE_TRUE),
|
||||||
F1("xml_parser_get_option", MAY_BE_NULL | MAY_BE_FALSE | MAY_BE_LONG | MAY_BE_STRING),
|
F1("xml_parser_get_option", MAY_BE_NULL | MAY_BE_FALSE | MAY_BE_LONG | MAY_BE_STRING),
|
||||||
|
|
|
@ -24,11 +24,39 @@
|
||||||
#include "zend_call_graph.h"
|
#include "zend_call_graph.h"
|
||||||
#include "zend_worklist.h"
|
#include "zend_worklist.h"
|
||||||
|
|
||||||
//#define LOG_SSA_RANGE
|
/* The used range inference algorithm is described in:
|
||||||
//#define LOG_NEG_RANGE
|
* V. Campos, R. Rodrigues, I. de Assis Costa and F. Pereira.
|
||||||
|
* "Speed and Precision in Range Analysis", SBLP'12.
|
||||||
|
*
|
||||||
|
* There are a couple degrees of freedom, we use:
|
||||||
|
* * Propagation on SCCs.
|
||||||
|
* * e-SSA for live range splitting.
|
||||||
|
* * Only intra-procedural inference.
|
||||||
|
* * Widening with warmup passes, but without jump sets.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* Whether to handle symbolic range constraints */
|
||||||
#define SYM_RANGE
|
#define SYM_RANGE
|
||||||
|
|
||||||
|
/* Whether to handle negative range constraints */
|
||||||
#define NEG_RANGE
|
#define NEG_RANGE
|
||||||
#define RANGE_WARMAP_PASSES 16
|
|
||||||
|
/* Number of warmup passes to use prior to widening */
|
||||||
|
#define RANGE_WARMUP_PASSES 16
|
||||||
|
|
||||||
|
/* Logging for range inference in general */
|
||||||
|
#if 0
|
||||||
|
#define LOG_SSA_RANGE(...) fprintf(stderr, __VA_ARGS__)
|
||||||
|
#else
|
||||||
|
#define LOG_SSA_RANGE(...)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/* Logging for negative range constraints */
|
||||||
|
#if 0
|
||||||
|
#define LOG_NEG_RANGE(...) fprintf(stderr, __VA_ARGS__)
|
||||||
|
#else
|
||||||
|
#define LOG_NEG_RANGE(...)
|
||||||
|
#endif
|
||||||
|
|
||||||
#define CHECK_SCC_VAR(var2) \
|
#define CHECK_SCC_VAR(var2) \
|
||||||
do { \
|
do { \
|
||||||
|
@ -167,14 +195,14 @@ int zend_ssa_find_sccs(const zend_op_array *op_array, zend_ssa *ssa) /* {{{ */
|
||||||
root = do_alloca(sizeof(int) * ssa->vars_count, root_use_heap);
|
root = do_alloca(sizeof(int) * ssa->vars_count, root_use_heap);
|
||||||
ZEND_WORKLIST_STACK_ALLOCA(&stack, ssa->vars_count, stack_use_heap);
|
ZEND_WORKLIST_STACK_ALLOCA(&stack, ssa->vars_count, stack_use_heap);
|
||||||
|
|
||||||
/* Find SCCs */
|
/* Find SCCs using Tarjan's algorithm. */
|
||||||
for (j = 0; j < ssa->vars_count; j++) {
|
for (j = 0; j < ssa->vars_count; j++) {
|
||||||
if (!ssa->vars[j].no_val && dfs[j] < 0) {
|
if (!ssa->vars[j].no_val && dfs[j] < 0) {
|
||||||
zend_ssa_check_scc_var(op_array, ssa, j, &index, dfs, root, &stack);
|
zend_ssa_check_scc_var(op_array, ssa, j, &index, dfs, root, &stack);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Revert SCC order */
|
/* Revert SCC order. This results in a topological order. */
|
||||||
for (j = 0; j < ssa->vars_count; j++) {
|
for (j = 0; j < ssa->vars_count; j++) {
|
||||||
if (ssa->vars[j].scc >= 0) {
|
if (ssa->vars[j].scc >= 0) {
|
||||||
ssa->vars[j].scc = ssa->sccs - (ssa->vars[j].scc + 1);
|
ssa->vars[j].scc = ssa->sccs - (ssa->vars[j].scc + 1);
|
||||||
|
@ -490,56 +518,41 @@ int zend_inference_calc_range(const zend_op_array *op_array, zend_ssa *ssa, int
|
||||||
zend_ssa_range_constraint *constraint = &p->constraint.range;
|
zend_ssa_range_constraint *constraint = &p->constraint.range;
|
||||||
if (constraint->negative) {
|
if (constraint->negative) {
|
||||||
if (ssa->var_info[p->sources[0]].has_range) {
|
if (ssa->var_info[p->sources[0]].has_range) {
|
||||||
tmp->underflow = ssa->var_info[p->sources[0]].range.underflow;
|
*tmp = ssa->var_info[p->sources[0]].range;
|
||||||
tmp->min = ssa->var_info[p->sources[0]].range.min;
|
|
||||||
tmp->max = ssa->var_info[p->sources[0]].range.max;
|
|
||||||
tmp->overflow = ssa->var_info[p->sources[0]].range.overflow;
|
|
||||||
} else if (narrowing) {
|
} else if (narrowing) {
|
||||||
tmp->underflow = 1;
|
tmp->underflow = 1;
|
||||||
tmp->min = ZEND_LONG_MIN;
|
tmp->min = ZEND_LONG_MIN;
|
||||||
tmp->max = ZEND_LONG_MAX;
|
tmp->max = ZEND_LONG_MAX;
|
||||||
tmp->overflow = 1;
|
tmp->overflow = 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef NEG_RANGE
|
#ifdef NEG_RANGE
|
||||||
if (constraint->min_ssa_var < 0 &&
|
if (constraint->min_ssa_var < 0 &&
|
||||||
constraint->min_ssa_var < 0 &&
|
constraint->max_ssa_var < 0 &&
|
||||||
ssa->var_info[p->ssa_var].has_range) {
|
ssa->var_info[p->ssa_var].has_range) {
|
||||||
#ifdef LOG_NEG_RANGE
|
LOG_NEG_RANGE("%s() #%d [%ld..%ld] -> [%ld..%ld]?\n",
|
||||||
fprintf(stderr, "%s() #%d [%ld..%ld] -> [%ld..%ld]?\n",
|
ZSTR_VAL(op_array->function_name),
|
||||||
op_array->function_name,
|
|
||||||
p->ssa_var,
|
p->ssa_var,
|
||||||
ssa->var_info[p->ssa_var].range.min,
|
ssa->var_info[p->ssa_var].range.min,
|
||||||
ssa->var_info[p->ssa_var].range.max,
|
ssa->var_info[p->ssa_var].range.max,
|
||||||
tmp->min,
|
tmp->min,
|
||||||
tmp->max);
|
tmp->max);
|
||||||
#endif
|
|
||||||
if (constraint->negative == NEG_USE_LT &&
|
if (constraint->negative == NEG_USE_LT &&
|
||||||
tmp->max >= constraint->range.min) {
|
tmp->max >= constraint->range.min) {
|
||||||
tmp->overflow = 0;
|
tmp->overflow = 0;
|
||||||
tmp->max = constraint->range.min - 1;
|
tmp->max = constraint->range.min - 1;
|
||||||
#ifdef LOG_NEG_RANGE
|
LOG_NEG_RANGE(" => [%ld..%ld]\n", tmp->min, tmp->max);
|
||||||
fprintf(stderr, " => [%ld..%ld]\n",
|
|
||||||
tmp->min,
|
|
||||||
tmp->max);
|
|
||||||
#endif
|
|
||||||
} else if (constraint->negative == NEG_USE_GT &&
|
} else if (constraint->negative == NEG_USE_GT &&
|
||||||
tmp->min <= constraint->range.max) {
|
tmp->min <= constraint->range.max) {
|
||||||
tmp->underflow = 0;
|
tmp->underflow = 0;
|
||||||
tmp->min = constraint->range.max + 1;
|
tmp->min = constraint->range.max + 1;
|
||||||
#ifdef LOG_NEG_RANGE
|
LOG_NEG_RANGE(" => [%ld..%ld]\n", tmp->min, tmp->max);
|
||||||
fprintf(stderr, " => [%ld..%ld]\n",
|
|
||||||
tmp->min,
|
|
||||||
tmp->max);
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
} else if (ssa->var_info[p->sources[0]].has_range) {
|
} else if (ssa->var_info[p->sources[0]].has_range) {
|
||||||
/* intersection */
|
/* intersection */
|
||||||
tmp->underflow = ssa->var_info[p->sources[0]].range.underflow;
|
*tmp = ssa->var_info[p->sources[0]].range;
|
||||||
tmp->min = ssa->var_info[p->sources[0]].range.min;
|
|
||||||
tmp->max = ssa->var_info[p->sources[0]].range.max;
|
|
||||||
tmp->overflow = ssa->var_info[p->sources[0]].range.overflow;
|
|
||||||
if (constraint->min_ssa_var < 0) {
|
if (constraint->min_ssa_var < 0) {
|
||||||
tmp->underflow = constraint->range.underflow && tmp->underflow;
|
tmp->underflow = constraint->range.underflow && tmp->underflow;
|
||||||
tmp->min = MAX(constraint->range.min, tmp->min);
|
tmp->min = MAX(constraint->range.min, tmp->min);
|
||||||
|
@ -1694,9 +1707,7 @@ void zend_inference_init_range(const zend_op_array *op_array, zend_ssa *ssa, int
|
||||||
ssa->var_info[var].range.min = min;
|
ssa->var_info[var].range.min = min;
|
||||||
ssa->var_info[var].range.max = max;
|
ssa->var_info[var].range.max = max;
|
||||||
ssa->var_info[var].range.overflow = overflow;
|
ssa->var_info[var].range.overflow = overflow;
|
||||||
#ifdef LOG_SSA_RANGE
|
LOG_SSA_RANGE(" change range (init SCC %2d) %2d [%s%ld..%ld%s]\n", ssa->vars[var].scc, var, (underflow?"-- ":""), min, max, (overflow?" ++":""));
|
||||||
fprintf(stderr, " change range (init SCC %2d) %2d [%s%ld..%ld%s]\n", ssa->vars[var].scc, var, (underflow?"-- ":""), min, max, (overflow?" ++":""));
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
int zend_inference_widening_meet(zend_ssa_var_info *var_info, zend_ssa_range *r)
|
int zend_inference_widening_meet(zend_ssa_var_info *var_info, zend_ssa_range *r)
|
||||||
|
@ -1733,9 +1744,7 @@ static int zend_ssa_range_widening(const zend_op_array *op_array, zend_ssa *ssa,
|
||||||
|
|
||||||
if (zend_inference_calc_range(op_array, ssa, var, 1, 0, &tmp)) {
|
if (zend_inference_calc_range(op_array, ssa, var, 1, 0, &tmp)) {
|
||||||
if (zend_inference_widening_meet(&ssa->var_info[var], &tmp)) {
|
if (zend_inference_widening_meet(&ssa->var_info[var], &tmp)) {
|
||||||
#ifdef LOG_SSA_RANGE
|
LOG_SSA_RANGE(" change range (widening SCC %2d) %2d [%s%ld..%ld%s]\n", scc, var, (tmp.underflow?"-- ":""), tmp.min, tmp.max, (tmp.overflow?" ++":""));
|
||||||
fprintf(stderr, " change range (widening SCC %2d) %2d [%s%ld..%ld%s]\n", scc, var, (tmp.underflow?"-- ":""), tmp.min, tmp.max, (tmp.overflow?" ++":""));
|
|
||||||
#endif
|
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1780,9 +1789,7 @@ static int zend_ssa_range_narrowing(const zend_op_array *op_array, zend_ssa *ssa
|
||||||
|
|
||||||
if (zend_inference_calc_range(op_array, ssa, var, 0, 1, &tmp)) {
|
if (zend_inference_calc_range(op_array, ssa, var, 0, 1, &tmp)) {
|
||||||
if (zend_inference_narrowing_meet(&ssa->var_info[var], &tmp)) {
|
if (zend_inference_narrowing_meet(&ssa->var_info[var], &tmp)) {
|
||||||
#ifdef LOG_SSA_RANGE
|
LOG_SSA_RANGE(" change range (narrowing SCC %2d) %2d [%s%ld..%ld%s]\n", scc, var, (tmp.underflow?"-- ":""), tmp.min, tmp.max, (tmp.overflow?" ++":""));
|
||||||
fprintf(stderr, " change range (narrowing SCC %2d) %2d [%s%ld..%ld%s]\n", scc, var, (tmp.underflow?"-- ":""), tmp.min, tmp.max, (tmp.overflow?" ++":""));
|
|
||||||
#endif
|
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1815,19 +1822,17 @@ static int zend_check_inner_cycles(const zend_op_array *op_array, zend_ssa *ssa,
|
||||||
static void zend_infer_ranges_warmup(const zend_op_array *op_array, zend_ssa *ssa, int *scc_var, int *next_scc_var, int scc)
|
static void zend_infer_ranges_warmup(const zend_op_array *op_array, zend_ssa *ssa, int *scc_var, int *next_scc_var, int scc)
|
||||||
{
|
{
|
||||||
int worklist_len = zend_bitset_len(ssa->vars_count);
|
int worklist_len = zend_bitset_len(ssa->vars_count);
|
||||||
zend_bitset worklist;
|
|
||||||
zend_bitset visited;
|
|
||||||
int j, n;
|
int j, n;
|
||||||
zend_ssa_range tmp;
|
zend_ssa_range tmp;
|
||||||
|
ALLOCA_FLAG(use_heap);
|
||||||
|
zend_bitset worklist = do_alloca(sizeof(zend_ulong) * worklist_len * 2, use_heap);
|
||||||
|
zend_bitset visited = worklist + worklist_len;
|
||||||
#ifdef NEG_RANGE
|
#ifdef NEG_RANGE
|
||||||
int has_inner_cycles = 0;
|
int has_inner_cycles = 0;
|
||||||
ALLOCA_FLAG(use_heap);
|
|
||||||
|
|
||||||
worklist = do_alloca(sizeof(zend_ulong) * worklist_len * 2, use_heap);
|
|
||||||
visited = worklist + worklist_len;
|
|
||||||
memset(worklist, 0, sizeof(zend_ulong) * worklist_len);
|
memset(worklist, 0, sizeof(zend_ulong) * worklist_len);
|
||||||
memset(visited, 0, sizeof(zend_ulong) * worklist_len);
|
memset(visited, 0, sizeof(zend_ulong) * worklist_len);
|
||||||
j= scc_var[scc];
|
j = scc_var[scc];
|
||||||
while (j >= 0) {
|
while (j >= 0) {
|
||||||
if (!zend_bitset_in(visited, j) &&
|
if (!zend_bitset_in(visited, j) &&
|
||||||
zend_check_inner_cycles(op_array, ssa, worklist, visited, j)) {
|
zend_check_inner_cycles(op_array, ssa, worklist, visited, j)) {
|
||||||
|
@ -1840,7 +1845,7 @@ static void zend_infer_ranges_warmup(const zend_op_array *op_array, zend_ssa *ss
|
||||||
|
|
||||||
memset(worklist, 0, sizeof(zend_ulong) * worklist_len);
|
memset(worklist, 0, sizeof(zend_ulong) * worklist_len);
|
||||||
|
|
||||||
for (n = 0; n < RANGE_WARMAP_PASSES; n++) {
|
for (n = 0; n < RANGE_WARMUP_PASSES; n++) {
|
||||||
j= scc_var[scc];
|
j= scc_var[scc];
|
||||||
while (j >= 0) {
|
while (j >= 0) {
|
||||||
if (ssa->vars[j].scc_entry) {
|
if (ssa->vars[j].scc_entry) {
|
||||||
|
@ -1869,9 +1874,7 @@ static void zend_infer_ranges_warmup(const zend_op_array *op_array, zend_ssa *ss
|
||||||
if (tmp.min == ssa->var_info[j].range.min &&
|
if (tmp.min == ssa->var_info[j].range.min &&
|
||||||
tmp.max == ssa->var_info[j].range.max) {
|
tmp.max == ssa->var_info[j].range.max) {
|
||||||
if (constraint->negative == NEG_INIT) {
|
if (constraint->negative == NEG_INIT) {
|
||||||
#ifdef LOG_NEG_RANGE
|
LOG_NEG_RANGE("#%d INVARIANT\n", j);
|
||||||
fprintf(stderr, "#%d INVARIANT\n", j);
|
|
||||||
#endif
|
|
||||||
constraint->negative = NEG_INVARIANT;
|
constraint->negative = NEG_INVARIANT;
|
||||||
}
|
}
|
||||||
} else if (tmp.min == ssa->var_info[j].range.min &&
|
} else if (tmp.min == ssa->var_info[j].range.min &&
|
||||||
|
@ -1879,15 +1882,11 @@ static void zend_infer_ranges_warmup(const zend_op_array *op_array, zend_ssa *ss
|
||||||
tmp.max < constraint->range.min) {
|
tmp.max < constraint->range.min) {
|
||||||
if (constraint->negative == NEG_INIT ||
|
if (constraint->negative == NEG_INIT ||
|
||||||
constraint->negative == NEG_INVARIANT) {
|
constraint->negative == NEG_INVARIANT) {
|
||||||
#ifdef LOG_NEG_RANGE
|
LOG_NEG_RANGE("#%d LT\n", j);
|
||||||
fprintf(stderr, "#%d LT\n", j);
|
|
||||||
#endif
|
|
||||||
constraint->negative = NEG_USE_LT;
|
constraint->negative = NEG_USE_LT;
|
||||||
//???NEG
|
//???NEG
|
||||||
} else if (constraint->negative == NEG_USE_GT) {
|
} else if (constraint->negative == NEG_USE_GT) {
|
||||||
#ifdef LOG_NEG_RANGE
|
LOG_NEG_RANGE("#%d UNKNOWN\n", j);
|
||||||
fprintf(stderr, "#%d UNKNOWN\n", j);
|
|
||||||
#endif
|
|
||||||
constraint->negative = NEG_UNKNOWN;
|
constraint->negative = NEG_UNKNOWN;
|
||||||
}
|
}
|
||||||
} else if (tmp.max == ssa->var_info[j].range.max &&
|
} else if (tmp.max == ssa->var_info[j].range.max &&
|
||||||
|
@ -1895,29 +1894,21 @@ static void zend_infer_ranges_warmup(const zend_op_array *op_array, zend_ssa *ss
|
||||||
tmp.min > constraint->range.max) {
|
tmp.min > constraint->range.max) {
|
||||||
if (constraint->negative == NEG_INIT ||
|
if (constraint->negative == NEG_INIT ||
|
||||||
constraint->negative == NEG_INVARIANT) {
|
constraint->negative == NEG_INVARIANT) {
|
||||||
#ifdef LOG_NEG_RANGE
|
LOG_NEG_RANGE("#%d GT\n", j);
|
||||||
fprintf(stderr, "#%d GT\n", j);
|
|
||||||
#endif
|
|
||||||
constraint->negative = NEG_USE_GT;
|
constraint->negative = NEG_USE_GT;
|
||||||
//???NEG
|
//???NEG
|
||||||
} else if (constraint->negative == NEG_USE_LT) {
|
} else if (constraint->negative == NEG_USE_LT) {
|
||||||
#ifdef LOG_NEG_RANGE
|
LOG_NEG_RANGE("#%d UNKNOWN\n", j);
|
||||||
fprintf(stderr, "#%d UNKNOWN\n", j);
|
|
||||||
#endif
|
|
||||||
constraint->negative = NEG_UNKNOWN;
|
constraint->negative = NEG_UNKNOWN;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
#ifdef LOG_NEG_RANGE
|
LOG_NEG_RANGE("#%d UNKNOWN\n", j);
|
||||||
fprintf(stderr, "#%d UNKNOWN\n", j);
|
|
||||||
#endif
|
|
||||||
constraint->negative = NEG_UNKNOWN;
|
constraint->negative = NEG_UNKNOWN;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
if (zend_inference_narrowing_meet(&ssa->var_info[j], &tmp)) {
|
if (zend_inference_narrowing_meet(&ssa->var_info[j], &tmp)) {
|
||||||
#ifdef LOG_SSA_RANGE
|
LOG_SSA_RANGE(" change range (warmup %2d SCC %2d) %2d [%s%ld..%ld%s]\n", n, scc, j, (tmp.underflow?"-- ":""), tmp.min, tmp.max, (tmp.overflow?" ++":""));
|
||||||
fprintf(stderr, " change range (warmup %d SCC %2d) %2d [%s%ld..%ld%s]\n", n, scc, j, (tmp.underflow?"-- ":""), tmp.min, tmp.max, (tmp.overflow?" ++":""));
|
|
||||||
#endif
|
|
||||||
zend_bitset_incl(visited, j);
|
zend_bitset_incl(visited, j);
|
||||||
FOR_EACH_VAR_USAGE(j, ADD_SCC_VAR_1);
|
FOR_EACH_VAR_USAGE(j, ADD_SCC_VAR_1);
|
||||||
}
|
}
|
||||||
|
@ -1945,9 +1936,7 @@ static int zend_infer_ranges(const zend_op_array *op_array, zend_ssa *ssa) /* {{
|
||||||
next_scc_var = (int*)(worklist + worklist_len);
|
next_scc_var = (int*)(worklist + worklist_len);
|
||||||
scc_var = next_scc_var + ssa->vars_count;
|
scc_var = next_scc_var + ssa->vars_count;
|
||||||
|
|
||||||
#ifdef LOG_SSA_RANGE
|
LOG_SSA_RANGE("Range Inference\n");
|
||||||
fprintf(stderr, "Range Inference\n");
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/* Create linked lists of SSA variables for each SCC */
|
/* Create linked lists of SSA variables for each SCC */
|
||||||
memset(scc_var, -1, sizeof(int) * ssa->sccs);
|
memset(scc_var, -1, sizeof(int) * ssa->sccs);
|
||||||
|
@ -1977,7 +1966,7 @@ static int zend_infer_ranges(const zend_op_array *op_array, zend_ssa *ssa) /* {{
|
||||||
j = next_scc_var[j];
|
j = next_scc_var[j];
|
||||||
} while (j >= 0);
|
} while (j >= 0);
|
||||||
|
|
||||||
#if RANGE_WARMAP_PASSES > 0
|
#if RANGE_WARMUP_PASSES > 0
|
||||||
zend_infer_ranges_warmup(op_array, ssa, scc_var, next_scc_var, scc);
|
zend_infer_ranges_warmup(op_array, ssa, scc_var, next_scc_var, scc);
|
||||||
j = scc_var[scc];
|
j = scc_var[scc];
|
||||||
do {
|
do {
|
||||||
|
|
8
ext/opcache/tests/block_pass_001.phpt
Normal file
8
ext/opcache/tests/block_pass_001.phpt
Normal file
|
@ -0,0 +1,8 @@
|
||||||
|
--TEST--
|
||||||
|
Block pass: Don't suppress undefined variable notice
|
||||||
|
--FILE--
|
||||||
|
<?php
|
||||||
|
(bool) (true ? $x : $y);
|
||||||
|
?>
|
||||||
|
--EXPECTF--
|
||||||
|
Notice: Undefined variable: x in %s on line %d
|
Loading…
Add table
Add a link
Reference in a new issue