diff mbox series

have pretty printer include NaN representation

Message ID ca29317f-db53-3bb5-b9ff-8cdad90d243d@gmail.com
State New
Headers show
Series have pretty printer include NaN representation | expand

Commit Message

Martin Sebor July 3, 2018, 10:59 p.m. UTC
The pretty-printer formats NaNs simply as Nan, even though
there is much more to a NaN than than that.  At the very
least, one might like to know if the NaN is signaling or
quiet, negative or positive.  If it's not in a canonical
form, one might also be interested in the significand
and exponent parts.  The attached patch enhances
the pretty printer to include all these details in
its detailed output.

Tested by bootstrapping & regtesting on x86_64-linux.

Martin

Comments

Jeff Law July 4, 2018, 12:04 a.m. UTC | #1
On 07/03/2018 04:59 PM, Martin Sebor wrote:
> The pretty-printer formats NaNs simply as Nan, even though
> there is much more to a NaN than than that.  At the very
> least, one might like to know if the NaN is signaling or
> quiet, negative or positive.  If it's not in a canonical
> form, one might also be interested in the significand
> and exponent parts.  The attached patch enhances
> the pretty printer to include all these details in
> its detailed output.
> 
> Tested by bootstrapping & regtesting on x86_64-linux.
> 
> Martin
> 
> gcc-print-real-cst.diff
> 
> 
> gcc/ChangeLog:
> 
> 	* print-tree.c (print_real_cst): New function.
> 	(print_node_brief): Call it.
> 	(print_node): Ditto.
OK.
jeff
diff mbox series

Patch

gcc/ChangeLog:

	* print-tree.c (print_real_cst): New function.
	(print_node_brief): Call it.
	(print_node): Ditto.

Index: gcc/print-tree.c
===================================================================
--- gcc/print-tree.c	(revision 262312)
+++ gcc/print-tree.c	(working copy)
@@ -52,6 +52,71 @@  dump_addr (FILE *file, const char *prefix, const v
     fprintf (file, "%s" HOST_PTR_PRINTF, prefix, addr);
 }
 
+/* Print to FILE a NODE representing a REAL_CST constant, including
+   Infinity and NaN.  Be verbose when BFRIEF is false.  */
+
+static void
+print_real_cst (FILE *file, const_tree node, bool brief)
+{
+  if (TREE_OVERFLOW (node))
+    fprintf (file, " overflow");
+
+  REAL_VALUE_TYPE d = TREE_REAL_CST (node);
+  if (REAL_VALUE_ISINF (d))
+    fprintf (file,  REAL_VALUE_NEGATIVE (d) ? " -Inf" : " Inf");
+  else if (REAL_VALUE_ISNAN (d))
+    {
+      /* Print a NaN in the format [-][Q|S]NaN[(significand[exponent])]
+	 where significand is a hexadecimal string that starts with
+	 the 0x prefix followed by 0 if the number is not canonical
+	 and a non-zero digit if it is, and exponent is decimal.  */
+      unsigned start = 0;
+      const char *psig = (const char *) d.sig;
+      for (unsigned i = 0; i != sizeof d.sig; ++i)
+	if (psig[i])
+	  {
+	    start = i;
+	    break;
+	  }
+
+      fprintf (file, " %s%sNaN", d.sign ? "-" : "",
+	       d.signalling ? "S" : "Q");
+
+      if (brief)
+	return;
+
+      if (start)
+	fprintf (file, "(0x%s", d.canonical ? "" : "0");
+      else if (d.uexp)
+	fprintf (file, "(%s", d.canonical ? "" : "0");
+      else if (!d.canonical)
+	{
+	  fprintf (file, "(0)");
+	  return;
+	}
+
+      if (psig[start])
+	{
+	  for (unsigned i = start; i != sizeof d.sig; ++i)
+	    if (i == start)
+	      fprintf (file, "%x", psig[i]);
+	    else
+	      fprintf (file, "%02x", psig[i]);
+	}
+
+      if (d.uexp)
+	fprintf (file, "%se%u)", psig[start] ? "," : "", d.uexp);
+      else if (psig[start])
+	fputc (')', file);
+    }
+  else
+    {
+      char string[64];
+      real_to_decimal (string, &d, sizeof (string), 0, 1);
+      fprintf (file, " %s", string);
+    }
+}
+
 /* Print a node in brief fashion, with just the code, address and name.  */
 
 void
@@ -121,24 +186,7 @@  print_node_brief (FILE *file, const char *prefix,
       print_dec (wi::to_wide (node), file, TYPE_SIGN (TREE_TYPE (node)));
     }
   if (TREE_CODE (node) == REAL_CST)
-    {
-      REAL_VALUE_TYPE d;
-
-      if (TREE_OVERFLOW (node))
-	fprintf (file, " overflow");
-
-      d = TREE_REAL_CST (node);
-      if (REAL_VALUE_ISINF (d))
-	fprintf (file,  REAL_VALUE_NEGATIVE (d) ? " -Inf" : " Inf");
-      else if (REAL_VALUE_ISNAN (d))
-	fprintf (file, " Nan");
-      else
-	{
-	  char string[60];
-	  real_to_decimal (string, &d, sizeof (string), 0, 1);
-	  fprintf (file, " %s", string);
-	}
-    }
+    print_real_cst (file, node, true);
   if (TREE_CODE (node) == FIXED_CST)
     {
       FIXED_VALUE_TYPE f;
@@ -730,24 +778,7 @@  print_node (FILE *file, const char *prefix, tree n
 	  break;
 
 	case REAL_CST:
-	  {
-	    REAL_VALUE_TYPE d;
-
-	    if (TREE_OVERFLOW (node))
-	      fprintf (file, " overflow");
-
-	    d = TREE_REAL_CST (node);
-	    if (REAL_VALUE_ISINF (d))
-	      fprintf (file,  REAL_VALUE_NEGATIVE (d) ? " -Inf" : " Inf");
-	    else if (REAL_VALUE_ISNAN (d))
-	      fprintf (file, " Nan");
-	    else
-	      {
-		char string[64];
-		real_to_decimal (string, &d, sizeof (string), 0, 1);
-		fprintf (file, " %s", string);
-	      }
-	  }
+	  print_real_cst (file, node, false);
 	  break;
 
 	case FIXED_CST: