GCC Middle and Back End API Reference
value-range.h
Go to the documentation of this file.
1/* Support routines for value ranges.
2 Copyright (C) 2019-2025 Free Software Foundation, Inc.
3 Contributed by Aldy Hernandez <aldyh@redhat.com> and
4 Andrew Macleod <amacleod@redhat.com>.
5
6This file is part of GCC.
7
8GCC is free software; you can redistribute it and/or modify
9it under the terms of the GNU General Public License as published by
10the Free Software Foundation; either version 3, or (at your option)
11any later version.
12
13GCC is distributed in the hope that it will be useful,
14but WITHOUT ANY WARRANTY; without even the implied warranty of
15MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16GNU General Public License for more details.
17
18You should have received a copy of the GNU General Public License
19along with GCC; see the file COPYING3. If not see
20<http://www.gnu.org/licenses/>. */
21
22#ifndef GCC_VALUE_RANGE_H
23#define GCC_VALUE_RANGE_H
24
25class irange;
26
27// Types of value ranges.
29{
30 /* Empty range. */
32 /* Range spans the entire domain. */
34 /* Range is [MIN, MAX]. */
36 /* Range is ~[MIN, MAX]. */
38 /* Range is a NAN. */
40 /* Range is a nice guy. */
42};
43
44// Discriminator between different vrange types.
45
47{
48 // Range holds an integer or pointer.
50 // Pointer range.
52 // Floating point range.
54 // Range holds an unsupported type.
56};
57
58// Abstract class for ranges of any of the supported types.
59//
60// To query what types ranger and the entire ecosystem can support,
61// use value_range::supports_type_p(tree type). This is a static
62// method available independently of any vrange object.
63//
64// To query what a given vrange variant can support, use:
65// irange::supports_p ()
66// frange::supports_p ()
67// etc
68//
69// To query what a range object can support, use:
70// void foo (vrange &v, irange &i, frange &f)
71// {
72// if (v.supports_type_p (type)) ...
73// if (i.supports_type_p (type)) ...
74// if (f.supports_type_p (type)) ...
75// }
76
77class vrange
78{
79 template <typename T> friend bool is_a (vrange &);
80 friend class value_range;
81 friend void streamer_write_vrange (struct output_block *, const vrange &);
82 friend class range_op_handler;
83public:
84 virtual void accept (const class vrange_visitor &v) const = 0;
85 virtual void set (tree, tree, value_range_kind = VR_RANGE) = 0;
86 virtual tree type () const = 0;
87 virtual bool supports_type_p (const_tree type) const = 0;
88 virtual void set_varying (tree type) = 0;
89 virtual void set_undefined () = 0;
90 virtual bool union_ (const vrange &) = 0;
91 virtual bool intersect (const vrange &) = 0;
92 virtual bool singleton_p (tree *result = NULL) const = 0;
93 virtual bool contains_p (tree cst) const = 0;
94 virtual bool zero_p () const = 0;
95 virtual bool nonzero_p () const = 0;
96 virtual void set_nonzero (tree type) = 0;
97 virtual void set_zero (tree type) = 0;
98 virtual void set_nonnegative (tree type) = 0;
99 virtual bool fits_p (const vrange &r) const = 0;
100 virtual ~vrange () { }
101 virtual tree lbound () const = 0;
102 virtual tree ubound () const = 0;
103 virtual void update_bitmask (const class irange_bitmask &);
104 virtual irange_bitmask get_bitmask () const;
105 wide_int get_nonzero_bits () const;
106 void set_nonzero_bits (const wide_int &bits);
107
108 bool varying_p () const;
109 bool undefined_p () const;
110 vrange& operator= (const vrange &);
111 bool operator== (const vrange &) const;
112 bool operator!= (const vrange &r) const { return !(*this == r); }
113 void dump (FILE *) const;
114 virtual void verify_range () const { }
115protected:
117 ENUM_BITFIELD(value_range_kind) m_kind : 8;
119};
120
121namespace inchash
122{
123 extern void add_vrange (const vrange &, hash &, unsigned flags = 0);
124}
125
126// A pair of values representing the known bits in a range. Zero bits
127// in MASK cover constant values. Set bits in MASK cover unknown
128// values. VALUE are the known bits.
129//
130// Set bits in MASK (no meaningful information) must have their
131// corresponding bits in VALUE cleared, as this speeds up union and
132// intersect.
133
135{
136public:
137 irange_bitmask () { /* uninitialized */ }
138 irange_bitmask (unsigned prec) { set_unknown (prec); }
139 irange_bitmask (const wide_int &value, const wide_int &mask);
140 irange_bitmask (tree type, const wide_int &min, const wide_int &max);
141
142 wide_int value () const { return m_value; }
143 wide_int mask () const { return m_mask; }
144 void set_unknown (unsigned prec);
145 bool unknown_p () const;
146 unsigned get_precision () const;
147 void union_ (const irange_bitmask &src);
148 bool intersect (const irange_bitmask &src);
149 bool operator== (const irange_bitmask &src) const;
150 bool operator!= (const irange_bitmask &src) const { return !(*this == src); }
151 void verify_mask () const;
152 void dump (FILE *) const;
153 bool range_from_mask (irange &r, tree type) const;
154
155 bool member_p (const wide_int &val) const;
156
157 // Convenience functions for nonzero bitmask compatibility.
158 wide_int get_nonzero_bits () const;
159 void set_nonzero_bits (const wide_int &bits);
160private:
163};
164
165inline void
167{
168 m_value = wi::zero (prec);
169 m_mask = wi::minus_one (prec);
170 if (flag_checking)
171 verify_mask ();
172}
173
174// Return TRUE if THIS does not have any meaningful information.
175
176inline bool
178{
179 return m_mask == -1;
180}
181
182inline
184{
185 m_value = value;
186 m_mask = mask;
187 if (flag_checking)
188 verify_mask ();
189}
190
191inline unsigned
193{
194 return m_mask.get_precision ();
195}
196
197// The following two functions are meant for backwards compatability
198// with the nonzero bitmask. A cleared bit means the value must be 0.
199// A set bit means we have no information for the bit.
200
201// Return the nonzero bits.
202inline wide_int
204{
205 return m_value | m_mask;
206}
207
208// Set the bitmask to the nonzero bits in BITS.
209inline void
211{
212 m_value = wi::zero (bits.get_precision ());
213 m_mask = bits;
214 if (flag_checking)
215 verify_mask ();
216}
217
218// Return TRUE if val could be a valid value with this bitmask.
219
220inline bool
222{
223 if (unknown_p ())
224 return true;
225 wide_int res = m_mask & val;
226 if (m_value != 0)
227 res |= ~m_mask & m_value;
228 return res == val;
229}
230
231inline bool
233{
234 bool unknown1 = unknown_p ();
235 bool unknown2 = src.unknown_p ();
236 if (unknown1 || unknown2)
237 return unknown1 == unknown2;
238 return m_value == src.m_value && m_mask == src.m_mask;
239}
240
241inline void
243{
244 m_mask = (m_mask | src.m_mask) | (m_value ^ src.m_value);
245 m_value = m_value & src.m_value;
246 if (flag_checking)
247 verify_mask ();
248}
249
250// Return FALSE if the bitmask intersection is undefined.
251
252inline bool
254{
255 // If we have two known bits that are incompatible, the resulting
256 // bit and therefore entire range is undefined. Return FALSE.
257 if (wi::bit_and (~(m_mask | src.m_mask),
258 m_value ^ src.m_value) != 0)
259 return false;
260 else
261 {
262 m_mask = m_mask & src.m_mask;
263 m_value = m_value | src.m_value;
264 }
265 if (flag_checking)
266 verify_mask ();
267 return true;
268}
269
270// An integer range without any storage.
271
272class irange : public vrange
273{
274 friend class irange_storage;
275 friend class vrange_printer;
276public:
277 // In-place setters.
278 void set (tree type, const wide_int &, const wide_int &,
280 virtual void set_nonzero (tree type) override;
281 virtual void set_zero (tree type) override;
282 virtual void set_nonnegative (tree type) override;
283 virtual void set_varying (tree type) override;
284 virtual void set_undefined () override;
285
286 // Range types.
288 virtual bool supports_type_p (const_tree type) const override;
289 virtual tree type () const override;
290
291 // Iteration over sub-ranges.
292 unsigned num_pairs () const;
293 wide_int lower_bound (unsigned = 0) const;
294 wide_int upper_bound (unsigned) const;
296 virtual tree lbound () const override;
297 virtual tree ubound () const override;
298
299 // Predicates.
300 virtual bool zero_p () const override;
301 virtual bool nonzero_p () const override;
302 virtual bool singleton_p (tree *result = NULL) const override;
303 bool singleton_p (wide_int &) const;
304 bool contains_p (const wide_int &) const;
305 bool nonnegative_p () const;
306 bool nonpositive_p () const;
307
308 // In-place operators.
309 virtual bool union_ (const vrange &) override;
310 virtual bool intersect (const vrange &) override;
311 void invert ();
312
313 // Operator overloads.
314 irange& operator= (const irange &);
315 bool operator== (const irange &) const;
316 bool operator!= (const irange &r) const { return !(*this == r); }
317
318 // Misc methods.
319 virtual bool fits_p (const vrange &r) const override;
320 virtual void accept (const vrange_visitor &v) const override;
321
322 virtual void update_bitmask (const class irange_bitmask &) override;
323 virtual irange_bitmask get_bitmask () const override;
324
325 virtual void verify_range () const override;
326protected:
327 void maybe_resize (int needed);
328 virtual void set (tree, tree, value_range_kind = VR_RANGE) override;
329 virtual bool contains_p (tree cst) const override;
330 irange (wide_int *, unsigned nranges, bool resizable);
331
332 // In-place operators.
333 bool irange_contains_p (const irange &) const;
334 bool irange_single_pair_union (const irange &r);
335
337
338
339 // Hard limit on max ranges allowed.
340 static const int HARD_MAX_RANGES = 255;
341private:
342 bool varying_compatible_p () const;
343 bool intersect_bitmask (const irange &r);
344 bool union_bitmask (const irange &r);
346 bool snap_subranges ();
347 bool snap (const wide_int &, const wide_int &, wide_int &, wide_int &,
348 bool &);
349
350 bool intersect (const wide_int& lb, const wide_int& ub);
351 bool union_append (const irange &r);
352 unsigned char m_num_ranges;
354 unsigned char m_max_ranges;
357protected:
359};
360
361// Here we describe an irange with N pairs of ranges. The storage for
362// the pairs is embedded in the class as an array.
363//
364// If RESIZABLE is true, the storage will be resized on the heap when
365// the number of ranges needed goes past N up to a max of
366// HARD_MAX_RANGES. This new storage is freed upon destruction.
367
368template<unsigned N, bool RESIZABLE = false>
369class int_range final : public irange
370{
371public:
373 int_range (tree type, const wide_int &, const wide_int &,
377 int_range (const irange &);
378 ~int_range () final override;
379 int_range& operator= (const int_range &);
380protected:
382private:
384};
385
386class prange final : public vrange
387{
388 friend class prange_storage;
389 friend class vrange_printer;
390public:
391 prange ();
392 prange (const prange &);
393 prange (tree type);
394 prange (tree type, const wide_int &, const wide_int &,
396 static bool supports_p (const_tree type);
397 virtual bool supports_type_p (const_tree type) const final override;
398 virtual void accept (const vrange_visitor &v) const final override;
399 virtual void set_undefined () final override;
400 virtual void set_varying (tree type) final override;
401 virtual void set_nonzero (tree type) final override;
402 virtual void set_zero (tree type) final override;
403 virtual void set_nonnegative (tree type) final override;
404 virtual bool contains_p (tree cst) const final override;
405 virtual bool fits_p (const vrange &v) const final override;
406 virtual bool singleton_p (tree *result = NULL) const final override;
407 virtual bool zero_p () const final override;
408 virtual bool nonzero_p () const final override;
409 virtual void set (tree, tree, value_range_kind = VR_RANGE) final override;
410 virtual tree type () const final override;
411 virtual bool union_ (const vrange &v) final override;
412 virtual bool intersect (const vrange &v) final override;
413 virtual tree lbound () const final override;
414 virtual tree ubound () const final override;
415
416 prange& operator= (const prange &);
417 bool operator== (const prange &) const;
418 void set (tree type, const wide_int &, const wide_int &,
420 void invert ();
421 bool contains_p (const wide_int &) const;
422 wide_int lower_bound () const;
423 wide_int upper_bound () const;
424 virtual void verify_range () const final override;
425 irange_bitmask get_bitmask () const final override;
426 void update_bitmask (const irange_bitmask &) final override;
427protected:
428 bool varying_compatible_p () const;
429
434};
435
436// Unsupported temporaries may be created by ranger before it's known
437// they're unsupported, or by vr_values::get_value_range.
438
440{
441public:
444 {
445 set_undefined ();
446 }
452 void set (tree min, tree, value_range_kind = VR_RANGE) final override;
453 tree type () const final override;
454 bool supports_type_p (const_tree) const final override;
455 void set_varying (tree) final override;
456 void set_undefined () final override;
457 void accept (const vrange_visitor &v) const final override;
458 bool union_ (const vrange &r) final override;
459 bool intersect (const vrange &r) final override;
460 bool singleton_p (tree * = NULL) const final override;
461 bool contains_p (tree) const final override;
462 bool zero_p () const final override;
463 bool nonzero_p () const final override;
464 void set_nonzero (tree type) final override;
465 void set_zero (tree type) final override;
466 void set_nonnegative (tree type) final override;
467 bool fits_p (const vrange &) const final override;
468 unsupported_range& operator= (const unsupported_range &r);
469 tree lbound () const final override;
470 tree ubound () const final override;
471};
472
473// The NAN state as an opaque object.
474
476{
477public:
478 nan_state (bool);
479 nan_state (bool pos_nan, bool neg_nan);
480 bool neg_p () const;
481 bool pos_p () const;
482private:
485};
486
487// Set NAN state to +-NAN if NAN_P is true. Otherwise set NAN state
488// to false.
489
490inline
492{
493 m_pos_nan = nan_p;
494 m_neg_nan = nan_p;
495}
496
497// Constructor initializing the object to +NAN if POS_NAN is set, -NAN
498// if NEG_NAN is set, or +-NAN if both are set. Otherwise POS_NAN and
499// NEG_NAN are clear, and the object cannot be a NAN.
500
501inline
502nan_state::nan_state (bool pos_nan, bool neg_nan)
503{
504 m_pos_nan = pos_nan;
505 m_neg_nan = neg_nan;
506}
507
508// Return if +NAN is possible.
509
510inline bool
512{
513 return m_pos_nan;
514}
515
516// Return if -NAN is possible.
517
518inline bool
520{
521 return m_neg_nan;
522}
523
524// A floating point range.
525//
526// The representation is a type with a couple of endpoints, unioned
527// with the set of { -NAN, +Nan }.
528
529class frange final : public vrange
530{
531 friend class frange_storage;
532 friend class vrange_printer;
533public:
534 frange ();
535 frange (const frange &);
537 frange (tree type);
538 frange (tree type, const REAL_VALUE_TYPE &min, const REAL_VALUE_TYPE &max,
541 {
542 // ?? Decimal floats can have multiple representations for the
543 // same number. Supporting them may be as simple as just
544 // disabling them in singleton_p. No clue.
546 }
547 virtual tree type () const override;
548 void set (tree type, const REAL_VALUE_TYPE &, const REAL_VALUE_TYPE &,
550 void set (tree type, const REAL_VALUE_TYPE &, const REAL_VALUE_TYPE &,
552 void set_nan (tree type);
553 void set_nan (tree type, bool sign);
554 void set_nan (tree type, const nan_state &);
555 virtual void set_varying (tree type) override;
556 virtual void set_undefined () override;
557 virtual bool union_ (const vrange &) override;
558 virtual bool intersect (const vrange &) override;
559 bool contains_p (const REAL_VALUE_TYPE &) const;
560 virtual bool singleton_p (tree *result = NULL) const override;
561 bool singleton_p (REAL_VALUE_TYPE &r) const;
562 virtual bool supports_type_p (const_tree type) const override;
563 virtual void accept (const vrange_visitor &v) const override;
564 virtual bool zero_p () const override;
565 virtual bool nonzero_p () const override;
566 virtual void set_nonzero (tree type) override;
567 virtual void set_zero (tree type) override;
568 virtual void set_nonnegative (tree type) override;
569 virtual bool fits_p (const vrange &) const override;
570 frange& operator= (const frange &);
571 bool operator== (const frange &) const;
572 bool operator!= (const frange &r) const { return !(*this == r); }
573 const REAL_VALUE_TYPE &lower_bound () const;
574 const REAL_VALUE_TYPE &upper_bound () const;
575 virtual tree lbound () const override;
576 virtual tree ubound () const override;
577 nan_state get_nan_state () const;
578 void update_nan ();
579 void update_nan (bool sign);
580 void update_nan (tree) = delete; // Disallow silent conversion to bool.
581 void update_nan (const nan_state &);
582 void clear_nan ();
584
585 // fpclassify like API
586 bool known_isfinite () const;
587 bool known_isnan () const;
588 bool known_isinf () const;
589 bool maybe_isnan () const;
590 bool maybe_isnan (bool sign) const;
591 bool maybe_isinf () const;
592 bool signbit_p (bool &signbit) const;
593 bool nan_signbit_p (bool &signbit) const;
594 bool known_isnormal () const;
595 bool known_isdenormal_or_zero () const;
596 virtual void verify_range () const override;
597protected:
598 virtual bool contains_p (tree cst) const override;
599 virtual void set (tree, tree, value_range_kind = VR_RANGE) override;
600
601private:
603 bool normalize_kind ();
604 bool union_nans (const frange &);
605 bool intersect_nans (const frange &);
606 bool combine_zeros (const frange &, bool union_p);
607
613};
614
615inline const REAL_VALUE_TYPE &
617{
619 return m_min;
620}
621
622inline const REAL_VALUE_TYPE &
624{
626 return m_max;
627}
628
629// Return the NAN state.
630
631inline nan_state
633{
634 return nan_state (m_pos_nan, m_neg_nan);
635}
636
637// is_a<> and as_a<> implementation for vrange.
638
639// Anything we haven't specialized is a hard fail.
640template <typename T>
641inline bool
643{
645 return false;
646}
647
648template <typename T>
649inline bool
650is_a (const vrange &v)
651{
652 // Reuse is_a <vrange> to implement the const version.
653 const T &derived = static_cast<const T &> (v);
654 return is_a <T> (const_cast<T &> (derived));
655}
656
657template <typename T>
658inline T &
660{
662 return static_cast <T &> (v);
663}
664
665template <typename T>
666inline const T &
667as_a (const vrange &v)
668{
670 return static_cast <const T &> (v);
671}
672
673// Specializations for the different range types.
674
675template <>
676inline bool
678{
679 return v.m_discriminator == VR_IRANGE;
680}
681
682template <>
683inline bool
685{
686 return v.m_discriminator == VR_PRANGE;
687}
688
689template <>
690inline bool
692{
693 return v.m_discriminator == VR_FRANGE;
694}
695
696template <>
697inline bool
699{
700 return v.m_discriminator == VR_UNKNOWN;
701}
702
703// For resizable ranges, resize the range up to HARD_MAX_RANGES if the
704// NEEDED pairs is greater than the current capacity of the range.
705
706inline void
708{
710 return;
711
712 if (needed > m_max_ranges)
713 {
715 wide_int *newmem = new wide_int[m_max_ranges * 2];
716 unsigned n = num_pairs () * 2;
717 for (unsigned i = 0; i < n; ++i)
718 newmem[i] = m_base[i];
719 m_base = newmem;
720 }
721}
722
723template<unsigned N, bool RESIZABLE>
724inline
726{
727 if (RESIZABLE && m_base != m_ranges)
728 delete[] m_base;
729}
730
731// This is an "infinite" precision irange for use in temporary
732// calculations. It starts with a sensible default covering 99% of
733// uses, and goes up to HARD_MAX_RANGES when needed. Any allocated
734// storage is freed upon destruction.
735typedef int_range<3, /*RESIZABLE=*/true> int_range_max;
736
738{
739public:
740 virtual void visit (const irange &) const { }
741 virtual void visit (const prange &) const { }
742 virtual void visit (const frange &) const { }
743 virtual void visit (const unsupported_range &) const { }
744};
745
746// This is an "infinite" precision range object for use in temporary
747// calculations for any of the handled types. The object can be
748// transparently used as a vrange.
749//
750// Using any of the various constructors initializes the object
751// appropriately, but the default constructor is uninitialized and
752// must be initialized either with set_type() or by assigning into it.
753//
754// Assigning between incompatible types is allowed. For example if a
755// temporary holds an irange, you can assign an frange into it, and
756// all the right things will happen. However, before passing this
757// object to a function accepting a vrange, the correct type must be
758// set. If it isn't, you can do so with set_type().
759
761{
762public:
763 value_range ();
764 value_range (const vrange &r);
767 value_range (const value_range &);
768 ~value_range ();
769 void set_type (tree type);
770 vrange& operator= (const vrange &);
772 bool operator== (const value_range &r) const;
773 bool operator!= (const value_range &r) const;
774 operator vrange &();
775 operator const vrange &() const;
776 void dump (FILE *) const;
777 static bool supports_type_p (const_tree type);
778
779 tree type () { return m_vrange->type (); }
780 bool varying_p () const { return m_vrange->varying_p (); }
781 bool undefined_p () const { return m_vrange->undefined_p (); }
782 void set_varying (tree type) { init (type); m_vrange->set_varying (type); }
783 void set_undefined () { m_vrange->set_undefined (); }
784 bool union_ (const vrange &r) { return m_vrange->union_ (r); }
785 bool intersect (const vrange &r) { return m_vrange->intersect (r); }
786 bool contains_p (tree cst) const { return m_vrange->contains_p (cst); }
787 bool singleton_p (tree *result = NULL) const
788 { return m_vrange->singleton_p (result); }
789 void set_zero (tree type) { init (type); return m_vrange->set_zero (type); }
791 { init (type); return m_vrange->set_nonzero (type); }
792 bool nonzero_p () const { return m_vrange->nonzero_p (); }
793 bool zero_p () const { return m_vrange->zero_p (); }
794 tree lbound () const { return m_vrange->lbound (); }
795 tree ubound () const { return m_vrange->ubound (); }
796 irange_bitmask get_bitmask () const { return m_vrange->get_bitmask (); }
797 void update_bitmask (const class irange_bitmask &bm)
798 { return m_vrange->update_bitmask (bm); }
799 void accept (const vrange_visitor &v) const { m_vrange->accept (v); }
800 void verify_range () const { m_vrange->verify_range (); }
801private:
802 void init (tree type);
803 void init (const vrange &);
804
814};
815
816// The default constructor is uninitialized and must be initialized
817// with either set_type() or with an assignment into it.
818
819inline
821 : m_buffer ()
822{
823 m_vrange = NULL;
824}
825
826// Copy constructor.
827
828inline
830{
831 init (*r.m_vrange);
832}
833
834// Copy constructor from a vrange.
835
836inline
838{
839 init (r);
840}
841
842// Construct an UNDEFINED range that can hold ranges of TYPE. If TYPE
843// is not supported, default to unsupported_range.
844
845inline
850
851// Construct a range that can hold a range of [MIN, MAX], where MIN
852// and MAX are trees.
853
854inline
856{
857 init (TREE_TYPE (min));
858 m_vrange->set (min, max, kind);
859}
860
861inline
863{
864 if (m_vrange)
865 m_vrange->~vrange ();
866}
867
868// Initialize object to an UNDEFINED range that can hold ranges of
869// TYPE. Clean-up memory if there was a previous object.
870
871inline void
873{
874 if (m_vrange)
875 m_vrange->~vrange ();
876 init (type);
877}
878
879// Initialize object to an UNDEFINED range that can hold ranges of
880// TYPE.
881
882inline void
884{
886
888 m_vrange = new (&m_buffer.ints) int_range_max ();
889 else if (prange::supports_p (type))
890 m_vrange = new (&m_buffer.pointers) prange ();
891 else if (frange::supports_p (type))
892 m_vrange = new (&m_buffer.floats) frange ();
893 else
894 m_vrange = new (&m_buffer.unsupported) unsupported_range ();
895}
896
897// Initialize object with a copy of R.
898
899inline void
901{
902 if (is_a <irange> (r))
904 else if (is_a <prange> (r))
905 m_vrange = new (&m_buffer.pointers) prange (as_a <prange> (r));
906 else if (is_a <frange> (r))
907 m_vrange = new (&m_buffer.floats) frange (as_a <frange> (r));
908 else
909 m_vrange = new (&m_buffer.unsupported)
911}
912
913// Assignment operator. Copying incompatible types is allowed. That
914// is, assigning an frange to an object holding an irange does the
915// right thing.
916
917inline vrange &
919{
920 if (m_vrange)
921 m_vrange->~vrange ();
922 init (r);
923 return *m_vrange;
924}
925
926inline value_range &
928{
929 // No need to call the m_vrange destructor here, as we will do so in
930 // the assignment below.
931 *this = *r.m_vrange;
932 return *this;
933}
934
935inline bool
937{
938 return *m_vrange == *r.m_vrange;
939}
940
941inline bool
943{
944 return *m_vrange != *r.m_vrange;
945}
946
947inline
948value_range::operator vrange &()
949{
950 return *m_vrange;
951}
952
953inline
954value_range::operator const vrange &() const
955{
956 return *m_vrange;
957}
958
959// Return TRUE if TYPE is supported by the vrange infrastructure.
960
961inline bool
968
969extern value_range_kind get_legacy_range (const vrange &, tree &min, tree &max);
970extern void dump_value_range (FILE *, const vrange *);
974
975// Number of sub-ranges in a range.
976
977inline unsigned
979{
980 return m_num_ranges;
981}
982
983inline tree
985{
987 return m_type;
988}
989
990inline bool
992{
993 if (m_num_ranges != 1)
994 return false;
995
996 const wide_int &l = m_base[0];
997 const wide_int &u = m_base[1];
998 tree t = m_type;
999
1000 if (m_kind == VR_VARYING)
1001 return true;
1002
1003 unsigned prec = TYPE_PRECISION (t);
1004 signop sign = TYPE_SIGN (t);
1005 if (INTEGRAL_TYPE_P (t) || POINTER_TYPE_P (t))
1006 return (l == wi::min_value (prec, sign)
1007 && u == wi::max_value (prec, sign)
1008 && m_bitmask.unknown_p ());
1009 return true;
1010}
1011
1012inline bool
1014{
1015 return m_kind == VR_VARYING;
1016}
1017
1018inline bool
1020{
1021 return m_kind == VR_UNDEFINED;
1022}
1023
1024inline bool
1026{
1027 return (m_kind == VR_RANGE && m_num_ranges == 1
1028 && lower_bound (0) == 0
1029 && upper_bound (0) == 0);
1030}
1031
1032inline bool
1034{
1035 if (undefined_p ())
1036 return false;
1037
1038 wide_int zero = wi::zero (TYPE_PRECISION (type ()));
1039 return *this == int_range<2> (type (), zero, zero, VR_ANTI_RANGE);
1040}
1041
1042inline bool
1047
1048inline bool
1050{
1051 return contains_p (wi::to_wide (cst));
1052}
1053
1054inline bool
1056{
1057 if (vr.undefined_p ())
1058 return false;
1059
1060 if (vr.varying_p ())
1061 return true;
1062
1063 return vr.contains_p (build_zero_cst (vr.type ()));
1064}
1065
1066// Constructors for irange
1067
1068inline
1069irange::irange (wide_int *base, unsigned nranges, bool resizable)
1070 : vrange (VR_IRANGE),
1071 m_resizable (resizable),
1072 m_max_ranges (nranges)
1073{
1074 m_base = base;
1075 set_undefined ();
1076}
1077
1078// Constructors for int_range<>.
1079
1080template<unsigned N, bool RESIZABLE>
1081inline
1083 : irange (m_ranges, N, RESIZABLE)
1084{
1085}
1086
1087template<unsigned N, bool RESIZABLE>
1089 : irange (m_ranges, N, RESIZABLE)
1090{
1091 irange::operator= (other);
1092}
1093
1094template<unsigned N, bool RESIZABLE>
1096 : irange (m_ranges, N, RESIZABLE)
1097{
1098 irange::set (min, max, kind);
1099}
1100
1101template<unsigned N, bool RESIZABLE>
1107
1108template<unsigned N, bool RESIZABLE>
1110 value_range_kind kind)
1111 : irange (m_ranges, N, RESIZABLE)
1112{
1113 set (type, wmin, wmax, kind);
1114}
1115
1116template<unsigned N, bool RESIZABLE>
1118 : irange (m_ranges, N, RESIZABLE)
1119{
1120 irange::operator= (other);
1121}
1122
1123template<unsigned N, bool RESIZABLE>
1126{
1127 irange::operator= (src);
1128 return *this;
1129}
1130
1131inline void
1137
1138inline void
1140{
1142 m_num_ranges = 1;
1143 m_bitmask.set_unknown (TYPE_PRECISION (type));
1144
1146 {
1147 m_type = type;
1148 // Strict enum's require varying to be not TYPE_MIN/MAX, but rather
1149 // min_value and max_value.
1152 }
1153 else
1155}
1156
1157// Return the lower bound of a sub-range. PAIR is the sub-range in
1158// question.
1159
1160inline wide_int
1162{
1165 return m_base[pair * 2];
1166}
1167
1168// Return the upper bound of a sub-range. PAIR is the sub-range in
1169// question.
1170
1171inline wide_int
1173{
1176 return m_base[pair * 2 + 1];
1177}
1178
1179// Return the highest bound of a range.
1180
1181inline wide_int
1183{
1184 unsigned pairs = num_pairs ();
1185 gcc_checking_assert (pairs > 0);
1186 return upper_bound (pairs - 1);
1187}
1188
1189// Set value range VR to a nonzero range of type TYPE.
1190
1191inline void
1193{
1194 unsigned prec = TYPE_PRECISION (type);
1195
1196 if (TYPE_UNSIGNED (type))
1197 {
1198 m_type = type;
1199 m_kind = VR_RANGE;
1200 m_base[0] = wi::one (prec);
1201 m_base[1] = wi::minus_one (prec);
1202 m_bitmask.set_unknown (prec);
1203 m_num_ranges = 1;
1204
1205 if (flag_checking)
1206 verify_range ();
1207 }
1208 else
1209 {
1210 wide_int zero = wi::zero (prec);
1211 set (type, zero, zero, VR_ANTI_RANGE);
1212 }
1213}
1214
1215// Set value range VR to a ZERO range of type TYPE.
1216
1217inline void
1219{
1221 set (type, zero, zero);
1222}
1223
1224// Normalize a range to VARYING or UNDEFINED if possible.
1225
1226inline void
1228{
1229 if (m_num_ranges == 0)
1230 set_undefined ();
1231 else if (varying_compatible_p ())
1232 {
1233 if (m_kind == VR_RANGE)
1235 else if (m_kind == VR_ANTI_RANGE)
1236 set_undefined ();
1237 }
1238 if (flag_checking)
1239 verify_range ();
1240}
1241
1242inline bool
1244{
1245 if (r.undefined_p ())
1246 return false;
1247
1248 wide_int zero = wi::zero (TYPE_PRECISION (r.type ()));
1249 return r.contains_p (zero);
1250}
1251
1252inline wide_int
1258
1259inline wide_int
1265
1266inline
1268 : vrange (VR_PRANGE)
1269{
1270 set_undefined ();
1271}
1272
1273inline
1275 : vrange (VR_PRANGE)
1276{
1277 *this = r;
1278}
1279
1280inline
1282 : vrange (VR_PRANGE)
1283{
1284 set_varying (type);
1285}
1286
1287inline
1289 value_range_kind kind)
1290 : vrange (VR_PRANGE)
1291{
1292 set (type, lb, ub, kind);
1293}
1294
1295inline bool
1300
1301inline bool
1303{
1304 return POINTER_TYPE_P (type);
1305}
1306
1307inline void
1312
1313inline void
1315{
1317 m_type = type;
1320 m_bitmask.set_unknown (TYPE_PRECISION (type));
1321
1322 if (flag_checking)
1323 verify_range ();
1324}
1325
1326inline void
1328{
1329 m_kind = VR_RANGE;
1330 m_type = type;
1333 m_bitmask.set_unknown (TYPE_PRECISION (type));
1334
1335 if (flag_checking)
1336 verify_range ();
1337}
1338
1339inline void
1341{
1342 m_kind = VR_RANGE;
1343 m_type = type;
1345 m_min = m_max = zero;
1346 m_bitmask = irange_bitmask (zero, zero);
1347
1348 if (flag_checking)
1349 verify_range ();
1350}
1351
1352inline bool
1354{
1355 return contains_p (wi::to_wide (cst));
1356}
1357
1358inline bool
1360{
1361 return m_kind == VR_RANGE && m_min == 0 && m_max == 0;
1362}
1363
1364inline bool
1366{
1367 return m_kind == VR_RANGE && m_min == 1 && m_max == -1;
1368}
1369
1370inline tree
1372{
1374 return m_type;
1375}
1376
1377inline wide_int
1379{
1381 return m_min;
1382}
1383
1384inline wide_int
1386{
1388 return m_max;
1389}
1390
1391inline bool
1393{
1394 return (!undefined_p ()
1395 && m_min == 0 && m_max == -1 && get_bitmask ().unknown_p ());
1396}
1397
1398inline irange_bitmask
1400{
1401 return m_bitmask;
1402}
1403
1404inline bool
1405prange::fits_p (const vrange &) const
1406{
1407 return true;
1408}
1409
1410
1411inline
1413 : vrange (VR_FRANGE)
1414{
1415 set_undefined ();
1416}
1417
1418inline
1420 : vrange (VR_FRANGE)
1421{
1422 *this = src;
1423}
1424
1425inline
1427 : vrange (VR_FRANGE)
1428{
1429 set_varying (type);
1430}
1431
1432// frange constructor from REAL_VALUE_TYPE endpoints.
1433
1434inline
1436 const REAL_VALUE_TYPE &min, const REAL_VALUE_TYPE &max,
1437 value_range_kind kind)
1438 : vrange (VR_FRANGE)
1439{
1440 set (type, min, max, kind);
1441}
1442
1443// frange constructor from trees.
1444
1445inline
1447 : vrange (VR_FRANGE)
1448{
1449 set (min, max, kind);
1450}
1451
1452inline tree
1454{
1456 return m_type;
1457}
1458
1459inline void
1461{
1463 m_type = type;
1466 if (HONOR_NANS (m_type))
1467 {
1468 m_pos_nan = true;
1469 m_neg_nan = true;
1470 }
1471 else
1472 {
1473 m_pos_nan = false;
1474 m_neg_nan = false;
1475 }
1476}
1477
1478inline void
1480{
1482 m_type = NULL;
1483 m_pos_nan = false;
1484 m_neg_nan = false;
1485 // m_min and m_min are uninitialized as they are REAL_VALUE_TYPE ??.
1486 if (flag_checking)
1487 verify_range ();
1488}
1489
1490// Set the NAN bits to NAN and adjust the range.
1491
1492inline void
1494{
1496 if (HONOR_NANS (m_type))
1497 {
1498 m_pos_nan = nan.pos_p ();
1499 m_neg_nan = nan.neg_p ();
1500 normalize_kind ();
1501 if (flag_checking)
1502 verify_range ();
1503 }
1504}
1505
1506// Set the NAN bit to +-NAN.
1507
1508inline void
1510{
1512 nan_state nan (true);
1513 update_nan (nan);
1514}
1515
1516// Like above, but set the sign of the NAN.
1517
1518inline void
1520{
1522 nan_state nan (/*pos=*/!sign, /*neg=*/sign);
1523 update_nan (nan);
1524}
1525
1526inline bool
1528{
1529 return contains_p (*TREE_REAL_CST_PTR (cst));
1530}
1531
1532// Clear the NAN bit and adjust the range.
1533
1534inline void
1536{
1538 m_pos_nan = false;
1539 m_neg_nan = false;
1540 normalize_kind ();
1541 if (flag_checking)
1542 verify_range ();
1543}
1544
1545// Set R to maximum representable value for TYPE.
1546
1547inline REAL_VALUE_TYPE
1549{
1551 char buf[128];
1553 buf, sizeof (buf), false);
1554 int res = real_from_string (&r, buf);
1555 gcc_checking_assert (!res);
1556 return r;
1557}
1558
1559// Return the minimum representable value for TYPE.
1560
1561inline REAL_VALUE_TYPE
1568
1569// Return the minimum value for TYPE.
1570
1571inline REAL_VALUE_TYPE
1573{
1574 if (HONOR_INFINITIES (type))
1575 return dconstninf;
1576 else
1578}
1579
1580// Return the maximum value for TYPE.
1581
1582inline REAL_VALUE_TYPE
1584{
1585 if (HONOR_INFINITIES (type))
1586 return dconstinf;
1587 else
1589}
1590
1591// Return TRUE if R is the minimum value for TYPE.
1592
1593inline bool
1595{
1597 return real_identical (&min, &r);
1598}
1599
1600// Return TRUE if R is the max value for TYPE.
1601
1602inline bool
1604{
1606 return real_identical (&max, &r);
1607}
1608
1609// Build a NAN with a state of NAN.
1610
1611inline void
1613{
1614 gcc_checking_assert (nan.pos_p () || nan.neg_p ());
1615 if (HONOR_NANS (type))
1616 {
1617 m_kind = VR_NAN;
1618 m_type = type;
1619 m_neg_nan = nan.neg_p ();
1620 m_pos_nan = nan.pos_p ();
1621 if (flag_checking)
1622 verify_range ();
1623 }
1624 else
1625 set_undefined ();
1626}
1627
1628// Build a signless NAN of type TYPE.
1629
1630inline void
1632{
1633 nan_state nan (true);
1634 set_nan (type, nan);
1635}
1636
1637// Build a NAN of type TYPE with SIGN.
1638
1639inline void
1641{
1642 nan_state nan (/*pos=*/!sign, /*neg=*/sign);
1643 set_nan (type, nan);
1644}
1645
1646// Return TRUE if range is known to be finite.
1647
1648inline bool
1650{
1651 if (undefined_p () || varying_p () || m_kind == VR_ANTI_RANGE)
1652 return false;
1653 return (!maybe_isnan () && !real_isinf (&m_min) && !real_isinf (&m_max));
1654}
1655
1656// Return TRUE if range is known to be normal.
1657
1658inline bool
1660{
1661 if (!known_isfinite ())
1662 return false;
1663
1664 machine_mode mode = TYPE_MODE (type ());
1665 return (!real_isdenormal (&m_min, mode) && !real_isdenormal (&m_max, mode)
1666 && !real_iszero (&m_min) && !real_iszero (&m_max)
1667 && (!real_isneg (&m_min) || real_isneg (&m_max)));
1668}
1669
1670// Return TRUE if range is known to be denormal.
1671
1672inline bool
1674{
1675 if (!known_isfinite ())
1676 return false;
1677
1678 machine_mode mode = TYPE_MODE (type ());
1679 return ((real_isdenormal (&m_min, mode) || real_iszero (&m_min))
1680 && (real_isdenormal (&m_max, mode) || real_iszero (&m_max)));
1681}
1682
1683// Return TRUE if range may be infinite.
1684
1685inline bool
1687{
1688 if (undefined_p () || m_kind == VR_ANTI_RANGE || m_kind == VR_NAN)
1689 return false;
1690 if (varying_p ())
1691 return true;
1692 return real_isinf (&m_min) || real_isinf (&m_max);
1693}
1694
1695// Return TRUE if range is known to be the [-INF,-INF] or [+INF,+INF].
1696
1697inline bool
1699{
1700 return (m_kind == VR_RANGE
1701 && !maybe_isnan ()
1702 && real_identical (&m_min, &m_max)
1703 && real_isinf (&m_min));
1704}
1705
1706// Return TRUE if range is possibly a NAN.
1707
1708inline bool
1710{
1711 if (undefined_p ())
1712 return false;
1713 return m_pos_nan || m_neg_nan;
1714}
1715
1716// Return TRUE if range is possibly a NAN with SIGN.
1717
1718inline bool
1719frange::maybe_isnan (bool sign) const
1720{
1721 if (undefined_p ())
1722 return false;
1723 if (sign)
1724 return m_neg_nan;
1725 return m_pos_nan;
1726}
1727
1728// Return TRUE if range is a +NAN or -NAN.
1729
1730inline bool
1732{
1733 return m_kind == VR_NAN;
1734}
1735
1736// If the signbit for the range is known, set it in SIGNBIT and return
1737// TRUE.
1738
1739inline bool
1740frange::signbit_p (bool &signbit) const
1741{
1742 if (undefined_p ())
1743 return false;
1744
1745 // NAN with unknown sign.
1746 if (m_pos_nan && m_neg_nan)
1747 return false;
1748 // No NAN.
1749 if (!m_pos_nan && !m_neg_nan)
1750 {
1751 if (m_min.sign == m_max.sign)
1752 {
1753 signbit = m_min.sign;
1754 return true;
1755 }
1756 return false;
1757 }
1758 // NAN with known sign.
1759 bool nan_sign = m_neg_nan;
1760 if (known_isnan ()
1761 || (nan_sign == m_min.sign && nan_sign == m_max.sign))
1762 {
1763 signbit = nan_sign;
1764 return true;
1765 }
1766 return false;
1767}
1768
1769// If range has a NAN with a known sign, set it in SIGNBIT and return
1770// TRUE.
1771
1772inline bool
1773frange::nan_signbit_p (bool &signbit) const
1774{
1775 if (undefined_p ())
1776 return false;
1777
1778 if (m_pos_nan == m_neg_nan)
1779 return false;
1780
1781 signbit = m_neg_nan;
1782 return true;
1783}
1784
1785void frange_nextafter (enum machine_mode, REAL_VALUE_TYPE &,
1786 const REAL_VALUE_TYPE &);
1788 const REAL_VALUE_TYPE &, const REAL_VALUE_TYPE &,
1789 const REAL_VALUE_TYPE &);
1790
1791// Return true if TYPE1 and TYPE2 are compatible range types.
1792
1793inline bool
1795{
1796 // types_compatible_p requires conversion in both directions to be useless.
1797 // GIMPLE only requires a cast one way in order to be compatible.
1798 // Ranges really only need the sign and precision to be the same.
1799 return (TYPE_PRECISION (type1) == TYPE_PRECISION (type2)
1800 && TYPE_SIGN (type1) == TYPE_SIGN (type2));
1801}
1802#endif // GCC_VALUE_RANGE_H
Definition value-range.h:530
tree m_type
Definition value-range.h:608
void update_nan(tree)=delete
void set(tree type, const REAL_VALUE_TYPE &, const REAL_VALUE_TYPE &, value_range_kind=VR_RANGE)
Definition value-range.cc:916
void update_nan()
Definition value-range.h:1509
void clear_nan()
Definition value-range.h:1535
REAL_VALUE_TYPE m_min
Definition value-range.h:609
bool known_isfinite() const
Definition value-range.h:1649
bool known_isdenormal_or_zero() const
Definition value-range.h:1673
REAL_VALUE_TYPE m_max
Definition value-range.h:610
bool intersect_nans(const frange &)
Definition value-range.cc:1081
bool maybe_isinf() const
Definition value-range.h:1686
bool internal_singleton_p(REAL_VALUE_TYPE *=NULL) const
Definition value-range.cc:1242
bool m_neg_nan
Definition value-range.h:612
bool known_isnormal() const
Definition value-range.h:1659
bool nan_signbit_p(bool &signbit) const
Definition value-range.h:1773
virtual void set_varying(tree type) override
Definition value-range.h:1460
bool m_pos_nan
Definition value-range.h:611
bool known_isnan() const
Definition value-range.h:1731
void flush_denormals_to_zero()
Definition value-range.cc:817
bool union_nans(const frange &)
Definition value-range.cc:1009
virtual void set_undefined() override
Definition value-range.h:1479
bool maybe_isnan() const
Definition value-range.h:1709
bool normalize_kind()
Definition value-range.cc:939
virtual void verify_range() const override
Definition value-range.cc:1297
bool known_isinf() const
Definition value-range.h:1698
const REAL_VALUE_TYPE & upper_bound() const
Definition value-range.h:623
void set_nan(tree type)
Definition value-range.h:1631
friend class vrange_printer
Definition value-range.h:532
frange()
Definition value-range.h:1412
const REAL_VALUE_TYPE & lower_bound() const
Definition value-range.h:616
bool combine_zeros(const frange &, bool union_p)
Definition value-range.cc:977
friend class frange_storage
Definition value-range.h:531
bool signbit_p(bool &signbit) const
Definition value-range.h:1740
bool contains_p(const REAL_VALUE_TYPE &) const
Definition value-range.cc:1203
static bool supports_p(const_tree type)
Definition value-range.h:540
virtual tree type() const override
Definition value-range.h:1453
nan_state get_nan_state() const
Definition value-range.h:632
Definition inchash.h:38
Definition value-range.h:370
wide_int m_ranges[N *2]
Definition value-range.h:383
int_range()
Definition value-range.h:1082
int_range(tree type, const wide_int &, const wide_int &, value_range_kind=VR_RANGE)
Definition value-range.h:1109
int_range(tree type)
Definition value-range.h:1102
int_range(const irange &)
Definition value-range.h:1117
int_range(const int_range &)
Definition value-range.h:1088
int_range & operator=(const int_range &)
Definition value-range.h:1125
~int_range() final override
Definition value-range.h:725
Definition value-range.h:135
irange_bitmask(unsigned prec)
Definition value-range.h:138
void dump(FILE *) const
Definition value-range.cc:381
bool range_from_mask(irange &r, tree type) const
Definition value-range.cc:63
void verify_mask() const
Definition value-range.cc:2639
void set_nonzero_bits(const wide_int &bits)
Definition value-range.h:210
unsigned get_precision() const
Definition value-range.h:192
bool member_p(const wide_int &val) const
Definition value-range.h:221
void set_unknown(unsigned prec)
Definition value-range.h:166
bool unknown_p() const
Definition value-range.h:177
void union_(const irange_bitmask &src)
Definition value-range.h:242
bool operator==(const irange_bitmask &src) const
Definition value-range.h:232
wide_int get_nonzero_bits() const
Definition value-range.h:203
wide_int mask() const
Definition value-range.h:143
bool operator!=(const irange_bitmask &src) const
Definition value-range.h:150
bool intersect(const irange_bitmask &src)
Definition value-range.h:253
irange_bitmask()
Definition value-range.h:137
wide_int m_mask
Definition value-range.h:162
wide_int m_value
Definition value-range.h:161
wide_int value() const
Definition value-range.h:142
Definition value-range.h:273
friend class irange_storage
Definition value-range.h:274
void invert()
Definition value-range.cc:2270
bool union_bitmask(const irange &r)
Definition value-range.cc:2598
virtual bool nonzero_p() const override
Definition value-range.h:1033
virtual bool zero_p() const override
Definition value-range.h:1025
bool m_resizable
Definition value-range.h:353
virtual bool supports_type_p(const_tree type) const override
Definition value-range.cc:486
virtual void set_nonzero(tree type) override
Definition value-range.h:1192
unsigned num_pairs() const
Definition value-range.h:978
unsigned char m_max_ranges
Definition value-range.h:354
virtual bool union_(const vrange &) override
Definition value-range.cc:1850
virtual void set_nonnegative(tree type) override
Definition value-range.cc:500
bool snap(const wide_int &, const wide_int &, wide_int &, wide_int &, bool &)
Definition value-range.cc:2377
void maybe_resize(int needed)
Definition value-range.h:707
bool union_append(const irange &r)
Definition value-range.cc:1812
virtual void set_varying(tree type) override
Definition value-range.h:1139
virtual tree lbound() const override
Definition value-range.cc:2627
bool intersect_bitmask(const irange &r)
Definition value-range.cc:2566
tree m_type
Definition value-range.h:355
virtual bool contains_p(tree cst) const override
Definition value-range.h:1049
virtual bool intersect(const vrange &) override
Definition value-range.cc:2040
bool nonnegative_p() const
Definition value-range.cc:474
virtual irange_bitmask get_bitmask() const override
Definition value-range.cc:2507
wide_int * m_base
Definition value-range.h:358
static const int HARD_MAX_RANGES
Definition value-range.h:340
bool operator==(const irange &) const
Definition value-range.cc:1654
virtual bool fits_p(const vrange &r) const override
Definition value-range.cc:494
void set(tree type, const wide_int &, const wide_int &, value_range_kind=VR_RANGE)
Definition value-range.cc:1530
unsigned char m_num_ranges
Definition value-range.h:352
virtual void accept(const vrange_visitor &v) const override
Definition value-range.cc:146
bool irange_single_pair_union(const irange &r)
Definition value-range.cc:1745
virtual bool singleton_p(tree *result=NULL) const override
Definition value-range.cc:1691
static bool supports_p(const_tree type)
Definition value-range.h:1043
wide_int upper_bound() const
Definition value-range.h:1182
wide_int lower_bound(unsigned=0) const
Definition value-range.h:1161
irange_bitmask m_bitmask
Definition value-range.h:356
virtual void set_undefined() override
Definition value-range.h:1132
virtual tree ubound() const override
Definition value-range.cc:2633
bool nonpositive_p() const
Definition value-range.cc:480
irange & operator=(const irange &)
Definition value-range.cc:1409
friend class vrange_printer
Definition value-range.h:275
virtual void set_zero(tree type) override
Definition value-range.h:1218
virtual void update_bitmask(const class irange_bitmask &) override
Definition value-range.cc:2484
bool contains_p(const wide_int &) const
Definition value-range.cc:1720
bool set_range_from_bitmask()
Definition value-range.cc:2467
bool irange_contains_p(const irange &) const
Definition value-range.cc:1989
bool varying_compatible_p() const
Definition value-range.h:991
virtual tree type() const override
Definition value-range.h:984
void normalize_kind()
Definition value-range.h:1227
bool snap_subranges()
Definition value-range.cc:2428
wide_int upper_bound(unsigned) const
Definition value-range.h:1172
bool operator!=(const irange &r) const
Definition value-range.h:316
irange(wide_int *, unsigned nranges, bool resizable)
Definition value-range.h:1069
virtual void verify_range() const override
Definition value-range.cc:1607
Definition value-range.h:476
bool neg_p() const
Definition value-range.h:519
bool m_neg_nan
Definition value-range.h:484
bool pos_p() const
Definition value-range.h:511
bool m_pos_nan
Definition value-range.h:483
nan_state(bool)
Definition value-range.h:491
Definition value-range.h:387
virtual bool supports_type_p(const_tree type) const final override
Definition value-range.h:1302
wide_int m_min
Definition value-range.h:431
virtual bool intersect(const vrange &v) final override
Definition value-range.cc:645
virtual void set_nonnegative(tree type) final override
Definition value-range.cc:516
void invert()
Definition value-range.cc:725
prange()
Definition value-range.h:1267
virtual void verify_range() const final override
Definition value-range.cc:757
virtual tree lbound() const final override
Definition value-range.cc:593
wide_int upper_bound() const
Definition value-range.h:1385
irange_bitmask get_bitmask() const final override
Definition value-range.h:1399
wide_int m_max
Definition value-range.h:432
virtual bool contains_p(tree cst) const final override
Definition value-range.h:1353
tree m_type
Definition value-range.h:430
bool varying_compatible_p() const
Definition value-range.h:1392
virtual void set_varying(tree type) final override
Definition value-range.h:1314
static bool supports_p(const_tree type)
Definition value-range.h:1296
virtual void set_zero(tree type) final override
Definition value-range.h:1340
wide_int lower_bound() const
Definition value-range.h:1378
virtual bool fits_p(const vrange &v) const final override
Definition value-range.h:1405
virtual bool zero_p() const final override
Definition value-range.h:1359
virtual void set_undefined() final override
Definition value-range.h:1308
void update_bitmask(const irange_bitmask &) final override
Definition value-range.cc:776
virtual void set_nonzero(tree type) final override
Definition value-range.h:1327
virtual bool nonzero_p() const final override
Definition value-range.h:1365
friend class vrange_printer
Definition value-range.h:389
friend class prange_storage
Definition value-range.h:388
virtual bool singleton_p(tree *result=NULL) const final override
Definition value-range.cc:581
virtual tree ubound() const final override
Definition value-range.cc:599
virtual tree type() const final override
Definition value-range.h:1371
virtual void set(tree, tree, value_range_kind=VR_RANGE) final override
Definition value-range.cc:524
virtual bool union_(const vrange &v) final override
Definition value-range.cc:605
irange_bitmask m_bitmask
Definition value-range.h:433
Definition value-range.h:440
unsupported_range & operator=(const unsupported_range &r)
Definition value-range.cc:310
unsupported_range(const unsupported_range &src)
Definition value-range.h:447
unsupported_range()
Definition value-range.h:442
Definition value-range.h:761
void verify_range() const
Definition value-range.h:800
void set_zero(tree type)
Definition value-range.h:789
~value_range()
Definition value-range.h:862
bool undefined_p() const
Definition value-range.h:781
bool contains_p(tree cst) const
Definition value-range.h:786
static bool supports_type_p(const_tree type)
Definition value-range.h:962
void accept(const vrange_visitor &v) const
Definition value-range.h:799
bool nonzero_p() const
Definition value-range.h:792
bool varying_p() const
Definition value-range.h:780
vrange * m_vrange
Definition value-range.h:805
tree type()
Definition value-range.h:779
irange_bitmask get_bitmask() const
Definition value-range.h:796
tree ubound() const
Definition value-range.h:795
value_range()
Definition value-range.h:820
bool intersect(const vrange &r)
Definition value-range.h:785
void update_bitmask(const class irange_bitmask &bm)
Definition value-range.h:797
bool union_(const vrange &r)
Definition value-range.h:784
void set_nonzero(tree type)
Definition value-range.h:790
void set_type(tree type)
Definition value-range.h:872
void set_undefined()
Definition value-range.h:783
bool zero_p() const
Definition value-range.h:793
bool operator!=(const value_range &r) const
Definition value-range.h:942
bool singleton_p(tree *result=NULL) const
Definition value-range.h:787
tree lbound() const
Definition value-range.h:794
void set_varying(tree type)
Definition value-range.h:782
vrange & operator=(const vrange &)
Definition value-range.h:918
union value_range::buffer_type m_buffer
bool operator==(const value_range &r) const
Definition value-range.h:936
void init(tree type)
Definition value-range.h:883
Definition value-range.h:738
virtual void visit(const unsupported_range &) const
Definition value-range.h:743
virtual void visit(const irange &) const
Definition value-range.h:740
virtual void visit(const frange &) const
Definition value-range.h:742
virtual void visit(const prange &) const
Definition value-range.h:741
Definition value-range.h:78
virtual void verify_range() const
Definition value-range.h:114
friend class value_range
Definition value-range.h:80
virtual irange_bitmask get_bitmask() const
Definition value-range.cc:188
vrange(enum value_range_discriminator d)
Definition value-range.h:116
enum value_range_kind m_kind
Definition value-range.h:117
virtual bool singleton_p(tree *result=NULL) const =0
bool operator!=(const vrange &r) const
Definition value-range.h:112
virtual bool supports_type_p(const_tree type) const =0
virtual void set_zero(tree type)=0
virtual bool union_(const vrange &)=0
virtual ~vrange()
Definition value-range.h:100
virtual bool nonzero_p() const =0
friend class range_op_handler
Definition value-range.h:82
virtual bool zero_p() const =0
virtual void set(tree, tree, value_range_kind=VR_RANGE)=0
virtual void set_varying(tree type)=0
bool undefined_p() const
Definition value-range.h:1019
enum value_range_discriminator m_discriminator
Definition value-range.h:118
virtual void set_undefined()=0
virtual bool intersect(const vrange &)=0
virtual void set_nonzero(tree type)=0
virtual void update_bitmask(const class irange_bitmask &)
Definition value-range.cc:183
virtual tree ubound() const =0
friend bool is_a(vrange &)
Definition value-range.h:642
void set_nonzero_bits(const wide_int &bits)
Definition value-range.cc:2545
virtual void set_nonnegative(tree type)=0
virtual void accept(const class vrange_visitor &v) const =0
virtual bool contains_p(tree cst) const =0
vrange & operator=(const vrange &)
Definition value-range.cc:337
virtual tree lbound() const =0
virtual tree type() const =0
void dump(FILE *) const
Definition value-range.cc:370
friend void streamer_write_vrange(struct output_block *, const vrange &)
Definition data-streamer-out.cc:408
wide_int get_nonzero_bits() const
Definition value-range.cc:2555
virtual bool fits_p(const vrange &r) const =0
bool varying_p() const
Definition value-range.h:1013
bool operator==(const vrange &) const
Definition value-range.cc:356
const union tree_node * const_tree
Definition coretypes.h:98
union tree_node * tree
Definition coretypes.h:97
static bool operator!=(cfa_reg &cfa, rtx reg)
Definition dwarf2cfi.cc:1174
static bool operator==(cfa_reg &cfa, rtx reg)
Definition dwarf2cfi.cc:1164
REAL_VALUE_TYPE dconstninf
Definition emit-rtl.cc:114
REAL_VALUE_TYPE dconstinf
Definition emit-rtl.cc:113
void final(rtx_insn *first, FILE *file, int optimize_p)
Definition final.cc:2009
static type_p type(options_p *optsp, bool nested)
Definition gengtype-parse.cc:883
static struct token T
Definition gengtype-parse.cc:45
tree_code
Definition genmatch.cc:1002
#define N
Definition gensupport.cc:202
Definition fold-const.cc:4345
void add_vrange(const vrange &v, inchash::hash &hstate, unsigned int)
Definition value-range.cc:407
wide_int min_value(machine_mode, signop)
Definition rtl.h:2364
hwi_with_prec minus_one(unsigned int)
Definition wide-int.h:2011
hwi_with_prec zero(unsigned int)
Definition wide-int.h:2018
BINARY_FUNCTION bit_and(const T1 &, const T2 &)
wide_int max_value(machine_mode, signop)
Definition rtl.h:2372
tree_to_wide_ref to_wide(const_tree)
Definition tree.h:6559
hwi_with_prec one(unsigned int)
Definition wide-int.h:2025
poly_int< N, C > r
Definition poly-int.h:774
i
Definition poly-int.h:776
static bool maybe_isnan(const frange &op1, const frange &op2)
Definition range-op-float.cc:239
static bool zero_p(const REAL_VALUE_TYPE &lb, const REAL_VALUE_TYPE &ub)
Definition range-op-float.cc:2266
int real_from_string(REAL_VALUE_TYPE *r, const char *str)
Definition real.cc:2011
bool HONOR_NANS(machine_mode m)
Definition real.cc:5517
REAL_VALUE_TYPE real_value_negate(const REAL_VALUE_TYPE *op0)
Definition real.cc:1115
bool real_isneg(const REAL_VALUE_TYPE *r)
Definition real.cc:1280
bool real_isinf(const REAL_VALUE_TYPE *r)
Definition real.cc:1242
static bool real_isdenormal(const REAL_VALUE_TYPE *r)
Definition real.cc:120
bool real_identical(const REAL_VALUE_TYPE *a, const REAL_VALUE_TYPE *b)
Definition real.cc:1312
bool HONOR_INFINITIES(machine_mode m)
Definition real.cc:5558
bool real_iszero(const REAL_VALUE_TYPE *r)
Definition real.cc:1288
void get_max_float(const struct real_format *fmt, char *buf, size_t len, bool norm_max)
Definition real.cc:5455
#define REAL_MODE_FORMAT(MODE)
Definition real.h:183
#define REAL_VALUE_TYPE
Definition real.h:68
signop
Definition signop.h:28
@ UNSIGNED
Definition signop.h:30
Definition lto-streamer.h:709
Definition gengtype.h:218
Definition cse.cc:4127
Definition gengtype.h:252
#define NULL
Definition system.h:50
#define gcc_unreachable()
Definition system.h:841
#define gcc_checking_assert(EXPR)
Definition system.h:821
tree build_zero_cst(tree type)
Definition tree.cc:2780
#define DECIMAL_FLOAT_TYPE_P(TYPE)
Definition tree.h:681
#define TYPE_PRECISION(NODE)
Definition tree.h:2365
#define SCALAR_FLOAT_TYPE_P(TYPE)
Definition tree.h:649
#define TREE_REAL_CST_PTR(NODE)
Definition tree.h:1174
#define TYPE_UNSIGNED(NODE)
Definition tree.h:963
#define TYPE_MODE(NODE)
Definition tree.h:2374
#define TYPE_SIGN(NODE)
Definition tree.h:966
#define POINTER_TYPE_P(TYPE)
Definition tree.h:701
#define TYPE_P(NODE)
Definition tree.h:227
#define TREE_TYPE(NODE)
Definition tree.h:513
#define INTEGRAL_TYPE_P(TYPE)
Definition tree.h:614
#define error_mark_node
Definition tree.h:4536
unsupported_range unsupported
Definition value-range.h:809
buffer_type()
Definition value-range.h:811
prange pointers
Definition value-range.h:810
~buffer_type()
Definition value-range.h:812
frange floats
Definition value-range.h:808
int_range_max ints
Definition value-range.h:807
T & as_a(vrange &v)
Definition value-range.h:659
REAL_VALUE_TYPE frange_val_max(const_tree type)
Definition value-range.h:1583
bool range_includes_zero_p(const vrange &vr)
Definition value-range.h:1055
wide_int irange_val_max(const_tree type)
Definition value-range.h:1260
value_range_kind
Definition value-range.h:29
@ VR_ANTI_RANGE
Definition value-range.h:37
@ VR_RANGE
Definition value-range.h:35
@ VR_LAST
Definition value-range.h:41
@ VR_NAN
Definition value-range.h:39
@ VR_VARYING
Definition value-range.h:33
@ VR_UNDEFINED
Definition value-range.h:31
void dump_value_range(FILE *, const vrange *)
Definition value-range.cc:2646
bool is_a< prange >(vrange &v)
Definition value-range.h:684
bool is_a< unsupported_range >(vrange &v)
Definition value-range.h:698
value_range_discriminator
Definition value-range.h:47
@ VR_UNKNOWN
Definition value-range.h:55
@ VR_IRANGE
Definition value-range.h:49
@ VR_PRANGE
Definition value-range.h:51
@ VR_FRANGE
Definition value-range.h:53
REAL_VALUE_TYPE real_min_representable(const_tree type)
Definition value-range.h:1562
void frange_arithmetic(enum tree_code, tree, REAL_VALUE_TYPE &, const REAL_VALUE_TYPE &, const REAL_VALUE_TYPE &, const REAL_VALUE_TYPE &)
Definition range-op-float.cc:331
int_range< 3, true > int_range_max
Definition value-range.h:735
value_range_kind get_legacy_range(const vrange &, tree &min, tree &max)
Definition value-range.cc:1512
bool is_a< frange >(vrange &v)
Definition value-range.h:691
void frange_nextafter(enum machine_mode, REAL_VALUE_TYPE &, const REAL_VALUE_TYPE &)
Definition range-op-float.cc:298
REAL_VALUE_TYPE real_max_representable(const_tree type)
Definition value-range.h:1548
wide_int irange_val_min(const_tree type)
Definition value-range.h:1253
bool range_compatible_p(tree type1, tree type2)
Definition value-range.h:1794
bool frange_val_is_min(const REAL_VALUE_TYPE &r, const_tree type)
Definition value-range.h:1594
bool contains_zero_p(const irange &r)
Definition value-range.h:1243
bool frange_val_is_max(const REAL_VALUE_TYPE &r, const_tree type)
Definition value-range.h:1603
bool vrp_operand_equal_p(const_tree, const_tree)
Definition value-range.cc:2667
REAL_VALUE_TYPE frange_val_min(const_tree type)
Definition value-range.h:1572
bool is_a< irange >(vrange &v)
Definition value-range.h:677
generic_wide_int< wide_int_storage > wide_int
Definition wide-int.h:343