public inbox for gcc-cvs@sourceware.org
help / color / mirror / Atom feed
From: Aldy Hernandez <aldyh@gcc.gnu.org>
To: gcc-cvs@gcc.gnu.org
Subject: [gcc r13-3104] Setting explicit NANs sets UNDEFINED for -ffinite-math-only.
Date: Thu,  6 Oct 2022 06:23:41 +0000 (GMT)	[thread overview]
Message-ID: <20221006062341.75581383FB98@sourceware.org> (raw)

https://gcc.gnu.org/g:e9d50e7a4e290d7476cc7e6b5a8f2f1fb496c570

commit r13-3104-ge9d50e7a4e290d7476cc7e6b5a8f2f1fb496c570
Author: Aldy Hernandez <aldyh@redhat.com>
Date:   Wed Oct 5 20:22:38 2022 +0200

    Setting explicit NANs sets UNDEFINED for -ffinite-math-only.
    
    We recently agreed that setting a range of NAN should instead set
    UNDEFINED for -ffinite-math-only.  This patch makes that change to
    frange::set_nan() directly.  Also, calling frange::update_nan() will now
    be a nop for !HONOR_NANS.
    
    Doing this in the setters simplifies everywhere we set NANs, as it keeps
    us from introducing NANs by mistake.
    
    gcc/ChangeLog:
    
            * value-range.cc (frange::set): Call set_nan unconditionally.
            (range_tests_nan): Adjust tests.
            (range_tests_signed_zeros): Same.
            (range_tests_floats): Same.
            * value-range.h (frange::update_nan): Guard with HONOR_NANS.
            (frange::set_nan): Set undefined if !HONOR_NANS.

Diff:
---
 gcc/value-range.cc | 59 ++++++++++++++++++++++++++---------------------------
 gcc/value-range.h  | 60 ++++++++++++++++++++++++++++++++++--------------------
 2 files changed, 67 insertions(+), 52 deletions(-)

diff --git a/gcc/value-range.cc b/gcc/value-range.cc
index a307559b654..87239fafa77 100644
--- a/gcc/value-range.cc
+++ b/gcc/value-range.cc
@@ -304,13 +304,8 @@ frange::set (tree type,
   if (real_isnan (&min) || real_isnan (&max))
     {
       gcc_checking_assert (real_identical (&min, &max));
-      if (HONOR_NANS (type))
-	{
-	  bool sign = real_isneg (&min);
-	  set_nan (type, sign);
-	}
-      else
-	set_undefined ();
+      bool sign = real_isneg (&min);
+      set_nan (type, sign);
       return;
     }
 
@@ -3624,6 +3619,7 @@ range_tests_nan ()
 {
   frange r0, r1;
   REAL_VALUE_TYPE q, r;
+  bool signbit;
 
   // Equal ranges but with differing NAN bits are not equal.
   if (HONOR_NANS (float_type_node))
@@ -3735,6 +3731,26 @@ range_tests_nan ()
   r0.set_nan (float_type_node);
   r0.clear_nan ();
   ASSERT_TRUE (r0.undefined_p ());
+
+  // [10,20] NAN ^ [21,25] NAN = [NAN]
+  r0 = frange_float ("10", "20");
+  r0.update_nan ();
+  r1 = frange_float ("21", "25");
+  r1.update_nan ();
+  r0.intersect (r1);
+  ASSERT_TRUE (r0.known_isnan ());
+
+  // NAN U [5,6] should be [5,6] +-NAN.
+  r0.set_nan (float_type_node);
+  r1 = frange_float ("5", "6");
+  r1.clear_nan ();
+  r0.union_ (r1);
+  real_from_string (&q, "5");
+  real_from_string (&r, "6");
+  ASSERT_TRUE (real_identical (&q, &r0.lower_bound ()));
+  ASSERT_TRUE (real_identical (&r, &r0.upper_bound ()));
+  ASSERT_TRUE (!r0.signbit_p (signbit));
+  ASSERT_TRUE (r0.maybe_isnan ());
 }
 
 static void
@@ -3742,7 +3758,6 @@ range_tests_signed_zeros ()
 {
   tree zero = build_zero_cst (float_type_node);
   tree neg_zero = fold_build1 (NEGATE_EXPR, float_type_node, zero);
-  REAL_VALUE_TYPE q, r;
   frange r0, r1;
   bool signbit;
 
@@ -3788,18 +3803,6 @@ range_tests_signed_zeros ()
   r0.intersect (r1);
   ASSERT_TRUE (r0.zero_p ());
 
-  // NAN U [5,6] should be [5,6] NAN.
-  r0.set_nan (float_type_node);
-  r1 = frange_float ("5", "6");
-  r1.clear_nan ();
-  r0.union_ (r1);
-  real_from_string (&q, "5");
-  real_from_string (&r, "6");
-  ASSERT_TRUE (real_identical (&q, &r0.lower_bound ()));
-  ASSERT_TRUE (real_identical (&r, &r0.upper_bound ()));
-  ASSERT_TRUE (!r0.signbit_p (signbit));
-  ASSERT_TRUE (r0.maybe_isnan ());
-
   r0 = frange_float ("+0", "5");
   r0.clear_nan ();
   ASSERT_TRUE (r0.signbit_p (signbit) && !signbit);
@@ -3823,7 +3826,10 @@ range_tests_signed_zeros ()
   r1 = frange_float ("0", "0");
   r1.update_nan ();
   r0.intersect (r1);
-  ASSERT_TRUE (r0.known_isnan ());
+  if (HONOR_NANS (float_type_node))
+    ASSERT_TRUE (r0.known_isnan ());
+  else
+    ASSERT_TRUE (r0.undefined_p ());
 
   r0.set_nonnegative (float_type_node);
   ASSERT_TRUE (r0.signbit_p (signbit) && !signbit);
@@ -3863,7 +3869,8 @@ range_tests_floats ()
 {
   frange r0, r1;
 
-  range_tests_nan ();
+  if (HONOR_NANS (float_type_node))
+    range_tests_nan ();
   range_tests_signbit ();
 
   if (HONOR_SIGNED_ZEROS (float_type_node))
@@ -3936,14 +3943,6 @@ range_tests_floats ()
   r0.intersect (r1);
   ASSERT_EQ (r0, frange_float ("15", "20"));
 
-  // [10,20] NAN ^ [21,25] NAN = [NAN]
-  r0 = frange_float ("10", "20");
-  r0.update_nan ();
-  r1 = frange_float ("21", "25");
-  r1.update_nan ();
-  r0.intersect (r1);
-  ASSERT_TRUE (r0.known_isnan ());
-
   // [10,20] ^ [21,25] = []
   r0 = frange_float ("10", "20");
   r0.clear_nan ();
diff --git a/gcc/value-range.h b/gcc/value-range.h
index d1663620444..b06ca7477cd 100644
--- a/gcc/value-range.h
+++ b/gcc/value-range.h
@@ -1111,11 +1111,14 @@ inline void
 frange::update_nan ()
 {
   gcc_checking_assert (!undefined_p ());
-  m_pos_nan = true;
-  m_neg_nan = true;
-  normalize_kind ();
-  if (flag_checking)
-    verify_range ();
+  if (HONOR_NANS (m_type))
+    {
+      m_pos_nan = true;
+      m_neg_nan = true;
+      normalize_kind ();
+      if (flag_checking)
+	verify_range ();
+    }
 }
 
 // Like above, but set the sign of the NAN.
@@ -1124,11 +1127,14 @@ inline void
 frange::update_nan (bool sign)
 {
   gcc_checking_assert (!undefined_p ());
-  m_pos_nan = !sign;
-  m_neg_nan = sign;
-  normalize_kind ();
-  if (flag_checking)
-    verify_range ();
+  if (HONOR_NANS (m_type))
+    {
+      m_pos_nan = !sign;
+      m_neg_nan = sign;
+      normalize_kind ();
+      if (flag_checking)
+	verify_range ();
+    }
 }
 
 // Clear the NAN bit and adjust the range.
@@ -1213,12 +1219,17 @@ frange_val_is_max (const REAL_VALUE_TYPE &r, const_tree type)
 inline void
 frange::set_nan (tree type)
 {
-  m_kind = VR_NAN;
-  m_type = type;
-  m_pos_nan = true;
-  m_neg_nan = true;
-  if (flag_checking)
-    verify_range ();
+  if (HONOR_NANS (type))
+    {
+      m_kind = VR_NAN;
+      m_type = type;
+      m_pos_nan = true;
+      m_neg_nan = true;
+      if (flag_checking)
+	verify_range ();
+    }
+  else
+    set_undefined ();
 }
 
 // Build a NAN of type TYPE with SIGN.
@@ -1226,12 +1237,17 @@ frange::set_nan (tree type)
 inline void
 frange::set_nan (tree type, bool sign)
 {
-  m_kind = VR_NAN;
-  m_type = type;
-  m_neg_nan = sign;
-  m_pos_nan = !sign;
-  if (flag_checking)
-    verify_range ();
+  if (HONOR_NANS (type))
+    {
+      m_kind = VR_NAN;
+      m_type = type;
+      m_neg_nan = sign;
+      m_pos_nan = !sign;
+      if (flag_checking)
+	verify_range ();
+    }
+  else
+    set_undefined ();
 }
 
 // Return TRUE if range is known to be finite.

                 reply	other threads:[~2022-10-06  6:23 UTC|newest]

Thread overview: [no followups] expand[flat|nested]  mbox.gz  Atom feed

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20221006062341.75581383FB98@sourceware.org \
    --to=aldyh@gcc.gnu.org \
    --cc=gcc-cvs@gcc.gnu.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).