]>
Commit | Line | Data |
---|---|---|
c296f633 | 1 | /* Support routines for Value Range Propagation (VRP). |
8e8f6434 | 2 | Copyright (C) 2016-2018 Free Software Foundation, Inc. |
c296f633 | 3 | |
4 | This file is part of GCC. | |
5 | ||
6 | GCC is free software; you can redistribute it and/or modify | |
7 | it under the terms of the GNU General Public License as published by | |
8 | the Free Software Foundation; either version 3, or (at your option) | |
9 | any later version. | |
10 | ||
11 | GCC is distributed in the hope that it will be useful, | |
12 | but WITHOUT ANY WARRANTY; without even the implied warranty of | |
13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
14 | GNU General Public License for more details. | |
15 | ||
16 | You should have received a copy of the GNU General Public License | |
17 | along with GCC; see the file COPYING3. If not see | |
18 | <http://www.gnu.org/licenses/>. */ | |
19 | ||
b7e72cd7 | 20 | #ifndef GCC_TREE_VRP_H |
21 | #define GCC_TREE_VRP_H | |
22 | ||
be44111e | 23 | /* Types of value ranges. */ |
24 | enum value_range_kind | |
25 | { | |
26 | /* Empty range. */ | |
27 | VR_UNDEFINED, | |
28 | /* Range spans the entire domain. */ | |
29 | VR_VARYING, | |
30 | /* Range is [MIN, MAX]. */ | |
31 | VR_RANGE, | |
32 | /* Range is ~[MIN, MAX]. */ | |
33 | VR_ANTI_RANGE, | |
34 | /* Range is a nice guy. */ | |
35 | VR_LAST | |
36 | }; | |
c296f633 | 37 | |
a1054504 | 38 | |
c296f633 | 39 | /* Range of values that can be associated with an SSA_NAME after VRP |
40 | has executed. */ | |
a1054504 | 41 | class GTY((for_user)) value_range_base |
42 | { | |
43 | public: | |
44 | value_range_base (); | |
45 | value_range_base (value_range_kind, tree, tree); | |
46 | ||
47 | enum value_range_kind kind () const; | |
48 | tree min () const; | |
49 | tree max () const; | |
50 | ||
51 | /* Types of value ranges. */ | |
52 | bool undefined_p () const; | |
53 | bool varying_p () const; | |
54 | ||
55 | void union_ (const value_range_base *); | |
56 | ||
57 | bool ignore_equivs_equal_p (const value_range_base &) const; | |
58 | ||
59 | void set_varying (); | |
60 | void set_undefined (); | |
61 | ||
62 | /* Misc methods. */ | |
63 | tree type () const; | |
64 | bool may_contain_p (tree) const; | |
65 | void set_and_canonicalize (enum value_range_kind, tree, tree); | |
66 | ||
67 | void dump (FILE *) const; | |
68 | ||
69 | protected: | |
70 | void set (value_range_kind, tree, tree); | |
71 | void check (); | |
72 | ||
73 | enum value_range_kind m_kind; | |
74 | ||
75 | tree m_min; | |
76 | tree m_max; | |
77 | ||
78 | friend void gt_ggc_mx_value_range_base (void *); | |
79 | friend void gt_pch_p_16value_range_base (void *, void *, | |
80 | gt_pointer_operator, void *); | |
81 | friend void gt_pch_nx_value_range_base (void *); | |
82 | friend void gt_ggc_mx (value_range_base &); | |
83 | friend void gt_ggc_mx (value_range_base *&); | |
84 | friend void gt_pch_nx (value_range_base &); | |
85 | friend void gt_pch_nx (value_range_base *, gt_pointer_operator, void *); | |
86 | }; | |
87 | ||
88 | /* Note value_range cannot currently be used with GC memory, only | |
89 | value_range_base is fully set up for this. */ | |
90 | class GTY((user)) value_range : public value_range_base | |
c296f633 | 91 | { |
be44111e | 92 | public: |
93 | value_range (); | |
a1054504 | 94 | value_range (const value_range_base &); |
be44111e | 95 | value_range (value_range_kind, tree, tree, bitmap = NULL); |
96 | void update (value_range_kind, tree, tree); | |
97 | bool operator== (const value_range &) const; | |
98 | bool operator!= (const value_range &) const; | |
99 | void intersect (const value_range *); | |
100 | void union_ (const value_range *); | |
101 | ||
102 | /* Types of value ranges. */ | |
be44111e | 103 | bool symbolic_p () const; |
104 | bool constant_p () const; | |
105 | void set_undefined (); | |
106 | void set_varying (); | |
107 | ||
108 | /* Equivalence bitmap methods. */ | |
109 | bitmap equiv () const; | |
110 | void equiv_clear (); | |
111 | void equiv_add (const_tree, const value_range *, bitmap_obstack * = NULL); | |
112 | ||
113 | /* Misc methods. */ | |
3485e096 | 114 | bool zero_p () const; |
be44111e | 115 | bool singleton_p (tree *result = NULL) const; |
116 | void deep_copy (const value_range *); | |
be44111e | 117 | void set_and_canonicalize (enum value_range_kind, tree, tree, bitmap); |
118 | void dump (FILE *) const; | |
119 | void dump () const; | |
120 | ||
be44111e | 121 | private: |
122 | void set (value_range_kind, tree, tree, bitmap); | |
a1054504 | 123 | void set_equiv (bitmap); |
be44111e | 124 | void check (); |
125 | bool equal_p (const value_range &, bool ignore_equivs) const; | |
126 | void intersect_helper (value_range *, const value_range *); | |
127 | void union_helper (value_range *, const value_range *); | |
128 | ||
be44111e | 129 | /* Set of SSA names whose value ranges are equivalent to this one. |
130 | This set is only valid when TYPE is VR_RANGE or VR_ANTI_RANGE. */ | |
131 | bitmap m_equiv; | |
132 | }; | |
c296f633 | 133 | |
be44111e | 134 | inline |
a1054504 | 135 | value_range_base::value_range_base () |
be44111e | 136 | { |
137 | m_kind = VR_UNDEFINED; | |
138 | m_min = m_max = NULL; | |
a1054504 | 139 | } |
140 | ||
141 | inline | |
142 | value_range::value_range () | |
143 | : value_range_base () | |
144 | { | |
be44111e | 145 | m_equiv = NULL; |
146 | } | |
c296f633 | 147 | |
be44111e | 148 | /* Return the kind of this range. */ |
c296f633 | 149 | |
be44111e | 150 | inline value_range_kind |
a1054504 | 151 | value_range_base::kind () const |
be44111e | 152 | { |
153 | return m_kind; | |
154 | } | |
c296f633 | 155 | |
be44111e | 156 | inline bitmap |
157 | value_range::equiv () const | |
158 | { | |
159 | return m_equiv; | |
160 | } | |
c296f633 | 161 | |
be44111e | 162 | /* Return the lower bound. */ |
11822fb2 | 163 | |
be44111e | 164 | inline tree |
a1054504 | 165 | value_range_base::min () const |
be44111e | 166 | { |
167 | return m_min; | |
168 | } | |
169 | ||
170 | /* Return the upper bound. */ | |
171 | ||
172 | inline tree | |
a1054504 | 173 | value_range_base::max () const |
be44111e | 174 | { |
175 | return m_max; | |
176 | } | |
177 | ||
178 | /* Return TRUE if range spans the entire possible domain. */ | |
179 | ||
180 | inline bool | |
a1054504 | 181 | value_range_base::varying_p () const |
be44111e | 182 | { |
183 | return m_kind == VR_VARYING; | |
184 | } | |
185 | ||
186 | /* Return TRUE if range is undefined (essentially the empty set). */ | |
187 | ||
188 | inline bool | |
a1054504 | 189 | value_range_base::undefined_p () const |
be44111e | 190 | { |
191 | return m_kind == VR_UNDEFINED; | |
192 | } | |
193 | ||
194 | /* Return TRUE if range is the constant zero. */ | |
195 | ||
196 | inline bool | |
3485e096 | 197 | value_range::zero_p () const |
be44111e | 198 | { |
199 | return (m_kind == VR_RANGE | |
200 | && integer_zerop (m_min) | |
201 | && integer_zerop (m_max)); | |
202 | } | |
c296f633 | 203 | |
c296f633 | 204 | extern void dump_value_range (FILE *, const value_range *); |
a1054504 | 205 | extern void dump_value_range_base (FILE *, const value_range_base *); |
b09a4365 | 206 | extern void extract_range_from_unary_expr (value_range *vr, |
207 | enum tree_code code, | |
208 | tree type, | |
3278521b | 209 | const value_range *vr0_, |
b09a4365 | 210 | tree op0_type); |
c296f633 | 211 | |
9c015ccf | 212 | extern bool vrp_operand_equal_p (const_tree, const_tree); |
be44111e | 213 | extern enum value_range_kind intersect_range_with_nonzero_bits |
214 | (enum value_range_kind, wide_int *, wide_int *, const wide_int &, signop); | |
9c015ccf | 215 | |
216 | struct assert_info | |
217 | { | |
218 | /* Predicate code for the ASSERT_EXPR. Must be COMPARISON_CLASS_P. */ | |
219 | enum tree_code comp_code; | |
220 | ||
221 | /* Name to register the assert for. */ | |
222 | tree name; | |
223 | ||
224 | /* Value being compared against. */ | |
225 | tree val; | |
226 | ||
227 | /* Expression to compare. */ | |
228 | tree expr; | |
229 | }; | |
230 | ||
231 | extern void register_edge_assert_for (tree, edge, enum tree_code, | |
232 | tree, tree, vec<assert_info> &); | |
233 | extern bool stmt_interesting_for_vrp (gimple *); | |
234 | extern void set_value_range_to_varying (value_range *); | |
a1054504 | 235 | extern bool range_includes_zero_p (const value_range_base *); |
9c015ccf | 236 | extern bool infer_value_range (gimple *, tree, tree_code *, tree *); |
237 | ||
94d86adc | 238 | extern void set_value_range_to_nonnull (value_range *, tree); |
be44111e | 239 | extern void set_value_range (value_range *, enum value_range_kind, tree, |
94d86adc | 240 | tree, bitmap); |
94d86adc | 241 | extern bool vrp_bitmap_equal_p (const_bitmap, const_bitmap); |
3278521b | 242 | extern tree value_range_constant_singleton (const value_range *); |
94d86adc | 243 | extern int compare_values (tree, tree); |
244 | extern int compare_values_warnv (tree, tree, bool *); | |
245 | extern bool vrp_val_is_min (const_tree); | |
246 | extern bool vrp_val_is_max (const_tree); | |
94d86adc | 247 | extern void set_value_range_to_value (value_range *, tree, bitmap); |
248 | extern void extract_range_from_binary_expr_1 (value_range *, enum tree_code, | |
3278521b | 249 | tree, const value_range *, |
250 | const value_range *); | |
94d86adc | 251 | extern tree vrp_val_min (const_tree); |
252 | extern tree vrp_val_max (const_tree); | |
253 | extern void set_value_range_to_null (value_range *, tree); | |
3278521b | 254 | extern bool range_int_cst_p (const value_range *); |
94d86adc | 255 | extern int operand_less_p (tree, tree); |
256 | extern bool find_case_label_range (gswitch *, tree, tree, size_t *, size_t *); | |
257 | extern bool find_case_label_index (gswitch *, size_t, tree, size_t *); | |
3278521b | 258 | extern bool vrp_set_zero_nonzero_bits (const tree, const value_range *, |
94d86adc | 259 | wide_int *, wide_int *); |
260 | extern bool overflow_comparison_p (tree_code, tree, tree, bool, tree *); | |
3278521b | 261 | extern bool range_int_cst_singleton_p (const value_range *); |
94d86adc | 262 | extern int value_inside_range (tree, tree, tree); |
263 | extern tree get_single_symbol (tree, bool *, tree *); | |
dd435793 | 264 | extern void maybe_set_nonzero_bits (edge, tree); |
be44111e | 265 | extern value_range_kind determine_value_range (tree, wide_int *, wide_int *); |
b7e72cd7 | 266 | #endif /* GCC_TREE_VRP_H */ |