This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: [PATCH]: PR middle-end/29335 use MPFR for cabs, and fold complex sign ops


On 1/23/07, Kaveh R. GHAZI <ghazi@caip.rutgers.edu> wrote:
This patch enhances sign folding for complex math functions, similar to
what we already do for the regular ones.  I also used MPFR for cabs with
constant args.  (Hopefully all of these will be less controversial than
the csin folding...)

Anyway, the details of the changes are listed below:

1.  When cabs has a constant arg, it currently uses the real.c routines to
calculate the result at compile-time using a simplistic sqrt(r*r+i*i).
While this is more accurate than the same calculation in the host float
precision, my understanding is that MPFR goes to extra lengths to ensure
exact results in its hypot routine.  By getting exact results from MPFR,
it also allows me to remove the check on -funsafe-math-optimizations.

One nit is that the MPFR infrastructure I wrote is setup *not* to do the
transformation if the argument (or return value) is Inf or NaN. This is to
avoid having to special-case each c99 function as to how they handle these
values and their signs as well as possibly generating runtime exceptions
and/or errors.  I'd like to keep it that way.

The current cabs hand-calculation allows Inf/NaN only if -fno-traping-math
is used (in addition to -funsafe-math-optimizations as noted above).  My
change stops GCC from compile-time calculating cabs of Inf/NaN under those
circumstances in return for greater accuracy for all other values as well
as not requiring the -f*math* flags.  Hopefully this won't be considered a
big deal.

2.  I changed folding of cabs, which was hand detecting negate or conj
argument, to instead use fold_strip_sign_ops.  This handles many more
cases and is also recursive.

3.  I treat ccos and ccosh as "even" functions, just like we already do
for cos/cosh/fabs and cabs.  This enables them to strip sign ops from
their argument.

4.  I treat casin, casinh, catan, catanh, csin, csinh, ctan and ctanh as
'odd' functions.  This allows various sign stripping opportunities.

5.  I add a few more EXPRs to fold_strip_sign_ops to handle various cases
of complex functions and/or complex arguments.

6.  Finally of course, I add a bunch of wierd testcases to exercise all
these new transformations.

Arguably, #1 is conceptually separate from the rest.  I can split it out
if necessary.  Hopefully not. :-)

Bootstrapped on sparc-sun-solaris2.10 (with --disable-libgcj due to
PR30513) and the libstdc++ testsuite is useless because of the libiconv
problems.  With those caveats, I had no regressions and the new cases all
pass.

Okay for mainline?

This is ok if you are sufficiently sure about the negate_mathfn_p and fold_strip_sign_ops change. I think you should add/change the comments before these functions to document the property they guarantee for complex valued functions.

Thanks,
Richard.

2007-01-21 Kaveh R. Ghazi <ghazi@caip.rutgers.edu>

        * builtins.c (fold_builtin_cabs): Use fold_strip_sign_ops
        instead of manually checking for EXPRs.
        (fold_builtin_1): Treat ccos and ccosh as 'even' functions.

        * fold-const.c (negate_mathfn_p): Treat casin, casinh, catan,
        catanh, csin, csinh, ctan and ctanh as 'odd' functions.
        (fold_strip_sign_ops): Handle CONJ_EXPR, REALPART_EXPR,
        IMAGPART_EXPR and COMPLEX_EXPR.

        PR middle-end/29335
        * builtins.c (fold_builtin_cabs): Use MPFR to evaluate a
        constant argument to cabs and do it without checking for
        -funsafe-math-optimizations.

testsuite:
        * gcc.dg/builtins-54.c: Add more cases.
        * gcc.dg/torture/builtin-symmetric-1.c: Likewise.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]