| 1 | // Licensed to the .NET Foundation under one or more agreements. | 
| 2 | // The .NET Foundation licenses this file to you under the MIT license. | 
| 3 | // See the LICENSE file in the project root for more information. | 
| 4 |  | 
| 5 | /*============================================================================= | 
| 6 | ** | 
| 7 | ** Source: test1.c | 
| 8 | ** | 
| 9 | ** Purpose: Test to ensure that asinhf return the correct values | 
| 10 | **  | 
| 11 | ** Dependencies: PAL_Initialize | 
| 12 | **               PAL_Terminate | 
| 13 | **               Fail | 
| 14 | **               fabs | 
| 15 | ** | 
| 16 | **===========================================================================*/ | 
| 17 |  | 
| 18 | #include <palsuite.h> | 
| 19 |  | 
| 20 | // binary32 (float) has a machine epsilon of 2^-23 (approx. 1.19e-07). However, this  | 
| 21 | // is slightly too accurate when writing tests meant to run against libm implementations | 
| 22 | // for various platforms. 2^-21 (approx. 4.76e-07) seems to be as accurate as we can get. | 
| 23 | // | 
| 24 | // The tests themselves will take PAL_EPSILON and adjust it according to the expected result | 
| 25 | // so that the delta used for comparison will compare the most significant digits and ignore | 
| 26 | // any digits that are outside the double precision range (6-9 digits). | 
| 27 |  | 
| 28 | // For example, a test with an expect result in the format of 0.xxxxxxxxx will use PAL_EPSILON | 
| 29 | // for the variance, while an expected result in the format of 0.0xxxxxxxxx will use | 
| 30 | // PAL_EPSILON / 10 and and expected result in the format of x.xxxxxx will use PAL_EPSILON * 10. | 
| 31 | #define PAL_EPSILON 4.76837158e-07 | 
| 32 |  | 
| 33 | #define PAL_NAN     sqrtf(-1.0f) | 
| 34 | #define PAL_POSINF -logf(0.0f) | 
| 35 | #define PAL_NEGINF  logf(0.0f) | 
| 36 |  | 
| 37 | /** | 
| 38 |  * Helper test structure | 
| 39 |  */ | 
| 40 | struct test | 
| 41 | { | 
| 42 |     float value;     /* value to test the function with */ | 
| 43 |     float expected;  /* expected result */ | 
| 44 |     float variance;  /* maximum delta between the expected and actual result */ | 
| 45 | }; | 
| 46 |  | 
| 47 | /** | 
| 48 |  * validate | 
| 49 |  * | 
| 50 |  * test validation function | 
| 51 |  */ | 
| 52 | void __cdecl validate(float value, float expected, float variance) | 
| 53 | { | 
| 54 |     float result = asinhf(value); | 
| 55 |  | 
| 56 |     /* | 
| 57 |      * The test is valid when the difference between result | 
| 58 |      * and expected is less than or equal to variance | 
| 59 |      */ | 
| 60 |     float delta = fabsf(result - expected); | 
| 61 |  | 
| 62 |     if (delta > variance) | 
| 63 |     { | 
| 64 |         Fail("asinhf(%g) returned %10.9g when it should have returned %10.9g" , | 
| 65 |              value, result, expected); | 
| 66 |     } | 
| 67 | } | 
| 68 |  | 
| 69 | /** | 
| 70 |  * validate | 
| 71 |  * | 
| 72 |  * test validation function for values returning NaN | 
| 73 |  */ | 
| 74 | void __cdecl validate_isnan(float value) | 
| 75 | { | 
| 76 |     float result = asinhf(value); | 
| 77 |  | 
| 78 |     if (!_isnanf(result)) | 
| 79 |     { | 
| 80 |         Fail("asinhf(%g) returned %10.9g when it should have returned %10.9g" , | 
| 81 |              value, result, PAL_NAN); | 
| 82 |     } | 
| 83 | } | 
| 84 |  | 
| 85 | /** | 
| 86 |  * validate | 
| 87 |  * | 
| 88 |  * test validation function for values returning +INF | 
| 89 |  */ | 
| 90 | void __cdecl validate_isinf_positive(float value) | 
| 91 | { | 
| 92 |     float result = asinhf(value); | 
| 93 |  | 
| 94 |     if (result != PAL_POSINF) | 
| 95 |     { | 
| 96 |         Fail("asinhf(%g) returned %10.9g when it should have returned %10.9g" , | 
| 97 |              value, result, PAL_POSINF); | 
| 98 |     } | 
| 99 | } | 
| 100 |  | 
| 101 | /** | 
| 102 |  * main | 
| 103 |  *  | 
| 104 |  * executable entry point | 
| 105 |  */ | 
| 106 | int __cdecl main(int argc, char **argv) | 
| 107 | { | 
| 108 |     struct test tests[] =  | 
| 109 |     { | 
| 110 |         /* value            expected         variance */ | 
| 111 |         {  0,               0,               PAL_EPSILON }, | 
| 112 |         {  0.323712439f,    0.318309886f,    PAL_EPSILON },           // expected:  1 / pi | 
| 113 |         {  0.448075979f,    0.434294482f,    PAL_EPSILON },           // expected:  log10f(e) | 
| 114 |         {  0.680501678f,    0.636619772f,    PAL_EPSILON },           // expected:  2 / pi | 
| 115 |         {  0.75,            0.693147181f,    PAL_EPSILON },           // expected:  ln(2) | 
| 116 |         {  0.767523145f,    0.707106781f,    PAL_EPSILON },           // expected:  1 / sqrtf(2) | 
| 117 |         {  0.868670961f,    0.785398163f,    PAL_EPSILON },           // expected:  pi / 4 | 
| 118 |         {  1.17520119f,     1,               PAL_EPSILON * 10 }, | 
| 119 |         {  1.38354288f,     1.12837917f,     PAL_EPSILON * 10 },      // expected:  2 / sqrtf(pi) | 
| 120 |         {  1.93506682f,     1.41421356f,     PAL_EPSILON * 10 },      // expected:  sqrtf(2) | 
| 121 |         {  1.99789801f,     1.44269504f,     PAL_EPSILON * 10 },      // expected:  logf2(e) | 
| 122 |         {  2.30129890f,     1.57079633f,     PAL_EPSILON * 10 },      // expected:  pi / 2 | 
| 123 |         {  4.95f,           2.30258509f,     PAL_EPSILON * 10 },      // expected:  ln(10) | 
| 124 |         {  7.54413710f,     2.71828183f,     PAL_EPSILON * 10 },      // expected:  e | 
| 125 |         {  11.5487394f,     3.14159265f,     PAL_EPSILON * 10 },      // expected:  pi | 
| 126 |         {  PAL_POSINF,      PAL_POSINF,      0 }, | 
| 127 |     }; | 
| 128 |  | 
| 129 |     /* PAL initialization */ | 
| 130 |     if (PAL_Initialize(argc, argv) != 0) | 
| 131 |     { | 
| 132 |         return FAIL; | 
| 133 |     } | 
| 134 |  | 
| 135 |     for (int i = 0; i < (sizeof(tests) / sizeof(struct test)); i++) | 
| 136 |     { | 
| 137 |         validate( tests[i].value,  tests[i].expected, tests[i].variance); | 
| 138 |         validate(-tests[i].value, -tests[i].expected, tests[i].variance); | 
| 139 |     } | 
| 140 |  | 
| 141 |     validate_isnan(PAL_NAN); | 
| 142 |  | 
| 143 |     PAL_Terminate(); | 
| 144 |     return PASS; | 
| 145 | } | 
| 146 |  |