Add type to VR_VARYING.
From-SVN: r274561
This commit is contained in:
parent
e3cfbeaf6b
commit
97ecc8d576
8 changed files with 221 additions and 89 deletions
|
@ -1,3 +1,51 @@
|
|||
2019-08-16 Aldy Hernandez <aldyh@redhat.com>
|
||||
|
||||
* gimple-ssa-evrp-analyze.c (record_ranges_from_phis): Skip PHIs
|
||||
for which we can't represent a range.
|
||||
* ipa-cp.c (ipcp_vr_lattice::set_to_bottom): Pass type to
|
||||
set_varying.
|
||||
* tree-ssa-threadedge.c (record_temporary_equivalences_from_phis):
|
||||
Set VR_UNDEFINED if type is not supported.
|
||||
* tree-ssanames.c (get_range_info): Pass type to set_varying.
|
||||
* tree-vrp.c (value_range_base::check): Assert that a varying has
|
||||
min/max set.
|
||||
(value_range_base::equal_p): Early bail for undefines.
|
||||
(value_range_base::set_varying): Accept a type.
|
||||
(value_range::set_varying): Same.
|
||||
(value_range_base::type): VARYING can have a type, while UNDEFINE
|
||||
is typeless.
|
||||
(value_range_base::dump): Print type for VARYING nodes.
|
||||
(value_range_base::set): Add type to VARYING.
|
||||
(extract_range_from_multiplicative_op): Pass type to set_varying.
|
||||
(extract_range_from_binary_expr): Same.
|
||||
(value_range_base::intersect_helper): Same.
|
||||
(value_range_base::union_helper): Same.
|
||||
(value_range_base::normalize_symbolics): Same.
|
||||
(determine_value_range_1): Same.
|
||||
* tree-vrp.h (class value_range_base): Add type to set_varying.
|
||||
Add prototype for dump(void).
|
||||
Add prototype for supports_type_p.
|
||||
(class value_range): Add type to set_varying.
|
||||
Add prototype for dump(void).
|
||||
* vr-values.c (set_value_range_to_truthvalue): Pass type to
|
||||
set_varying.
|
||||
(vr_values::get_lattice_entry): Set varying even if propagation
|
||||
finished.
|
||||
Pass type to set_varying.
|
||||
(vr_values::get_value_range): Remove vr_const_varying.
|
||||
Reallocate the lattice if needed.
|
||||
(vr_values::update_value_range): Pass type to set_varying.
|
||||
(vr_values::extract_range_for_var_from_comparison_expr): Same.
|
||||
(vr_values::extract_range_from_binary_expr): Same.
|
||||
(vr_values::extract_range_from_unary_expr): Same.
|
||||
(vr_values::extract_range_from_cond_expr): Same.
|
||||
(vr_values::check_for_binary_op_overflow): Same.
|
||||
(vr_values::extract_range_basic): Same.
|
||||
(vr_values::extract_range_from_assignment): Same.
|
||||
(vr_values::vr_values): Increase size of num_vr_values.
|
||||
(vr_values::extract_range_from_phi_node): Pass type to
|
||||
set_varying.
|
||||
|
||||
2019-08-15 H.J. Lu <hongjiu.lu@intel.com>
|
||||
|
||||
PR target/90878
|
||||
|
|
|
@ -254,13 +254,18 @@ evrp_range_analyzer::record_ranges_from_phis (basic_block bb)
|
|||
if (virtual_operand_p (lhs))
|
||||
continue;
|
||||
|
||||
/* Skips floats and other things we can't represent in a
|
||||
range. */
|
||||
if (!value_range_base::supports_type_p (TREE_TYPE (lhs)))
|
||||
continue;
|
||||
|
||||
value_range vr_result;
|
||||
bool interesting = stmt_interesting_for_vrp (phi);
|
||||
if (!has_unvisited_preds && interesting)
|
||||
vr_values->extract_range_from_phi_node (phi, &vr_result);
|
||||
else
|
||||
{
|
||||
vr_result.set_varying ();
|
||||
vr_result.set_varying (TREE_TYPE (lhs));
|
||||
/* When we have an unvisited executable predecessor we can't
|
||||
use PHI arg ranges which may be still UNDEFINED but have
|
||||
to use VARYING for them. But we can still resort to
|
||||
|
|
|
@ -977,7 +977,12 @@ ipcp_vr_lattice::set_to_bottom ()
|
|||
{
|
||||
if (m_vr.varying_p ())
|
||||
return false;
|
||||
m_vr.set_varying ();
|
||||
/* ?? We create all sorts of VARYING ranges for floats, structures,
|
||||
and other types which we cannot handle as ranges. We should
|
||||
probably avoid handling them throughout the pass, but it's easier
|
||||
to create a sensible VARYING here and let the lattice
|
||||
propagate. */
|
||||
m_vr.set_varying (integer_type_node);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
|
@ -183,7 +183,7 @@ record_temporary_equivalences_from_phis (edge e,
|
|||
else if (TREE_CODE (src) == INTEGER_CST)
|
||||
new_vr->set (src);
|
||||
else
|
||||
new_vr->set_varying ();
|
||||
new_vr->set_varying (TREE_TYPE (src));
|
||||
|
||||
/* This is a temporary range for DST, so push it. */
|
||||
evrp_range_analyzer->push_value_range (dst, new_vr);
|
||||
|
|
|
@ -440,14 +440,16 @@ get_range_info (const_tree name, value_range_base &vr)
|
|||
wide_int wmin, wmax;
|
||||
enum value_range_kind kind = get_range_info (name, &wmin, &wmax);
|
||||
|
||||
if (kind == VR_VARYING || kind == VR_UNDEFINED)
|
||||
min = max = NULL;
|
||||
if (kind == VR_VARYING)
|
||||
vr.set_varying (TREE_TYPE (name));
|
||||
else if (kind == VR_UNDEFINED)
|
||||
vr.set_undefined ();
|
||||
else
|
||||
{
|
||||
min = wide_int_to_tree (TREE_TYPE (name), wmin);
|
||||
max = wide_int_to_tree (TREE_TYPE (name), wmax);
|
||||
vr.set (kind, min, max);
|
||||
}
|
||||
vr.set (kind, min, max);
|
||||
return kind;
|
||||
}
|
||||
|
||||
|
|
142
gcc/tree-vrp.c
142
gcc/tree-vrp.c
|
@ -186,9 +186,11 @@ value_range_base::check ()
|
|||
break;
|
||||
}
|
||||
case VR_UNDEFINED:
|
||||
case VR_VARYING:
|
||||
gcc_assert (!min () && !max ());
|
||||
break;
|
||||
case VR_VARYING:
|
||||
gcc_assert (m_min && m_max);
|
||||
break;
|
||||
default:
|
||||
gcc_unreachable ();
|
||||
}
|
||||
|
@ -214,6 +216,10 @@ value_range::check ()
|
|||
bool
|
||||
value_range_base::equal_p (const value_range_base &other) const
|
||||
{
|
||||
/* Ignore types for undefined. All undefines are equal. */
|
||||
if (undefined_p ())
|
||||
return m_kind == other.m_kind;
|
||||
|
||||
return (m_kind == other.m_kind
|
||||
&& vrp_operand_equal_p (m_min, other.m_min)
|
||||
&& vrp_operand_equal_p (m_max, other.m_max));
|
||||
|
@ -269,16 +275,24 @@ value_range::set_undefined ()
|
|||
}
|
||||
|
||||
void
|
||||
value_range_base::set_varying ()
|
||||
value_range_base::set_varying (tree type)
|
||||
{
|
||||
m_kind = VR_VARYING;
|
||||
m_min = m_max = NULL;
|
||||
if (supports_type_p (type))
|
||||
{
|
||||
m_min = vrp_val_min (type, true);
|
||||
m_max = vrp_val_max (type, true);
|
||||
}
|
||||
else
|
||||
/* We can't do anything range-wise with these types. */
|
||||
m_min = m_max = error_mark_node;
|
||||
}
|
||||
|
||||
void
|
||||
value_range::set_varying ()
|
||||
value_range::set_varying (tree type)
|
||||
{
|
||||
set (VR_VARYING, NULL, NULL, NULL);
|
||||
value_range_base::set_varying (type);
|
||||
equiv_clear ();
|
||||
}
|
||||
|
||||
/* Return TRUE if it is possible that range contains VAL. */
|
||||
|
@ -355,9 +369,7 @@ value_range_base::singleton_p (tree *result) const
|
|||
tree
|
||||
value_range_base::type () const
|
||||
{
|
||||
/* Types are only valid for VR_RANGE and VR_ANTI_RANGE, which are
|
||||
known to have non-zero min/max. */
|
||||
gcc_assert (min ());
|
||||
gcc_assert (m_min || undefined_p ());
|
||||
return TREE_TYPE (min ());
|
||||
}
|
||||
|
||||
|
@ -395,11 +407,20 @@ value_range_base::dump (FILE *file) const
|
|||
fprintf (file, "]");
|
||||
}
|
||||
else if (varying_p ())
|
||||
fprintf (file, "VARYING");
|
||||
{
|
||||
print_generic_expr (file, type ());
|
||||
fprintf (file, " VARYING");
|
||||
}
|
||||
else
|
||||
gcc_unreachable ();
|
||||
}
|
||||
|
||||
void
|
||||
value_range_base::dump () const
|
||||
{
|
||||
dump (stderr);
|
||||
}
|
||||
|
||||
void
|
||||
value_range::dump (FILE *file) const
|
||||
{
|
||||
|
@ -423,6 +444,12 @@ value_range::dump (FILE *file) const
|
|||
}
|
||||
}
|
||||
|
||||
void
|
||||
value_range::dump () const
|
||||
{
|
||||
dump (stderr);
|
||||
}
|
||||
|
||||
void
|
||||
dump_value_range (FILE *file, const value_range *vr)
|
||||
{
|
||||
|
@ -658,7 +685,14 @@ value_range_base::set (enum value_range_kind kind, tree min, tree max)
|
|||
}
|
||||
else if (kind == VR_VARYING)
|
||||
{
|
||||
set_varying ();
|
||||
gcc_assert (TREE_TYPE (min) == TREE_TYPE (max));
|
||||
tree typ = TREE_TYPE (min);
|
||||
if (supports_type_p (typ))
|
||||
{
|
||||
gcc_assert (vrp_val_min (typ, true));
|
||||
gcc_assert (vrp_val_max (typ, true));
|
||||
}
|
||||
set_varying (typ);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -683,7 +717,7 @@ value_range_base::set (enum value_range_kind kind, tree min, tree max)
|
|||
for VR_ANTI_RANGE empty range, so drop to varying as well. */
|
||||
if (TYPE_PRECISION (TREE_TYPE (min)) == 1)
|
||||
{
|
||||
set_varying ();
|
||||
set_varying (TREE_TYPE (min));
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -697,7 +731,7 @@ value_range_base::set (enum value_range_kind kind, tree min, tree max)
|
|||
to varying in this case. */
|
||||
if (tree_int_cst_lt (max, min))
|
||||
{
|
||||
set_varying ();
|
||||
set_varying (TREE_TYPE (min));
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -720,7 +754,7 @@ value_range_base::set (enum value_range_kind kind, tree min, tree max)
|
|||
{
|
||||
/* We cannot deal with empty ranges, drop to varying.
|
||||
??? This could be VR_UNDEFINED instead. */
|
||||
set_varying ();
|
||||
set_varying (type);
|
||||
return;
|
||||
}
|
||||
else if (TYPE_PRECISION (TREE_TYPE (min)) == 1
|
||||
|
@ -767,7 +801,7 @@ value_range_base::set (enum value_range_kind kind, tree min, tree max)
|
|||
&& wi::eq_p (wi::to_wide (max), wi::max_value (prec, sign)))
|
||||
{
|
||||
if (kind == VR_RANGE)
|
||||
set_varying ();
|
||||
set_varying (type);
|
||||
else if (kind == VR_ANTI_RANGE)
|
||||
set_undefined ();
|
||||
else
|
||||
|
@ -1297,7 +1331,7 @@ extract_range_from_multiplicative_op (value_range_base *vr,
|
|||
|| code == LSHIFT_EXPR);
|
||||
if (!range_int_cst_p (vr1))
|
||||
{
|
||||
vr->set_varying ();
|
||||
vr->set_varying (type);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -1332,7 +1366,7 @@ extract_range_from_multiplicative_op (value_range_base *vr,
|
|||
vr->set (VR_RANGE, wide_int_to_tree (type, res_lb),
|
||||
wide_int_to_tree (type, res_ub));
|
||||
else
|
||||
vr->set_varying ();
|
||||
vr->set_varying (type);
|
||||
}
|
||||
|
||||
/* If BOUND will include a symbolic bound, adjust it accordingly,
|
||||
|
@ -1541,7 +1575,7 @@ extract_range_from_binary_expr (value_range_base *vr,
|
|||
if (!INTEGRAL_TYPE_P (expr_type)
|
||||
&& !POINTER_TYPE_P (expr_type))
|
||||
{
|
||||
vr->set_varying ();
|
||||
vr->set_varying (expr_type);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -1565,7 +1599,7 @@ extract_range_from_binary_expr (value_range_base *vr,
|
|||
&& code != BIT_IOR_EXPR
|
||||
&& code != BIT_XOR_EXPR)
|
||||
{
|
||||
vr->set_varying ();
|
||||
vr->set_varying (expr_type);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -1580,9 +1614,9 @@ extract_range_from_binary_expr (value_range_base *vr,
|
|||
have UNDEFINED result for all or some value-ranges of the not UNDEFINED
|
||||
operand. */
|
||||
else if (vr0.undefined_p ())
|
||||
vr0.set_varying ();
|
||||
vr0.set_varying (expr_type);
|
||||
else if (vr1.undefined_p ())
|
||||
vr1.set_varying ();
|
||||
vr1.set_varying (expr_type);
|
||||
|
||||
/* We get imprecise results from ranges_from_anti_range when
|
||||
code is EXACT_DIV_EXPR. We could mask out bits in the resulting
|
||||
|
@ -1654,7 +1688,7 @@ extract_range_from_binary_expr (value_range_base *vr,
|
|||
|| vr0.symbolic_p ()
|
||||
|| vr1.symbolic_p ()))
|
||||
{
|
||||
vr->set_varying ();
|
||||
vr->set_varying (expr_type);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -1672,7 +1706,7 @@ extract_range_from_binary_expr (value_range_base *vr,
|
|||
else if (vr0.zero_p () && vr1.zero_p ())
|
||||
vr->set_zero (expr_type);
|
||||
else
|
||||
vr->set_varying ();
|
||||
vr->set_varying (expr_type);
|
||||
}
|
||||
else if (code == POINTER_PLUS_EXPR)
|
||||
{
|
||||
|
@ -1701,7 +1735,7 @@ extract_range_from_binary_expr (value_range_base *vr,
|
|||
else if (vr0.zero_p () && vr1.zero_p ())
|
||||
vr->set_zero (expr_type);
|
||||
else
|
||||
vr->set_varying ();
|
||||
vr->set_varying (expr_type);
|
||||
}
|
||||
else if (code == BIT_AND_EXPR)
|
||||
{
|
||||
|
@ -1712,10 +1746,10 @@ extract_range_from_binary_expr (value_range_base *vr,
|
|||
else if (vr0.zero_p () || vr1.zero_p ())
|
||||
vr->set_zero (expr_type);
|
||||
else
|
||||
vr->set_varying ();
|
||||
vr->set_varying (expr_type);
|
||||
}
|
||||
else
|
||||
vr->set_varying ();
|
||||
vr->set_varying (expr_type);
|
||||
|
||||
return;
|
||||
}
|
||||
|
@ -1793,7 +1827,7 @@ extract_range_from_binary_expr (value_range_base *vr,
|
|||
if (((bool)min_ovf && sym_min_op0 != sym_min_op1)
|
||||
|| ((bool)max_ovf && sym_max_op0 != sym_max_op1))
|
||||
{
|
||||
vr->set_varying ();
|
||||
vr->set_varying (expr_type);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -1804,7 +1838,7 @@ extract_range_from_binary_expr (value_range_base *vr,
|
|||
wmin, wmax, min_ovf, max_ovf);
|
||||
if (type == VR_VARYING)
|
||||
{
|
||||
vr->set_varying ();
|
||||
vr->set_varying (expr_type);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -1830,7 +1864,7 @@ extract_range_from_binary_expr (value_range_base *vr,
|
|||
a single range or anti-range as the above is
|
||||
[-INF+1, +INF(OVF)] intersected with ~[5, 5]
|
||||
but one could use a scheme similar to equivalences for this. */
|
||||
vr->set_varying ();
|
||||
vr->set_varying (expr_type);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
@ -1847,7 +1881,7 @@ extract_range_from_binary_expr (value_range_base *vr,
|
|||
vr->set (VR_RANGE, wide_int_to_tree (expr_type, wmin),
|
||||
wide_int_to_tree (expr_type, wmax));
|
||||
else
|
||||
vr->set_varying ();
|
||||
vr->set_varying (expr_type);
|
||||
return;
|
||||
}
|
||||
else if (code == MULT_EXPR)
|
||||
|
@ -1855,7 +1889,7 @@ extract_range_from_binary_expr (value_range_base *vr,
|
|||
if (!range_int_cst_p (&vr0)
|
||||
|| !range_int_cst_p (&vr1))
|
||||
{
|
||||
vr->set_varying ();
|
||||
vr->set_varying (expr_type);
|
||||
return;
|
||||
}
|
||||
extract_range_from_multiplicative_op (vr, code, expr_type, &vr0, &vr1);
|
||||
|
@ -1895,7 +1929,7 @@ extract_range_from_binary_expr (value_range_base *vr,
|
|||
}
|
||||
}
|
||||
}
|
||||
vr->set_varying ();
|
||||
vr->set_varying (expr_type);
|
||||
return;
|
||||
}
|
||||
else if (code == TRUNC_DIV_EXPR
|
||||
|
@ -1932,7 +1966,7 @@ extract_range_from_binary_expr (value_range_base *vr,
|
|||
TYPE_OVERFLOW_UNDEFINED (expr_type),
|
||||
extra_range_p, extra_min, extra_max))
|
||||
{
|
||||
vr->set_varying ();
|
||||
vr->set_varying (expr_type);
|
||||
return;
|
||||
}
|
||||
vr->set (VR_RANGE, wide_int_to_tree (expr_type, wmin),
|
||||
|
@ -1991,7 +2025,7 @@ extract_range_from_binary_expr (value_range_base *vr,
|
|||
vr->set (VR_RANGE, min, max);
|
||||
}
|
||||
else
|
||||
vr->set_varying ();
|
||||
vr->set_varying (expr_type);
|
||||
return;
|
||||
}
|
||||
else if (code == BIT_IOR_EXPR)
|
||||
|
@ -2009,7 +2043,7 @@ extract_range_from_binary_expr (value_range_base *vr,
|
|||
vr->set (VR_RANGE, min, max);
|
||||
}
|
||||
else
|
||||
vr->set_varying ();
|
||||
vr->set_varying (expr_type);
|
||||
return;
|
||||
}
|
||||
else if (code == BIT_XOR_EXPR)
|
||||
|
@ -2025,7 +2059,7 @@ extract_range_from_binary_expr (value_range_base *vr,
|
|||
vr->set (VR_RANGE, min, max);
|
||||
}
|
||||
else
|
||||
vr->set_varying ();
|
||||
vr->set_varying (expr_type);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
@ -2039,7 +2073,7 @@ extract_range_from_binary_expr (value_range_base *vr,
|
|||
|| max == NULL_TREE
|
||||
|| TREE_OVERFLOW_P (max))
|
||||
{
|
||||
vr->set_varying ();
|
||||
vr->set_varying (expr_type);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -2048,7 +2082,7 @@ extract_range_from_binary_expr (value_range_base *vr,
|
|||
Note that we do accept [-INF, -INF] and [+INF, +INF]. */
|
||||
if (vrp_val_is_min (min) && vrp_val_is_max (max))
|
||||
{
|
||||
vr->set_varying ();
|
||||
vr->set_varying (expr_type);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -2058,7 +2092,7 @@ extract_range_from_binary_expr (value_range_base *vr,
|
|||
/* If the new range has its limits swapped around (MIN > MAX),
|
||||
then the operation caused one of them to wrap around, mark
|
||||
the new range VARYING. */
|
||||
vr->set_varying ();
|
||||
vr->set_varying (expr_type);
|
||||
}
|
||||
else
|
||||
vr->set (type, min, max);
|
||||
|
@ -2084,7 +2118,7 @@ extract_range_from_unary_expr (value_range_base *vr,
|
|||
|| !(INTEGRAL_TYPE_P (type)
|
||||
|| POINTER_TYPE_P (type)))
|
||||
{
|
||||
vr->set_varying ();
|
||||
vr->set_varying (type);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -2156,7 +2190,7 @@ extract_range_from_unary_expr (value_range_base *vr,
|
|||
else if (vr0.zero_p ())
|
||||
vr->set_zero (type);
|
||||
else
|
||||
vr->set_varying ();
|
||||
vr->set_varying (type);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -2190,7 +2224,7 @@ extract_range_from_unary_expr (value_range_base *vr,
|
|||
vr->set (VR_RANGE, min, max);
|
||||
}
|
||||
else
|
||||
vr->set_varying ();
|
||||
vr->set_varying (outer_type);
|
||||
return;
|
||||
}
|
||||
else if (code == ABS_EXPR)
|
||||
|
@ -2203,7 +2237,7 @@ extract_range_from_unary_expr (value_range_base *vr,
|
|||
vr->set (VR_RANGE, wide_int_to_tree (type, wmin),
|
||||
wide_int_to_tree (type, wmax));
|
||||
else
|
||||
vr->set_varying ();
|
||||
vr->set_varying (type);
|
||||
return;
|
||||
}
|
||||
else if (code == ABSU_EXPR)
|
||||
|
@ -2219,7 +2253,7 @@ extract_range_from_unary_expr (value_range_base *vr,
|
|||
}
|
||||
|
||||
/* For unhandled operations fall back to varying. */
|
||||
vr->set_varying ();
|
||||
vr->set_varying (type);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -6100,7 +6134,12 @@ value_range_base::intersect_helper (const value_range_base *vr0,
|
|||
VR_RANGE can still be a VR_RANGE. Work on a temporary so we can
|
||||
fall back to vr0 when this turns things to varying. */
|
||||
value_range_base tem;
|
||||
tem.set (vr0type, vr0min, vr0max);
|
||||
if (vr0type == VR_UNDEFINED)
|
||||
tem.set_undefined ();
|
||||
else if (vr0type == VR_VARYING)
|
||||
tem.set_varying (vr0->type ());
|
||||
else
|
||||
tem.set (vr0type, vr0min, vr0max);
|
||||
/* If that failed, use the saved original VR0. */
|
||||
if (tem.varying_p ())
|
||||
return *vr0;
|
||||
|
@ -6205,7 +6244,12 @@ value_range_base::union_helper (const value_range_base *vr0,
|
|||
|
||||
/* Work on a temporary so we can still use vr0 when union returns varying. */
|
||||
value_range_base tem;
|
||||
tem.set (vr0type, vr0min, vr0max);
|
||||
if (vr0type == VR_UNDEFINED)
|
||||
tem.set_undefined ();
|
||||
else if (vr0type == VR_VARYING)
|
||||
tem.set_varying (vr0->type ());
|
||||
else
|
||||
tem.set (vr0type, vr0min, vr0max);
|
||||
|
||||
/* Failed to find an efficient meet. Before giving up and setting
|
||||
the result to VARYING, see if we can at least derive a useful
|
||||
|
@ -6302,7 +6346,7 @@ value_range_base::normalize_symbolics () const
|
|||
if (min_symbolic && max_symbolic)
|
||||
{
|
||||
value_range_base var;
|
||||
var.set_varying ();
|
||||
var.set_varying (ttype);
|
||||
return var;
|
||||
}
|
||||
if (kind () == VR_RANGE)
|
||||
|
@ -6323,7 +6367,7 @@ value_range_base::normalize_symbolics () const
|
|||
return value_range_base (VR_RANGE, n, vrp_val_max (ttype));
|
||||
}
|
||||
value_range_base var;
|
||||
var.set_varying ();
|
||||
var.set_varying (ttype);
|
||||
return var;
|
||||
}
|
||||
// ~[NUM, SYM] -> [-MIN, NUM - 1]
|
||||
|
@ -6333,7 +6377,7 @@ value_range_base::normalize_symbolics () const
|
|||
return value_range_base (VR_RANGE, vrp_val_min (ttype), n);
|
||||
}
|
||||
value_range_base var;
|
||||
var.set_varying ();
|
||||
var.set_varying (ttype);
|
||||
return var;
|
||||
}
|
||||
|
||||
|
@ -7010,7 +7054,7 @@ determine_value_range_1 (value_range_base *vr, tree expr)
|
|||
vr->set (kind, wide_int_to_tree (TREE_TYPE (expr), min),
|
||||
wide_int_to_tree (TREE_TYPE (expr), max));
|
||||
else
|
||||
vr->set_varying ();
|
||||
vr->set_varying (TREE_TYPE (expr));
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -58,7 +58,7 @@ public:
|
|||
bool constant_p () const;
|
||||
bool undefined_p () const;
|
||||
bool varying_p () const;
|
||||
void set_varying ();
|
||||
void set_varying (tree type);
|
||||
void set_undefined ();
|
||||
|
||||
void union_ (const value_range_base *);
|
||||
|
@ -75,7 +75,9 @@ public:
|
|||
bool nonzero_p () const;
|
||||
bool singleton_p (tree *result = NULL) const;
|
||||
void dump (FILE *) const;
|
||||
void dump () const;
|
||||
|
||||
static bool supports_type_p (tree);
|
||||
value_range_base normalize_symbolics () const;
|
||||
|
||||
protected:
|
||||
|
@ -135,7 +137,7 @@ class GTY((user)) value_range : public value_range_base
|
|||
|
||||
/* Types of value ranges. */
|
||||
void set_undefined ();
|
||||
void set_varying ();
|
||||
void set_varying (tree);
|
||||
|
||||
/* Equivalence bitmap methods. */
|
||||
bitmap equiv () const;
|
||||
|
@ -145,6 +147,7 @@ class GTY((user)) value_range : public value_range_base
|
|||
/* Misc methods. */
|
||||
void deep_copy (const value_range *);
|
||||
void dump (FILE *) const;
|
||||
void dump () const;
|
||||
|
||||
private:
|
||||
/* Deep-copies bitmap argument. */
|
||||
|
@ -254,6 +257,17 @@ struct assert_info
|
|||
tree expr;
|
||||
};
|
||||
|
||||
// Return true if TYPE is a valid type for value_range to operate on.
|
||||
// Otherwise return FALSE.
|
||||
|
||||
inline bool
|
||||
value_range_base::supports_type_p (tree type)
|
||||
{
|
||||
if (type && (INTEGRAL_TYPE_P (type) || POINTER_TYPE_P (type)))
|
||||
return type;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
extern void register_edge_assert_for (tree, edge, enum tree_code,
|
||||
tree, tree, vec<assert_info> &);
|
||||
extern bool stmt_interesting_for_vrp (gimple *);
|
||||
|
|
|
@ -64,7 +64,7 @@ static inline void
|
|||
set_value_range_to_truthvalue (value_range *vr, tree type)
|
||||
{
|
||||
if (TYPE_PRECISION (type) == 1)
|
||||
vr->set_varying ();
|
||||
vr->set_varying (type);
|
||||
else
|
||||
vr->update (VR_RANGE, build_int_cst (type, 0), build_int_cst (type, 1));
|
||||
}
|
||||
|
@ -89,12 +89,16 @@ vr_values::get_lattice_entry (const_tree var)
|
|||
if (vr)
|
||||
return vr;
|
||||
|
||||
/* After propagation finished do not allocate new value-ranges. */
|
||||
if (values_propagated)
|
||||
return NULL;
|
||||
|
||||
/* Create a default value range. */
|
||||
vr_value[ver] = vr = vrp_value_range_pool.allocate ();
|
||||
|
||||
/* After propagation finished return varying. */
|
||||
if (values_propagated)
|
||||
{
|
||||
vr->set_varying (TREE_TYPE (var));
|
||||
return vr;
|
||||
}
|
||||
|
||||
vr->set_undefined ();
|
||||
|
||||
/* If VAR is a default definition of a parameter, the variable can
|
||||
|
@ -118,10 +122,10 @@ vr_values::get_lattice_entry (const_tree var)
|
|||
{
|
||||
get_range_info (var, *vr);
|
||||
if (vr->undefined_p ())
|
||||
vr->set_varying ();
|
||||
vr->set_varying (TREE_TYPE (sym));
|
||||
}
|
||||
else
|
||||
vr->set_varying ();
|
||||
vr->set_varying (TREE_TYPE (sym));
|
||||
}
|
||||
else if (TREE_CODE (sym) == RESULT_DECL
|
||||
&& DECL_BY_REFERENCE (sym))
|
||||
|
@ -142,15 +146,25 @@ vr_values::get_lattice_entry (const_tree var)
|
|||
const value_range *
|
||||
vr_values::get_value_range (const_tree var)
|
||||
{
|
||||
static const value_range vr_const_varying (VR_VARYING, NULL, NULL);
|
||||
|
||||
/* If we have no recorded ranges, then return NULL. */
|
||||
if (!vr_value)
|
||||
return NULL;
|
||||
|
||||
value_range *vr = get_lattice_entry (var);
|
||||
|
||||
/* Reallocate the lattice if needed. */
|
||||
if (!vr)
|
||||
return &vr_const_varying;
|
||||
{
|
||||
unsigned int old_sz = num_vr_values;
|
||||
num_vr_values = num_ssa_names + num_ssa_names / 10;
|
||||
vr_value = XRESIZEVEC (value_range *, vr_value, num_vr_values);
|
||||
for ( ; old_sz < num_vr_values; old_sz++)
|
||||
vr_value [old_sz] = NULL;
|
||||
|
||||
/* Now that the lattice has been resized, we should never fail. */
|
||||
vr = get_lattice_entry (var);
|
||||
gcc_assert (vr);
|
||||
}
|
||||
|
||||
return vr;
|
||||
}
|
||||
|
@ -162,7 +176,7 @@ vr_values::set_def_to_varying (const_tree def)
|
|||
{
|
||||
value_range *vr = get_lattice_entry (def);
|
||||
if (vr)
|
||||
vr->set_varying ();
|
||||
vr->set_varying (TREE_TYPE (def));
|
||||
}
|
||||
|
||||
/* Set value-ranges of all SSA names defined by STMT to varying. */
|
||||
|
@ -220,13 +234,13 @@ vr_values::update_value_range (const_tree var, value_range *new_vr)
|
|||
called, if we are anyway, keep it VARYING. */
|
||||
if (old_vr->varying_p ())
|
||||
{
|
||||
new_vr->set_varying ();
|
||||
new_vr->set_varying (new_vr->type ());
|
||||
is_new = false;
|
||||
}
|
||||
else if (new_vr->undefined_p ())
|
||||
{
|
||||
old_vr->set_varying ();
|
||||
new_vr->set_varying ();
|
||||
old_vr->set_varying (TREE_TYPE (var));
|
||||
new_vr->set_varying (TREE_TYPE (var));
|
||||
return true;
|
||||
}
|
||||
else
|
||||
|
@ -457,7 +471,7 @@ vr_values::extract_range_for_var_from_comparison_expr (tree var,
|
|||
if ((POINTER_TYPE_P (type) && cond_code != NE_EXPR && cond_code != EQ_EXPR)
|
||||
|| limit == var)
|
||||
{
|
||||
vr_p->set_varying ();
|
||||
vr_p->set_varying (type);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -617,7 +631,7 @@ vr_values::extract_range_for_var_from_comparison_expr (tree var,
|
|||
all should be optimized away above us. */
|
||||
if (cond_code == LT_EXPR
|
||||
&& compare_values (max, min) == 0)
|
||||
vr_p->set_varying ();
|
||||
vr_p->set_varying (TREE_TYPE (min));
|
||||
else
|
||||
{
|
||||
/* For LT_EXPR, we create the range [MIN, MAX - 1]. */
|
||||
|
@ -657,7 +671,7 @@ vr_values::extract_range_for_var_from_comparison_expr (tree var,
|
|||
all should be optimized away above us. */
|
||||
if (cond_code == GT_EXPR
|
||||
&& compare_values (min, max) == 0)
|
||||
vr_p->set_varying ();
|
||||
vr_p->set_varying (TREE_TYPE (min));
|
||||
else
|
||||
{
|
||||
/* For GT_EXPR, we create the range [MIN + 1, MAX]. */
|
||||
|
@ -765,14 +779,14 @@ vr_values::extract_range_from_binary_expr (value_range *vr,
|
|||
else if (is_gimple_min_invariant (op0))
|
||||
vr0.set (op0);
|
||||
else
|
||||
vr0.set_varying ();
|
||||
vr0.set_varying (TREE_TYPE (op0));
|
||||
|
||||
if (TREE_CODE (op1) == SSA_NAME)
|
||||
vr1 = *(get_value_range (op1));
|
||||
else if (is_gimple_min_invariant (op1))
|
||||
vr1.set (op1);
|
||||
else
|
||||
vr1.set_varying ();
|
||||
vr1.set_varying (TREE_TYPE (op1));
|
||||
|
||||
/* If one argument is varying, we can sometimes still deduce a
|
||||
range for the output: any + [3, +INF] is in [MIN+3, +INF]. */
|
||||
|
@ -913,7 +927,7 @@ vr_values::extract_range_from_unary_expr (value_range *vr, enum tree_code code,
|
|||
else if (is_gimple_min_invariant (op0))
|
||||
vr0.set (op0);
|
||||
else
|
||||
vr0.set_varying ();
|
||||
vr0.set_varying (type);
|
||||
|
||||
::extract_range_from_unary_expr (vr, code, type, &vr0, TREE_TYPE (op0));
|
||||
}
|
||||
|
@ -935,7 +949,7 @@ vr_values::extract_range_from_cond_expr (value_range *vr, gassign *stmt)
|
|||
else if (is_gimple_min_invariant (op0))
|
||||
tem0.set (op0);
|
||||
else
|
||||
tem0.set_varying ();
|
||||
tem0.set_varying (TREE_TYPE (op0));
|
||||
|
||||
tree op1 = gimple_assign_rhs3 (stmt);
|
||||
value_range tem1;
|
||||
|
@ -945,7 +959,7 @@ vr_values::extract_range_from_cond_expr (value_range *vr, gassign *stmt)
|
|||
else if (is_gimple_min_invariant (op1))
|
||||
tem1.set (op1);
|
||||
else
|
||||
tem1.set_varying ();
|
||||
tem1.set_varying (TREE_TYPE (op1));
|
||||
|
||||
/* The resulting value range is the union of the operand ranges */
|
||||
vr->deep_copy (vr0);
|
||||
|
@ -997,14 +1011,14 @@ vr_values::check_for_binary_op_overflow (enum tree_code subcode, tree type,
|
|||
else if (TREE_CODE (op0) == INTEGER_CST)
|
||||
vr0.set (op0);
|
||||
else
|
||||
vr0.set_varying ();
|
||||
vr0.set_varying (TREE_TYPE (op0));
|
||||
|
||||
if (TREE_CODE (op1) == SSA_NAME)
|
||||
vr1 = *get_value_range (op1);
|
||||
else if (TREE_CODE (op1) == INTEGER_CST)
|
||||
vr1.set (op1);
|
||||
else
|
||||
vr1.set_varying ();
|
||||
vr1.set_varying (TREE_TYPE (op1));
|
||||
|
||||
tree vr0min = vr0.min (), vr0max = vr0.max ();
|
||||
tree vr1min = vr1.min (), vr1max = vr1.max ();
|
||||
|
@ -1332,7 +1346,7 @@ vr_values::extract_range_basic (value_range *vr, gimple *stmt)
|
|||
if (vr->kind () == VR_RANGE
|
||||
&& (vr->min () == vr->max ()
|
||||
|| operand_equal_p (vr->min (), vr->max (), 0)))
|
||||
vr->set_varying ();
|
||||
vr->set_varying (vr->type ());
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
@ -1388,7 +1402,7 @@ vr_values::extract_range_basic (value_range *vr, gimple *stmt)
|
|||
vr->set (build_int_cst (type, ovf));
|
||||
else if (TYPE_PRECISION (type) == 1
|
||||
&& !TYPE_UNSIGNED (type))
|
||||
vr->set_varying ();
|
||||
vr->set_varying (type);
|
||||
else
|
||||
vr->set (VR_RANGE, build_int_cst (type, 0),
|
||||
build_int_cst (type, 1));
|
||||
|
@ -1433,7 +1447,7 @@ vr_values::extract_range_basic (value_range *vr, gimple *stmt)
|
|||
vr->equiv_clear ();
|
||||
}
|
||||
else
|
||||
vr->set_varying ();
|
||||
vr->set_varying (type);
|
||||
}
|
||||
|
||||
|
||||
|
@ -1469,7 +1483,7 @@ vr_values::extract_range_from_assignment (value_range *vr, gassign *stmt)
|
|||
&& is_gimple_min_invariant (gimple_assign_rhs1 (stmt)))
|
||||
vr->set (gimple_assign_rhs1 (stmt));
|
||||
else
|
||||
vr->set_varying ();
|
||||
vr->set_varying (TREE_TYPE (gimple_assign_lhs (stmt)));
|
||||
|
||||
if (vr->varying_p ())
|
||||
extract_range_basic (vr, stmt);
|
||||
|
@ -1938,7 +1952,7 @@ vr_values::dump_all_value_ranges (FILE *file)
|
|||
vr_values::vr_values () : vrp_value_range_pool ("Tree VRP value ranges")
|
||||
{
|
||||
values_propagated = false;
|
||||
num_vr_values = num_ssa_names;
|
||||
num_vr_values = num_ssa_names * 2;
|
||||
vr_value = XCNEWVEC (value_range *, num_vr_values);
|
||||
vr_phi_edge_counts = XCNEWVEC (int, num_ssa_names);
|
||||
bitmap_obstack_initialize (&vrp_equiv_obstack);
|
||||
|
@ -2875,7 +2889,7 @@ vr_values::extract_range_from_phi_node (gphi *phi, value_range *vr_result)
|
|||
vr_arg_tem.set (vr_arg_->kind (), vr_arg_->min (),
|
||||
vr_arg_->max (), NULL);
|
||||
if (vr_arg_tem.symbolic_p ())
|
||||
vr_arg_tem.set_varying ();
|
||||
vr_arg_tem.set_varying (TREE_TYPE (arg));
|
||||
}
|
||||
else
|
||||
vr_arg = vr_arg_;
|
||||
|
@ -2997,7 +3011,7 @@ vr_values::extract_range_from_phi_node (gphi *phi, value_range *vr_result)
|
|||
goto update_range;
|
||||
|
||||
varying:
|
||||
vr_result->set_varying ();
|
||||
vr_result->set_varying (TREE_TYPE (lhs));
|
||||
|
||||
scev_check:
|
||||
/* If this is a loop PHI node SCEV may known more about its value-range.
|
||||
|
@ -3018,7 +3032,7 @@ infinite_check:
|
|||
|| compare_values (vr_result->min (), vr_result->max ()) > 0))
|
||||
;
|
||||
else
|
||||
vr_result->set_varying ();
|
||||
vr_result->set_varying (TREE_TYPE (lhs));
|
||||
|
||||
/* If the new range is different than the previous value, keep
|
||||
iterating. */
|
||||
|
|
Loading…
Add table
Reference in a new issue