tree-optimization/112281 - loop distribution and zero dependence distances
[official-gcc.git] / gcc / range-op-mixed.h
blob45e11df57dfda849595b64643d66c7035a00dd63
1 /* Header file for mixed range operator class.
2 Copyright (C) 2017-2023 Free Software Foundation, Inc.
3 Contributed by Andrew MacLeod <amacleod@redhat.com>
4 and Aldy Hernandez <aldyh@redhat.com>.
6 This file is part of GCC.
8 GCC is free software; you can redistribute it and/or modify it under
9 the terms of the GNU General Public License as published by the Free
10 Software Foundation; either version 3, or (at your option) any later
11 version.
13 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
14 WARRANTY; without even the implied warranty of MERCHANTABILITY or
15 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
16 for more details.
18 You should have received a copy of the GNU General Public License
19 along with GCC; see the file COPYING3. If not see
20 <http://www.gnu.org/licenses/>. */
22 #ifndef GCC_RANGE_OP_MIXED_H
23 #define GCC_RANGE_OP_MIXED_H
25 void update_known_bitmask (irange &, tree_code, const irange &, const irange &);
26 bool minus_op1_op2_relation_effect (irange &lhs_range, tree type,
27 const irange &, const irange &,
28 relation_kind rel);
31 // Return TRUE if 0 is within [WMIN, WMAX].
33 inline bool
34 wi_includes_zero_p (tree type, const wide_int &wmin, const wide_int &wmax)
36 signop sign = TYPE_SIGN (type);
37 return wi::le_p (wmin, 0, sign) && wi::ge_p (wmax, 0, sign);
40 // Return TRUE if [WMIN, WMAX] is the singleton 0.
42 inline bool
43 wi_zero_p (tree type, const wide_int &wmin, const wide_int &wmax)
45 unsigned prec = TYPE_PRECISION (type);
46 return wmin == wmax && wi::eq_p (wmin, wi::zero (prec));
50 enum bool_range_state { BRS_FALSE, BRS_TRUE, BRS_EMPTY, BRS_FULL };
51 bool_range_state get_bool_state (vrange &r, const vrange &lhs, tree val_type);
53 // If the range of either op1 or op2 is undefined, set the result to
54 // varying and return TRUE. If the caller truly cares about a result,
55 // they should pass in a varying if it has an undefined that it wants
56 // treated as a varying.
58 inline bool
59 empty_range_varying (vrange &r, tree type,
60 const vrange &op1, const vrange & op2)
62 if (op1.undefined_p () || op2.undefined_p ())
64 r.set_varying (type);
65 return true;
67 else
68 return false;
71 // For relation opcodes, first try to see if the supplied relation
72 // forces a true or false result, and return that.
73 // Then check for undefined operands. If none of this applies,
74 // return false.
76 inline bool
77 relop_early_resolve (irange &r, tree type, const vrange &op1,
78 const vrange &op2, relation_trio trio,
79 relation_kind my_rel)
81 relation_kind rel = trio.op1_op2 ();
82 // If known relation is a complete subset of this relation, always true.
83 if (relation_union (rel, my_rel) == my_rel)
85 r = range_true (type);
86 return true;
89 // If known relation has no subset of this relation, always false.
90 if (relation_intersect (rel, my_rel) == VREL_UNDEFINED)
92 r = range_false (type);
93 return true;
96 // If either operand is undefined, return VARYING.
97 if (empty_range_varying (r, type, op1, op2))
98 return true;
100 return false;
103 // ----------------------------------------------------------------------
104 // Mixed Mode Operators.
105 // ----------------------------------------------------------------------
107 class operator_equal : public range_operator
109 public:
110 using range_operator::fold_range;
111 using range_operator::op1_range;
112 using range_operator::op2_range;
113 using range_operator::op1_op2_relation;
114 bool fold_range (irange &r, tree type,
115 const irange &op1, const irange &op2,
116 relation_trio = TRIO_VARYING) const final override;
117 bool fold_range (irange &r, tree type,
118 const frange &op1, const frange &op2,
119 relation_trio = TRIO_VARYING) const final override;
121 bool op1_range (irange &r, tree type,
122 const irange &lhs, const irange &val,
123 relation_trio = TRIO_VARYING) const final override;
124 bool op1_range (frange &r, tree type,
125 const irange &lhs, const frange &op2,
126 relation_trio = TRIO_VARYING) const final override;
128 bool op2_range (irange &r, tree type,
129 const irange &lhs, const irange &val,
130 relation_trio = TRIO_VARYING) const final override;
131 bool op2_range (frange &r, tree type,
132 const irange &lhs, const frange &op1,
133 relation_trio rel = TRIO_VARYING) const final override;
135 relation_kind op1_op2_relation (const irange &lhs, const irange &,
136 const irange &) const final override;
137 relation_kind op1_op2_relation (const irange &lhs, const frange &,
138 const frange &) const final override;
139 void update_bitmask (irange &r, const irange &lh,
140 const irange &rh) const final override;
143 class operator_not_equal : public range_operator
145 public:
146 using range_operator::fold_range;
147 using range_operator::op1_range;
148 using range_operator::op2_range;
149 using range_operator::op1_op2_relation;
150 bool fold_range (irange &r, tree type,
151 const irange &op1, const irange &op2,
152 relation_trio = TRIO_VARYING) const final override;
153 bool fold_range (irange &r, tree type,
154 const frange &op1, const frange &op2,
155 relation_trio rel = TRIO_VARYING) const final override;
157 bool op1_range (irange &r, tree type,
158 const irange &lhs, const irange &op2,
159 relation_trio = TRIO_VARYING) const final override;
160 bool op1_range (frange &r, tree type,
161 const irange &lhs, const frange &op2,
162 relation_trio = TRIO_VARYING) const final override;
164 bool op2_range (irange &r, tree type,
165 const irange &lhs, const irange &op1,
166 relation_trio = TRIO_VARYING) const final override;
167 bool op2_range (frange &r, tree type,
168 const irange &lhs, const frange &op1,
169 relation_trio = TRIO_VARYING) const final override;
171 relation_kind op1_op2_relation (const irange &lhs, const irange &,
172 const irange &) const final override;
173 relation_kind op1_op2_relation (const irange &lhs, const frange &,
174 const frange &) const final override;
175 void update_bitmask (irange &r, const irange &lh,
176 const irange &rh) const final override;
179 class operator_lt : public range_operator
181 public:
182 using range_operator::fold_range;
183 using range_operator::op1_range;
184 using range_operator::op2_range;
185 using range_operator::op1_op2_relation;
186 bool fold_range (irange &r, tree type,
187 const irange &op1, const irange &op2,
188 relation_trio = TRIO_VARYING) const final override;
189 bool fold_range (irange &r, tree type,
190 const frange &op1, const frange &op2,
191 relation_trio = TRIO_VARYING) const final override;
192 bool op1_range (irange &r, tree type,
193 const irange &lhs, const irange &op2,
194 relation_trio = TRIO_VARYING) const final override;
195 bool op1_range (frange &r, tree type,
196 const irange &lhs, const frange &op2,
197 relation_trio = TRIO_VARYING) const final override;
198 bool op2_range (irange &r, tree type,
199 const irange &lhs, const irange &op1,
200 relation_trio = TRIO_VARYING) const final override;
201 bool op2_range (frange &r, tree type,
202 const irange &lhs, const frange &op1,
203 relation_trio = TRIO_VARYING) const final override;
204 relation_kind op1_op2_relation (const irange &lhs, const irange &,
205 const irange &) const final override;
206 relation_kind op1_op2_relation (const irange &lhs, const frange &,
207 const frange &) const final override;
208 void update_bitmask (irange &r, const irange &lh,
209 const irange &rh) const final override;
212 class operator_le : public range_operator
214 public:
215 using range_operator::fold_range;
216 using range_operator::op1_range;
217 using range_operator::op2_range;
218 using range_operator::op1_op2_relation;
219 bool fold_range (irange &r, tree type,
220 const irange &op1, const irange &op2,
221 relation_trio = TRIO_VARYING) const final override;
222 bool fold_range (irange &r, tree type,
223 const frange &op1, const frange &op2,
224 relation_trio rel = TRIO_VARYING) const final override;
226 bool op1_range (irange &r, tree type,
227 const irange &lhs, const irange &op2,
228 relation_trio = TRIO_VARYING) const final override;
229 bool op1_range (frange &r, tree type,
230 const irange &lhs, const frange &op2,
231 relation_trio rel = TRIO_VARYING) const final override;
233 bool op2_range (irange &r, tree type,
234 const irange &lhs, const irange &op1,
235 relation_trio = TRIO_VARYING) const final override;
236 bool op2_range (frange &r, tree type,
237 const irange &lhs, const frange &op1,
238 relation_trio rel = TRIO_VARYING) const final override;
240 relation_kind op1_op2_relation (const irange &lhs, const irange &,
241 const irange &) const final override;
242 relation_kind op1_op2_relation (const irange &lhs, const frange &,
243 const frange &) const final override;
244 void update_bitmask (irange &r, const irange &lh,
245 const irange &rh) const final override;
248 class operator_gt : public range_operator
250 public:
251 using range_operator::fold_range;
252 using range_operator::op1_range;
253 using range_operator::op2_range;
254 using range_operator::op1_op2_relation;
255 bool fold_range (irange &r, tree type,
256 const irange &op1, const irange &op2,
257 relation_trio = TRIO_VARYING) const final override;
258 bool fold_range (irange &r, tree type,
259 const frange &op1, const frange &op2,
260 relation_trio = TRIO_VARYING) const final override;
262 bool op1_range (irange &r, tree type,
263 const irange &lhs, const irange &op2,
264 relation_trio = TRIO_VARYING) const final override;
265 bool op1_range (frange &r, tree type,
266 const irange &lhs, const frange &op2,
267 relation_trio = TRIO_VARYING) const final override;
269 bool op2_range (irange &r, tree type,
270 const irange &lhs, const irange &op1,
271 relation_trio = TRIO_VARYING) const final override;
272 bool op2_range (frange &r, tree type,
273 const irange &lhs, const frange &op1,
274 relation_trio = TRIO_VARYING) const final override;
275 relation_kind op1_op2_relation (const irange &lhs, const irange &,
276 const irange &) const final override;
277 relation_kind op1_op2_relation (const irange &lhs, const frange &,
278 const frange &) const final override;
279 void update_bitmask (irange &r, const irange &lh,
280 const irange &rh) const final override;
283 class operator_ge : public range_operator
285 public:
286 using range_operator::fold_range;
287 using range_operator::op1_range;
288 using range_operator::op2_range;
289 using range_operator::op1_op2_relation;
290 bool fold_range (irange &r, tree type,
291 const irange &op1, const irange &op2,
292 relation_trio = TRIO_VARYING) const final override;
293 bool fold_range (irange &r, tree type,
294 const frange &op1, const frange &op2,
295 relation_trio = TRIO_VARYING) const final override;
297 bool op1_range (irange &r, tree type,
298 const irange &lhs, const irange &op2,
299 relation_trio = TRIO_VARYING) const final override;
300 bool op1_range (frange &r, tree type,
301 const irange &lhs, const frange &op2,
302 relation_trio = TRIO_VARYING) const final override;
304 bool op2_range (irange &r, tree type,
305 const irange &lhs, const irange &op1,
306 relation_trio = TRIO_VARYING) const final override;
307 bool op2_range (frange &r, tree type,
308 const irange &lhs, const frange &op1,
309 relation_trio = TRIO_VARYING) const final override;
311 relation_kind op1_op2_relation (const irange &lhs, const irange &,
312 const irange &) const final override;
313 relation_kind op1_op2_relation (const irange &lhs, const frange &,
314 const frange &) const final override;
315 void update_bitmask (irange &r, const irange &lh,
316 const irange &rh) const final override;
319 class operator_identity : public range_operator
321 public:
322 using range_operator::fold_range;
323 using range_operator::op1_range;
324 using range_operator::lhs_op1_relation;
325 bool fold_range (irange &r, tree type,
326 const irange &op1, const irange &op2,
327 relation_trio rel = TRIO_VARYING) const final override;
328 bool fold_range (frange &r, tree type ATTRIBUTE_UNUSED,
329 const frange &op1, const frange &op2 ATTRIBUTE_UNUSED,
330 relation_trio = TRIO_VARYING) const final override;
331 bool op1_range (irange &r, tree type,
332 const irange &lhs, const irange &op2,
333 relation_trio rel = TRIO_VARYING) const final override;
334 bool op1_range (frange &r, tree type ATTRIBUTE_UNUSED,
335 const frange &lhs, const frange &op2 ATTRIBUTE_UNUSED,
336 relation_trio = TRIO_VARYING) const final override;
337 relation_kind lhs_op1_relation (const irange &lhs,
338 const irange &op1, const irange &op2,
339 relation_kind rel) const final override;
342 class operator_cst : public range_operator
344 public:
345 using range_operator::fold_range;
346 bool fold_range (irange &r, tree type,
347 const irange &op1, const irange &op2,
348 relation_trio rel = TRIO_VARYING) const final override;
349 bool fold_range (frange &r, tree type,
350 const frange &op1, const frange &op2,
351 relation_trio = TRIO_VARYING) const final override;
355 class operator_cast: public range_operator
357 public:
358 using range_operator::fold_range;
359 using range_operator::op1_range;
360 using range_operator::lhs_op1_relation;
361 bool fold_range (irange &r, tree type,
362 const irange &op1, const irange &op2,
363 relation_trio rel = TRIO_VARYING) const final override;
364 bool op1_range (irange &r, tree type,
365 const irange &lhs, const irange &op2,
366 relation_trio rel = TRIO_VARYING) const final override;
367 relation_kind lhs_op1_relation (const irange &lhs,
368 const irange &op1, const irange &op2,
369 relation_kind) const final override;
370 void update_bitmask (irange &r, const irange &lh,
371 const irange &rh) const final override;
372 private:
373 bool truncating_cast_p (const irange &inner, const irange &outer) const;
374 bool inside_domain_p (const wide_int &min, const wide_int &max,
375 const irange &outer) const;
376 void fold_pair (irange &r, unsigned index, const irange &inner,
377 const irange &outer) const;
380 class operator_plus : public range_operator
382 public:
383 using range_operator::op1_range;
384 using range_operator::op2_range;
385 using range_operator::lhs_op1_relation;
386 using range_operator::lhs_op2_relation;
387 bool op1_range (irange &r, tree type,
388 const irange &lhs, const irange &op2,
389 relation_trio) const final override;
390 bool op1_range (frange &r, tree type,
391 const frange &lhs, const frange &op2,
392 relation_trio = TRIO_VARYING) const final override;
394 bool op2_range (irange &r, tree type,
395 const irange &lhs, const irange &op1,
396 relation_trio) const final override;
397 bool op2_range (frange &r, tree type,
398 const frange &lhs, const frange &op1,
399 relation_trio = TRIO_VARYING) const final override;
401 relation_kind lhs_op1_relation (const irange &lhs, const irange &op1,
402 const irange &op2,
403 relation_kind rel) const final override;
404 relation_kind lhs_op2_relation (const irange &lhs, const irange &op1,
405 const irange &op2,
406 relation_kind rel) const final override;
407 void update_bitmask (irange &r, const irange &lh,
408 const irange &rh) const final override;
410 virtual bool overflow_free_p (const irange &lh, const irange &rh,
411 relation_trio = TRIO_VARYING) const;
413 private:
414 void wi_fold (irange &r, tree type, const wide_int &lh_lb,
415 const wide_int &lh_ub, const wide_int &rh_lb,
416 const wide_int &rh_ub) const final override;
417 void rv_fold (frange &r, tree type,
418 const REAL_VALUE_TYPE &lh_lb, const REAL_VALUE_TYPE &lh_ub,
419 const REAL_VALUE_TYPE &rh_lb, const REAL_VALUE_TYPE &rh_ub,
420 relation_kind) const final override;
423 class operator_abs : public range_operator
425 public:
426 using range_operator::fold_range;
427 using range_operator::op1_range;
428 bool fold_range (frange &r, tree type,
429 const frange &op1, const frange &,
430 relation_trio = TRIO_VARYING) const final override;
432 bool op1_range (irange &r, tree type, const irange &lhs,
433 const irange &op2, relation_trio) const final override;
434 bool op1_range (frange &r, tree type,
435 const frange &lhs, const frange &op2,
436 relation_trio rel = TRIO_VARYING) const final override;
437 void update_bitmask (irange &r, const irange &lh,
438 const irange &rh) const final override;
439 private:
440 void wi_fold (irange &r, tree type, const wide_int &lh_lb,
441 const wide_int &lh_ub, const wide_int &rh_lb,
442 const wide_int &rh_ub) const final override;
446 class operator_minus : public range_operator
448 public:
449 using range_operator::fold_range;
450 using range_operator::op1_range;
451 using range_operator::op2_range;
452 using range_operator::lhs_op1_relation;
453 bool op1_range (irange &r, tree type,
454 const irange &lhs, const irange &op2,
455 relation_trio) const final override;
456 bool op1_range (frange &r, tree type,
457 const frange &lhs, const frange &op2,
458 relation_trio = TRIO_VARYING) const final override;
460 bool op2_range (irange &r, tree type,
461 const irange &lhs, const irange &op1,
462 relation_trio) const final override;
463 bool op2_range (frange &r, tree type,
464 const frange &lhs,
465 const frange &op1,
466 relation_trio = TRIO_VARYING) const final override;
468 relation_kind lhs_op1_relation (const irange &lhs,
469 const irange &op1, const irange &op2,
470 relation_kind rel) const final override;
471 bool op1_op2_relation_effect (irange &lhs_range, tree type,
472 const irange &op1_range,
473 const irange &op2_range,
474 relation_kind rel) const final override;
475 void update_bitmask (irange &r, const irange &lh,
476 const irange &rh) const final override;
478 virtual bool overflow_free_p (const irange &lh, const irange &rh,
479 relation_trio = TRIO_VARYING) const;
481 private:
482 void wi_fold (irange &r, tree type, const wide_int &lh_lb,
483 const wide_int &lh_ub, const wide_int &rh_lb,
484 const wide_int &rh_ub) const final override;
485 void rv_fold (frange &r, tree type,
486 const REAL_VALUE_TYPE &lh_lb, const REAL_VALUE_TYPE &lh_ub,
487 const REAL_VALUE_TYPE &rh_lb, const REAL_VALUE_TYPE &rh_ub,
488 relation_kind) const final override;
491 class operator_negate : public range_operator
493 public:
494 using range_operator::fold_range;
495 using range_operator::op1_range;
496 bool fold_range (irange &r, tree type,
497 const irange &op1, const irange &op2,
498 relation_trio rel = TRIO_VARYING) const final override;
499 bool fold_range (frange &r, tree type,
500 const frange &op1, const frange &op2,
501 relation_trio = TRIO_VARYING) const final override;
503 bool op1_range (irange &r, tree type,
504 const irange &lhs, const irange &op2,
505 relation_trio rel = TRIO_VARYING) const final override;
506 bool op1_range (frange &r, tree type,
507 const frange &lhs, const frange &op2,
508 relation_trio rel = TRIO_VARYING) const final override;
512 class cross_product_operator : public range_operator
514 public:
515 virtual bool wi_op_overflows (wide_int &r,
516 tree type,
517 const wide_int &,
518 const wide_int &) const = 0;
519 void wi_cross_product (irange &r, tree type,
520 const wide_int &lh_lb,
521 const wide_int &lh_ub,
522 const wide_int &rh_lb,
523 const wide_int &rh_ub) const;
526 class operator_mult : public cross_product_operator
528 public:
529 using range_operator::op1_range;
530 using range_operator::op2_range;
531 bool op1_range (irange &r, tree type,
532 const irange &lhs, const irange &op2,
533 relation_trio) const final override;
534 bool op1_range (frange &r, tree type,
535 const frange &lhs, const frange &op2,
536 relation_trio = TRIO_VARYING) const final override;
538 bool op2_range (irange &r, tree type,
539 const irange &lhs, const irange &op1,
540 relation_trio) const final override;
541 bool op2_range (frange &r, tree type,
542 const frange &lhs, const frange &op1,
543 relation_trio = TRIO_VARYING) const final override;
545 void update_bitmask (irange &r, const irange &lh,
546 const irange &rh) const final override;
548 void wi_fold (irange &r, tree type, const wide_int &lh_lb,
549 const wide_int &lh_ub, const wide_int &rh_lb,
550 const wide_int &rh_ub) const final override;
551 bool wi_op_overflows (wide_int &res, tree type, const wide_int &w0,
552 const wide_int &w1) const final override;
554 void rv_fold (frange &r, tree type,
555 const REAL_VALUE_TYPE &lh_lb, const REAL_VALUE_TYPE &lh_ub,
556 const REAL_VALUE_TYPE &rh_lb, const REAL_VALUE_TYPE &rh_ub,
557 relation_kind kind) const final override;
558 virtual bool overflow_free_p (const irange &lh, const irange &rh,
559 relation_trio = TRIO_VARYING) const;
563 class operator_addr_expr : public range_operator
565 public:
566 using range_operator::fold_range;
567 using range_operator::op1_range;
568 bool fold_range (irange &r, tree type,
569 const irange &op1, const irange &op2,
570 relation_trio rel = TRIO_VARYING) const final override;
571 bool op1_range (irange &r, tree type,
572 const irange &lhs, const irange &op2,
573 relation_trio rel = TRIO_VARYING) const final override;
576 class operator_bitwise_not : public range_operator
578 public:
579 using range_operator::fold_range;
580 using range_operator::op1_range;
581 bool fold_range (irange &r, tree type,
582 const irange &lh, const irange &rh,
583 relation_trio rel = TRIO_VARYING) const final override;
584 bool op1_range (irange &r, tree type,
585 const irange &lhs, const irange &op2,
586 relation_trio rel = TRIO_VARYING) const final override;
587 void update_bitmask (irange &r, const irange &lh,
588 const irange &rh) const final override;
591 class operator_bitwise_xor : public range_operator
593 public:
594 using range_operator::op1_range;
595 using range_operator::op2_range;
596 bool op1_range (irange &r, tree type,
597 const irange &lhs, const irange &op2,
598 relation_trio rel = TRIO_VARYING) const final override;
599 bool op2_range (irange &r, tree type,
600 const irange &lhs, const irange &op1,
601 relation_trio rel = TRIO_VARYING) const final override;
602 bool op1_op2_relation_effect (irange &lhs_range,
603 tree type,
604 const irange &op1_range,
605 const irange &op2_range,
606 relation_kind rel) const final override;
607 void update_bitmask (irange &r, const irange &lh,
608 const irange &rh) const final override;
609 private:
610 void wi_fold (irange &r, tree type, const wide_int &lh_lb,
611 const wide_int &lh_ub, const wide_int &rh_lb,
612 const wide_int &rh_ub) const final override;
615 class operator_bitwise_and : public range_operator
617 public:
618 using range_operator::op1_range;
619 using range_operator::op2_range;
620 using range_operator::lhs_op1_relation;
621 bool op1_range (irange &r, tree type,
622 const irange &lhs, const irange &op2,
623 relation_trio rel = TRIO_VARYING) const override;
624 bool op2_range (irange &r, tree type,
625 const irange &lhs, const irange &op1,
626 relation_trio rel = TRIO_VARYING) const override;
627 relation_kind lhs_op1_relation (const irange &lhs,
628 const irange &op1, const irange &op2,
629 relation_kind) const override;
630 void update_bitmask (irange &r, const irange &lh,
631 const irange &rh) const override;
632 protected:
633 void wi_fold (irange &r, tree type, const wide_int &lh_lb,
634 const wide_int &lh_ub, const wide_int &rh_lb,
635 const wide_int &rh_ub) const override;
636 void simple_op1_range_solver (irange &r, tree type,
637 const irange &lhs,
638 const irange &op2) const;
641 class operator_bitwise_or : public range_operator
643 public:
644 using range_operator::op1_range;
645 using range_operator::op2_range;
646 bool op1_range (irange &r, tree type,
647 const irange &lhs, const irange &op2,
648 relation_trio rel = TRIO_VARYING) const override;
649 bool op2_range (irange &r, tree type,
650 const irange &lhs, const irange &op1,
651 relation_trio rel = TRIO_VARYING) const override;
652 void update_bitmask (irange &r, const irange &lh,
653 const irange &rh) const override;
654 protected:
655 void wi_fold (irange &r, tree type, const wide_int &lh_lb,
656 const wide_int &lh_ub, const wide_int &rh_lb,
657 const wide_int &rh_ub) const override;
660 class operator_min : public range_operator
662 public:
663 void update_bitmask (irange &r, const irange &lh,
664 const irange &rh) const override;
665 protected:
666 void wi_fold (irange &r, tree type, const wide_int &lh_lb,
667 const wide_int &lh_ub, const wide_int &rh_lb,
668 const wide_int &rh_ub) const override;
671 class operator_max : public range_operator
673 public:
674 void update_bitmask (irange &r, const irange &lh,
675 const irange &rh) const override;
676 protected:
677 void wi_fold (irange &r, tree type, const wide_int &lh_lb,
678 const wide_int &lh_ub, const wide_int &rh_lb,
679 const wide_int &rh_ub) const override;
681 #endif // GCC_RANGE_OP_MIXED_H