1 /* Support routines for value ranges.
2 Copyright (C) 2019-2023 Free Software Foundation, Inc.
3 Contributed by Aldy Hernandez <aldyh@redhat.com> and
4 Andrew Macleod <amacleod@redhat.com>.
6 This file is part of GCC.
8 GCC is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 3, or (at your option)
13 GCC is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License 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_VALUE_RANGE_H
23 #define GCC_VALUE_RANGE_H
27 // Types of value ranges.
32 /* Range spans the entire domain. */
34 /* Range is [MIN, MAX]. */
36 /* Range is ~[MIN, MAX]. */
40 /* Range is a nice guy. */
44 // Discriminator between different vrange types.
46 enum value_range_discriminator
48 // Range holds an integer or pointer.
50 // Floating point range.
52 // Range holds an unsupported type.
56 // Abstract class for ranges of any of the supported types.
58 // To query what types ranger and the entire ecosystem can support,
59 // use Value_Range::supports_type_p(tree type). This is a static
60 // method available independently of any vrange object.
62 // To query what a given vrange variant can support, use:
63 // irange::supports_p ()
64 // frange::supports_p ()
67 // To query what a range object can support, use:
68 // void foo (vrange &v, irange &i, frange &f)
70 // if (v.supports_type_p (type)) ...
71 // if (i.supports_type_p (type)) ...
72 // if (f.supports_type_p (type)) ...
75 class GTY((user
)) vrange
77 template <typename T
> friend bool is_a (vrange
&);
78 friend class Value_Range
;
79 friend void streamer_write_vrange (struct output_block
*, const vrange
&);
80 friend class range_op_handler
;
82 virtual void accept (const class vrange_visitor
&v
) const = 0;
83 virtual void set (tree
, tree
, value_range_kind
= VR_RANGE
);
84 virtual tree
type () const;
85 virtual bool supports_type_p (const_tree type
) const;
86 virtual void set_varying (tree type
);
87 virtual void set_undefined ();
88 virtual bool union_ (const vrange
&);
89 virtual bool intersect (const vrange
&);
90 virtual bool singleton_p (tree
*result
= NULL
) const;
91 virtual bool contains_p (tree cst
) const;
92 virtual bool zero_p () const;
93 virtual bool nonzero_p () const;
94 virtual void set_nonzero (tree type
);
95 virtual void set_zero (tree type
);
96 virtual void set_nonnegative (tree type
);
97 virtual bool fits_p (const vrange
&r
) const;
99 bool varying_p () const;
100 bool undefined_p () const;
101 vrange
& operator= (const vrange
&);
102 bool operator== (const vrange
&) const;
103 bool operator!= (const vrange
&r
) const { return !(*this == r
); }
104 void dump (FILE *) const;
106 vrange (enum value_range_discriminator d
) : m_discriminator (d
) { }
107 ENUM_BITFIELD(value_range_kind
) m_kind
: 8;
108 const ENUM_BITFIELD(value_range_discriminator
) m_discriminator
: 4;
113 extern void add_vrange (const vrange
&, hash
&, unsigned flags
= 0);
116 // A pair of values representing the known bits in a range. Zero bits
117 // in MASK cover constant values. Set bits in MASK cover unknown
118 // values. VALUE are the known bits.
120 // Set bits in MASK (no meaningful information) must have their
121 // corresponding bits in VALUE cleared, as this speeds up union and
127 irange_bitmask () { /* uninitialized */ }
128 irange_bitmask (unsigned prec
) { set_unknown (prec
); }
129 irange_bitmask (const wide_int
&value
, const wide_int
&mask
);
130 wide_int
value () const { return m_value
; }
131 wide_int
mask () const { return m_mask
; }
132 void set_unknown (unsigned prec
);
133 bool unknown_p () const;
134 unsigned get_precision () const;
135 bool union_ (const irange_bitmask
&src
);
136 bool intersect (const irange_bitmask
&src
);
137 bool operator== (const irange_bitmask
&src
) const;
138 bool operator!= (const irange_bitmask
&src
) const { return !(*this == src
); }
139 void verify_mask () const;
140 void dump (FILE *) const;
142 bool member_p (const wide_int
&val
) const;
143 void adjust_range (irange
&r
) const;
145 // Convenience functions for nonzero bitmask compatibility.
146 wide_int
get_nonzero_bits () const;
147 void set_nonzero_bits (const wide_int
&bits
);
154 irange_bitmask::set_unknown (unsigned prec
)
156 m_value
= wi::zero (prec
);
157 m_mask
= wi::minus_one (prec
);
162 // Return TRUE if THIS does not have any meaningful information.
165 irange_bitmask::unknown_p () const
171 irange_bitmask::irange_bitmask (const wide_int
&value
, const wide_int
&mask
)
180 irange_bitmask::get_precision () const
182 return m_mask
.get_precision ();
185 // The following two functions are meant for backwards compatability
186 // with the nonzero bitmask. A cleared bit means the value must be 0.
187 // A set bit means we have no information for the bit.
189 // Return the nonzero bits.
191 irange_bitmask::get_nonzero_bits () const
193 return m_value
| m_mask
;
196 // Set the bitmask to the nonzero bits in BITS.
198 irange_bitmask::set_nonzero_bits (const wide_int
&bits
)
200 m_value
= wi::zero (bits
.get_precision ());
206 // Return TRUE if val could be a valid value with this bitmask.
209 irange_bitmask::member_p (const wide_int
&val
) const
213 wide_int res
= m_mask
& val
;
215 res
|= ~m_mask
& m_value
;
220 irange_bitmask::operator== (const irange_bitmask
&src
) const
222 bool unknown1
= unknown_p ();
223 bool unknown2
= src
.unknown_p ();
224 if (unknown1
|| unknown2
)
225 return unknown1
== unknown2
;
226 return m_value
== src
.m_value
&& m_mask
== src
.m_mask
;
230 irange_bitmask::union_ (const irange_bitmask
&orig_src
)
233 irange_bitmask
src (orig_src
.m_value
& ~orig_src
.m_mask
, orig_src
.m_mask
);
236 irange_bitmask
save (*this);
237 m_mask
= (m_mask
| src
.m_mask
) | (m_value
^ src
.m_value
);
238 m_value
= m_value
& src
.m_value
;
241 return *this != save
;
245 irange_bitmask::intersect (const irange_bitmask
&orig_src
)
248 irange_bitmask
src (orig_src
.m_value
& ~orig_src
.m_mask
, orig_src
.m_mask
);
251 irange_bitmask
save (*this);
252 // If we have two known bits that are incompatible, the resulting
253 // bit is undefined. It is unclear whether we should set the entire
254 // range to UNDEFINED, or just a subset of it. For now, set the
255 // entire bitmask to unknown (VARYING).
256 if (wi::bit_and (~(m_mask
| src
.m_mask
),
257 m_value
^ src
.m_value
) != 0)
259 unsigned prec
= m_mask
.get_precision ();
260 m_mask
= wi::minus_one (prec
);
261 m_value
= wi::zero (prec
);
265 m_mask
= m_mask
& src
.m_mask
;
266 m_value
= m_value
| src
.m_value
;
270 return *this != save
;
273 // An integer range without any storage.
275 class GTY((user
)) irange
: public vrange
277 friend value_range_kind
get_legacy_range (const irange
&, tree
&, tree
&);
278 friend class irange_storage
;
279 friend class vrange_printer
;
282 void set (tree type
, const wide_int
&, const wide_int
&,
283 value_range_kind
= VR_RANGE
);
284 virtual void set_nonzero (tree type
) override
;
285 virtual void set_zero (tree type
) override
;
286 virtual void set_nonnegative (tree type
) override
;
287 virtual void set_varying (tree type
) override
;
288 virtual void set_undefined () override
;
291 static bool supports_p (const_tree type
);
292 virtual bool supports_type_p (const_tree type
) const override
;
293 virtual tree
type () const override
;
295 // Iteration over sub-ranges.
296 unsigned num_pairs () const;
297 wide_int
lower_bound (unsigned = 0) const;
298 wide_int
upper_bound (unsigned) const;
299 wide_int
upper_bound () const;
302 virtual bool zero_p () const override
;
303 virtual bool nonzero_p () const override
;
304 virtual bool singleton_p (tree
*result
= NULL
) const override
;
305 bool singleton_p (wide_int
&) const;
306 bool contains_p (const wide_int
&) const;
307 bool nonnegative_p () const;
308 bool nonpositive_p () const;
310 // In-place operators.
311 virtual bool union_ (const vrange
&) override
;
312 virtual bool intersect (const vrange
&) override
;
315 // Operator overloads.
316 irange
& operator= (const irange
&);
317 bool operator== (const irange
&) const;
318 bool operator!= (const irange
&r
) const { return !(*this == r
); }
321 virtual bool fits_p (const vrange
&r
) const override
;
322 virtual void accept (const vrange_visitor
&v
) const override
;
324 void update_bitmask (const irange_bitmask
&);
325 irange_bitmask
get_bitmask () const;
327 wide_int
get_nonzero_bits () const;
328 void set_nonzero_bits (const wide_int
&bits
);
331 void maybe_resize (int needed
);
332 virtual void set (tree
, tree
, value_range_kind
= VR_RANGE
) override
;
333 virtual bool contains_p (tree cst
) const override
;
334 irange (wide_int
*, unsigned nranges
, bool resizable
);
336 // In-place operators.
337 bool irange_contains_p (const irange
&) const;
338 bool irange_single_pair_union (const irange
&r
);
340 void normalize_kind ();
342 void verify_range ();
344 // Hard limit on max ranges allowed.
345 static const int HARD_MAX_RANGES
= 255;
347 friend void gt_ggc_mx (irange
*);
348 friend void gt_pch_nx (irange
*);
349 friend void gt_pch_nx (irange
*, gt_pointer_operator
, void *);
351 bool varying_compatible_p () const;
352 bool intersect_bitmask (const irange
&r
);
353 bool union_bitmask (const irange
&r
);
354 irange_bitmask
get_bitmask_from_range () const;
355 bool set_range_from_bitmask ();
357 bool intersect (const wide_int
& lb
, const wide_int
& ub
);
358 bool union_append (const irange
&r
);
359 unsigned char m_num_ranges
;
361 unsigned char m_max_ranges
;
363 irange_bitmask m_bitmask
;
368 // Here we describe an irange with N pairs of ranges. The storage for
369 // the pairs is embedded in the class as an array.
371 // If RESIZABLE is true, the storage will be resized on the heap when
372 // the number of ranges needed goes past N up to a max of
373 // HARD_MAX_RANGES. This new storage is freed upon destruction.
375 template<unsigned N
, bool RESIZABLE
= false>
376 class GTY((user
)) int_range
: public irange
380 int_range (tree type
, const wide_int
&, const wide_int
&,
381 value_range_kind
= VR_RANGE
);
382 int_range (tree type
);
383 int_range (const int_range
&);
384 int_range (const irange
&);
385 virtual ~int_range ();
386 int_range
& operator= (const int_range
&);
388 int_range (tree
, tree
, value_range_kind
= VR_RANGE
);
390 wide_int m_ranges
[N
*2];
393 // Unsupported temporaries may be created by ranger before it's known
394 // they're unsupported, or by vr_values::get_value_range.
396 class unsupported_range
: public vrange
400 : vrange (VR_UNKNOWN
)
404 virtual void set_undefined () final override
406 m_kind
= VR_UNDEFINED
;
408 virtual void accept (const vrange_visitor
&v
) const override
;
411 // The NAN state as an opaque object.
417 nan_state (bool pos_nan
, bool neg_nan
);
425 // Set NAN state to +-NAN if NAN_P is true. Otherwise set NAN state
429 nan_state::nan_state (bool nan_p
)
435 // Constructor initializing the object to +NAN if POS_NAN is set, -NAN
436 // if NEG_NAN is set, or +-NAN if both are set. Otherwise POS_NAN and
437 // NEG_NAN are clear, and the object cannot be a NAN.
440 nan_state::nan_state (bool pos_nan
, bool neg_nan
)
446 // Return if +NAN is possible.
449 nan_state::pos_p () const
454 // Return if -NAN is possible.
457 nan_state::neg_p () const
462 // A floating point range.
464 // The representation is a type with a couple of endpoints, unioned
465 // with the set of { -NAN, +Nan }.
467 class GTY((user
)) frange
: public vrange
469 friend class frange_storage
;
470 friend class vrange_printer
;
471 friend void gt_ggc_mx (frange
*);
472 friend void gt_pch_nx (frange
*);
473 friend void gt_pch_nx (frange
*, gt_pointer_operator
, void *);
476 frange (const frange
&);
477 frange (tree
, tree
, value_range_kind
= VR_RANGE
);
479 frange (tree type
, const REAL_VALUE_TYPE
&min
, const REAL_VALUE_TYPE
&max
,
480 value_range_kind
= VR_RANGE
);
481 static bool supports_p (const_tree type
)
483 // ?? Decimal floats can have multiple representations for the
484 // same number. Supporting them may be as simple as just
485 // disabling them in singleton_p. No clue.
486 return SCALAR_FLOAT_TYPE_P (type
) && !DECIMAL_FLOAT_TYPE_P (type
);
488 virtual tree
type () const override
;
489 void set (tree type
, const REAL_VALUE_TYPE
&, const REAL_VALUE_TYPE
&,
490 value_range_kind
= VR_RANGE
);
491 void set (tree type
, const REAL_VALUE_TYPE
&, const REAL_VALUE_TYPE
&,
492 const nan_state
&, value_range_kind
= VR_RANGE
);
493 void set_nan (tree type
);
494 void set_nan (tree type
, bool sign
);
495 void set_nan (tree type
, const nan_state
&);
496 virtual void set_varying (tree type
) override
;
497 virtual void set_undefined () override
;
498 virtual bool union_ (const vrange
&) override
;
499 virtual bool intersect (const vrange
&) override
;
500 bool contains_p (const REAL_VALUE_TYPE
&) const;
501 virtual bool singleton_p (tree
*result
= NULL
) const override
;
502 bool singleton_p (REAL_VALUE_TYPE
&r
) const;
503 virtual bool supports_type_p (const_tree type
) const override
;
504 virtual void accept (const vrange_visitor
&v
) const override
;
505 virtual bool zero_p () const override
;
506 virtual bool nonzero_p () const override
;
507 virtual void set_nonzero (tree type
) override
;
508 virtual void set_zero (tree type
) override
;
509 virtual void set_nonnegative (tree type
) override
;
510 frange
& operator= (const frange
&);
511 bool operator== (const frange
&) const;
512 bool operator!= (const frange
&r
) const { return !(*this == r
); }
513 const REAL_VALUE_TYPE
&lower_bound () const;
514 const REAL_VALUE_TYPE
&upper_bound () const;
515 nan_state
get_nan_state () const;
517 void update_nan (bool sign
);
518 void update_nan (tree
) = delete; // Disallow silent conversion to bool.
519 void update_nan (const nan_state
&);
521 void flush_denormals_to_zero ();
523 // fpclassify like API
524 bool known_isfinite () const;
525 bool known_isnan () const;
526 bool known_isinf () const;
527 bool maybe_isnan () const;
528 bool maybe_isnan (bool sign
) const;
529 bool maybe_isinf () const;
530 bool signbit_p (bool &signbit
) const;
531 bool nan_signbit_p (bool &signbit
) const;
534 virtual bool contains_p (tree cst
) const override
;
535 virtual void set (tree
, tree
, value_range_kind
= VR_RANGE
) override
;
538 bool internal_singleton_p (REAL_VALUE_TYPE
* = NULL
) const;
539 void verify_range ();
540 bool normalize_kind ();
541 bool union_nans (const frange
&);
542 bool intersect_nans (const frange
&);
543 bool combine_zeros (const frange
&, bool union_p
);
546 REAL_VALUE_TYPE m_min
;
547 REAL_VALUE_TYPE m_max
;
552 inline const REAL_VALUE_TYPE
&
553 frange::lower_bound () const
555 gcc_checking_assert (!undefined_p () && !known_isnan ());
559 inline const REAL_VALUE_TYPE
&
560 frange::upper_bound () const
562 gcc_checking_assert (!undefined_p () && !known_isnan ());
566 // Return the NAN state.
569 frange::get_nan_state () const
571 return nan_state (m_pos_nan
, m_neg_nan
);
574 // is_a<> and as_a<> implementation for vrange.
576 // Anything we haven't specialized is a hard fail.
577 template <typename T
>
585 template <typename T
>
587 is_a (const vrange
&v
)
589 // Reuse is_a <vrange> to implement the const version.
590 const T
&derived
= static_cast<const T
&> (v
);
591 return is_a
<T
> (const_cast<T
&> (derived
));
594 template <typename T
>
598 gcc_checking_assert (is_a
<T
> (v
));
599 return static_cast <T
&> (v
);
602 template <typename T
>
604 as_a (const vrange
&v
)
606 gcc_checking_assert (is_a
<T
> (v
));
607 return static_cast <const T
&> (v
);
610 // Specializations for the different range types.
614 is_a
<irange
> (vrange
&v
)
616 return v
.m_discriminator
== VR_IRANGE
;
621 is_a
<frange
> (vrange
&v
)
623 return v
.m_discriminator
== VR_FRANGE
;
628 is_a
<unsupported_range
> (vrange
&v
)
630 return v
.m_discriminator
== VR_UNKNOWN
;
633 // For resizable ranges, resize the range up to HARD_MAX_RANGES if the
634 // NEEDED pairs is greater than the current capacity of the range.
637 irange::maybe_resize (int needed
)
639 if (!m_resizable
|| m_max_ranges
== HARD_MAX_RANGES
)
642 if (needed
> m_max_ranges
)
644 m_max_ranges
= HARD_MAX_RANGES
;
645 wide_int
*newmem
= new wide_int
[m_max_ranges
* 2];
646 unsigned n
= num_pairs () * 2;
647 for (unsigned i
= 0; i
< n
; ++i
)
648 newmem
[i
] = m_base
[i
];
653 template<unsigned N
, bool RESIZABLE
>
655 int_range
<N
, RESIZABLE
>::~int_range ()
657 if (RESIZABLE
&& m_base
!= m_ranges
)
661 // This is an "infinite" precision irange for use in temporary
662 // calculations. It starts with a sensible default covering 99% of
663 // uses, and goes up to HARD_MAX_RANGES when needed. Any allocated
664 // storage is freed upon destruction.
665 typedef int_range
<3, /*RESIZABLE=*/true> int_range_max
;
670 virtual void visit (const irange
&) const { }
671 virtual void visit (const frange
&) const { }
672 virtual void visit (const unsupported_range
&) const { }
675 typedef int_range
<2> value_range
;
677 // This is an "infinite" precision range object for use in temporary
678 // calculations for any of the handled types. The object can be
679 // transparently used as a vrange.
685 Value_Range (const vrange
&r
);
686 Value_Range (tree type
);
687 Value_Range (tree
, tree
, value_range_kind kind
= VR_RANGE
);
688 Value_Range (const Value_Range
&);
689 void set_type (tree type
);
690 vrange
& operator= (const vrange
&);
691 Value_Range
& operator= (const Value_Range
&);
692 bool operator== (const Value_Range
&r
) const;
693 bool operator!= (const Value_Range
&r
) const;
695 operator const vrange
&() const;
696 void dump (FILE *) const;
697 static bool supports_type_p (const_tree type
);
699 // Convenience methods for vrange compatibility.
700 tree
type () { return m_vrange
->type (); }
701 bool varying_p () const { return m_vrange
->varying_p (); }
702 bool undefined_p () const { return m_vrange
->undefined_p (); }
703 void set_varying (tree type
) { init (type
); m_vrange
->set_varying (type
); }
704 void set_undefined () { m_vrange
->set_undefined (); }
705 bool union_ (const vrange
&r
) { return m_vrange
->union_ (r
); }
706 bool intersect (const vrange
&r
) { return m_vrange
->intersect (r
); }
707 bool contains_p (tree cst
) const { return m_vrange
->contains_p (cst
); }
708 bool singleton_p (tree
*result
= NULL
) const
709 { return m_vrange
->singleton_p (result
); }
710 void set_zero (tree type
) { init (type
); return m_vrange
->set_zero (type
); }
711 void set_nonzero (tree type
)
712 { init (type
); return m_vrange
->set_nonzero (type
); }
713 bool nonzero_p () const { return m_vrange
->nonzero_p (); }
714 bool zero_p () const { return m_vrange
->zero_p (); }
715 wide_int
lower_bound () const; // For irange/prange comparability.
716 wide_int
upper_bound () const; // For irange/prange comparability.
717 void accept (const vrange_visitor
&v
) const { m_vrange
->accept (v
); }
719 void init (tree type
);
720 unsupported_range m_unsupported
;
722 int_range_max m_irange
;
727 Value_Range::Value_Range ()
729 m_vrange
= &m_unsupported
;
732 // Copy constructor from a vrange.
735 Value_Range::Value_Range (const vrange
&r
)
740 // Copy constructor from a TYPE. The range of the temporary is set to
744 Value_Range::Value_Range (tree type
)
750 Value_Range::Value_Range (tree min
, tree max
, value_range_kind kind
)
752 init (TREE_TYPE (min
));
753 m_vrange
->set (min
, max
, kind
);
757 Value_Range::Value_Range (const Value_Range
&r
)
762 // Initialize object so it is possible to store temporaries of TYPE
766 Value_Range::init (tree type
)
768 gcc_checking_assert (TYPE_P (type
));
770 if (irange::supports_p (type
))
771 m_vrange
= &m_irange
;
772 else if (frange::supports_p (type
))
773 m_vrange
= &m_frange
;
775 m_vrange
= &m_unsupported
;
778 // Set the temporary to allow storing temporaries of TYPE. The range
779 // of the temporary is set to UNDEFINED.
782 Value_Range::set_type (tree type
)
785 m_vrange
->set_undefined ();
788 // Assignment operator for temporaries. Copying incompatible types is
792 Value_Range::operator= (const vrange
&r
)
794 if (is_a
<irange
> (r
))
796 m_irange
= as_a
<irange
> (r
);
797 m_vrange
= &m_irange
;
799 else if (is_a
<frange
> (r
))
801 m_frange
= as_a
<frange
> (r
);
802 m_vrange
= &m_frange
;
804 else if (is_a
<unsupported_range
> (r
))
806 m_unsupported
= as_a
<unsupported_range
> (r
);
807 m_vrange
= &m_unsupported
;
816 Value_Range::operator= (const Value_Range
&r
)
818 if (r
.m_vrange
== &r
.m_irange
)
820 m_irange
= r
.m_irange
;
821 m_vrange
= &m_irange
;
823 else if (r
.m_vrange
== &r
.m_frange
)
825 m_frange
= r
.m_frange
;
826 m_vrange
= &m_frange
;
828 else if (r
.m_vrange
== &r
.m_unsupported
)
830 m_unsupported
= r
.m_unsupported
;
831 m_vrange
= &m_unsupported
;
840 Value_Range::operator== (const Value_Range
&r
) const
842 return *m_vrange
== *r
.m_vrange
;
846 Value_Range::operator!= (const Value_Range
&r
) const
848 return *m_vrange
!= *r
.m_vrange
;
852 Value_Range::operator vrange
&()
858 Value_Range::operator const vrange
&() const
863 // Return TRUE if TYPE is supported by the vrange infrastructure.
866 Value_Range::supports_type_p (const_tree type
)
868 return irange::supports_p (type
) || frange::supports_p (type
);
871 extern value_range_kind
get_legacy_range (const irange
&, tree
&min
, tree
&max
);
872 extern void dump_value_range (FILE *, const vrange
*);
873 extern bool vrp_operand_equal_p (const_tree
, const_tree
);
874 inline REAL_VALUE_TYPE
frange_val_min (const_tree type
);
875 inline REAL_VALUE_TYPE
frange_val_max (const_tree type
);
877 // Number of sub-ranges in a range.
880 irange::num_pairs () const
886 irange::type () const
888 gcc_checking_assert (m_num_ranges
> 0);
893 irange::varying_compatible_p () const
895 if (m_num_ranges
!= 1)
898 const wide_int
&l
= m_base
[0];
899 const wide_int
&u
= m_base
[1];
902 if (m_kind
== VR_VARYING
&& t
== error_mark_node
)
905 unsigned prec
= TYPE_PRECISION (t
);
906 signop sign
= TYPE_SIGN (t
);
907 if (INTEGRAL_TYPE_P (t
) || POINTER_TYPE_P (t
))
908 return (l
== wi::min_value (prec
, sign
)
909 && u
== wi::max_value (prec
, sign
)
910 && m_bitmask
.unknown_p ());
915 vrange::varying_p () const
917 return m_kind
== VR_VARYING
;
921 vrange::undefined_p () const
923 return m_kind
== VR_UNDEFINED
;
927 irange::zero_p () const
929 return (m_kind
== VR_RANGE
&& m_num_ranges
== 1
930 && lower_bound (0) == 0
931 && upper_bound (0) == 0);
935 irange::nonzero_p () const
940 wide_int zero
= wi::zero (TYPE_PRECISION (type ()));
941 return *this == int_range
<2> (type (), zero
, zero
, VR_ANTI_RANGE
);
945 irange::supports_p (const_tree type
)
947 return INTEGRAL_TYPE_P (type
) || POINTER_TYPE_P (type
);
951 irange::contains_p (tree cst
) const
953 return contains_p (wi::to_wide (cst
));
957 range_includes_zero_p (const irange
*vr
)
959 if (vr
->undefined_p ())
962 if (vr
->varying_p ())
965 wide_int zero
= wi::zero (TYPE_PRECISION (vr
->type ()));
966 return vr
->contains_p (zero
);
969 extern void gt_ggc_mx (vrange
*);
970 extern void gt_pch_nx (vrange
*);
971 extern void gt_pch_nx (vrange
*, gt_pointer_operator
, void *);
972 extern void gt_ggc_mx (irange
*);
973 extern void gt_pch_nx (irange
*);
974 extern void gt_pch_nx (irange
*, gt_pointer_operator
, void *);
975 extern void gt_ggc_mx (frange
*);
976 extern void gt_pch_nx (frange
*);
977 extern void gt_pch_nx (frange
*, gt_pointer_operator
, void *);
981 gt_ggc_mx (int_range
<N
> *x
)
983 gt_ggc_mx ((irange
*) x
);
988 gt_pch_nx (int_range
<N
> *x
)
990 gt_pch_nx ((irange
*) x
);
995 gt_pch_nx (int_range
<N
> *x
, gt_pointer_operator op
, void *cookie
)
997 gt_pch_nx ((irange
*) x
, op
, cookie
);
1000 // Constructors for irange
1003 irange::irange (wide_int
*base
, unsigned nranges
, bool resizable
)
1004 : vrange (VR_IRANGE
),
1005 m_resizable (resizable
),
1006 m_max_ranges (nranges
)
1012 // Constructors for int_range<>.
1014 template<unsigned N
, bool RESIZABLE
>
1016 int_range
<N
, RESIZABLE
>::int_range ()
1017 : irange (m_ranges
, N
, RESIZABLE
)
1021 template<unsigned N
, bool RESIZABLE
>
1022 int_range
<N
, RESIZABLE
>::int_range (const int_range
&other
)
1023 : irange (m_ranges
, N
, RESIZABLE
)
1025 irange::operator= (other
);
1028 template<unsigned N
, bool RESIZABLE
>
1029 int_range
<N
, RESIZABLE
>::int_range (tree min
, tree max
, value_range_kind kind
)
1030 : irange (m_ranges
, N
, RESIZABLE
)
1032 irange::set (min
, max
, kind
);
1035 template<unsigned N
, bool RESIZABLE
>
1036 int_range
<N
, RESIZABLE
>::int_range (tree type
)
1037 : irange (m_ranges
, N
, RESIZABLE
)
1042 template<unsigned N
, bool RESIZABLE
>
1043 int_range
<N
, RESIZABLE
>::int_range (tree type
, const wide_int
&wmin
, const wide_int
&wmax
,
1044 value_range_kind kind
)
1045 : irange (m_ranges
, N
, RESIZABLE
)
1047 set (type
, wmin
, wmax
, kind
);
1050 template<unsigned N
, bool RESIZABLE
>
1051 int_range
<N
, RESIZABLE
>::int_range (const irange
&other
)
1052 : irange (m_ranges
, N
, RESIZABLE
)
1054 irange::operator= (other
);
1057 template<unsigned N
, bool RESIZABLE
>
1058 int_range
<N
, RESIZABLE
>&
1059 int_range
<N
, RESIZABLE
>::operator= (const int_range
&src
)
1061 irange::operator= (src
);
1066 irange::set_undefined ()
1068 m_kind
= VR_UNDEFINED
;
1073 irange::set_varying (tree type
)
1075 m_kind
= VR_VARYING
;
1077 m_bitmask
.set_unknown (TYPE_PRECISION (type
));
1079 if (INTEGRAL_TYPE_P (type
) || POINTER_TYPE_P (type
))
1082 // Strict enum's require varying to be not TYPE_MIN/MAX, but rather
1083 // min_value and max_value.
1084 m_base
[0] = wi::min_value (TYPE_PRECISION (type
), TYPE_SIGN (type
));
1085 m_base
[1] = wi::max_value (TYPE_PRECISION (type
), TYPE_SIGN (type
));
1088 m_type
= error_mark_node
;
1091 // Return the lower bound of a sub-range. PAIR is the sub-range in
1095 irange::lower_bound (unsigned pair
) const
1097 gcc_checking_assert (m_num_ranges
> 0);
1098 gcc_checking_assert (pair
+ 1 <= num_pairs ());
1099 return m_base
[pair
* 2];
1102 // Return the upper bound of a sub-range. PAIR is the sub-range in
1106 irange::upper_bound (unsigned pair
) const
1108 gcc_checking_assert (m_num_ranges
> 0);
1109 gcc_checking_assert (pair
+ 1 <= num_pairs ());
1110 return m_base
[pair
* 2 + 1];
1113 // Return the highest bound of a range.
1116 irange::upper_bound () const
1118 unsigned pairs
= num_pairs ();
1119 gcc_checking_assert (pairs
> 0);
1120 return upper_bound (pairs
- 1);
1123 // Set value range VR to a nonzero range of type TYPE.
1126 irange::set_nonzero (tree type
)
1128 unsigned prec
= TYPE_PRECISION (type
);
1130 if (TYPE_UNSIGNED (type
))
1134 m_base
[0] = wi::one (prec
);
1135 m_base
[1] = wi::minus_one (prec
);
1136 m_bitmask
.set_unknown (prec
);
1144 wide_int zero
= wi::zero (prec
);
1145 set (type
, zero
, zero
, VR_ANTI_RANGE
);
1149 // Set value range VR to a ZERO range of type TYPE.
1152 irange::set_zero (tree type
)
1154 wide_int zero
= wi::zero (TYPE_PRECISION (type
));
1155 set (type
, zero
, zero
);
1158 // Normalize a range to VARYING or UNDEFINED if possible.
1161 irange::normalize_kind ()
1163 if (m_num_ranges
== 0)
1165 else if (varying_compatible_p ())
1167 if (m_kind
== VR_RANGE
)
1168 m_kind
= VR_VARYING
;
1169 else if (m_kind
== VR_ANTI_RANGE
)
1177 contains_zero_p (const irange
&r
)
1179 if (r
.undefined_p ())
1182 wide_int zero
= wi::zero (TYPE_PRECISION (r
.type ()));
1183 return r
.contains_p (zero
);
1187 irange_val_min (const_tree type
)
1189 gcc_checking_assert (irange::supports_p (type
));
1190 return wi::min_value (TYPE_PRECISION (type
), TYPE_SIGN (type
));
1194 irange_val_max (const_tree type
)
1196 gcc_checking_assert (irange::supports_p (type
));
1197 return wi::max_value (TYPE_PRECISION (type
), TYPE_SIGN (type
));
1202 : vrange (VR_FRANGE
)
1208 frange::frange (const frange
&src
)
1209 : vrange (VR_FRANGE
)
1215 frange::frange (tree type
)
1216 : vrange (VR_FRANGE
)
1221 // frange constructor from REAL_VALUE_TYPE endpoints.
1224 frange::frange (tree type
,
1225 const REAL_VALUE_TYPE
&min
, const REAL_VALUE_TYPE
&max
,
1226 value_range_kind kind
)
1227 : vrange (VR_FRANGE
)
1229 set (type
, min
, max
, kind
);
1232 // frange constructor from trees.
1235 frange::frange (tree min
, tree max
, value_range_kind kind
)
1236 : vrange (VR_FRANGE
)
1238 set (min
, max
, kind
);
1242 frange::type () const
1244 gcc_checking_assert (!undefined_p ());
1249 frange::set_varying (tree type
)
1251 m_kind
= VR_VARYING
;
1253 m_min
= frange_val_min (type
);
1254 m_max
= frange_val_max (type
);
1255 if (HONOR_NANS (m_type
))
1268 frange::set_undefined ()
1270 m_kind
= VR_UNDEFINED
;
1274 // m_min and m_min are uninitialized as they are REAL_VALUE_TYPE ??.
1279 // Set the NAN bits to NAN and adjust the range.
1282 frange::update_nan (const nan_state
&nan
)
1284 gcc_checking_assert (!undefined_p ());
1285 if (HONOR_NANS (m_type
))
1287 m_pos_nan
= nan
.pos_p ();
1288 m_neg_nan
= nan
.neg_p ();
1295 // Set the NAN bit to +-NAN.
1298 frange::update_nan ()
1300 gcc_checking_assert (!undefined_p ());
1301 nan_state
nan (true);
1305 // Like above, but set the sign of the NAN.
1308 frange::update_nan (bool sign
)
1310 gcc_checking_assert (!undefined_p ());
1311 nan_state
nan (/*pos=*/!sign
, /*neg=*/sign
);
1316 frange::contains_p (tree cst
) const
1318 return contains_p (*TREE_REAL_CST_PTR (cst
));
1321 // Clear the NAN bit and adjust the range.
1324 frange::clear_nan ()
1326 gcc_checking_assert (!undefined_p ());
1334 // Set R to maximum representable value for TYPE.
1336 inline REAL_VALUE_TYPE
1337 real_max_representable (const_tree type
)
1341 get_max_float (REAL_MODE_FORMAT (TYPE_MODE (type
)),
1342 buf
, sizeof (buf
), false);
1343 int res
= real_from_string (&r
, buf
);
1344 gcc_checking_assert (!res
);
1348 // Return the minimum representable value for TYPE.
1350 inline REAL_VALUE_TYPE
1351 real_min_representable (const_tree type
)
1353 REAL_VALUE_TYPE r
= real_max_representable (type
);
1354 r
= real_value_negate (&r
);
1358 // Return the minimum value for TYPE.
1360 inline REAL_VALUE_TYPE
1361 frange_val_min (const_tree type
)
1363 if (HONOR_INFINITIES (type
))
1366 return real_min_representable (type
);
1369 // Return the maximum value for TYPE.
1371 inline REAL_VALUE_TYPE
1372 frange_val_max (const_tree type
)
1374 if (HONOR_INFINITIES (type
))
1377 return real_max_representable (type
);
1380 // Return TRUE if R is the minimum value for TYPE.
1383 frange_val_is_min (const REAL_VALUE_TYPE
&r
, const_tree type
)
1385 REAL_VALUE_TYPE min
= frange_val_min (type
);
1386 return real_identical (&min
, &r
);
1389 // Return TRUE if R is the max value for TYPE.
1392 frange_val_is_max (const REAL_VALUE_TYPE
&r
, const_tree type
)
1394 REAL_VALUE_TYPE max
= frange_val_max (type
);
1395 return real_identical (&max
, &r
);
1398 // Build a NAN with a state of NAN.
1401 frange::set_nan (tree type
, const nan_state
&nan
)
1403 gcc_checking_assert (nan
.pos_p () || nan
.neg_p ());
1404 if (HONOR_NANS (type
))
1408 m_neg_nan
= nan
.neg_p ();
1409 m_pos_nan
= nan
.pos_p ();
1417 // Build a signless NAN of type TYPE.
1420 frange::set_nan (tree type
)
1422 nan_state
nan (true);
1423 set_nan (type
, nan
);
1426 // Build a NAN of type TYPE with SIGN.
1429 frange::set_nan (tree type
, bool sign
)
1431 nan_state
nan (/*pos=*/!sign
, /*neg=*/sign
);
1432 set_nan (type
, nan
);
1435 // Return TRUE if range is known to be finite.
1438 frange::known_isfinite () const
1440 if (undefined_p () || varying_p () || m_kind
== VR_ANTI_RANGE
)
1442 return (!maybe_isnan () && !real_isinf (&m_min
) && !real_isinf (&m_max
));
1445 // Return TRUE if range may be infinite.
1448 frange::maybe_isinf () const
1450 if (undefined_p () || m_kind
== VR_ANTI_RANGE
|| m_kind
== VR_NAN
)
1454 return real_isinf (&m_min
) || real_isinf (&m_max
);
1457 // Return TRUE if range is known to be the [-INF,-INF] or [+INF,+INF].
1460 frange::known_isinf () const
1462 return (m_kind
== VR_RANGE
1464 && real_identical (&m_min
, &m_max
)
1465 && real_isinf (&m_min
));
1468 // Return TRUE if range is possibly a NAN.
1471 frange::maybe_isnan () const
1475 return m_pos_nan
|| m_neg_nan
;
1478 // Return TRUE if range is possibly a NAN with SIGN.
1481 frange::maybe_isnan (bool sign
) const
1490 // Return TRUE if range is a +NAN or -NAN.
1493 frange::known_isnan () const
1495 return m_kind
== VR_NAN
;
1498 // If the signbit for the range is known, set it in SIGNBIT and return
1502 frange::signbit_p (bool &signbit
) const
1507 // NAN with unknown sign.
1508 if (m_pos_nan
&& m_neg_nan
)
1511 if (!m_pos_nan
&& !m_neg_nan
)
1513 if (m_min
.sign
== m_max
.sign
)
1515 signbit
= m_min
.sign
;
1520 // NAN with known sign.
1521 bool nan_sign
= m_neg_nan
;
1523 || (nan_sign
== m_min
.sign
&& nan_sign
== m_max
.sign
))
1531 // If range has a NAN with a known sign, set it in SIGNBIT and return
1535 frange::nan_signbit_p (bool &signbit
) const
1540 if (m_pos_nan
== m_neg_nan
)
1543 signbit
= m_neg_nan
;
1547 void frange_nextafter (enum machine_mode
, REAL_VALUE_TYPE
&,
1548 const REAL_VALUE_TYPE
&);
1549 void frange_arithmetic (enum tree_code
, tree
, REAL_VALUE_TYPE
&,
1550 const REAL_VALUE_TYPE
&, const REAL_VALUE_TYPE
&,
1551 const REAL_VALUE_TYPE
&);
1553 #endif // GCC_VALUE_RANGE_H