This is the mail archive of the libc-alpha@sourceware.org mailing list for the glibc 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] [BZ #2749] soft-fp fixes


On Sun, Jan 14, 2007 at 05:05:33PM -0600, Steven Munroe wrote:
> >That's too high level picture.  Looking at ports CVS, on ppc nofpu x*x+x 
> >for x = NaN
> >with some non-zero bits in the fraction is libc/soft-fp/mulsf3.c followed
> >by libc/soft-fp/addsf3.c, right?
> 
> The x*x+x was a read herring. The killer is truncdfsf2!
> 
> Without this patch the soft-fp trunc[dfsf|tfsf|tfdf] functions fail for 
> NAN. In soft-fp a NAN has a "nonzero fraction" which is nominally all 
> "1"s. The FP_TRUNC(S,D,...); macro copies the high order 26 (23 plus 3 
> guard) bits of fraction from double and sets the exponent to MAX=255. 
> This results in nonzero guard bits being passed into FP_PACK_SEMIRAW. 
> The values are R_s=0, R_e=255, R_f=03ffffff.

Then the right fix is IMNSHO to fix FP_TRUNC to never set work bits
in semi-raw NaNs.  No other operation which works on semi-raw format
sets them. 

2007-01-15  Jakub Jelinek  <jakub@redhat.com>

	* soft-fp/op-common.h (FP_TRUNC): When truncating a NaN, clear
	workbits in semi-raw fraction.

--- libc/soft-fp/op-common.h	2006-04-04 10:24:47.000000000 +0200
+++ libc/soft-fp/op-common.h	2007-01-15 12:41:16.000000000 +0100
@@ -1,5 +1,5 @@
 /* Software floating-point emulation. Common operations.
-   Copyright (C) 1997,1998,1999,2006 Free Software Foundation, Inc.
+   Copyright (C) 1997,1998,1999,2006,2007 Free Software Foundation, Inc.
    This file is part of the GNU C Library.
    Contributed by Richard Henderson (rth@cygnus.com),
 		  Jakub Jelinek (jj@ultra.linux.cz),
@@ -1252,6 +1252,9 @@ do {									     \
 	      _FP_FRAC_SRL_##swc(S, (_FP_WFRACBITS_##sfs		     \
 				     - _FP_WFRACBITS_##dfs));		     \
 	      _FP_FRAC_COPY_##dwc##_##swc(D, S);			     \
+	      /* Semi-raw NaN must have all workbits cleared.  */	     \
+	      _FP_FRAC_LOW_##dwc(D)					     \
+		&= ~(_FP_W_TYPE) ((1 << _FP_WORKBITS) - 1);		     \
 	      _FP_FRAC_HIGH_##dfs(D) |= _FP_QNANBIT_SH_##dfs;		     \
 	    }								     \
 	}								     \


	Jakub


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