1414namespace dart {
1515namespace compiler {
1616
17+ TEST_CASE (ReciprocalOps) {
18+ EXPECT_EQ (true , isinf (ReciprocalEstimate (-0 .0f )));
19+ EXPECT_EQ (true , signbit (ReciprocalEstimate (-0 .0f )));
20+ EXPECT_EQ (true , isinf (ReciprocalEstimate (0 .0f )));
21+ EXPECT_EQ (true , !signbit (ReciprocalEstimate (0 .0f )));
22+ EXPECT_EQ (true , isnan (ReciprocalEstimate (NAN)));
23+
24+ #define AS_UINT32 (v ) (bit_cast<uint32_t , float >(v))
25+ #define EXPECT_BITWISE_EQ (a, b ) EXPECT_EQ(AS_UINT32(a), AS_UINT32(b))
26+
27+ EXPECT_BITWISE_EQ (0 .0f , ReciprocalEstimate (kPosInfinity ));
28+ EXPECT_BITWISE_EQ (-0 .0f , ReciprocalEstimate (kNegInfinity ));
29+ EXPECT_BITWISE_EQ (2 .0f , ReciprocalStep (0 .0f , kPosInfinity ));
30+ EXPECT_BITWISE_EQ (2 .0f , ReciprocalStep (0 .0f , kNegInfinity ));
31+ EXPECT_BITWISE_EQ (2 .0f , ReciprocalStep (-0 .0f , kPosInfinity ));
32+ EXPECT_BITWISE_EQ (2 .0f , ReciprocalStep (-0 .0f , kNegInfinity ));
33+ EXPECT_BITWISE_EQ (2 .0f , ReciprocalStep (kPosInfinity , 0 .0f ));
34+ EXPECT_BITWISE_EQ (2 .0f , ReciprocalStep (kNegInfinity , 0 .0f ));
35+ EXPECT_BITWISE_EQ (2 .0f , ReciprocalStep (kPosInfinity , -0 .0f ));
36+ EXPECT_BITWISE_EQ (2 .0f , ReciprocalStep (kNegInfinity , -0 .0f ));
37+ EXPECT_EQ (true , isnan (ReciprocalStep (NAN, 1 .0f )));
38+ EXPECT_EQ (true , isnan (ReciprocalStep (1 .0f , NAN)));
39+
40+ EXPECT_EQ (true , isnan (ReciprocalSqrtEstimate (-1 .0f )));
41+ EXPECT_EQ (true , isnan (ReciprocalSqrtEstimate (kNegInfinity )));
42+ EXPECT_EQ (true , isnan (ReciprocalSqrtEstimate (-1 .0f )));
43+ EXPECT_EQ (true , isinf (ReciprocalSqrtEstimate (-0 .0f )));
44+ EXPECT_EQ (true , signbit (ReciprocalSqrtEstimate (-0 .0f )));
45+ EXPECT_EQ (true , isinf (ReciprocalSqrtEstimate (0 .0f )));
46+ EXPECT_EQ (true , !signbit (ReciprocalSqrtEstimate (0 .0f )));
47+ EXPECT_EQ (true , isnan (ReciprocalSqrtEstimate (NAN)));
48+ EXPECT_BITWISE_EQ (0 .0f , ReciprocalSqrtEstimate (kPosInfinity ));
49+
50+ EXPECT_BITWISE_EQ (1 .5f , ReciprocalSqrtStep (0 .0f , kPosInfinity ));
51+ EXPECT_BITWISE_EQ (1 .5f , ReciprocalSqrtStep (0 .0f , kNegInfinity ));
52+ EXPECT_BITWISE_EQ (1 .5f , ReciprocalSqrtStep (-0 .0f , kPosInfinity ));
53+ EXPECT_BITWISE_EQ (1 .5f , ReciprocalSqrtStep (-0 .0f , kNegInfinity ));
54+ EXPECT_BITWISE_EQ (1 .5f , ReciprocalSqrtStep (kPosInfinity , 0 .0f ));
55+ EXPECT_BITWISE_EQ (1 .5f , ReciprocalSqrtStep (kNegInfinity , 0 .0f ));
56+ EXPECT_BITWISE_EQ (1 .5f , ReciprocalSqrtStep (kPosInfinity , -0 .0f ));
57+ EXPECT_BITWISE_EQ (1 .5f , ReciprocalSqrtStep (kNegInfinity , -0 .0f ));
58+ EXPECT_EQ (true , isnan (ReciprocalSqrtStep (NAN, 1 .0f )));
59+ EXPECT_EQ (true , isnan (ReciprocalSqrtStep (1 .0f , NAN)));
60+
61+ #undef AS_UINT32
62+ #undef EXPECT_BITWISE_EQ
63+ }
64+
1765#define __ assembler->
1866
1967ASSEMBLER_TEST_GENERATE (Simple, assembler) {
@@ -3430,43 +3478,6 @@ ASSEMBLER_TEST_RUN(Vmaxqs, test) {
34303478 }
34313479}
34323480
3433- // This is the same function as in the Simulator.
3434- static float arm_recip_estimate (float a) {
3435- // From the ARM Architecture Reference Manual A2-85.
3436- if (isinf (a) || (fabs (a) >= exp2f (126 )))
3437- return 0.0 ;
3438- else if (a == 0.0 )
3439- return kPosInfinity ;
3440- else if (isnan (a))
3441- return a;
3442-
3443- uint32_t a_bits = bit_cast<uint32_t , float >(a);
3444- // scaled = '0011 1111 1110' : a<22:0> : Zeros(29)
3445- uint64_t scaled = (static_cast <uint64_t >(0x3fe ) << 52 ) |
3446- ((static_cast <uint64_t >(a_bits) & 0x7fffff ) << 29 );
3447- // result_exp = 253 - UInt(a<30:23>)
3448- int32_t result_exp = 253 - ((a_bits >> 23 ) & 0xff );
3449- ASSERT ((result_exp >= 1 ) && (result_exp <= 252 ));
3450-
3451- double scaled_d = bit_cast<double , uint64_t >(scaled);
3452- ASSERT ((scaled_d >= 0.5 ) && (scaled_d < 1.0 ));
3453-
3454- // a in units of 1/512 rounded down.
3455- int32_t q = static_cast <int32_t >(scaled_d * 512.0 );
3456- // reciprocal r.
3457- double r = 1.0 / ((static_cast <double >(q) + 0.5 ) / 512.0 );
3458- // r in units of 1/256 rounded to nearest.
3459- int32_t s = static_cast <int32_t >(256.0 * r + 0.5 );
3460- double estimate = static_cast <double >(s) / 256.0 ;
3461- ASSERT ((estimate >= 1.0 ) && (estimate <= (511.0 / 256.0 )));
3462-
3463- // result = sign : result_exp<7:0> : estimate<51:29>
3464- int32_t result_bits =
3465- (a_bits & 0x80000000 ) | ((result_exp & 0xff ) << 23 ) |
3466- ((bit_cast<uint64_t , double >(estimate) >> 29 ) & 0x7fffff );
3467- return bit_cast<float , int32_t >(result_bits);
3468- }
3469-
34703481ASSEMBLER_TEST_GENERATE (Vrecpeqs, assembler) {
34713482 if (TargetCPUFeatures::neon_supported ()) {
34723483 __ LoadSImmediate (S4, 147.0 );
@@ -3483,7 +3494,7 @@ ASSEMBLER_TEST_RUN(Vrecpeqs, test) {
34833494 if (TargetCPUFeatures::neon_supported ()) {
34843495 typedef float (*Vrecpeqs)() DART_UNUSED;
34853496 float res = EXECUTE_TEST_CODE_FLOAT (Vrecpeqs, test->entry ());
3486- EXPECT_FLOAT_EQ (arm_recip_estimate (147.0 ), res, 0 .0001f );
3497+ EXPECT_FLOAT_EQ (ReciprocalEstimate (147.0 ), res, 0 .0001f );
34873498 }
34883499}
34893500
@@ -3540,60 +3551,6 @@ ASSEMBLER_TEST_RUN(Reciprocal, test) {
35403551 }
35413552}
35423553
3543- static float arm_reciprocal_sqrt_estimate (float a) {
3544- // From the ARM Architecture Reference Manual A2-87.
3545- if (isinf (a) || (fabs (a) >= exp2f (126 )))
3546- return 0.0 ;
3547- else if (a == 0.0 )
3548- return kPosInfinity ;
3549- else if (isnan (a))
3550- return a;
3551-
3552- uint32_t a_bits = bit_cast<uint32_t , float >(a);
3553- uint64_t scaled;
3554- if (((a_bits >> 23 ) & 1 ) != 0 ) {
3555- // scaled = '0 01111111101' : operand<22:0> : Zeros(29)
3556- scaled = (static_cast <uint64_t >(0x3fd ) << 52 ) |
3557- ((static_cast <uint64_t >(a_bits) & 0x7fffff ) << 29 );
3558- } else {
3559- // scaled = '0 01111111110' : operand<22:0> : Zeros(29)
3560- scaled = (static_cast <uint64_t >(0x3fe ) << 52 ) |
3561- ((static_cast <uint64_t >(a_bits) & 0x7fffff ) << 29 );
3562- }
3563- // result_exp = (380 - UInt(operand<30:23>) DIV 2;
3564- int32_t result_exp = (380 - ((a_bits >> 23 ) & 0xff )) / 2 ;
3565-
3566- double scaled_d = bit_cast<double , uint64_t >(scaled);
3567- ASSERT ((scaled_d >= 0.25 ) && (scaled_d < 1.0 ));
3568-
3569- double r;
3570- if (scaled_d < 0.5 ) {
3571- // range 0.25 <= a < 0.5
3572-
3573- // a in units of 1/512 rounded down.
3574- int32_t q0 = static_cast <int32_t >(scaled_d * 512.0 );
3575- // reciprocal root r.
3576- r = 1.0 / sqrt ((static_cast <double >(q0) + 0.5 ) / 512.0 );
3577- } else {
3578- // range 0.5 <= a < 1.0
3579-
3580- // a in units of 1/256 rounded down.
3581- int32_t q1 = static_cast <int32_t >(scaled_d * 256.0 );
3582- // reciprocal root r.
3583- r = 1.0 / sqrt ((static_cast <double >(q1) + 0.5 ) / 256.0 );
3584- }
3585- // r in units of 1/256 rounded to nearest.
3586- int32_t s = static_cast <int >(256.0 * r + 0.5 );
3587- double estimate = static_cast <double >(s) / 256.0 ;
3588- ASSERT ((estimate >= 1.0 ) && (estimate <= (511.0 / 256.0 )));
3589-
3590- // result = 0 : result_exp<7:0> : estimate<51:29>
3591- int32_t result_bits =
3592- ((result_exp & 0xff ) << 23 ) |
3593- ((bit_cast<uint64_t , double >(estimate) >> 29 ) & 0x7fffff );
3594- return bit_cast<float , int32_t >(result_bits);
3595- }
3596-
35973554ASSEMBLER_TEST_GENERATE (Vrsqrteqs, assembler) {
35983555 if (TargetCPUFeatures::neon_supported ()) {
35993556 __ LoadSImmediate (S4, 147.0 );
@@ -3611,7 +3568,7 @@ ASSEMBLER_TEST_RUN(Vrsqrteqs, test) {
36113568 if (TargetCPUFeatures::neon_supported ()) {
36123569 typedef float (*Vrsqrteqs)() DART_UNUSED;
36133570 float res = EXECUTE_TEST_CODE_FLOAT (Vrsqrteqs, test->entry ());
3614- EXPECT_FLOAT_EQ (arm_reciprocal_sqrt_estimate (147.0 ), res, 0 .0001f );
3571+ EXPECT_FLOAT_EQ (ReciprocalSqrtEstimate (147.0 ), res, 0 .0001f );
36153572 }
36163573}
36173574
0 commit comments