Bug 27627 - __builtin_nanf("") doesn't return a _quiet_ nan on parisc
Summary: __builtin_nanf("") doesn't return a _quiet_ nan on parisc
Status: RESOLVED FIXED
Alias: None
Product: gcc
Classification: Unclassified
Component: target (show other bugs)
Version: 4.1.1
: P3 normal
Target Milestone: ---
Assignee: Not yet assigned to anyone
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2006-05-16 11:48 UTC by Joel Soete
Modified: 2006-05-25 22:48 UTC (History)
2 users (show)

See Also:
Host: hppa-unknown-linux-gnu
Target: hppa-unknown-linux-gnu
Build: hppa-unknown-linux-gnu
Known to work:
Known to fail:
Last reconfirmed:


Attachments
precompile nan test case (12.97 KB, application/octet-stream)
2006-05-16 11:51 UTC, Joel Soete
Details
a very simpler test case (688 bytes, text/plain)
2006-05-16 15:58 UTC, Joel Soete
Details
just another similar test case regarding double equivalent pb (694 bytes, text/plain)
2006-05-17 08:56 UTC, Joel Soete
Details

Note You need to log in before you can comment on or make changes to this bug.
Description Joel Soete 2006-05-16 11:48:49 UTC
hppa-unknown-linux-gnu


configured with: ../src/configure -v
--enable-languages=c,c++,java,fortran,objc,obj-c++,ada,treelang --prefix=/usr
--enable-shared --with-system-zlib --libexecdir=/usr/lib
+--without-included-gettext --enable-threads=posix --enable-nls
--program-suffix=-4.1 --enable-__cxa_atexit --enable-clocale=gnu
--enable-libstdcxx-debug --enable-java-awt=gtk
+--enable-gtk-cairo
--with-java-home=/usr/lib/jvm/java-1.4.2-gcj-4.1-1.4.2.0/jre --enable-mpfr
--enable-checking=release hppa-linux-gnu 

Hi all,


Trying to debug glibc test-float failures on linux parisc, it appears that a
place where one pb occures was during:

__real__ res = (float) M_PI_2 - __real__ y; //(1)

of '__cacosf (__complex__ float x);'

where __real__ y == nan;

The glibc test was failing because resulting of computation (1) is a
_signaling_ nan: the fpsr v bit (i.e. Invalid operation) is set.

Afaik this occures because __real__ y is itself a _signaling_ nan?

And this came from imho casinf() computation hunk:
[snip]
else if (__isinff (__real__ x) || __isinff (__imag__ x))
{
__real__ res = __nanf ("");
__imag__ res = __copysignf (HUGE_VALF, __imag__ x);
}
[snip]

It seems so that __nanf (""), precompiled as __builtin_nanf(""), return a
signaling nan.

I will attach a precompile file of this simple test case:

#ifndef _GNU_SOURCE
# define _GNU_SOURCE
#endif

#include <math.h>
#include <float.h>
#include <limits.h>

#include <errno.h>
#include <stdlib.h>
#include <stdio.h>
#include <string.h>

static float
L_nanf (const char *tagp)
{
if (tagp[0] != '\0')
{
char buf[6 + strlen (tagp)];
sprintf (buf, "NAN(%s)", tagp);
return strtof (buf, NULL);
}

printf ("tagp[0] == '\\0'\n");
return NAN;
}

int
main (int argc, char **argv)
{

union { unsigned long long l; unsigned int sw[2]; } s;

float res, tst;

res = L_nanf ("");
//printf ("res: 0x%x\n", (int)res);

tst = 4.0 - res;

__asm__("#BannerIn");
/* Get the current status word. */
__asm__ ("\n\t"
"fstd %%fr0,0(%1)"
: "=m" (s.l)
: "r" (&s.l)
);

printf ("s.sw[0]: 0x%x.\n", s.sw[0]);
printf ("s.sw[0] >> 27: 0x%x.\n", (s.sw[0] >> 27));

__asm__("#BannerOut");

return (int)tst;
}

reporting well:


tagp[0] == '\0'
s.sw[0]: 0x80000000.
s.sw[0] >> 27: 0x10.

Tx,
Joel

PS: compile options for test case:
gcc-4.1: warning: -pipe ignored because -save-temps specified
Using built-in specs.
Target: hppa-linux-gnu
Configured with: ../src/configure -v
--enable-languages=c,c++,java,fortran,objc,obj-c++,ada,treelang --prefix=/usr
--enable-shared --with-system-zlib --libexecdir=/usr/lib --without-i
ncluded-gettext --enable-threads=posix --enable-nls --program-suffix=-4.1
--enable-__cxa_atexit --enable-clocale=gnu --enable-libstdcxx-debug
--enable-java-awt=gtk --enable-gtk-cairo
--with-java-home=/usr/lib/jvm/java-1.4.2-gcj-4.1-1.4.2.0/jre --enable-mpfr
--enable-checking=release hppa-linux-gnu
Thread model: posix
gcc version 4.1.1 20060511 (prerelease) (Debian 4.1.0-4)
/usr/lib/gcc/hppa-linux-gnu/4.1.1/cc1 -E -quiet -nostdinc -v -I../include -I.
-I/CAD/parisc-linux/Dpkg/dpkg-work/glibc-2.3.6/build-tree/hppa-libc/math -I..
-I../libio -I/CAD/parisc-l
inux/Dpkg/dpkg-work/glibc-2.3.6/build-tree/hppa-libc -I../sysdeps/hppa/elf
-I../libidn/sysdeps/unix -I../linuxthreads/sysdeps/unix/sysv/linux/hppa
-I../linuxthreads/sysdeps/unix/sysv/
linux -I../linuxthreads/sysdeps/pthread -I../sysdeps/pthread
-I../linuxthreads/sysdeps/unix/sysv -I../linuxthreads/sysdeps/unix
-I../linuxthreads/sysdeps/hppa -I../sysdeps/unix/sysv/l
inux/hppa -I../sysdeps/unix/sysv/linux -I../sysdeps/gnu
-I../sysdeps/unix/common -I../sysdeps/unix/mman -I../sysdeps/unix/inet
-I../sysdeps/unix/sysv -I../sysdeps/unix -I../sysdeps/po
six -I../sysdeps/hppa/hppa1.1 -I../sysdeps/wordsize-32
-I../sysdeps/ieee754/flt-32 -I../sysdeps/ieee754/dbl-64 -I../sysdeps/hppa/fpu
-I../sysdeps/hppa -I../sysdeps/ieee754 -I../sysdep
s/generic/elf -I../sysdeps/generic -MD
/CAD/parisc-linux/Dpkg/dpkg-work/glibc-2.3.6/build-tree/hppa-libc/math/Nan.d
-MF /CAD/parisc-linux/Dpkg/dpkg-work/glibc-2.3.6/build-tree/hppa-li
bc/math/Nan.o.dt -MP -MT
/CAD/parisc-linux/Dpkg/dpkg-work/glibc-2.3.6/build-tree/hppa-libc/math/Nan.o
-MQ /CAD/parisc-linux/Dpkg/dpkg-work/glibc-2.3.6/build-tree/hppa-libc/math/Nan.o
-D__NO_MATH_INLINES -D__LIBC_INTERNAL_MATH_INLINES -DNO_LONG_DOUBLE
-D_Mlong_double_=double -D_LIBC_REENTRANT -DNOT_IN_libc=1 -isystem
/usr/lib/gcc/hppa-linux-gnu/4.1.1/include -isyst
em /CAD/parisc-linux/Dpkg/dpkg-work/glibc-2.3.6/debian/include -include
../include/libc-symbols.h Nan.c -std=gnu99 -Wall -Winline -Wstrict-prototypes
-Wwrite-strings -Wno-uninitialize
d -fstrict-aliasing -fno-inline -ffloat-store -fno-builtin -fworking-directory
-O2 -fpch-preprocess -o Nan.i
#include "..." search starts here:
#include <...> search starts here:
../include
.
/CAD/parisc-linux/Dpkg/dpkg-work/glibc-2.3.6/build-tree/hppa-libc/math
..
../libio
/CAD/parisc-linux/Dpkg/dpkg-work/glibc-2.3.6/build-tree/hppa-libc
../sysdeps/hppa/elf
../libidn/sysdeps/unix
../linuxthreads/sysdeps/unix/sysv/linux/hppa
../linuxthreads/sysdeps/unix/sysv/linux
../linuxthreads/sysdeps/pthread
../sysdeps/pthread
../linuxthreads/sysdeps/unix/sysv
../linuxthreads/sysdeps/unix
../linuxthreads/sysdeps/hppa
../sysdeps/unix/sysv/linux/hppa
../sysdeps/unix/sysv/linux
../sysdeps/gnu
../sysdeps/unix/common
../sysdeps/unix/mman
../sysdeps/unix/inet
../sysdeps/unix/sysv
../sysdeps/unix
../sysdeps/posix
../sysdeps/hppa/hppa1.1
../sysdeps/wordsize-32
../sysdeps/ieee754/flt-32
../sysdeps/ieee754/dbl-64
../sysdeps/hppa/fpu
../sysdeps/hppa
../sysdeps/ieee754
../sysdeps/generic/elf
../sysdeps/generic
/usr/lib/gcc/hppa-linux-gnu/4.1.1/include
/CAD/parisc-linux/Dpkg/dpkg-work/glibc-2.3.6/debian/include
End of search list.
/usr/lib/gcc/hppa-linux-gnu/4.1.1/cc1 -fpreprocessed Nan.i -quiet -dumpbase
Nan.c -auxbase-strip
/CAD/parisc-linux/Dpkg/dpkg-work/glibc-2.3.6/build-tree/hppa-libc/math/Nan.o
-g -O2 -
Wall -Winline -Wstrict-prototypes -Wwrite-strings -Wno-uninitialized
-std=gnu99 -version -fstrict-aliasing -fno-inline -ffloat-store -fno-builtin
-o Nan.s
GNU C version 4.1.1 20060511 (prerelease) (Debian 4.1.0-4) (hppa-linux-gnu)
compiled by GNU C version 4.1.1 20060511 (prerelease) (Debian 4.1.0-4).
GGC heuristics: --param ggc-min-expand=46 --param ggc-min-heapsize=31137
Compiler executable checksum: e86175deb88d866b27528eee26dfa969
as --traditional-format -V -o
/CAD/parisc-linux/Dpkg/dpkg-work/glibc-2.3.6/build-tree/hppa-libc/math/Nan.o Nan.s
GNU assembler version 2.16.91 (hppa-linux-gnu) using BFD version 2.16.91
20060413 Debian GNU/Linux
Comment 1 Joel Soete 2006-05-16 11:51:06 UTC
Created attachment 11476 [details]
precompile nan test case
Comment 2 Joel Soete 2006-05-16 15:58:05 UTC
Created attachment 11477 [details]
a very simpler test case

afaik don't need precompile (just rebuild) (e.g. gcc -o nan2 Nan2.c; ./nan2)
Comment 3 Andrew Pinski 2006-05-16 17:17:19 UTC
Why do you think this is a GCC bug?
Comment 4 John David Anglin 2006-05-17 00:49:12 UTC
This isn't a target bug as far as I can tell.  The value generated
by __builtin_nanf("") as shown by Nan2.c is 0x7fc00000.  The same
value is printed on x86.  This is a signaling NaN.  Positive quiet
NaNs range between 0x7f800001 and 0x7fbfffff.

We have the following code for at -02:

.LC0:
        .word   2143289344
        .text
        .align 4
.globl main
        .type   main, @function
main:
        .PROC
        .CALLINFO FRAME=0,CALLS,SAVE_RP
        .ENTRY
        stw %r2,-20(%r30)
        ldil LR'.LC0,%r28
        ldil LR'.LC1,%r26
        ldw RR'.LC0(%r28),%r25
        ldo RR'.LC1(%r26),%r26
        ldw -20(%r30),%r2
        bl printf,%r0
        nop
        nop
        .EXIT

2143289344 is 0x7fc00000 hex.
Comment 5 Joel Soete 2006-05-17 08:56:33 UTC
Created attachment 11481 [details]
just another similar test case regarding double equivalent pb

compile with -O2 the Nan3.s is:
 .LEVEL 1.1
 .section .rodata.str1.4,"aMS",@progbits,1
 .align 4
.LC1:
.stringz"__builtin_nan(): 0x%llx.\n"
 .section .rodata.cst8,"aM",@progbits,8
 .align 8
.LC0:
 .word 2146959360
 .word 0
 .text
 .align 4
.globl main
 .type main, @function
main:
 .PROC
 .CALLINFO FRAME=0,CALLS,SAVE_RP
 .ENTRY
 stw %r2,-20(%r30)
 ldil LR'.LC0,%r28
 ldil LR'.LC1,%r26
 ldw RR'.LC0(%r28),%r23
 ldw RR'.LC0+4(%r28),%r24
 ldo RR'.LC1(%r26),%r26
 ldw -20(%r30),%r2
 bl printf,%r0
 nop
 nop
 .EXIT
 .PROCEND
 .size main, .-main
 .ident "GCC: (GNU) 4.1.1 20060511 (prerelease) (Debian 4.1.0-4)"

and print out:
__builtin_nan(): 0x7ff8000000000000.

or bin form of 1 32bit word: 01111111111110000000000000000000

i.e.
- the first bit being the sign == 0
- next 11 being the exponenent all == 1
- next 52 one being fraction have the first bit == 1, making this NAN a signaling NAN.

And according to this thread (I don't have access to C99 std ;-( ):
<http://gcc.gnu.org/ml/libstdc++/2002-09/msg00030.html>
as well as gcc info
/quote
 -- Built-in Function: double __builtin_nan (const char *str)
     This is an implementation of the ISO C99 function `nan'.

     Since ISO C99 defines this function in terms of `strtod', which we
     do not implement, a description of the parsing is in order.  The
     string is parsed as by `strtol'; that is, the base is recognized by
     leading `0' or `0x' prefixes.  The number parsed is placed in the
     significand such that the least significant bit of the number is
     at the least significant bit of the significand.  The number is
     truncated to fit the significand field provided.  The significand
     is forced to be a quiet NaN.

     This function, if given a string literal, is evaluated early enough
     that it is considered a compile-time constant.
/quote

__builtin_nan[f](""); should return a quiet NAN. To do so, the parisc2.0 doc, says that the fraction part have to be <> 0 but with first bit == 0.
Comment 6 Richard Henderson 2006-05-23 15:00:25 UTC
(In reply to comment #4)
> This isn't a target bug as far as I can tell.  The value generated
> by __builtin_nanf("") as shown by Nan2.c is 0x7fc00000.  The same
> value is printed on x86.  This is a signaling NaN.  Positive quiet
> NaNs range between 0x7f800001 and 0x7fbfffff.

Incorrect.  The canonical QNaN on x86 (and most other targets) is
0x7fc00000.  It would seem that PA has the same reversed quiet bit
as MIPS.  See real_format->qnan_msb_set and mips_ieee_single.
Comment 7 dave 2006-05-23 16:28:07 UTC
Subject: Re:  __builtin_nanf("") doesn't return a _quiet_ nan on parisc

> ------- Comment #6 from rth at gcc dot gnu dot org  2006-05-23 15:00 -------
> (In reply to comment #4)
> > This isn't a target bug as far as I can tell.  The value generated
> > by __builtin_nanf("") as shown by Nan2.c is 0x7fc00000.  The same
> > value is printed on x86.  This is a signaling NaN.  Positive quiet
> > NaNs range between 0x7f800001 and 0x7fbfffff.
> 
> Incorrect.  The canonical QNaN on x86 (and most other targets) is
> 0x7fc00000.  It would seem that PA has the same reversed quiet bit
> as MIPS.  See real_format->qnan_msb_set and mips_ieee_single.

Interesting.  The HP architecture docments for PA 1.1 and 2.0
state that PA-RISC fully conforms to ANSI/IEEE Std 754-1985, so
I presume that this isn't specified (don't have a copy of the
spec handy), so there's no actual canonical format.  I see this
was something of a point of contention in 754R meetings.

Google tells me that MIPS didn't discriminant in early processors,
then used the same convention as PA-RISC, and finally switched again.
So, don't much like calling this the "mips" format.

Dave
Comment 8 gdr@cs.tamu.edu 2006-05-23 21:58:45 UTC
Subject: Re:  __builtin_nanf("") doesn't return a _quiet_ nan on parisc

"dave at hiauly1 dot hia dot nrc dot ca" <gcc-bugzilla@gcc.gnu.org> writes:

| ------- Comment #7 from dave at hiauly1 dot hia dot nrc dot ca  2006-05-23 16:28 -------
| Subject: Re:  __builtin_nanf("") doesn't return a _quiet_ nan on parisc
| 
| > ------- Comment #6 from rth at gcc dot gnu dot org  2006-05-23 15:00 -------
| > (In reply to comment #4)
| > > This isn't a target bug as far as I can tell.  The value generated
| > > by __builtin_nanf("") as shown by Nan2.c is 0x7fc00000.  The same
| > > value is printed on x86.  This is a signaling NaN.  Positive quiet
| > > NaNs range between 0x7f800001 and 0x7fbfffff.
| > 
| > Incorrect.  The canonical QNaN on x86 (and most other targets) is
| > 0x7fc00000.  It would seem that PA has the same reversed quiet bit
| > as MIPS.  See real_format->qnan_msb_set and mips_ieee_single.
| 
| Interesting.  The HP architecture docments for PA 1.1 and 2.0
| state that PA-RISC fully conforms to ANSI/IEEE Std 754-1985, so
| I presume that this isn't specified (don't have a copy of the
| spec handy), so there's no actual canonical format.  I see this
| was something of a point of contention in 754R meetings.

The IEEE--754 specification is a *conceptual model*, not a "physical"
wired format.  As long as the units behave functionally as required,
it should be fine.

-- Gaby
Comment 9 John David Anglin 2006-05-24 23:23:20 UTC
Subject: Bug 27627

Author: danglin
Date: Wed May 24 23:23:10 2006
New Revision: 114059

URL: http://gcc.gnu.org/viewcvs?root=gcc&view=rev&rev=114059
Log:
	PR target/27627
	* pa/pa-modes.def: Use mips_single_format, mips_double_format and
	mips_quad_format formats instead of ieee_single_format,
	ieee_double_format and ieee_quad_format formats, respectively.


Modified:
    trunk/gcc/ChangeLog
    trunk/gcc/config/pa/pa-modes.def

Comment 10 Andrew Pinski 2006-05-24 23:26:06 UTC
Subject: Re:  __builtin_nanf("") doesn't return a _quiet_ nan on parisc

> 
> 
> 
> ------- Comment #9 from danglin at gcc dot gnu dot org  2006-05-24 23:23 -------
> Subject: Bug 27627
> 
> Author: danglin
> Date: Wed May 24 23:23:10 2006
> New Revision: 114059
> 
> URL: http://gcc.gnu.org/viewcvs?root=gcc&view=rev&rev=114059
> Log:
>         PR target/27627
>         * pa/pa-modes.def: Use mips_single_format, mips_double_format and
>         mips_quad_format formats instead of ieee_single_format,
>         ieee_double_format and ieee_quad_format formats, respectively.

You might not want to us MIPS_QUAD format because it is not even close
to IEEE Quad format but instead it is more like the PPC quad format.


-- Pinski
Comment 11 dave 2006-05-24 23:32:17 UTC
Subject: Re:  __builtin_nanf("") doesn't return a _quiet_ nan on parisc

> > Log:
> >         PR target/27627
> >         * pa/pa-modes.def: Use mips_single_format, mips_double_format and
> >         mips_quad_format formats instead of ieee_single_format,
> >         ieee_double_format and ieee_quad_format formats, respectively.
> 
> You might not want to us MIPS_QUAD format because it is not even close
> to IEEE Quad format but instead it is more like the PPC quad format.

I looked at the struct in real.c and the initialization seemed identical
to the ieee struct except for the qnan_msb_set.  Are you possibly confusing
the mips_extended_format with the mips_quad_format?

Dave
Comment 12 John David Anglin 2006-05-25 22:48:49 UTC
Fixed by patch on trunk.