Annotation of qemu/fpu/softfloat-native.c, revision 1.1.1.2

1.1       root        1: /* Native implementation of soft float functions. Only a single status
                      2:    context is supported */
                      3: #include "softfloat.h"
                      4: #include <math.h>
                      5: 
                      6: void set_float_rounding_mode(int val STATUS_PARAM)
                      7: {
                      8:     STATUS(float_rounding_mode) = val;
                      9: #if defined(_BSD) && !defined(__APPLE__)
                     10:     fpsetround(val);
                     11: #elif defined(__arm__)
                     12:     /* nothing to do */
                     13: #else
                     14:     fesetround(val);
                     15: #endif
                     16: }
                     17: 
                     18: #ifdef FLOATX80
                     19: void set_floatx80_rounding_precision(int val STATUS_PARAM)
                     20: {
                     21:     STATUS(floatx80_rounding_precision) = val;
                     22: }
                     23: #endif
                     24: 
                     25: #if defined(_BSD)
1.1.1.2 ! root       26: #define lrint(d)               ((long)rint(d))
        !            27: #define llrint(d)              ((long long)rint(d))
1.1       root       28: #endif
                     29: 
                     30: #if defined(__powerpc__)
                     31: 
                     32: /* correct (but slow) PowerPC rint() (glibc version is incorrect) */
                     33: double qemu_rint(double x)
                     34: {
                     35:     double y = 4503599627370496.0;
                     36:     if (fabs(x) >= y)
                     37:         return x;
                     38:     if (x < 0) 
                     39:         y = -y;
                     40:     y = (x + y) - y;
                     41:     if (y == 0.0)
                     42:         y = copysign(y, x);
                     43:     return y;
                     44: }
                     45: 
                     46: #define rint qemu_rint
                     47: #endif
                     48: 
                     49: /*----------------------------------------------------------------------------
                     50: | Software IEC/IEEE integer-to-floating-point conversion routines.
                     51: *----------------------------------------------------------------------------*/
                     52: float32 int32_to_float32(int v STATUS_PARAM)
                     53: {
                     54:     return (float32)v;
                     55: }
                     56: 
                     57: float64 int32_to_float64(int v STATUS_PARAM)
                     58: {
                     59:     return (float64)v;
                     60: }
                     61: 
                     62: #ifdef FLOATX80
                     63: floatx80 int32_to_floatx80(int v STATUS_PARAM)
                     64: {
                     65:     return (floatx80)v;
                     66: }
                     67: #endif
                     68: float32 int64_to_float32( int64_t v STATUS_PARAM)
                     69: {
                     70:     return (float32)v;
                     71: }
                     72: float64 int64_to_float64( int64_t v STATUS_PARAM)
                     73: {
                     74:     return (float64)v;
                     75: }
                     76: #ifdef FLOATX80
                     77: floatx80 int64_to_floatx80( int64_t v STATUS_PARAM)
                     78: {
                     79:     return (floatx80)v;
                     80: }
                     81: #endif
                     82: 
1.1.1.2 ! root       83: /* XXX: this code implements the x86 behaviour, not the IEEE one.  */
        !            84: #if HOST_LONG_BITS == 32
        !            85: static inline int long_to_int32(long a)
        !            86: {
        !            87:     return a;
        !            88: }
        !            89: #else
        !            90: static inline int long_to_int32(long a)
        !            91: {
        !            92:     if (a != (int32_t)a) 
        !            93:         a = 0x80000000;
        !            94:     return a;
        !            95: }
        !            96: #endif
        !            97: 
1.1       root       98: /*----------------------------------------------------------------------------
                     99: | Software IEC/IEEE single-precision conversion routines.
                    100: *----------------------------------------------------------------------------*/
                    101: int float32_to_int32( float32 a STATUS_PARAM)
                    102: {
1.1.1.2 ! root      103:     return long_to_int32(lrintf(a));
1.1       root      104: }
                    105: int float32_to_int32_round_to_zero( float32 a STATUS_PARAM)
                    106: {
                    107:     return (int)a;
                    108: }
                    109: int64_t float32_to_int64( float32 a STATUS_PARAM)
                    110: {
                    111:     return llrintf(a);
                    112: }
                    113: 
                    114: int64_t float32_to_int64_round_to_zero( float32 a STATUS_PARAM)
                    115: {
                    116:     return (int64_t)a;
                    117: }
                    118: 
                    119: float64 float32_to_float64( float32 a STATUS_PARAM)
                    120: {
                    121:     return a;
                    122: }
                    123: #ifdef FLOATX80
                    124: floatx80 float32_to_floatx80( float32 a STATUS_PARAM)
                    125: {
                    126:     return a;
                    127: }
                    128: #endif
                    129: 
                    130: /*----------------------------------------------------------------------------
                    131: | Software IEC/IEEE single-precision operations.
                    132: *----------------------------------------------------------------------------*/
                    133: float32 float32_round_to_int( float32 a STATUS_PARAM)
                    134: {
                    135:     return rintf(a);
                    136: }
                    137: 
                    138: float32 float32_rem( float32 a, float32 b STATUS_PARAM)
                    139: {
                    140:     return remainderf(a, b);
                    141: }
                    142: 
                    143: float32 float32_sqrt( float32 a STATUS_PARAM)
                    144: {
                    145:     return sqrtf(a);
                    146: }
                    147: char float32_compare( float32 a, float32 b STATUS_PARAM )
                    148: {
                    149:     if (a < b) {
                    150:         return -1;
                    151:     } else if (a == b) {
                    152:         return 0;
                    153:     } else if (a > b) {
                    154:         return 1;
                    155:     } else {
                    156:         return 2;
                    157:     }
                    158: }
                    159: char float32_compare_quiet( float32 a, float32 b STATUS_PARAM )
                    160: {
                    161:     if (isless(a, b)) {
                    162:         return -1;
                    163:     } else if (a == b) {
                    164:         return 0;
                    165:     } else if (isgreater(a, b)) {
                    166:         return 1;
                    167:     } else {
                    168:         return 2;
                    169:     }
                    170: }
                    171: char float32_is_signaling_nan( float32 a1)
                    172: {
                    173:     float32u u;
                    174:     uint32_t a;
                    175:     u.f = a1;
                    176:     a = u.i;
                    177:     return ( ( ( a>>22 ) & 0x1FF ) == 0x1FE ) && ( a & 0x003FFFFF );
                    178: }
                    179: 
                    180: /*----------------------------------------------------------------------------
                    181: | Software IEC/IEEE double-precision conversion routines.
                    182: *----------------------------------------------------------------------------*/
                    183: int float64_to_int32( float64 a STATUS_PARAM)
                    184: {
1.1.1.2 ! root      185:     return long_to_int32(lrint(a));
1.1       root      186: }
                    187: int float64_to_int32_round_to_zero( float64 a STATUS_PARAM)
                    188: {
                    189:     return (int)a;
                    190: }
                    191: int64_t float64_to_int64( float64 a STATUS_PARAM)
                    192: {
                    193:     return llrint(a);
                    194: }
                    195: int64_t float64_to_int64_round_to_zero( float64 a STATUS_PARAM)
                    196: {
                    197:     return (int64_t)a;
                    198: }
                    199: float32 float64_to_float32( float64 a STATUS_PARAM)
                    200: {
                    201:     return a;
                    202: }
                    203: #ifdef FLOATX80
                    204: floatx80 float64_to_floatx80( float64 a STATUS_PARAM)
                    205: {
                    206:     return a;
                    207: }
                    208: #endif
                    209: #ifdef FLOAT128
                    210: float128 float64_to_float128( float64 a STATUS_PARAM)
                    211: {
                    212:     return a;
                    213: }
                    214: #endif
                    215: 
                    216: /*----------------------------------------------------------------------------
                    217: | Software IEC/IEEE double-precision operations.
                    218: *----------------------------------------------------------------------------*/
                    219: float64 float64_round_to_int( float64 a STATUS_PARAM )
                    220: {
                    221: #if defined(__arm__)
                    222:     switch(STATUS(float_rounding_mode)) {
                    223:     default:
                    224:     case float_round_nearest_even:
                    225:         asm("rndd %0, %1" : "=f" (a) : "f"(a));
                    226:         break;
                    227:     case float_round_down:
                    228:         asm("rnddm %0, %1" : "=f" (a) : "f"(a));
                    229:         break;
                    230:     case float_round_up:
                    231:         asm("rnddp %0, %1" : "=f" (a) : "f"(a));
                    232:         break;
                    233:     case float_round_to_zero:
                    234:         asm("rnddz %0, %1" : "=f" (a) : "f"(a));
                    235:         break;
                    236:     }
                    237: #else
                    238:     return rint(a);
                    239: #endif
                    240: }
                    241: 
                    242: float64 float64_rem( float64 a, float64 b STATUS_PARAM)
                    243: {
                    244:     return remainder(a, b);
                    245: }
                    246: 
                    247: float64 float64_sqrt( float64 a STATUS_PARAM)
                    248: {
                    249:     return sqrt(a);
                    250: }
                    251: char float64_compare( float64 a, float64 b STATUS_PARAM )
                    252: {
                    253:     if (a < b) {
                    254:         return -1;
                    255:     } else if (a == b) {
                    256:         return 0;
                    257:     } else if (a > b) {
                    258:         return 1;
                    259:     } else {
                    260:         return 2;
                    261:     }
                    262: }
                    263: char float64_compare_quiet( float64 a, float64 b STATUS_PARAM )
                    264: {
                    265:     if (isless(a, b)) {
                    266:         return -1;
                    267:     } else if (a == b) {
                    268:         return 0;
                    269:     } else if (isgreater(a, b)) {
                    270:         return 1;
                    271:     } else {
                    272:         return 2;
                    273:     }
                    274: }
                    275: char float64_is_signaling_nan( float64 a1)
                    276: {
                    277:     float64u u;
                    278:     uint64_t a;
                    279:     u.f = a1;
                    280:     a = u.i;
                    281:     return
                    282:            ( ( ( a>>51 ) & 0xFFF ) == 0xFFE )
                    283:         && ( a & LIT64( 0x0007FFFFFFFFFFFF ) );
                    284: 
                    285: }
                    286: 
                    287: #ifdef FLOATX80
                    288: 
                    289: /*----------------------------------------------------------------------------
                    290: | Software IEC/IEEE extended double-precision conversion routines.
                    291: *----------------------------------------------------------------------------*/
                    292: int floatx80_to_int32( floatx80 a STATUS_PARAM)
                    293: {
1.1.1.2 ! root      294:     return long_to_int32(lrintl(a));
1.1       root      295: }
                    296: int floatx80_to_int32_round_to_zero( floatx80 a STATUS_PARAM)
                    297: {
                    298:     return (int)a;
                    299: }
                    300: int64_t floatx80_to_int64( floatx80 a STATUS_PARAM)
                    301: {
                    302:     return llrintl(a);
                    303: }
                    304: int64_t floatx80_to_int64_round_to_zero( floatx80 a STATUS_PARAM)
                    305: {
                    306:     return (int64_t)a;
                    307: }
                    308: float32 floatx80_to_float32( floatx80 a STATUS_PARAM)
                    309: {
                    310:     return a;
                    311: }
                    312: float64 floatx80_to_float64( floatx80 a STATUS_PARAM)
                    313: {
                    314:     return a;
                    315: }
                    316: 
                    317: /*----------------------------------------------------------------------------
                    318: | Software IEC/IEEE extended double-precision operations.
                    319: *----------------------------------------------------------------------------*/
                    320: floatx80 floatx80_round_to_int( floatx80 a STATUS_PARAM)
                    321: {
                    322:     return rintl(a);
                    323: }
                    324: floatx80 floatx80_rem( floatx80 a, floatx80 b STATUS_PARAM)
                    325: {
                    326:     return remainderl(a, b);
                    327: }
                    328: floatx80 floatx80_sqrt( floatx80 a STATUS_PARAM)
                    329: {
                    330:     return sqrtl(a);
                    331: }
                    332: char floatx80_compare( floatx80 a, floatx80 b STATUS_PARAM )
                    333: {
                    334:     if (a < b) {
                    335:         return -1;
                    336:     } else if (a == b) {
                    337:         return 0;
                    338:     } else if (a > b) {
                    339:         return 1;
                    340:     } else {
                    341:         return 2;
                    342:     }
                    343: }
                    344: char floatx80_compare_quiet( floatx80 a, floatx80 b STATUS_PARAM )
                    345: {
                    346:     if (isless(a, b)) {
                    347:         return -1;
                    348:     } else if (a == b) {
                    349:         return 0;
                    350:     } else if (isgreater(a, b)) {
                    351:         return 1;
                    352:     } else {
                    353:         return 2;
                    354:     }
                    355: }
                    356: char floatx80_is_signaling_nan( floatx80 a1)
                    357: {
                    358:     floatx80u u;
                    359:     u.f = a1;
                    360:     return ( ( u.i.high & 0x7FFF ) == 0x7FFF ) && (bits64) ( u.i.low<<1 );
                    361: }
                    362: 
                    363: #endif

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.