/*----------------------------------------------------------------------------
| Assuming at least one of the two 128-bit floating-point values pointed to by
| `aWPtr' and `bWPtr' is a NaN, stores the combined NaN result at the location
| pointed to by `zWPtr'.  If either original floating-point value is a
| signaling NaN, the invalid exception is raised.  Each of `aWPtr', `bWPtr',
| and `zWPtr' points to an array of four 32-bit elements that concatenate in
| the platform's normal endian order to form a 128-bit floating-point value.
*----------------------------------------------------------------------------*/
void
 softfloat_propagateNaNF128M(
     const uint32_t *aWPtr, const uint32_t *bWPtr, uint32_t *zWPtr )
{
    bool isSigNaNA;
    const uint32_t *ptr;
    bool isSigNaNB;
    uint32_t uiA96, uiB96, wordMagA, wordMagB;

    isSigNaNA = f128M_isSignalingNaN( (const float128_t *) aWPtr );
    ptr = aWPtr;
    if ( ! bWPtr ) {
        if ( isSigNaNA ) softfloat_raiseFlags( softfloat_flag_invalid );
        goto copy;
    }
    isSigNaNB = f128M_isSignalingNaN( (const float128_t *) bWPtr );
    if ( isSigNaNA | isSigNaNB ) {
        softfloat_raiseFlags( softfloat_flag_invalid );
        if ( isSigNaNA ) {
            if ( isSigNaNB ) goto returnLargerUIMag;
            if ( softfloat_isNaNF128M( bWPtr ) ) goto copyB;
            goto copy;
        } else {
            if ( softfloat_isNaNF128M( aWPtr ) ) goto copy;
            goto copyB;
        }
    }
 returnLargerUIMag:
    uiA96 = aWPtr[indexWordHi( 4 )];
    uiB96 = bWPtr[indexWordHi( 4 )];
    wordMagA = uiA96 & 0x7FFFFFFF;
    wordMagB = uiB96 & 0x7FFFFFFF;
    if ( wordMagA < wordMagB ) goto copyB;
    if ( wordMagB < wordMagA ) goto copy;
    wordMagA = aWPtr[indexWord( 4, 2 )];
    wordMagB = bWPtr[indexWord( 4, 2 )];
    if ( wordMagA < wordMagB ) goto copyB;
    if ( wordMagB < wordMagA ) goto copy;
    wordMagA = aWPtr[indexWord( 4, 1 )];
    wordMagB = bWPtr[indexWord( 4, 1 )];
    if ( wordMagA < wordMagB ) goto copyB;
    if ( wordMagB < wordMagA ) goto copy;
    wordMagA = aWPtr[indexWord( 4, 0 )];
    wordMagB = bWPtr[indexWord( 4, 0 )];
    if ( wordMagA < wordMagB ) goto copyB;
    if ( wordMagB < wordMagA ) goto copy;
    if ( uiA96 < uiB96 ) goto copy;
 copyB:
    ptr = bWPtr;
 copy:
    zWPtr[indexWordHi( 4 )] = ptr[indexWordHi( 4 )] | 0x00008000;
    zWPtr[indexWord( 4, 2 )] = ptr[indexWord( 4, 2 )];
    zWPtr[indexWord( 4, 1 )] = ptr[indexWord( 4, 1 )];
    zWPtr[indexWord( 4, 0 )] = ptr[indexWord( 4, 0 )];

}
Exemplo n.º 2
0
void
 test_az_f128(
     void trueFunction( const float128_t *, float128_t * ),
     void subjFunction( const float128_t *, float128_t * )
 )
{
    int count;
    float128_t trueZ;
    uint_fast8_t trueFlags;
    float128_t subjZ;
    uint_fast8_t subjFlags;

    genCases_f128_a_init();
    genCases_writeTestsTotal( testLoops_forever );
    verCases_errorCount = 0;
    verCases_tenThousandsCount = 0;
    count = 10000;
    while ( ! genCases_done || testLoops_forever ) {
        genCases_f128_a_next();
        *testLoops_trueFlagsPtr = 0;
        trueFunction( &genCases_f128_a, &trueZ );
        trueFlags = *testLoops_trueFlagsPtr;
        testLoops_subjFlagsFunction();
        subjFunction( &genCases_f128_a, &subjZ );
        subjFlags = testLoops_subjFlagsFunction();
        --count;
        if ( ! count ) {
            verCases_perTenThousand();
            count = 10000;
        }
        if ( ! f128M_same( &trueZ, &subjZ ) || (trueFlags != subjFlags) ) {
            if (
                ! verCases_checkNaNs
                    && f128M_isSignalingNaN( &genCases_f128_a )
            ) {
                trueFlags |= softfloat_flag_invalid;
            }
            if (
                   verCases_checkNaNs
                || ! f128M_isNaN( &trueZ )
                || ! f128M_isNaN( &subjZ )
                || f128M_isSignalingNaN( &subjZ )
                || (trueFlags != subjFlags)
            ) {
                ++verCases_errorCount;
                verCases_writeErrorFound( 10000 - count );
                writeCase_a_f128M( &genCases_f128_a, "  " );
                writeCase_z_f128M( &trueZ, trueFlags, &subjZ, subjFlags );
                if ( verCases_errorCount == verCases_maxErrorCount ) break;
            }
        }
    }
    verCases_writeTestsPerformed( 10000 - count );

}
Exemplo n.º 3
0
void
 test_a_f128_z_ui32_rx(
     uint_fast32_t trueFunction( const float128_t *, uint_fast8_t, bool ),
     uint_fast32_t subjFunction( const float128_t *, uint_fast8_t, bool ),
     uint_fast8_t roundingMode,
     bool exact
 )
{
    int count;
    uint_fast32_t trueZ;
    uint_fast8_t trueFlags;
    uint_fast32_t subjZ;
    uint_fast8_t subjFlags;

    genCases_f128_a_init();
    genCases_writeTestsTotal( testLoops_forever );
    verCases_errorCount = 0;
    verCases_tenThousandsCount = 0;
    count = 10000;
    while ( ! genCases_done || testLoops_forever ) {
        genCases_f128_a_next();
        *testLoops_trueFlagsPtr = 0;
        trueZ = trueFunction( &genCases_f128_a, roundingMode, exact );
        trueFlags = *testLoops_trueFlagsPtr;
        testLoops_subjFlagsFunction();
        subjZ = subjFunction( &genCases_f128_a, roundingMode, exact );
        subjFlags = testLoops_subjFlagsFunction();
        --count;
        if ( ! count ) {
            verCases_perTenThousand();
            count = 10000;
        }
        if ( (trueZ != subjZ) || (trueFlags != subjFlags) ) {
            if (
                ! verCases_checkNaNs
                    && f128M_isSignalingNaN( &genCases_f128_a )
            ) {
                trueFlags |= softfloat_flag_invalid;
            }
            if (
                   (trueZ != 0xFFFFFFFF)
                || (subjZ != 0xFFFFFFFF)
                || (trueFlags != softfloat_flag_invalid)
                || (subjFlags != softfloat_flag_invalid)
            ) {
                ++verCases_errorCount;
                verCases_writeErrorFound( 10000 - count );
                writeCase_a_f128M( &genCases_f128_a, "  " );
                writeCase_z_ui32( trueZ, trueFlags, subjZ, subjFlags );
                if ( verCases_errorCount == verCases_maxErrorCount ) break;
            }
        }
    }
    verCases_writeTestsPerformed( 10000 - count );

}
Exemplo n.º 4
0
bool f128M_eq( const float128_t *aPtr, const float128_t *bPtr )
{
    const uint32_t *aWPtr, *bWPtr;
    uint32_t wordA, wordB, uiA96, uiB96;
    bool possibleOppositeZeros;
    uint32_t mashWord;

    aWPtr = (const uint32_t *) aPtr;
    bWPtr = (const uint32_t *) bPtr;
    wordA = aWPtr[indexWord( 4, 2 )];
    wordB = bWPtr[indexWord( 4, 2 )];
    if ( wordA != wordB ) goto false_checkSigNaNs;
    uiA96 = aWPtr[indexWordHi( 4 )];
    uiB96 = bWPtr[indexWordHi( 4 )];
    possibleOppositeZeros = false;
    if ( uiA96 != uiB96 ) {
        possibleOppositeZeros = (((uiA96 | uiB96) & 0x7FFFFFFF) == 0);
        if ( ! possibleOppositeZeros ) goto false_checkSigNaNs;
    }
    mashWord = wordA | wordB;
    wordA = aWPtr[indexWord( 4, 1 )];
    wordB = bWPtr[indexWord( 4, 1 )];
    if ( wordA != wordB ) goto false_checkSigNaNs;
    mashWord |= wordA | wordB;
    wordA = aWPtr[indexWord( 4, 0 )];
    wordB = bWPtr[indexWord( 4, 0 )];
    if ( wordA != wordB ) goto false_checkSigNaNs;
    if ( possibleOppositeZeros && ((mashWord | wordA | wordB) != 0) ) {
        goto false_checkSigNaNs;
    }
    if ( ! softfloat_isNaNF128M( aWPtr ) && ! softfloat_isNaNF128M( bWPtr ) ) {
        return true;
    }
 false_checkSigNaNs:
    if (
           f128M_isSignalingNaN( (const float128_t *) aWPtr )
        || f128M_isSignalingNaN( (const float128_t *) bWPtr )
    ) {
        softfloat_raiseFlags( softfloat_flag_invalid );
    }
    return false;

}
Exemplo n.º 5
0
/*----------------------------------------------------------------------------
| Assuming the 128-bit floating-point value pointed to by `aWPtr' is a NaN,
| converts this NaN to the common NaN form, and stores the resulting common
| NaN at the location pointed to by `zPtr'.  If the NaN is a signaling NaN,
| the invalid exception is raised.  Argument `aWPtr' points to an array of
| four 32-bit elements that concatenate in the platform's normal endian order
| to form a 128-bit floating-point value.
*----------------------------------------------------------------------------*/
void
 softfloat_f128MToCommonNaN( const uint32_t *aWPtr, struct commonNaN *zPtr )
{

    if ( f128M_isSignalingNaN( (const float128_t *) aWPtr ) ) {
        softfloat_raiseFlags( softfloat_flag_invalid );
    }
    zPtr->sign = aWPtr[indexWordHi( 4 )]>>31;
    softfloat_shortShiftLeft128M( aWPtr, 16, (uint32_t *) &zPtr->v0 );

}
Exemplo n.º 6
0
/*----------------------------------------------------------------------------
| Assuming at least one of the two 128-bit floating-point values pointed to by
| `aWPtr' and `bWPtr' is a NaN, stores the combined NaN result at the location
| pointed to by `zWPtr'.  If either original floating-point value is a
| signaling NaN, the invalid exception is raised.  Each of `aWPtr', `bWPtr',
| and `zWPtr' points to an array of four 32-bit elements that concatenate in
| the platform's normal endian order to form a 128-bit floating-point value.
*----------------------------------------------------------------------------*/
void
 softfloat_propagateNaNF128M(
     const uint32_t *aWPtr, const uint32_t *bWPtr, uint32_t *zWPtr )
{
    bool isSigNaNA;
    const uint32_t *ptr;

    ptr = aWPtr;
    isSigNaNA = f128M_isSignalingNaN( (const float128_t *) aWPtr );
    if (
        isSigNaNA
            || (bWPtr && f128M_isSignalingNaN( (const float128_t *) bWPtr ))
    ) {
        softfloat_raiseFlags( softfloat_flag_invalid );
        if ( isSigNaNA ) goto copy;
    }
    if ( ! softfloat_isNaNF128M( aWPtr ) ) ptr = bWPtr;
 copy:
    zWPtr[indexWordHi( 4 )] = ptr[indexWordHi( 4 )] | 0x00008000;
    zWPtr[indexWord( 4, 2 )] = ptr[indexWord( 4, 2 )];
    zWPtr[indexWord( 4, 1 )] = ptr[indexWord( 4, 1 )];
    zWPtr[indexWord( 4, 0 )] = ptr[indexWord( 4, 0 )];

}