1/*
2 * QEMU float support
3 *
4 * Derived from SoftFloat.
5 */
6
7/*============================================================================
8
9This C source fragment is part of the SoftFloat IEC/IEEE Floating-point
10Arithmetic Package, Release 2b.
11
12Written by John R. Hauser.  This work was made possible in part by the
13International Computer Science Institute, located at Suite 600, 1947 Center
14Street, Berkeley, California 94704.  Funding was partially provided by the
15National Science Foundation under grant MIP-9311980.  The original version
16of this code was written as part of a project to build a fixed-point vector
17processor in collaboration with the University of California at Berkeley,
18overseen by Profs. Nelson Morgan and John Wawrzynek.  More information
19is available through the Web page `http://www.cs.berkeley.edu/~jhauser/
20arithmetic/SoftFloat.html'.
21
22THIS SOFTWARE IS DISTRIBUTED AS IS, FOR FREE.  Although reasonable effort has
23been made to avoid it, THIS SOFTWARE MAY CONTAIN FAULTS THAT WILL AT TIMES
24RESULT IN INCORRECT BEHAVIOR.  USE OF THIS SOFTWARE IS RESTRICTED TO PERSONS
25AND ORGANIZATIONS WHO CAN AND WILL TAKE FULL RESPONSIBILITY FOR ALL LOSSES,
26COSTS, OR OTHER PROBLEMS THEY INCUR DUE TO THE SOFTWARE, AND WHO FURTHERMORE
27EFFECTIVELY INDEMNIFY JOHN HAUSER AND THE INTERNATIONAL COMPUTER SCIENCE
28INSTITUTE (possibly via similar legal warning) AGAINST ALL LOSSES, COSTS, OR
29OTHER PROBLEMS INCURRED BY THEIR CUSTOMERS AND CLIENTS DUE TO THE SOFTWARE.
30
31Derivative works are acceptable, even for commercial purposes, so long as
32(1) the source code for the derivative work includes prominent notice that
33the work is derivative, and (2) the source code includes prominent notice with
34these four paragraphs for those parts of this code that are retained.
35
36=============================================================================*/
37
38/*----------------------------------------------------------------------------
39| Raises the exceptions specified by `flags'.  Floating-point traps can be
40| defined here if desired.  It is currently not possible for such a trap
41| to substitute a result value.  If traps are not implemented, this routine
42| should be simply `float_exception_flags |= flags;'.
43*----------------------------------------------------------------------------*/
44
45void float_raise( int8 flags STATUS_PARAM )
46{
47    STATUS(float_exception_flags) |= flags;
48}
49
50/*----------------------------------------------------------------------------
51| Internal canonical NaN format.
52*----------------------------------------------------------------------------*/
53typedef struct {
54    flag sign;
55    uint64_t high, low;
56} commonNaNT;
57
58/*----------------------------------------------------------------------------
59| Returns 1 if the half-precision floating-point value `a' is a quiet
60| NaN; otherwise returns 0.
61*----------------------------------------------------------------------------*/
62
63int float16_is_quiet_nan(float16 a_)
64{
65    uint16_t a = float16_val(a_);
66#if SNAN_BIT_IS_ONE
67    return (((a >> 9) & 0x3F) == 0x3E) && (a & 0x1FF);
68#else
69    return ((a & ~0x8000) >= 0x7c80);
70#endif
71}
72
73/*----------------------------------------------------------------------------
74| Returns 1 if the half-precision floating-point value `a' is a signaling
75| NaN; otherwise returns 0.
76*----------------------------------------------------------------------------*/
77
78int float16_is_signaling_nan(float16 a_)
79{
80    uint16_t a = float16_val(a_);
81#if SNAN_BIT_IS_ONE
82    return ((a & ~0x8000) >= 0x7c80);
83#else
84    return (((a >> 9) & 0x3F) == 0x3E) && (a & 0x1FF);
85#endif
86}
87
88/*----------------------------------------------------------------------------
89| Returns a quiet NaN if the half-precision floating point value `a' is a
90| signaling NaN; otherwise returns `a'.
91*----------------------------------------------------------------------------*/
92float16 float16_maybe_silence_nan(float16 a_)
93{
94    if (float16_is_signaling_nan(a_)) {
95#if SNAN_BIT_IS_ONE
96#  if defined(TARGET_MIPS) || defined(TARGET_SH4) || defined(TARGET_UNICORE32)
97        return float16_default_nan;
98#  else
99#    error Rules for silencing a signaling NaN are target-specific
100#  endif
101#else
102        uint16_t a = float16_val(a_);
103        a |= (1 << 9);
104        return make_float16(a);
105#endif
106    }
107    return a_;
108}
109
110/*----------------------------------------------------------------------------
111| Returns the result of converting the half-precision floating-point NaN
112| `a' to the canonical NaN format.  If `a' is a signaling NaN, the invalid
113| exception is raised.
114*----------------------------------------------------------------------------*/
115
116static commonNaNT float16ToCommonNaN( float16 a STATUS_PARAM )
117{
118    commonNaNT z;
119
120    if ( float16_is_signaling_nan( a ) ) float_raise( float_flag_invalid STATUS_VAR );
121    z.sign = float16_val(a) >> 15;
122    z.low = 0;
123    z.high = ((uint64_t) float16_val(a))<<54;
124    return z;
125}
126
127/*----------------------------------------------------------------------------
128| Returns the result of converting the canonical NaN `a' to the half-
129| precision floating-point format.
130*----------------------------------------------------------------------------*/
131
132static float16 commonNaNToFloat16(commonNaNT a STATUS_PARAM)
133{
134    uint16_t mantissa = a.high>>54;
135
136    if (STATUS(default_nan_mode)) {
137        return float16_default_nan;
138    }
139
140    if (mantissa) {
141        return make_float16(((((uint16_t) a.sign) << 15)
142                             | (0x1F << 10) | mantissa));
143    } else {
144        return float16_default_nan;
145    }
146}
147
148/*----------------------------------------------------------------------------
149| Returns 1 if the single-precision floating-point value `a' is a quiet
150| NaN; otherwise returns 0.
151*----------------------------------------------------------------------------*/
152
153int float32_is_quiet_nan( float32 a_ )
154{
155    uint32_t a = float32_val(a_);
156#if SNAN_BIT_IS_ONE
157    return ( ( ( a>>22 ) & 0x1FF ) == 0x1FE ) && ( a & 0x003FFFFF );
158#else
159    return ( 0xFF800000 <= (uint32_t) ( a<<1 ) );
160#endif
161}
162
163/*----------------------------------------------------------------------------
164| Returns 1 if the single-precision floating-point value `a' is a signaling
165| NaN; otherwise returns 0.
166*----------------------------------------------------------------------------*/
167
168int float32_is_signaling_nan( float32 a_ )
169{
170    uint32_t a = float32_val(a_);
171#if SNAN_BIT_IS_ONE
172    return ( 0xFF800000 <= (uint32_t) ( a<<1 ) );
173#else
174    return ( ( ( a>>22 ) & 0x1FF ) == 0x1FE ) && ( a & 0x003FFFFF );
175#endif
176}
177
178/*----------------------------------------------------------------------------
179| Returns a quiet NaN if the single-precision floating point value `a' is a
180| signaling NaN; otherwise returns `a'.
181*----------------------------------------------------------------------------*/
182
183float32 float32_maybe_silence_nan( float32 a_ )
184{
185    if (float32_is_signaling_nan(a_)) {
186#if SNAN_BIT_IS_ONE
187#  if defined(TARGET_MIPS) || defined(TARGET_SH4) || defined(TARGET_UNICORE32)
188        return float32_default_nan;
189#  else
190#    error Rules for silencing a signaling NaN are target-specific
191#  endif
192#else
193        uint32_t a = float32_val(a_);
194        a |= (1 << 22);
195        return make_float32(a);
196#endif
197    }
198    return a_;
199}
200
201/*----------------------------------------------------------------------------
202| Returns the result of converting the single-precision floating-point NaN
203| `a' to the canonical NaN format.  If `a' is a signaling NaN, the invalid
204| exception is raised.
205*----------------------------------------------------------------------------*/
206
207static commonNaNT float32ToCommonNaN( float32 a STATUS_PARAM )
208{
209    commonNaNT z;
210
211    if ( float32_is_signaling_nan( a ) ) float_raise( float_flag_invalid STATUS_VAR );
212    z.sign = float32_val(a)>>31;
213    z.low = 0;
214    z.high = ( (uint64_t) float32_val(a) )<<41;
215    return z;
216}
217
218/*----------------------------------------------------------------------------
219| Returns the result of converting the canonical NaN `a' to the single-
220| precision floating-point format.
221*----------------------------------------------------------------------------*/
222
223static float32 commonNaNToFloat32( commonNaNT a STATUS_PARAM)
224{
225    uint32_t mantissa = a.high>>41;
226
227    if ( STATUS(default_nan_mode) ) {
228        return float32_default_nan;
229    }
230
231    if ( mantissa )
232        return make_float32(
233            ( ( (uint32_t) a.sign )<<31 ) | 0x7F800000 | ( a.high>>41 ) );
234    else
235        return float32_default_nan;
236}
237
238/*----------------------------------------------------------------------------
239| Select which NaN to propagate for a two-input operation.
240| IEEE754 doesn't specify all the details of this, so the
241| algorithm is target-specific.
242| The routine is passed various bits of information about the
243| two NaNs and should return 0 to select NaN a and 1 for NaN b.
244| Note that signalling NaNs are always squashed to quiet NaNs
245| by the caller, by calling floatXX_maybe_silence_nan() before
246| returning them.
247|
248| aIsLargerSignificand is only valid if both a and b are NaNs
249| of some kind, and is true if a has the larger significand,
250| or if both a and b have the same significand but a is
251| positive but b is negative. It is only needed for the x87
252| tie-break rule.
253*----------------------------------------------------------------------------*/
254
255#if defined(TARGET_ARM)
256static int pickNaN(flag aIsQNaN, flag aIsSNaN, flag bIsQNaN, flag bIsSNaN,
257                    flag aIsLargerSignificand)
258{
259    /* ARM mandated NaN propagation rules: take the first of:
260     *  1. A if it is signaling
261     *  2. B if it is signaling
262     *  3. A (quiet)
263     *  4. B (quiet)
264     * A signaling NaN is always quietened before returning it.
265     */
266    if (aIsSNaN) {
267        return 0;
268    } else if (bIsSNaN) {
269        return 1;
270    } else if (aIsQNaN) {
271        return 0;
272    } else {
273        return 1;
274    }
275}
276#elif defined(TARGET_MIPS)
277static int pickNaN(flag aIsQNaN, flag aIsSNaN, flag bIsQNaN, flag bIsSNaN,
278                    flag aIsLargerSignificand)
279{
280    /* According to MIPS specifications, if one of the two operands is
281     * a sNaN, a new qNaN has to be generated. This is done in
282     * floatXX_maybe_silence_nan(). For qNaN inputs the specifications
283     * says: "When possible, this QNaN result is one of the operand QNaN
284     * values." In practice it seems that most implementations choose
285     * the first operand if both operands are qNaN. In short this gives
286     * the following rules:
287     *  1. A if it is signaling
288     *  2. B if it is signaling
289     *  3. A (quiet)
290     *  4. B (quiet)
291     * A signaling NaN is always silenced before returning it.
292     */
293    if (aIsSNaN) {
294        return 0;
295    } else if (bIsSNaN) {
296        return 1;
297    } else if (aIsQNaN) {
298        return 0;
299    } else {
300        return 1;
301    }
302}
303#elif defined(TARGET_PPC)
304static int pickNaN(flag aIsQNaN, flag aIsSNaN, flag bIsQNaN, flag bIsSNaN,
305                   flag aIsLargerSignificand)
306{
307    /* PowerPC propagation rules:
308     *  1. A if it sNaN or qNaN
309     *  2. B if it sNaN or qNaN
310     * A signaling NaN is always silenced before returning it.
311     */
312    if (aIsSNaN || aIsQNaN) {
313        return 0;
314    } else {
315        return 1;
316    }
317}
318#else
319static int pickNaN(flag aIsQNaN, flag aIsSNaN, flag bIsQNaN, flag bIsSNaN,
320                    flag aIsLargerSignificand)
321{
322    /* This implements x87 NaN propagation rules:
323     * SNaN + QNaN => return the QNaN
324     * two SNaNs => return the one with the larger significand, silenced
325     * two QNaNs => return the one with the larger significand
326     * SNaN and a non-NaN => return the SNaN, silenced
327     * QNaN and a non-NaN => return the QNaN
328     *
329     * If we get down to comparing significands and they are the same,
330     * return the NaN with the positive sign bit (if any).
331     */
332    if (aIsSNaN) {
333        if (bIsSNaN) {
334            return aIsLargerSignificand ? 0 : 1;
335        }
336        return bIsQNaN ? 1 : 0;
337    }
338    else if (aIsQNaN) {
339        if (bIsSNaN || !bIsQNaN)
340            return 0;
341        else {
342            return aIsLargerSignificand ? 0 : 1;
343        }
344    } else {
345        return 1;
346    }
347}
348#endif
349
350/*----------------------------------------------------------------------------
351| Takes two single-precision floating-point values `a' and `b', one of which
352| is a NaN, and returns the appropriate NaN result.  If either `a' or `b' is a
353| signaling NaN, the invalid exception is raised.
354*----------------------------------------------------------------------------*/
355
356static float32 propagateFloat32NaN( float32 a, float32 b STATUS_PARAM)
357{
358    flag aIsQuietNaN, aIsSignalingNaN, bIsQuietNaN, bIsSignalingNaN;
359    flag aIsLargerSignificand;
360    uint32_t av, bv;
361
362    aIsQuietNaN = float32_is_quiet_nan( a );
363    aIsSignalingNaN = float32_is_signaling_nan( a );
364    bIsQuietNaN = float32_is_quiet_nan( b );
365    bIsSignalingNaN = float32_is_signaling_nan( b );
366    av = float32_val(a);
367    bv = float32_val(b);
368
369    if ( aIsSignalingNaN | bIsSignalingNaN ) float_raise( float_flag_invalid STATUS_VAR);
370
371    if ( STATUS(default_nan_mode) )
372        return float32_default_nan;
373
374    if ((uint32_t)(av<<1) < (uint32_t)(bv<<1)) {
375        aIsLargerSignificand = 0;
376    } else if ((uint32_t)(bv<<1) < (uint32_t)(av<<1)) {
377        aIsLargerSignificand = 1;
378    } else {
379        aIsLargerSignificand = (av < bv) ? 1 : 0;
380    }
381
382    if (pickNaN(aIsQuietNaN, aIsSignalingNaN, bIsQuietNaN, bIsSignalingNaN,
383                aIsLargerSignificand)) {
384        return float32_maybe_silence_nan(b);
385    } else {
386        return float32_maybe_silence_nan(a);
387    }
388}
389
390/*----------------------------------------------------------------------------
391| Returns 1 if the double-precision floating-point value `a' is a quiet
392| NaN; otherwise returns 0.
393*----------------------------------------------------------------------------*/
394
395int float64_is_quiet_nan( float64 a_ )
396{
397    uint64_t a = float64_val(a_);
398#if SNAN_BIT_IS_ONE
399    return
400           ( ( ( a>>51 ) & 0xFFF ) == 0xFFE )
401        && ( a & LIT64( 0x0007FFFFFFFFFFFF ) );
402#else
403    return ( LIT64( 0xFFF0000000000000 ) <= (uint64_t) ( a<<1 ) );
404#endif
405}
406
407/*----------------------------------------------------------------------------
408| Returns 1 if the double-precision floating-point value `a' is a signaling
409| NaN; otherwise returns 0.
410*----------------------------------------------------------------------------*/
411
412int float64_is_signaling_nan( float64 a_ )
413{
414    uint64_t a = float64_val(a_);
415#if SNAN_BIT_IS_ONE
416    return ( LIT64( 0xFFF0000000000000 ) <= (uint64_t) ( a<<1 ) );
417#else
418    return
419           ( ( ( a>>51 ) & 0xFFF ) == 0xFFE )
420        && ( a & LIT64( 0x0007FFFFFFFFFFFF ) );
421#endif
422}
423
424/*----------------------------------------------------------------------------
425| Returns a quiet NaN if the double-precision floating point value `a' is a
426| signaling NaN; otherwise returns `a'.
427*----------------------------------------------------------------------------*/
428
429float64 float64_maybe_silence_nan( float64 a_ )
430{
431    if (float64_is_signaling_nan(a_)) {
432#if SNAN_BIT_IS_ONE
433#  if defined(TARGET_MIPS) || defined(TARGET_SH4) || defined(TARGET_UNICORE32)
434        return float64_default_nan;
435#  else
436#    error Rules for silencing a signaling NaN are target-specific
437#  endif
438#else
439        uint64_t a = float64_val(a_);
440        a |= LIT64( 0x0008000000000000 );
441        return make_float64(a);
442#endif
443    }
444    return a_;
445}
446
447/*----------------------------------------------------------------------------
448| Returns the result of converting the double-precision floating-point NaN
449| `a' to the canonical NaN format.  If `a' is a signaling NaN, the invalid
450| exception is raised.
451*----------------------------------------------------------------------------*/
452
453static commonNaNT float64ToCommonNaN( float64 a STATUS_PARAM)
454{
455    commonNaNT z;
456
457    if ( float64_is_signaling_nan( a ) ) float_raise( float_flag_invalid STATUS_VAR);
458    z.sign = float64_val(a)>>63;
459    z.low = 0;
460    z.high = float64_val(a)<<12;
461    return z;
462}
463
464/*----------------------------------------------------------------------------
465| Returns the result of converting the canonical NaN `a' to the double-
466| precision floating-point format.
467*----------------------------------------------------------------------------*/
468
469static float64 commonNaNToFloat64( commonNaNT a STATUS_PARAM)
470{
471    uint64_t mantissa = a.high>>12;
472
473    if ( STATUS(default_nan_mode) ) {
474        return float64_default_nan;
475    }
476
477    if ( mantissa )
478        return make_float64(
479              ( ( (uint64_t) a.sign )<<63 )
480            | LIT64( 0x7FF0000000000000 )
481            | ( a.high>>12 ));
482    else
483        return float64_default_nan;
484}
485
486/*----------------------------------------------------------------------------
487| Takes two double-precision floating-point values `a' and `b', one of which
488| is a NaN, and returns the appropriate NaN result.  If either `a' or `b' is a
489| signaling NaN, the invalid exception is raised.
490*----------------------------------------------------------------------------*/
491
492static float64 propagateFloat64NaN( float64 a, float64 b STATUS_PARAM)
493{
494    flag aIsQuietNaN, aIsSignalingNaN, bIsQuietNaN, bIsSignalingNaN;
495    flag aIsLargerSignificand;
496    uint64_t av, bv;
497
498    aIsQuietNaN = float64_is_quiet_nan( a );
499    aIsSignalingNaN = float64_is_signaling_nan( a );
500    bIsQuietNaN = float64_is_quiet_nan( b );
501    bIsSignalingNaN = float64_is_signaling_nan( b );
502    av = float64_val(a);
503    bv = float64_val(b);
504
505    if ( aIsSignalingNaN | bIsSignalingNaN ) float_raise( float_flag_invalid STATUS_VAR);
506
507    if ( STATUS(default_nan_mode) )
508        return float64_default_nan;
509
510    if ((uint64_t)(av<<1) < (uint64_t)(bv<<1)) {
511        aIsLargerSignificand = 0;
512    } else if ((uint64_t)(bv<<1) < (uint64_t)(av<<1)) {
513        aIsLargerSignificand = 1;
514    } else {
515        aIsLargerSignificand = (av < bv) ? 1 : 0;
516    }
517
518    if (pickNaN(aIsQuietNaN, aIsSignalingNaN, bIsQuietNaN, bIsSignalingNaN,
519                aIsLargerSignificand)) {
520        return float64_maybe_silence_nan(b);
521    } else {
522        return float64_maybe_silence_nan(a);
523    }
524}
525
526#ifdef FLOATX80
527
528/*----------------------------------------------------------------------------
529| Returns 1 if the extended double-precision floating-point value `a' is a
530| quiet NaN; otherwise returns 0. This slightly differs from the same
531| function for other types as floatx80 has an explicit bit.
532*----------------------------------------------------------------------------*/
533
534int floatx80_is_quiet_nan( floatx80 a )
535{
536#if SNAN_BIT_IS_ONE
537    uint64_t aLow;
538
539    aLow = a.low & ~ LIT64( 0x4000000000000000 );
540    return
541           ( ( a.high & 0x7FFF ) == 0x7FFF )
542        && (uint64_t) ( aLow<<1 )
543        && ( a.low == aLow );
544#else
545    return ( ( a.high & 0x7FFF ) == 0x7FFF )
546        && (LIT64( 0x8000000000000000 ) <= ((uint64_t) ( a.low<<1 )));
547#endif
548}
549
550/*----------------------------------------------------------------------------
551| Returns 1 if the extended double-precision floating-point value `a' is a
552| signaling NaN; otherwise returns 0. This slightly differs from the same
553| function for other types as floatx80 has an explicit bit.
554*----------------------------------------------------------------------------*/
555
556int floatx80_is_signaling_nan( floatx80 a )
557{
558#if SNAN_BIT_IS_ONE
559    return ( ( a.high & 0x7FFF ) == 0x7FFF )
560        && (LIT64( 0x8000000000000000 ) <= ((uint64_t) ( a.low<<1 )));
561#else
562    uint64_t aLow;
563
564    aLow = a.low & ~ LIT64( 0x4000000000000000 );
565    return
566           ( ( a.high & 0x7FFF ) == 0x7FFF )
567        && (uint64_t) ( aLow<<1 )
568        && ( a.low == aLow );
569#endif
570}
571
572/*----------------------------------------------------------------------------
573| Returns a quiet NaN if the extended double-precision floating point value
574| `a' is a signaling NaN; otherwise returns `a'.
575*----------------------------------------------------------------------------*/
576
577floatx80 floatx80_maybe_silence_nan( floatx80 a )
578{
579    if (floatx80_is_signaling_nan(a)) {
580#if SNAN_BIT_IS_ONE
581#  if defined(TARGET_MIPS) || defined(TARGET_SH4) || defined(TARGET_UNICORE32)
582        a.low = floatx80_default_nan_low;
583        a.high = floatx80_default_nan_high;
584#  else
585#    error Rules for silencing a signaling NaN are target-specific
586#  endif
587#else
588        a.low |= LIT64( 0xC000000000000000 );
589        return a;
590#endif
591    }
592    return a;
593}
594
595/*----------------------------------------------------------------------------
596| Returns the result of converting the extended double-precision floating-
597| point NaN `a' to the canonical NaN format.  If `a' is a signaling NaN, the
598| invalid exception is raised.
599*----------------------------------------------------------------------------*/
600
601static commonNaNT floatx80ToCommonNaN( floatx80 a STATUS_PARAM)
602{
603    commonNaNT z;
604
605    if ( floatx80_is_signaling_nan( a ) ) float_raise( float_flag_invalid STATUS_VAR);
606    if ( a.low >> 63 ) {
607        z.sign = a.high >> 15;
608        z.low = 0;
609        z.high = a.low << 1;
610    } else {
611        z.sign = floatx80_default_nan_high >> 15;
612        z.low = 0;
613        z.high = floatx80_default_nan_low << 1;
614    }
615    return z;
616}
617
618/*----------------------------------------------------------------------------
619| Returns the result of converting the canonical NaN `a' to the extended
620| double-precision floating-point format.
621*----------------------------------------------------------------------------*/
622
623static floatx80 commonNaNToFloatx80( commonNaNT a STATUS_PARAM)
624{
625    floatx80 z;
626
627    if ( STATUS(default_nan_mode) ) {
628        z.low = floatx80_default_nan_low;
629        z.high = floatx80_default_nan_high;
630        return z;
631    }
632
633    if (a.high >> 1) {
634        z.low = LIT64( 0x8000000000000000 ) | a.high >> 1;
635        z.high = ( ( (uint16_t) a.sign )<<15 ) | 0x7FFF;
636    } else {
637        z.low = floatx80_default_nan_low;
638        z.high = floatx80_default_nan_high;
639    }
640
641    return z;
642}
643
644/*----------------------------------------------------------------------------
645| Takes two extended double-precision floating-point values `a' and `b', one
646| of which is a NaN, and returns the appropriate NaN result.  If either `a' or
647| `b' is a signaling NaN, the invalid exception is raised.
648*----------------------------------------------------------------------------*/
649
650static floatx80 propagateFloatx80NaN( floatx80 a, floatx80 b STATUS_PARAM)
651{
652    flag aIsQuietNaN, aIsSignalingNaN, bIsQuietNaN, bIsSignalingNaN;
653    flag aIsLargerSignificand;
654
655    aIsQuietNaN = floatx80_is_quiet_nan( a );
656    aIsSignalingNaN = floatx80_is_signaling_nan( a );
657    bIsQuietNaN = floatx80_is_quiet_nan( b );
658    bIsSignalingNaN = floatx80_is_signaling_nan( b );
659
660    if ( aIsSignalingNaN | bIsSignalingNaN ) float_raise( float_flag_invalid STATUS_VAR);
661
662    if ( STATUS(default_nan_mode) ) {
663        a.low = floatx80_default_nan_low;
664        a.high = floatx80_default_nan_high;
665        return a;
666    }
667
668    if (a.low < b.low) {
669        aIsLargerSignificand = 0;
670    } else if (b.low < a.low) {
671        aIsLargerSignificand = 1;
672    } else {
673        aIsLargerSignificand = (a.high < b.high) ? 1 : 0;
674    }
675
676    if (pickNaN(aIsQuietNaN, aIsSignalingNaN, bIsQuietNaN, bIsSignalingNaN,
677                aIsLargerSignificand)) {
678        return floatx80_maybe_silence_nan(b);
679    } else {
680        return floatx80_maybe_silence_nan(a);
681    }
682}
683
684#endif
685
686#ifdef FLOAT128
687
688/*----------------------------------------------------------------------------
689| Returns 1 if the quadruple-precision floating-point value `a' is a quiet
690| NaN; otherwise returns 0.
691*----------------------------------------------------------------------------*/
692
693int float128_is_quiet_nan( float128 a )
694{
695#if SNAN_BIT_IS_ONE
696    return
697           ( ( ( a.high>>47 ) & 0xFFFF ) == 0xFFFE )
698        && ( a.low || ( a.high & LIT64( 0x00007FFFFFFFFFFF ) ) );
699#else
700    return
701           ( LIT64( 0xFFFE000000000000 ) <= (uint64_t) ( a.high<<1 ) )
702        && ( a.low || ( a.high & LIT64( 0x0000FFFFFFFFFFFF ) ) );
703#endif
704}
705
706/*----------------------------------------------------------------------------
707| Returns 1 if the quadruple-precision floating-point value `a' is a
708| signaling NaN; otherwise returns 0.
709*----------------------------------------------------------------------------*/
710
711int float128_is_signaling_nan( float128 a )
712{
713#if SNAN_BIT_IS_ONE
714    return
715           ( LIT64( 0xFFFE000000000000 ) <= (uint64_t) ( a.high<<1 ) )
716        && ( a.low || ( a.high & LIT64( 0x0000FFFFFFFFFFFF ) ) );
717#else
718    return
719           ( ( ( a.high>>47 ) & 0xFFFF ) == 0xFFFE )
720        && ( a.low || ( a.high & LIT64( 0x00007FFFFFFFFFFF ) ) );
721#endif
722}
723
724/*----------------------------------------------------------------------------
725| Returns a quiet NaN if the quadruple-precision floating point value `a' is
726| a signaling NaN; otherwise returns `a'.
727*----------------------------------------------------------------------------*/
728
729float128 float128_maybe_silence_nan( float128 a )
730{
731    if (float128_is_signaling_nan(a)) {
732#if SNAN_BIT_IS_ONE
733#  if defined(TARGET_MIPS) || defined(TARGET_SH4) || defined(TARGET_UNICORE32)
734        a.low = float128_default_nan_low;
735        a.high = float128_default_nan_high;
736#  else
737#    error Rules for silencing a signaling NaN are target-specific
738#  endif
739#else
740        a.high |= LIT64( 0x0000800000000000 );
741        return a;
742#endif
743    }
744    return a;
745}
746
747/*----------------------------------------------------------------------------
748| Returns the result of converting the quadruple-precision floating-point NaN
749| `a' to the canonical NaN format.  If `a' is a signaling NaN, the invalid
750| exception is raised.
751*----------------------------------------------------------------------------*/
752
753static commonNaNT float128ToCommonNaN( float128 a STATUS_PARAM)
754{
755    commonNaNT z;
756
757    if ( float128_is_signaling_nan( a ) ) float_raise( float_flag_invalid STATUS_VAR);
758    z.sign = a.high>>63;
759    shortShift128Left( a.high, a.low, 16, &z.high, &z.low );
760    return z;
761}
762
763/*----------------------------------------------------------------------------
764| Returns the result of converting the canonical NaN `a' to the quadruple-
765| precision floating-point format.
766*----------------------------------------------------------------------------*/
767
768static float128 commonNaNToFloat128( commonNaNT a STATUS_PARAM)
769{
770    float128 z;
771
772    if ( STATUS(default_nan_mode) ) {
773        z.low = float128_default_nan_low;
774        z.high = float128_default_nan_high;
775        return z;
776    }
777
778    shift128Right( a.high, a.low, 16, &z.high, &z.low );
779    z.high |= ( ( (uint64_t) a.sign )<<63 ) | LIT64( 0x7FFF000000000000 );
780    return z;
781}
782
783/*----------------------------------------------------------------------------
784| Takes two quadruple-precision floating-point values `a' and `b', one of
785| which is a NaN, and returns the appropriate NaN result.  If either `a' or
786| `b' is a signaling NaN, the invalid exception is raised.
787*----------------------------------------------------------------------------*/
788
789static float128 propagateFloat128NaN( float128 a, float128 b STATUS_PARAM)
790{
791    flag aIsQuietNaN, aIsSignalingNaN, bIsQuietNaN, bIsSignalingNaN;
792    flag aIsLargerSignificand;
793
794    aIsQuietNaN = float128_is_quiet_nan( a );
795    aIsSignalingNaN = float128_is_signaling_nan( a );
796    bIsQuietNaN = float128_is_quiet_nan( b );
797    bIsSignalingNaN = float128_is_signaling_nan( b );
798
799    if ( aIsSignalingNaN | bIsSignalingNaN ) float_raise( float_flag_invalid STATUS_VAR);
800
801    if ( STATUS(default_nan_mode) ) {
802        a.low = float128_default_nan_low;
803        a.high = float128_default_nan_high;
804        return a;
805    }
806
807    if (lt128(a.high<<1, a.low, b.high<<1, b.low)) {
808        aIsLargerSignificand = 0;
809    } else if (lt128(b.high<<1, b.low, a.high<<1, a.low)) {
810        aIsLargerSignificand = 1;
811    } else {
812        aIsLargerSignificand = (a.high < b.high) ? 1 : 0;
813    }
814
815    if (pickNaN(aIsQuietNaN, aIsSignalingNaN, bIsQuietNaN, bIsSignalingNaN,
816                aIsLargerSignificand)) {
817        return float128_maybe_silence_nan(b);
818    } else {
819        return float128_maybe_silence_nan(a);
820    }
821}
822
823#endif
824