filename | test/testmath.c |
changeset | 192:580d6c4d7802 |
prev | 185:6755a04c447f |
author | nkeynes |
date | Wed Jan 07 04:39:04 2009 +0000 (15 years ago) |
branch | lxdream-mem |
permissions | -rw-r--r-- |
last change | Introduce sh4_finalize_instruction to clean-up on instruction exits Remove the sh4_flush_icache special cases, now works through the general case. |
file | annotate | diff | log | raw |
nkeynes@185 | 1 | #include <stdio.h> |
nkeynes@185 | 2 | #include <assert.h> |
nkeynes@185 | 3 | #include <math.h> |
nkeynes@185 | 4 | |
nkeynes@185 | 5 | #define write_string(x) printf(x) |
nkeynes@185 | 6 | #define write_int(x) printf( "%08X", x ) |
nkeynes@185 | 7 | |
nkeynes@185 | 8 | int do_fsca(int angle, float *a, float *b); |
nkeynes@185 | 9 | float do_fsrra( float param ); |
nkeynes@185 | 10 | float do_fipr( float *vectora, float *vectorb ); |
nkeynes@185 | 11 | float do_fipr2( float *vectora, float *vectorb ); |
nkeynes@185 | 12 | void do_ftrv( float *matrix, float *vector ); |
nkeynes@185 | 13 | void do_ftrv2( float *matrix, float *vector ); |
nkeynes@185 | 14 | |
nkeynes@185 | 15 | unsigned int get_fpscr(); |
nkeynes@185 | 16 | void set_fpscr( unsigned int fpscr ); |
nkeynes@185 | 17 | |
nkeynes@185 | 18 | #define MAX_FLOAT_DIFF 0.00001 |
nkeynes@185 | 19 | |
nkeynes@192 | 20 | static inline float inttof( unsigned int i ) |
nkeynes@192 | 21 | { |
nkeynes@192 | 22 | return *((float *)&i); |
nkeynes@192 | 23 | } |
nkeynes@192 | 24 | |
nkeynes@192 | 25 | static inline double longtod( unsigned long long l ) |
nkeynes@192 | 26 | { |
nkeynes@192 | 27 | return *((double *)&l); |
nkeynes@192 | 28 | } |
nkeynes@192 | 29 | |
nkeynes@192 | 30 | static inline unsigned int ftoint( float f ) |
nkeynes@192 | 31 | { |
nkeynes@192 | 32 | return *((unsigned int *)&f); |
nkeynes@192 | 33 | } |
nkeynes@192 | 34 | |
nkeynes@192 | 35 | static inline unsigned long long dtolong( double d ) |
nkeynes@192 | 36 | { |
nkeynes@192 | 37 | return *((unsigned long long *)&d); |
nkeynes@192 | 38 | } |
nkeynes@192 | 39 | |
nkeynes@192 | 40 | #define QNANF inttof(0x7FBFFFFF) |
nkeynes@192 | 41 | #define QNAND longtod(0x7FF7FFFFFFFFFFFFLL) |
nkeynes@185 | 42 | |
nkeynes@185 | 43 | int compare_float( float a, float b ) |
nkeynes@185 | 44 | { |
nkeynes@192 | 45 | if( ftoint(a) == ftoint(b) ) /* Exact bit-pattern match */ |
nkeynes@185 | 46 | return 1; |
nkeynes@185 | 47 | float diff = (a>b?(a-b):(b-a)); |
nkeynes@185 | 48 | return diff < MAX_FLOAT_DIFF; |
nkeynes@185 | 49 | } |
nkeynes@185 | 50 | |
nkeynes@192 | 51 | #define FTOINT(a) (*((unsigned int *)&a)) |
nkeynes@192 | 52 | |
nkeynes@192 | 53 | #define TEST_FEQUALS( a, b ) if( !compare_float(a,b) ) { printf( "Assertion failed at %s.%d: expected %.8f (%08X) but was %.8f (%08X)\n", __FILE__, __LINE__, a, FTOINT(a), b, FTOINT(b) ); return 1; } |
nkeynes@185 | 54 | |
nkeynes@185 | 55 | int test_fsca( int angle, float expect_a, float expect_b ) |
nkeynes@185 | 56 | { |
nkeynes@185 | 57 | float a = 10.0; |
nkeynes@185 | 58 | float b = 10.0; |
nkeynes@185 | 59 | do_fsca(angle, &a, &b ); |
nkeynes@185 | 60 | |
nkeynes@185 | 61 | TEST_FEQUALS(expect_a, a); |
nkeynes@185 | 62 | TEST_FEQUALS(expect_b, b); |
nkeynes@185 | 63 | } |
nkeynes@185 | 64 | |
nkeynes@185 | 65 | int test_fsrra( float f, float expect ) |
nkeynes@185 | 66 | { |
nkeynes@185 | 67 | float f2 = do_fsrra( f ); |
nkeynes@185 | 68 | TEST_FEQUALS( expect, f2 ); |
nkeynes@185 | 69 | } |
nkeynes@185 | 70 | |
nkeynes@185 | 71 | void test_coercion( float f ) |
nkeynes@185 | 72 | { |
nkeynes@185 | 73 | double d = (double)f; |
nkeynes@185 | 74 | float q = (float)d; |
nkeynes@185 | 75 | unsigned int i = (unsigned int)d; |
nkeynes@185 | 76 | signed int j = (signed int)q; |
nkeynes@185 | 77 | |
nkeynes@185 | 78 | printf( "Coerce: %08X %08X%08X %08X %08X %08X\n", *((unsigned int *)&f), |
nkeynes@185 | 79 | *((unsigned int *)&d), *(((unsigned int *)&d)+1), |
nkeynes@185 | 80 | *((unsigned int *)&q), i, j ); |
nkeynes@185 | 81 | } |
nkeynes@185 | 82 | |
nkeynes@185 | 83 | void test_doublearr( int len ) |
nkeynes@185 | 84 | { |
nkeynes@185 | 85 | double arr[len]; |
nkeynes@185 | 86 | unsigned int *iarr = (unsigned int *)&arr; |
nkeynes@185 | 87 | int i; |
nkeynes@185 | 88 | arr[0] = 2.5; |
nkeynes@185 | 89 | for( i=1; i<len; i++ ) { |
nkeynes@185 | 90 | arr[i] = (arr[i-1] * arr[i-1] + arr[0]) / 1.25 - 0.19; |
nkeynes@185 | 91 | } |
nkeynes@185 | 92 | |
nkeynes@185 | 93 | printf( "arr: " ); |
nkeynes@185 | 94 | for( i=0; i<len; i++ ) { |
nkeynes@185 | 95 | printf( "%08X", *iarr++ ); |
nkeynes@185 | 96 | printf( "%08X ", *iarr++ ); |
nkeynes@185 | 97 | } |
nkeynes@185 | 98 | printf( "\n" ); |
nkeynes@185 | 99 | } |
nkeynes@185 | 100 | |
nkeynes@185 | 101 | void test_floatarr( int len ) |
nkeynes@185 | 102 | { |
nkeynes@185 | 103 | float arr[len]; |
nkeynes@185 | 104 | unsigned int *iarr = (unsigned int *)&arr; |
nkeynes@185 | 105 | int i; |
nkeynes@185 | 106 | arr[0] = 2.5; |
nkeynes@185 | 107 | for( i=1; i<len; i++ ) { |
nkeynes@185 | 108 | arr[i] = (arr[i-1] * arr[i-1] + arr[0]) / 1.25 - 0.19; |
nkeynes@185 | 109 | } |
nkeynes@185 | 110 | |
nkeynes@185 | 111 | write_string( "arr: " ); |
nkeynes@185 | 112 | for( i=0; i<len; i++ ) { |
nkeynes@185 | 113 | write_int( *iarr++ ); |
nkeynes@185 | 114 | write_string( " " ); |
nkeynes@185 | 115 | } |
nkeynes@185 | 116 | write_string( "\n" ); |
nkeynes@185 | 117 | } |
nkeynes@185 | 118 | |
nkeynes@185 | 119 | float __attribute__((aligned(8))) matrix[16] = { 1.26, 2.34, 5.67, 3.497, -1.23, 43.43, -45.68, 9.12, |
nkeynes@185 | 120 | 12.1, 34.301, -297.354, 0.05, 0.123, 23.34, 9.99, 33.321 }; |
nkeynes@185 | 121 | float __attribute__((aligned(8))) vec1[4] = { 5.65, 9.98, -34.12, 0.043 }; |
nkeynes@185 | 122 | float __attribute__((aligned(8))) vec2[4] = { 3.45, -123, 4.54, 98.0909 }; |
nkeynes@185 | 123 | float __attribute__((aligned(8))) vec3[4] = { 1.25, 2.25, 3.75, 5.12 }; |
nkeynes@185 | 124 | float __attribute__((aligned(8))) vec4[4] = {-0.25, 8.9, -2.3, 9.19 }; |
nkeynes@185 | 125 | |
nkeynes@185 | 126 | void test_fipr( ) |
nkeynes@185 | 127 | { |
nkeynes@185 | 128 | float r = do_fipr( vec3, vec4 ); |
nkeynes@185 | 129 | write_string( "fipr: " ); |
nkeynes@185 | 130 | write_int( *(unsigned int *)&r ); |
nkeynes@185 | 131 | write_string( "\n" ); |
nkeynes@185 | 132 | |
nkeynes@185 | 133 | r = do_fipr2( vec4, vec3 ); |
nkeynes@185 | 134 | write_string( "fipr: " ); |
nkeynes@185 | 135 | write_int( *(unsigned int *)&r ); |
nkeynes@185 | 136 | write_string( "\n" ); |
nkeynes@185 | 137 | |
nkeynes@185 | 138 | } |
nkeynes@185 | 139 | |
nkeynes@185 | 140 | void test_ftrv( ) |
nkeynes@185 | 141 | { |
nkeynes@185 | 142 | |
nkeynes@185 | 143 | do_ftrv( matrix, vec1 ); |
nkeynes@185 | 144 | write_string( "ftrv: " ); |
nkeynes@185 | 145 | write_int( *(unsigned int *)&vec1[0] ); |
nkeynes@185 | 146 | write_int( *(unsigned int *)&vec1[1] ); |
nkeynes@185 | 147 | write_int( *(unsigned int *)&vec1[2] ); |
nkeynes@185 | 148 | write_int( *(unsigned int *)&vec1[3] ); |
nkeynes@185 | 149 | write_string( "\n" ); |
nkeynes@185 | 150 | |
nkeynes@185 | 151 | do_ftrv2( matrix, vec2 ); |
nkeynes@185 | 152 | |
nkeynes@185 | 153 | write_string( "ftrv: " ); |
nkeynes@185 | 154 | write_int( *(unsigned int *)&vec2[0] ); |
nkeynes@185 | 155 | write_int( *(unsigned int *)&vec2[1] ); |
nkeynes@185 | 156 | write_int( *(unsigned int *)&vec2[2] ); |
nkeynes@185 | 157 | write_int( *(unsigned int *)&vec2[3] ); |
nkeynes@185 | 158 | write_string( "\n" ); |
nkeynes@185 | 159 | |
nkeynes@185 | 160 | } |
nkeynes@185 | 161 | |
nkeynes@185 | 162 | |
nkeynes@185 | 163 | int main() |
nkeynes@185 | 164 | { |
nkeynes@192 | 165 | fprintf( stderr, "LL: %d\n", sizeof(unsigned long long) ); |
nkeynes@192 | 166 | write_int( get_fpscr() ); |
nkeynes@192 | 167 | write_string( "\n" ); |
nkeynes@192 | 168 | test_fsca( 0x00000000, 0, 1 ); |
nkeynes@192 | 169 | test_fsca( 0x00011234, 0.43205646, 0.90184659 ); |
nkeynes@192 | 170 | test_fsca( 0xFEDCBA98, -0.99121743, -0.13224234 ); |
nkeynes@192 | 171 | test_fsrra( 25.0, 0.2 ); |
nkeynes@192 | 172 | test_fsrra( 0.05, 4.4721361 ); |
nkeynes@192 | 173 | test_fsrra( -12.345, QNANF ); |
nkeynes@192 | 174 | test_coercion( -3.1415926 ); |
nkeynes@192 | 175 | test_coercion( 123456789012346567.890 ); |
nkeynes@192 | 176 | test_coercion( -2147483648.0 ); |
nkeynes@192 | 177 | test_coercion( 5234.1234 ); |
nkeynes@192 | 178 | test_doublearr( 5 ); |
nkeynes@192 | 179 | test_floatarr( 5 ); |
nkeynes@192 | 180 | test_fipr(); |
nkeynes@192 | 181 | test_ftrv(); |
nkeynes@192 | 182 | return 1; |
nkeynes@185 | 183 | } |
nkeynes@192 | 184 |
.