===================================================================
@@ -5294,6 +5294,9 @@ wi::extended_tree <N>::get_len () const
namespace wi
{
template <typename T>
+ bool fits_to_boolean_p (const T &x, const_tree);
+
+ template <typename T>
bool fits_to_tree_p (const T &x, const_tree);
wide_int min_value (const_tree);
@@ -5303,14 +5306,21 @@ namespace wi
template <typename T>
bool
+wi::fits_to_boolean_p (const T &x, const_tree type)
+{
+ return eq_p (x, 0) || eq_p (x, TYPE_UNSIGNED (type) ? 1 : -1);
+}
+
+template <typename T>
+bool
wi::fits_to_tree_p (const T &x, const_tree type)
{
- /* Short-circuit boolean types since various transformations assume that
- they can only take values 0 and 1. */
+ /* Non-standard boolean types can have arbitrary precision but various
+ transformations assume that they can only take values 0 and +/-1. */
if (TREE_CODE (type) == BOOLEAN_TYPE)
- return eq_p (x, 0) || eq_p (x, 1);
+ return fits_to_boolean_p (x, type);
- if (TYPE_SIGN (type) == UNSIGNED)
+ if (TYPE_UNSIGNED (type))
return eq_p (x, zext (x, TYPE_PRECISION (type)));
else
return eq_p (x, sext (x, TYPE_PRECISION (type)));
===================================================================
@@ -9092,10 +9092,10 @@ int_fits_type_p (const_tree c, const_tre
bool ok_for_low_bound, ok_for_high_bound;
signop sgn_c = TYPE_SIGN (TREE_TYPE (c));
- /* Short-circuit boolean types since various transformations assume that
- they can only take values 0 and 1. */
+ /* Non-standard boolean types can have arbitrary precision but various
+ transformations assume that they can only take values 0 and +/-1. */
if (TREE_CODE (type) == BOOLEAN_TYPE)
- return integer_zerop (c) || integer_onep (c);
+ return wi::fits_to_boolean_p (c, type);
retry:
type_low_bound = TYPE_MIN_VALUE (type);