about summary refs log tree commit diff
path: root/math
diff options
context:
space:
mode:
Diffstat (limited to 'math')
-rw-r--r--math/libm-test.inc209
-rw-r--r--math/test-double.h4
-rw-r--r--math/test-float.h4
-rw-r--r--math/test-ldouble.h4
4 files changed, 127 insertions, 94 deletions
diff --git a/math/libm-test.inc b/math/libm-test.inc
index 84104b4a58..6dddf7cf44 100644
--- a/math/libm-test.inc
+++ b/math/libm-test.inc
@@ -34,7 +34,13 @@
    the specifier, not the percent and width arguments,
    e.g. "f".
    PRINTF_XEXPR	   Like PRINTF_EXPR, but print in hexadecimal format.
-   PRINTF_NEXPR Like PRINTF_EXPR, but print nice.  */
+   PRINTF_NEXPR Like PRINTF_EXPR, but print nice.
+   PREFIX A macro which defines the prefix for common macros for the
+   type (i.e LDBL, DBL, or FLT).
+   LIT A function which appends the correct suffix to a literal.
+   TYPE_STR A macro which defines a stringitized name of the type.
+   FTOSTR This macro defines a function similar in type to snprintf
+   which converts a FLOAT to a string.  */
 
 /* This testsuite has currently tests for:
    acos, acosh, asin, asinh, atan, atan2, atanh,
@@ -183,31 +189,74 @@ struct ulp_data
 #define NON_FINITE			0x40000
 #define TEST_SNAN			0x80000
 
+#define __CONCATX(a,b) __CONCAT(a,b)
+
+#define TYPE_MIN __CONCATX (PREFIX, _MIN)
+#define TYPE_TRUE_MIN __CONCATX (PREFIX, _TRUE_MIN)
+#define TYPE_MAX __CONCATX (PREFIX, _MAX)
+#define MIN_EXP __CONCATX (PREFIX, _MIN_EXP)
+#define MAX_EXP __CONCATX (PREFIX, _MAX_EXP)
+#define MANT_DIG __CONCATX (PREFIX, _MANT_DIG)
+
+/* Maximum character buffer to store a stringitized FLOAT value.  */
+#define FSTR_MAX (128)
+
+#if TEST_INLINE
+# define QTYPE_STR "i" TYPE_STR
+#else
+# define QTYPE_STR TYPE_STR
+#endif
+
+/* Format specific test macros.  */
+#define TEST_COND_binary32 (MANT_DIG == 24	\
+			    && MIN_EXP == -125	\
+			    && MAX_EXP == 128)
+
+#define TEST_COND_binary64 (MANT_DIG == 53	\
+			    && MIN_EXP == -1021	\
+			    && MAX_EXP == 1024)
+
+#define TEST_COND_binary128 (MANT_DIG == 113		\
+			     && MIN_EXP == -16381	\
+			     && MAX_EXP == 16384)
+
+#define TEST_COND_ibm128 (MANT_DIG == 106)
+
+#define TEST_COND_intel96 (MANT_DIG == 64	\
+			   && MIN_EXP == -16381	\
+			   && MAX_EXP == 16384)
+
+#define TEST_COND_m68k96 (MANT_DIG == 64	\
+			  && MIN_EXP == -16382	\
+			  && MAX_EXP == 16384)
+
 /* Values underflowing only for float.  */
-#ifdef TEST_FLOAT
+#if TEST_COND_binary32
 # define UNDERFLOW_EXCEPTION_FLOAT	UNDERFLOW_EXCEPTION
 # define UNDERFLOW_EXCEPTION_OK_FLOAT	UNDERFLOW_EXCEPTION_OK
 #else
 # define UNDERFLOW_EXCEPTION_FLOAT	0
 # define UNDERFLOW_EXCEPTION_OK_FLOAT	0
 #endif
+
 /* Values underflowing only for double or types with a larger least
    positive normal value.  */
-#if defined TEST_FLOAT || defined TEST_DOUBLE \
-  || (defined TEST_LDOUBLE && LDBL_MIN_EXP >= DBL_MIN_EXP)
+#if TEST_COND_binary32 || TEST_COND_binary64 || TEST_COND_ibm128
 # define UNDERFLOW_EXCEPTION_DOUBLE	UNDERFLOW_EXCEPTION
 # define UNDERFLOW_EXCEPTION_OK_DOUBLE	UNDERFLOW_EXCEPTION_OK
 #else
 # define UNDERFLOW_EXCEPTION_DOUBLE	0
 # define UNDERFLOW_EXCEPTION_OK_DOUBLE	0
 #endif
+
 /* Values underflowing only for IBM long double or types with a larger least
    positive normal value.  */
-#if defined TEST_FLOAT || (defined TEST_LDOUBLE && LDBL_MIN_EXP > DBL_MIN_EXP)
+#if TEST_COND_binary32 || TEST_COND_ibm128
 # define UNDERFLOW_EXCEPTION_LDOUBLE_IBM	UNDERFLOW_EXCEPTION
 #else
 # define UNDERFLOW_EXCEPTION_LDOUBLE_IBM	0
 #endif
+
 /* Values underflowing on architectures detecting tininess before
    rounding, but not on those detecting tininess after rounding.  */
 #define UNDERFLOW_EXCEPTION_BEFORE_ROUNDING	(TININESS_AFTER_ROUNDING \
@@ -227,36 +276,13 @@ struct ulp_data
 #endif
 
 /* Conditions used by tests generated by gen-auto-libm-tests.c.  */
-#ifdef TEST_FLOAT
-# define TEST_COND_flt_32	1
-#else
-# define TEST_COND_flt_32	0
-#endif
-#if defined TEST_DOUBLE || (defined TEST_LDOUBLE && LDBL_MANT_DIG == 53)
-# define TEST_COND_dbl_64	1
-#else
-# define TEST_COND_dbl_64	0
-#endif
-#if defined TEST_LDOUBLE && LDBL_MANT_DIG == 64 && LDBL_MIN_EXP == -16381
-# define TEST_COND_ldbl_96_intel	1
-#else
-# define TEST_COND_ldbl_96_intel	0
-#endif
-#if defined TEST_LDOUBLE && LDBL_MANT_DIG == 64 && LDBL_MIN_EXP == -16382
-# define TEST_COND_ldbl_96_m68k	1
-#else
-# define TEST_COND_ldbl_96_m68k	0
-#endif
-#if defined TEST_LDOUBLE && LDBL_MANT_DIG == 113
-# define TEST_COND_ldbl_128	1
-#else
-# define TEST_COND_ldbl_128	0
-#endif
-#if defined TEST_LDOUBLE && LDBL_MANT_DIG == 106
-# define TEST_COND_ldbl_128ibm	1
-#else
-# define TEST_COND_ldbl_128ibm	0
-#endif
+#define TEST_COND_flt_32 TEST_COND_binary32
+#define TEST_COND_dbl_64 TEST_COND_binary64
+#define TEST_COND_ldbl_96_intel TEST_COND_intel96
+#define TEST_COND_ldbl_96_m68k  TEST_COND_m68k96
+#define TEST_COND_ldbl_128 TEST_COND_binary128
+#define TEST_COND_ldbl_128ibm TEST_COND_ibm128
+
 #if LONG_MAX == 0x7fffffff
 # define TEST_COND_long32	1
 # define TEST_COND_long64	0
@@ -302,26 +328,15 @@ static int output_max_error;	/* Should the maximal errors printed?  */
 static int output_points;	/* Should the single function results printed?  */
 static int ignore_max_ulp;	/* Should we ignore max_ulp?  */
 
-#define plus_zero	CHOOSE (0.0L, 0.0, 0.0f,	\
-				0.0L, 0.0, 0.0f)
-#define minus_zero	CHOOSE (-0.0L, -0.0, -0.0f,	\
-				-0.0L, -0.0, -0.0f)
-#define plus_infty	CHOOSE (HUGE_VALL, HUGE_VAL, HUGE_VALF, \
-				HUGE_VALL, HUGE_VAL, HUGE_VALF)
-#define minus_infty	CHOOSE (-HUGE_VALL, -HUGE_VAL, -HUGE_VALF,	\
-				-HUGE_VALL, -HUGE_VAL, -HUGE_VALF)
+#define plus_zero	LIT (0.0)
+#define minus_zero	LIT (-0.0)
+#define plus_infty	FUNC (__builtin_inf) ()
+#define minus_infty	-(FUNC (__builtin_inf) ())
 #define qnan_value	FUNC (__builtin_nan) ("")
 #define snan_value	FUNC (__builtin_nans) ("")
-#define max_value	CHOOSE (LDBL_MAX, DBL_MAX, FLT_MAX,	\
-				LDBL_MAX, DBL_MAX, FLT_MAX)
-#define min_value	CHOOSE (LDBL_MIN, DBL_MIN, FLT_MIN,	\
-				LDBL_MIN, DBL_MIN, FLT_MIN)
-#define min_subnorm_value	CHOOSE (LDBL_TRUE_MIN,	\
-					DBL_TRUE_MIN,	\
-					FLT_TRUE_MIN,	\
-					LDBL_TRUE_MIN,	\
-					DBL_TRUE_MIN,	\
-					FLT_TRUE_MIN)
+#define max_value	TYPE_MAX
+#define min_value	TYPE_MIN
+#define min_subnorm_value TYPE_TRUE_MIN
 
 static FLOAT max_error, real_max_error, imag_max_error;
 
@@ -329,23 +344,12 @@ static FLOAT prev_max_error, prev_real_max_error, prev_imag_max_error;
 
 static FLOAT max_valid_error;
 
-#define MANT_DIG CHOOSE (LDBL_MANT_DIG, DBL_MANT_DIG, FLT_MANT_DIG,  \
-			 LDBL_MANT_DIG, DBL_MANT_DIG, FLT_MANT_DIG)
-#define MIN_EXP CHOOSE (LDBL_MIN_EXP, DBL_MIN_EXP, FLT_MIN_EXP,	\
-			LDBL_MIN_EXP, DBL_MIN_EXP, FLT_MIN_EXP)
-#define MAX_EXP CHOOSE (LDBL_MAX_EXP, DBL_MAX_EXP, FLT_MAX_EXP, \
-			LDBL_MAX_EXP, DBL_MAX_EXP, FLT_MAX_EXP)
 /* Sufficient numbers of digits to represent any floating-point value
    unambiguously (for any choice of the number of bits in the first
    hex digit, in the case of TYPE_HEX_DIG).  When used with printf
    formats where the precision counts only digits after the point, 1
    is subtracted from these values. */
-#define TYPE_DECIMAL_DIG CHOOSE (LDBL_DECIMAL_DIG,	\
-				 DBL_DECIMAL_DIG,	\
-				 FLT_DECIMAL_DIG,	\
-				 LDBL_DECIMAL_DIG,	\
-				 DBL_DECIMAL_DIG,	\
-				 FLT_DECIMAL_DIG)
+#define TYPE_DECIMAL_DIG __CONCATX (PREFIX, _DECIMAL_DIG)
 #define TYPE_HEX_DIG ((MANT_DIG + 6) / 4)
 
 /* Compare KEY (a string, with the name of a function) with ULP (a
@@ -428,8 +432,12 @@ print_float (FLOAT f)
   else if (isnan (f))
     printf ("qNaN\n");
   else
-    printf ("% .*" PRINTF_EXPR "  % .*" PRINTF_XEXPR "\n",
-	    TYPE_DECIMAL_DIG - 1, f, TYPE_HEX_DIG - 1, f);
+    {
+      char fstrn[FSTR_MAX], fstrx[FSTR_MAX];
+      FTOSTR (fstrn, FSTR_MAX, "% .*" PRINTF_EXPR, TYPE_DECIMAL_DIG - 1, f);
+      FTOSTR (fstrx, FSTR_MAX, "% .*" PRINTF_XEXPR, TYPE_HEX_DIG - 1, f);
+      printf ("%s  %s\n", fstrn, fstrx);
+    }
 }
 
 /* Should the message print to screen?  This depends on the verbose flag,
@@ -471,11 +479,10 @@ print_function_ulps (const char *function_name, FLOAT ulp)
 {
   if (output_ulps)
     {
+      char ustrn[FSTR_MAX];
+      FTOSTR (ustrn, FSTR_MAX, "%.0" PRINTF_NEXPR, FUNC (ceil) (ulp));
       fprintf (ulps_file, "Function: \"%s\":\n", function_name);
-      fprintf (ulps_file, "%s: %.0" PRINTF_NEXPR "\n",
-	       CHOOSE("ldouble", "double", "float",
-		      "ildouble", "idouble", "ifloat"),
-	       FUNC(ceil) (ulp));
+      fprintf (ulps_file, QTYPE_STR ": %s\n", ustrn);
     }
 }
 
@@ -486,21 +493,20 @@ print_complex_function_ulps (const char *function_name, FLOAT real_ulp,
 {
   if (output_ulps)
     {
+      char fstrn[FSTR_MAX];
       if (real_ulp != 0.0)
 	{
+	  FTOSTR (fstrn, FSTR_MAX, "%.0" PRINTF_NEXPR,
+	            FUNC (ceil) (real_ulp));
 	  fprintf (ulps_file, "Function: Real part of \"%s\":\n", function_name);
-	  fprintf (ulps_file, "%s: %.0" PRINTF_NEXPR "\n",
-		   CHOOSE("ldouble", "double", "float",
-			  "ildouble", "idouble", "ifloat"),
-		   FUNC(ceil) (real_ulp));
+	  fprintf (ulps_file, QTYPE_STR ": %s\n", fstrn);
 	}
       if (imag_ulp != 0.0)
 	{
+	  FTOSTR (fstrn, FSTR_MAX, "%.0" PRINTF_NEXPR,
+	            FUNC (ceil) (imag_ulp));
 	  fprintf (ulps_file, "Function: Imaginary part of \"%s\":\n", function_name);
-	  fprintf (ulps_file, "%s: %.0" PRINTF_NEXPR "\n",
-		   CHOOSE("ldouble", "double", "float",
-			  "ildouble", "idouble", "ifloat"),
-		   FUNC(ceil) (imag_ulp));
+	  fprintf (ulps_file, QTYPE_STR ": %s\n", fstrn);
 	}
 
 
@@ -548,10 +554,12 @@ print_max_error (const char *func_name)
 
   if (print_screen_max_error (ok))
     {
+      char mestr[FSTR_MAX], pmestr[FSTR_MAX];
+      FTOSTR (mestr, FSTR_MAX, "%.0" PRINTF_NEXPR, FUNC (ceil) (max_error));
+      FTOSTR (pmestr, FSTR_MAX, "%.0" PRINTF_NEXPR, FUNC (ceil) (prev_max_error));
       printf ("Maximal error of `%s'\n", func_name);
-      printf (" is      : %.0" PRINTF_NEXPR " ulp\n", FUNC(ceil) (max_error));
-      printf (" accepted: %.0" PRINTF_NEXPR " ulp\n",
-	      FUNC(ceil) (prev_max_error));
+      printf (" is      : %s ulp\n", mestr);
+      printf (" accepted: %s ulp\n", pmestr);
     }
 
   update_stats (ok);
@@ -584,16 +592,22 @@ print_complex_max_error (const char *func_name)
 
   if (print_screen_max_error (ok))
     {
+      char rmestr[FSTR_MAX], prmestr[FSTR_MAX];
+      char imestr[FSTR_MAX], pimestr[FSTR_MAX];
+      FTOSTR (rmestr, FSTR_MAX, "%.0" PRINTF_NEXPR,
+		FUNC (ceil) (real_max_error));
+      FTOSTR (prmestr, FSTR_MAX, "%.0" PRINTF_NEXPR,
+		FUNC (ceil) (prev_real_max_error));
+      FTOSTR (imestr, FSTR_MAX, "%.0" PRINTF_NEXPR,
+		FUNC (ceil) (imag_max_error));
+      FTOSTR (pimestr, FSTR_MAX, "%.0" PRINTF_NEXPR,
+		FUNC (ceil) (prev_imag_max_error));
       printf ("Maximal error of real part of: %s\n", func_name);
-      printf (" is      : %.0" PRINTF_NEXPR " ulp\n",
-	      FUNC(ceil) (real_max_error));
-      printf (" accepted: %.0" PRINTF_NEXPR " ulp\n",
-	      FUNC(ceil) (prev_real_max_error));
+      printf (" is      : %s ulp\n", rmestr);
+      printf (" accepted: %s ulp\n", prmestr);
       printf ("Maximal error of imaginary part of: %s\n", func_name);
-      printf (" is      : %.0" PRINTF_NEXPR " ulp\n",
-	      FUNC(ceil) (imag_max_error));
-      printf (" accepted: %.0" PRINTF_NEXPR " ulp\n",
-	      FUNC(ceil) (prev_imag_max_error));
+      printf (" is      : %s ulp\n", imestr);
+      printf (" accepted: %s ulp\n", pimestr);
     }
 
   update_stats (ok);
@@ -851,10 +865,17 @@ check_float_internal (const char *test_name, FLOAT computed, FLOAT expected,
       print_float (expected);
       if (print_diff)
 	{
-	  printf (" difference: % .*" PRINTF_EXPR "  % .*" PRINTF_XEXPR
-		  "\n", TYPE_DECIMAL_DIG - 1, diff, TYPE_HEX_DIG - 1, diff);
-	  printf (" ulp       : % .4" PRINTF_NEXPR "\n", ulps);
-	  printf (" max.ulp   : % .4" PRINTF_NEXPR "\n", max_ulp);
+	  char dstrn[FSTR_MAX], dstrx[FSTR_MAX];
+	  char ustrn[FSTR_MAX], mustrn[FSTR_MAX];
+	  FTOSTR (dstrn, FSTR_MAX, "% .*" PRINTF_EXPR,
+		  TYPE_DECIMAL_DIG - 1, diff);
+	  FTOSTR (dstrx, FSTR_MAX, "% .*" PRINTF_XEXPR,
+		  TYPE_HEX_DIG - 1, diff);
+	  FTOSTR (ustrn, FSTR_MAX, "% .4" PRINTF_NEXPR, ulps);
+	  FTOSTR (mustrn, FSTR_MAX, "% .4" PRINTF_NEXPR, max_ulp);
+	  printf (" difference: %s  %s\n", dstrn, dstrx);
+	  printf (" ulp       : %s\n", ustrn);
+	  printf (" max.ulp   : %s\n", mustrn);
 	}
     }
   update_stats (ok);
diff --git a/math/test-double.h b/math/test-double.h
index 16b4ce8081..6783b4449c 100644
--- a/math/test-double.h
+++ b/math/test-double.h
@@ -23,3 +23,7 @@
 #define PRINTF_NEXPR "f"
 #define TEST_DOUBLE 1
 #define BUILD_COMPLEX(real, imag) (CMPLX ((real), (imag)))
+#define PREFIX DBL
+#define LIT(x) (x)
+#define TYPE_STR "double"
+#define FTOSTR snprintf
diff --git a/math/test-float.h b/math/test-float.h
index 629f6ee68a..9bb3b84651 100644
--- a/math/test-float.h
+++ b/math/test-float.h
@@ -23,3 +23,7 @@
 #define PRINTF_NEXPR "f"
 #define TEST_FLOAT 1
 #define BUILD_COMPLEX(real, imag) (CMPLXF ((real), (imag)))
+#define PREFIX FLT
+#define TYPE_STR "float"
+#define LIT(x) (x ## f)
+#define FTOSTR snprintf
diff --git a/math/test-ldouble.h b/math/test-ldouble.h
index 481561f1e7..63f5008b95 100644
--- a/math/test-ldouble.h
+++ b/math/test-ldouble.h
@@ -23,3 +23,7 @@
 #define PRINTF_NEXPR "Lf"
 #define TEST_LDOUBLE 1
 #define BUILD_COMPLEX(real, imag) (CMPLXL ((real), (imag)))
+#define PREFIX LDBL
+#define TYPE_STR "ldouble"
+#define LIT(x) (x ## L)
+#define FTOSTR snprintf