This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
Re: Patch to add missing math tests
- From: "Kaveh R. Ghazi" <ghazi at caip dot rutgers dot edu>
- To: roger at eyesopen dot com
- Cc: gcc-patches at gcc dot gnu dot org
- Date: Sat, 2 Aug 2003 15:25:48 -0400 (EDT)
- Subject: Re: Patch to add missing math tests
- References: <Pine.LNX.4.44.0308020935530.16527-100000@www.eyesopen.com>
> From: Roger Sayle <roger@eyesopen.com>
>
> Yes. It's much better to rationalize the math builtins tests into a
> single file. -1.c and -4.c seemed appropriate when there were ony a
> handful, but as you point out it isn't extensible. And if we're doing
> that we should in theory test for the __builtin_ forms of all GCC's
> builtins (which of course we don't).
>
>
> > 2. We have a similar split between -3.c and -5.c. I don't see a need
> > for two files here either. Although -3.c gets -ffast-math and
> > -5.c doesn't. Was this intentional? The -3.c file seems to link
> > without it.
>
> Again I won't disagree. I think that the original distinction was that
> -3.c performs traditional "constant folding" where all the arguments
> are constant, whilst -5.c performs "algebraic simplification" when the
> result requires only some of the arguments to be constant. This is
> probably reading far too much into it, we tend to just submit a new
> testcase with each new builtin and/or optimization patch so the contents
> of our testsuites reflect the history of changes the compiler rather
> than a structured validation suite, like libstdc++'s testsuite.
>
> I think the -3.c might have originally required -ffast-math, but then
> we reduced requirements later, or more likely my fears that monotonicity
> requirements would eventually force us to only perform compile-time
> evaluation of mathematical functions with -ffast-math.
>
> Another clean-up is that once a link_error/abort testcase doesn't require
> special compiler options it can be moved to gcc.c-torture to run it with
> multiple flags rather than in gcc.dg. We have lots of builtins tests in
> both. I'm not sure if there's a policy or guideline here?
>
> Please feel free to completely reorganize the builtins-*.c tests.
> I've no love lost for any of it.
> Roger
Ok here's the final patch I came up with.
Notes:
1. I added tests for exp(1.0) "e" and atan(1.0) "pi/4". Hopefully
the assumption I made regarding precision and folding comparison
operators holds for all targets. Works for me.
2. I moved one of the tests into gcc.dg/torture. If we decide to zap
these builtins at -O0 as discussed in another thread we can always
wrap the test in __OPTIMIZE__.
Tested on solaris2 via "make check" and installed as obvious.
--Kaveh
2003-08-02 Kaveh R. Ghazi <ghazi@caip.rutgers.edu>
* gcc.dg/builtins-1.c: Add macro helpers. Add missing math
builtins. Move cases from builtins-4.c here.
* gcc.dg/torture/builtin-math-1.c: New test taken from
bits of gcc.dg/builtins-3.c, gcc.dg/builtins-5.c and also some
additional cases.
* gcc.dg/builtins-3.c, gcc.dg/builtins-4.c, gcc.dg/builtins-5.c:
Delete.
diff -rup orig/egcc-CVS20030802/gcc/testsuite/gcc.dg/builtins-1.c egcc-CVS20030802/gcc/testsuite/gcc.dg/builtins-1.c
--- orig/egcc-CVS20030802/gcc/testsuite/gcc.dg/builtins-1.c 2003-05-23 20:01:58.000000000 -0400
+++ egcc-CVS20030802/gcc/testsuite/gcc.dg/builtins-1.c 2003-08-02 14:34:18.631466051 -0400
@@ -1,4 +1,4 @@
-/* Copyright (C) 2002 Free Software Foundation.
+/* Copyright (C) 2002, 2003 Free Software Foundation.
Verify that all the __builtin_ math functions are recognized
by the compiler.
@@ -8,27 +8,51 @@
/* { dg-do compile } */
/* { dg-final { scan-assembler-not "__builtin_" } } */
-double test1(double x) { return __builtin_sqrt(x); }
-double test2(double x) { return __builtin_cos(x); }
-double test3(double x) { return __builtin_sin(x); }
-double test4(double x) { return __builtin_exp(x); }
-double test5(double x) { return __builtin_log(x); }
-double test6(double x) { return __builtin_tan(x); }
-double test7(double x) { return __builtin_atan(x); }
-
-float test1f(float x) { return __builtin_sqrtf(x); }
-float test2f(float x) { return __builtin_cosf(x); }
-float test3f(float x) { return __builtin_sinf(x); }
-float test4f(float x) { return __builtin_expf(x); }
-float test5f(float x) { return __builtin_logf(x); }
-float test6f(float x) { return __builtin_tanf(x); }
-float test7f(float x) { return __builtin_atanf(x); }
-
-long double test1l(long double x) { return __builtin_sqrtl(x); }
-long double test2l(long double x) { return __builtin_cosl(x); }
-long double test3l(long double x) { return __builtin_sinl(x); }
-long double test4l(long double x) { return __builtin_expl(x); }
-long double test5l(long double x) { return __builtin_logl(x); }
-long double test6l(long double x) { return __builtin_tanl(x); }
-long double test7l(long double x) { return __builtin_atanl(x); }
+/* These helper macros ensure we also check the float and long double
+ cases. */
+/* Test FP functions taking void. */
+#define FPTEST0(FN) \
+double test_##FN(void) { return __builtin_##FN(); } \
+float test_##FN##f(void) { return __builtin_##FN##f(); } \
+long double test_##FN##l(void) { return __builtin_##FN##l(); }
+
+/* Test FP functions taking one FP argument. */
+#define FPTEST1(FN) \
+double test_##FN(double x) { return __builtin_##FN(x); } \
+float test_##FN##f(float x) { return __builtin_##FN##f(x); } \
+long double test_##FN##l(long double x) { return __builtin_##FN##l(x); }
+
+/* Test FP functions taking one argument of a supplied type. */
+#define FPTEST1TYPE(FN, TYPE) \
+double test_##FN(TYPE x) { return __builtin_##FN(x); } \
+float test_##FN##f(TYPE x) { return __builtin_##FN##f(x); } \
+long double test_##FN##l(TYPE x) { return __builtin_##FN##l(x); }
+
+/* Test FP functions taking two FP arguments. */
+#define FPTEST2(FN) \
+double test_##FN(double x, double y) { return __builtin_##FN(x, y); } \
+float test_##FN##f(float x, float y) { return __builtin_##FN##f(x, y); } \
+long double test_##FN##l(long double x, long double y) { return __builtin_##FN##l(x, y); }
+
+/* Keep this list sorted alphabetically by function name. */
+FPTEST1 (atan)
+FPTEST2 (atan2)
+FPTEST1 (ceil)
+FPTEST1 (cos)
+FPTEST1 (exp)
+FPTEST1 (fabs)
+FPTEST1 (floor)
+FPTEST2 (fmod)
+FPTEST0 (huge_val)
+FPTEST0 (inf)
+FPTEST1 (log)
+FPTEST1TYPE (nan, char *)
+FPTEST1TYPE (nans, char *)
+FPTEST1 (nearbyint)
+FPTEST2 (pow)
+FPTEST1 (round)
+FPTEST1 (sin)
+FPTEST1 (sqrt)
+FPTEST1 (tan)
+FPTEST1 (trunc)
diff -rup orig/egcc-CVS20030802/gcc/testsuite/gcc.dg/torture/builtin-math-1.c egcc-CVS20030802/gcc/testsuite/gcc.dg/torture/builtin-math-1.c
--- orig/egcc-CVS20030802/gcc/testsuite/gcc.dg/torture/builtin-math-1.c 2003-08-02 14:35:58.813302706 -0400
+++ egcc-CVS20030802/gcc/testsuite/gcc.dg/torture/builtin-math-1.c 2003-08-02 14:35:31.035569472 -0400
@@ -0,0 +1,131 @@
+/* Copyright (C) 2002, 2003 Free Software Foundation.
+
+ Verify that built-in math function constant folding of constant
+ arguments is correctly performed by the compiler.
+
+ Written by Roger Sayle, 16th August 2002. */
+
+/* { dg-do link } */
+
+/* All references to link_error should go away at compile-time. */
+extern void link_error(void);
+
+void test (float f, double d, long double ld)
+{
+ if (sqrt (0.0) != 0.0)
+ link_error ();
+
+ if (sqrt (1.0) != 1.0)
+ link_error ();
+
+ if (exp (0.0) != 1.0)
+ link_error ();
+
+ if (exp (1.0) <= 2.71 || exp (1.0) >= 2.72)
+ link_error ();
+
+ if (log (1.0) != 0.0)
+ link_error ();
+
+ if (sin (0.0) != 0.0)
+ link_error ();
+
+ if (cos (0.0) != 1.0)
+ link_error ();
+
+ if (tan (0.0) != 0.0)
+ link_error ();
+
+ if (atan (0.0) != 0.0)
+ link_error ();
+
+ if (4.0*atan (1.0) <= 3.14 || 4.0*atan (1.0) >= 3.15)
+ link_error ();
+
+ if (pow (d, 0.0) != 1.0)
+ link_error ();
+
+ if (pow (1.0, d) != 1.0)
+ link_error ();
+
+
+ if (sqrtf (0.0F) != 0.0F)
+ link_error ();
+
+ if (sqrtf (1.0F) != 1.0F)
+ link_error ();
+
+ if (expf (0.0F) != 1.0F)
+ link_error ();
+
+ if (expf (1.0F) <= 2.71F || expf (1.0F) >= 2.72F)
+ link_error ();
+
+ if (logf (1.0F) != 0.0F)
+ link_error ();
+
+ if (sinf (0.0F) != 0.0F)
+ link_error ();
+
+ if (cosf (0.0F) != 1.0F)
+ link_error ();
+
+ if (tanf (0.0F) != 0.0F)
+ link_error ();
+
+ if (atanf (0.0F) != 0.0F)
+ link_error ();
+
+ if (4.0F*atanf (1.0F) <= 3.14F || 4.0F*atanf (1.0F) >= 3.15F)
+ link_error ();
+
+ if (powf (f, 0.0F) != 1.0F)
+ link_error ();
+
+ if (powf (1.0F, f) != 1.0F)
+ link_error ();
+
+
+ if (sqrtl (0.0L) != 0.0L)
+ link_error ();
+
+ if (sqrtl (1.0L) != 1.0L)
+ link_error ();
+
+ if (expl (0.0L) != 1.0L)
+ link_error ();
+
+ if (expl (1.0L) <= 2.71L || expl (1.0L) >= 2.72L)
+ link_error ();
+
+ if (logl (1.0L) != 0.0L)
+ link_error ();
+
+ if (sinl (0.0L) != 0.0L)
+ link_error ();
+
+ if (cosl (0.0L) != 1.0L)
+ link_error ();
+
+ if (tanl (0.0L) != 0.0L)
+ link_error ();
+
+ if (atanl (0.0) != 0.0L)
+ link_error ();
+
+ if (4.0L*atanl (1.0L) <= 3.14L || 4.0L*atanl (1.0L) >= 3.15L)
+ link_error ();
+
+ if (powl (ld, 0.0L) != 1.0L)
+ link_error ();
+
+ if (powl (1.0L, ld) != 1.0L)
+ link_error ();
+}
+
+int main()
+{
+ test (3.0, 3.0F, 3.0L);
+
+ return 0;
+}