OpenCores
URL https://opencores.org/ocsvn/fpu100/fpu100/trunk

Subversion Repositories fpu100

[/] [fpu100/] [branches/] [avendor/] [test_bench/] [SoftFloat/] [softfloat/] [bits32/] [timesoftfloat.c] - Blame information for rev 21

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 6 jidan
 
2
/*============================================================================
3
 
4
This C source file is part of the SoftFloat IEC/IEEE Floating-point Arithmetic
5
Package, Release 2b.
6
 
7
Written by John R. Hauser.  This work was made possible in part by the
8
International Computer Science Institute, located at Suite 600, 1947 Center
9
Street, Berkeley, California 94704.  Funding was partially provided by the
10
National Science Foundation under grant MIP-9311980.  The original version
11
of this code was written as part of a project to build a fixed-point vector
12
processor in collaboration with the University of California at Berkeley,
13
overseen by Profs. Nelson Morgan and John Wawrzynek.  More information
14
is available through the Web page `http://www.cs.berkeley.edu/~jhauser/
15
arithmetic/SoftFloat.html'.
16
 
17
THIS SOFTWARE IS DISTRIBUTED AS IS, FOR FREE.  Although reasonable effort has
18
been made to avoid it, THIS SOFTWARE MAY CONTAIN FAULTS THAT WILL AT TIMES
19
RESULT IN INCORRECT BEHAVIOR.  USE OF THIS SOFTWARE IS RESTRICTED TO PERSONS
20
AND ORGANIZATIONS WHO CAN AND WILL TAKE FULL RESPONSIBILITY FOR ALL LOSSES,
21
COSTS, OR OTHER PROBLEMS THEY INCUR DUE TO THE SOFTWARE, AND WHO FURTHERMORE
22
EFFECTIVELY INDEMNIFY JOHN HAUSER AND THE INTERNATIONAL COMPUTER SCIENCE
23
INSTITUTE (possibly via similar legal warning) AGAINST ALL LOSSES, COSTS, OR
24
OTHER PROBLEMS INCURRED BY THEIR CUSTOMERS AND CLIENTS DUE TO THE SOFTWARE.
25
 
26
Derivative works are acceptable, even for commercial purposes, so long as
27
(1) the source code for the derivative work includes prominent notice that
28
the work is derivative, and (2) the source code includes prominent notice with
29
these four paragraphs for those parts of this code that are retained.
30
 
31
=============================================================================*/
32
 
33
#include <stdlib.h>
34
#include <stdarg.h>
35
#include <string.h>
36
#include <stdio.h>
37
#include <time.h>
38
#include "milieu.h"
39
#include "softfloat.h"
40
 
41
enum {
42
    minIterations = 100000 //set the number of testcases for each arthimetic operation
43
};
44
 
45
void fail( const char *message, ... )
46
{
47
    va_list varArgs;
48
 
49
    fputs( "timesoftfloat: ", stderr );
50
    va_start( varArgs, message );
51
    vfprintf( stderr, message, varArgs );
52
    va_end( varArgs );
53
    fputs( ".\n", stderr );
54
    exit( EXIT_FAILURE );
55
 
56
}
57
 
58
static char *functionName, *roundingModeName, *tininessModeName;
59
 
60
static void reportTime( int32 count, long clocks )
61
{
62
 
63
    printf(
64
        "%8.1f kops/s: %s",
65
        ( count / ( ( (float) clocks ) / CLOCKS_PER_SEC ) ) / 1000,
66
        functionName
67
    );
68
    if ( roundingModeName ) {
69
        fputs( ", rounding ", stdout );
70
        fputs( roundingModeName, stdout );
71
        if ( tininessModeName ) {
72
            fputs( ", tininess ", stdout );
73
            fputs( tininessModeName, stdout );
74
            fputs( " rounding", stdout );
75
        }
76
    }
77
    fputc( '\n', stdout );
78
 
79
}
80
 
81
enum {
82
    numInputs_int32 = 32
83
};
84
 
85
static const int32 inputs_int32[ numInputs_int32 ] = {
86
    0xFFFFBB79, 0x405CF80F, 0x00000000, 0xFFFFFD04,
87
    0xFFF20002, 0x0C8EF795, 0xF00011FF, 0x000006CA,
88
    0x00009BFE, 0xFF4862E3, 0x9FFFEFFE, 0xFFFFFFB7,
89
    0x0BFF7FFF, 0x0000F37A, 0x0011DFFE, 0x00000006,
90
    0xFFF02006, 0xFFFFF7D1, 0x10200003, 0xDE8DF765,
91
    0x00003E02, 0x000019E8, 0x0008FFFE, 0xFFFFFB5C,
92
    0xFFDF7FFE, 0x07C42FBF, 0x0FFFE3FF, 0x040B9F13,
93
    0xBFFFFFF8, 0x0001BF56, 0x000017F6, 0x000A908A
94
};
95
 
96
static void time_a_int32_z_float32( float32 function( int32 ) )
97
{
98
    clock_t startClock, endClock;
99
    int32 count, i;
100
    int8 inputNum;
101
 
102
    count = 0;
103
    inputNum = 0;
104
    startClock = clock();
105
    do {
106
        for ( i = minIterations; i; --i ) {
107
            function( inputs_int32[ inputNum ] );
108
            inputNum = ( inputNum + 1 ) & ( numInputs_int32 - 1 );
109
        }
110
        count += minIterations;
111
    } while ( clock() - startClock < CLOCKS_PER_SEC );
112
    inputNum = 0;
113
    startClock = clock();
114
    for ( i = count; i; --i ) {
115
        function( inputs_int32[ inputNum ] );
116
        inputNum = ( inputNum + 1 ) & ( numInputs_int32 - 1 );
117
    }
118
    endClock = clock();
119
    reportTime( count, endClock - startClock );
120
 
121
}
122
 
123
static void time_a_int32_z_float64( float64 function( int32 ) )
124
{
125
    clock_t startClock, endClock;
126
    int32 count, i;
127
    int8 inputNum;
128
 
129
    count = 0;
130
    inputNum = 0;
131
    startClock = clock();
132
    do {
133
        for ( i = minIterations; i; --i ) {
134
            function( inputs_int32[ inputNum ] );
135
            inputNum = ( inputNum + 1 ) & ( numInputs_int32 - 1 );
136
        }
137
        count += minIterations;
138
    } while ( clock() - startClock < CLOCKS_PER_SEC );
139
    inputNum = 0;
140
    startClock = clock();
141
    for ( i = count; i; --i ) {
142
        function( inputs_int32[ inputNum ] );
143
        inputNum = ( inputNum + 1 ) & ( numInputs_int32 - 1 );
144
    }
145
    endClock = clock();
146
    reportTime( count, endClock - startClock );
147
 
148
}
149
 
150
enum {
151
    numInputs_float32 = 32
152
};
153
 
154
static const float32 inputs_float32[ numInputs_float32 ] = {
155
    0x4EFA0000, 0xC1D0B328, 0x80000000, 0x3E69A31E,
156
    0xAF803EFF, 0x3F800000, 0x17BF8000, 0xE74A301A,
157
    0x4E010003, 0x7EE3C75D, 0xBD803FE0, 0xBFFEFF00,
158
    0x7981F800, 0x431FFFFC, 0xC100C000, 0x3D87EFFF,
159
    0x4103FEFE, 0xBC000007, 0xBF01F7FF, 0x4E6C6B5C,
160
    0xC187FFFE, 0xC58B9F13, 0x4F88007F, 0xDF004007,
161
    0xB7FFD7FE, 0x7E8001FB, 0x46EFFBFF, 0x31C10000,
162
    0xDB428661, 0x33F89B1F, 0xA3BFEFFF, 0x537BFFBE
163
};
164
 
165
static void time_a_float32_z_int32( int32 function( float32 ) )
166
{
167
    clock_t startClock, endClock;
168
    int32 count, i;
169
    int8 inputNum;
170
 
171
    count = 0;
172
    inputNum = 0;
173
    startClock = clock();
174
    do {
175
        for ( i = minIterations; i; --i ) {
176
            function( inputs_float32[ inputNum ] );
177
            inputNum = ( inputNum + 1 ) & ( numInputs_float32 - 1 );
178
        }
179
        count += minIterations;
180
    } while ( clock() - startClock < CLOCKS_PER_SEC );
181
    inputNum = 0;
182
    startClock = clock();
183
    for ( i = count; i; --i ) {
184
        function( inputs_float32[ inputNum ] );
185
        inputNum = ( inputNum + 1 ) & ( numInputs_float32 - 1 );
186
    }
187
    endClock = clock();
188
    reportTime( count, endClock - startClock );
189
 
190
}
191
 
192
static void time_a_float32_z_float64( float64 function( float32 ) )
193
{
194
    clock_t startClock, endClock;
195
    int32 count, i;
196
    int8 inputNum;
197
 
198
    count = 0;
199
    inputNum = 0;
200
    startClock = clock();
201
    do {
202
        for ( i = minIterations; i; --i ) {
203
            function( inputs_float32[ inputNum ] );
204
            inputNum = ( inputNum + 1 ) & ( numInputs_float32 - 1 );
205
        }
206
        count += minIterations;
207
    } while ( clock() - startClock < CLOCKS_PER_SEC );
208
    inputNum = 0;
209
    startClock = clock();
210
    for ( i = count; i; --i ) {
211
        function( inputs_float32[ inputNum ] );
212
        inputNum = ( inputNum + 1 ) & ( numInputs_float32 - 1 );
213
    }
214
    endClock = clock();
215
    reportTime( count, endClock - startClock );
216
 
217
}
218
 
219
static void time_az_float32( float32 function( float32 ) )
220
{
221
    clock_t startClock, endClock;
222
    int32 count, i;
223
    int8 inputNum;
224
 
225
    count = 0;
226
    inputNum = 0;
227
    startClock = clock();
228
    do {
229
        for ( i = minIterations; i; --i ) {
230
            function( inputs_float32[ inputNum ] );
231
            inputNum = ( inputNum + 1 ) & ( numInputs_float32 - 1 );
232
        }
233
        count += minIterations;
234
    } while ( clock() - startClock < CLOCKS_PER_SEC );
235
    inputNum = 0;
236
    startClock = clock();
237
    for ( i = count; i; --i ) {
238
        function( inputs_float32[ inputNum ] );
239
        inputNum = ( inputNum + 1 ) & ( numInputs_float32 - 1 );
240
    }
241
    endClock = clock();
242
    reportTime( count, endClock - startClock );
243
 
244
}
245
 
246
static void time_ab_float32_z_flag( flag function( float32, float32 ) )
247
{
248
    clock_t startClock, endClock;
249
    int32 count, i;
250
    int8 inputNumA, inputNumB;
251
 
252
    count = 0;
253
    inputNumA = 0;
254
    inputNumB = 0;
255
    startClock = clock();
256
    do {
257
        for ( i = minIterations; i; --i ) {
258
            function(
259
                inputs_float32[ inputNumA ], inputs_float32[ inputNumB ] );
260
            inputNumA = ( inputNumA + 1 ) & ( numInputs_float32 - 1 );
261
            if ( inputNumA == 0 ) ++inputNumB;
262
            inputNumB = ( inputNumB + 1 ) & ( numInputs_float32 - 1 );
263
        }
264
        count += minIterations;
265
    } while ( clock() - startClock < CLOCKS_PER_SEC );
266
    inputNumA = 0;
267
    inputNumB = 0;
268
    startClock = clock();
269
    for ( i = count; i; --i ) {
270
            function(
271
                inputs_float32[ inputNumA ], inputs_float32[ inputNumB ] );
272
        inputNumA = ( inputNumA + 1 ) & ( numInputs_float32 - 1 );
273
        if ( inputNumA == 0 ) ++inputNumB;
274
        inputNumB = ( inputNumB + 1 ) & ( numInputs_float32 - 1 );
275
    }
276
    endClock = clock();
277
    reportTime( count, endClock - startClock );
278
 
279
}
280
 
281
//for testing FP arthimetic
282
/*static void time_abz_float32( float32 function( float32, float32 ) )
283
{
284
    int32 count, i;
285
    int8 inputNumA, inputNumB;
286
 
287
    count = 0;
288
    inputNumA = 0;
289
    inputNumB = 0;
290
 
291
            function(0x7F7FFFFF , 0x7F400000  );
292
 
293
}*/
294
 
295
static void time_abz_float32( float32 function( float32, float32 ) )
296
{
297
    int32 count, i;
298
    int8 inputNumA, inputNumB;
299
 
300
    count = 0;
301
    inputNumA = 0;
302
    inputNumB = 0;
303
 
304
        for ( i = minIterations; i; --i ) {
305
            function(
306
                inputs_float32[ inputNumA ], inputs_float32[ inputNumB ] );
307
            inputNumA = ( inputNumA + 1 ) & ( numInputs_float32 - 1 );
308
            if ( inputNumA == 0 ) ++inputNumB;
309
            inputNumB = ( inputNumB + 1 ) & ( numInputs_float32 - 1 );
310
        }
311
 
312
 
313
}
314
 
315
static const float32 inputs_float32_pos[ numInputs_float32 ] = {
316
    0x4EFA0000, 0x41D0B328, 0x00000000, 0x3E69A31E,
317
    0x2F803EFF, 0x3F800000, 0x17BF8000, 0x674A301A,
318
    0x4E010003, 0x7EE3C75D, 0x3D803FE0, 0x3FFEFF00,
319
    0x7981F800, 0x431FFFFC, 0x4100C000, 0x3D87EFFF,
320
    0x4103FEFE, 0x3C000007, 0x3F01F7FF, 0x4E6C6B5C,
321
    0x4187FFFE, 0x458B9F13, 0x4F88007F, 0x5F004007,
322
    0x37FFD7FE, 0x7E8001FB, 0x46EFFBFF, 0x31C10000,
323
    0x5B428661, 0x33F89B1F, 0x23BFEFFF, 0x537BFFBE
324
};
325
 
326
static void time_az_float32_pos( float32 function( float32 ) )
327
{
328
    int32 count, i;
329
    int8 inputNum;
330
 
331
    count = 0;
332
    inputNum = 0;
333
 
334
        for ( i = minIterations; i; --i ) {
335
            function( inputs_float32_pos[ inputNum ] );
336
            inputNum = ( inputNum + 1 ) & ( numInputs_float32 - 1 );
337
        }
338
 
339
}
340
 
341
enum {
342
    numInputs_float64 = 32
343
};
344
 
345
static const struct {
346
    bits32 high, low;
347
} inputs_float64[ numInputs_float64 ] = {
348
    { 0x422FFFC0, 0x08000000 },
349
    { 0xB7E00004, 0x80000000 },
350
    { 0xF3FD2546, 0x120B7935 },
351
    { 0x3FF00000, 0x00000000 },
352
    { 0xCE07F766, 0xF09588D6 },
353
    { 0x80000000, 0x00000000 },
354
    { 0x3FCE0004, 0x00000000 },
355
    { 0x8313B60F, 0x0032BED8 },
356
    { 0xC1EFFFFF, 0xC0002000 },
357
    { 0x3FB3C75D, 0x224F2B0F },
358
    { 0x7FD00000, 0x004000FF },
359
    { 0xA12FFF80, 0x00001FFF },
360
    { 0x3EE00000, 0x00FE0000 },
361
    { 0x00100000, 0x80000004 },
362
    { 0x41CFFFFE, 0x00000020 },
363
    { 0x40303FFF, 0xFFFFFFFD },
364
    { 0x3FD00000, 0x3FEFFFFF },
365
    { 0xBFD00000, 0x10000000 },
366
    { 0xB7FC6B5C, 0x16CA55CF },
367
    { 0x413EEB94, 0x0B9D1301 },
368
    { 0xC7E00200, 0x001FFFFF },
369
    { 0x47F00021, 0xFFFFFFFE },
370
    { 0xBFFFFFFF, 0xF80000FF },
371
    { 0xC07FFFFF, 0xE00FFFFF },
372
    { 0x001497A6, 0x3740C5E8 },
373
    { 0xC4BFFFE0, 0x001FFFFF },
374
    { 0x96FFDFFE, 0xFFFFFFFF },
375
    { 0x403FC000, 0x000001FE },
376
    { 0xFFD00000, 0x000001F6 },
377
    { 0x06404000, 0x02000000 },
378
    { 0x479CEE1E, 0x4F789FE0 },
379
    { 0xC237FFFF, 0xFFFFFDFE }
380
};
381
 
382
static void time_a_float64_z_int32( int32 function( float64 ) )
383
{
384
    clock_t startClock, endClock;
385
    int32 count, i;
386
    int8 inputNum;
387
    float64 a;
388
 
389
    count = 0;
390
    inputNum = 0;
391
    startClock = clock();
392
    do {
393
        for ( i = minIterations; i; --i ) {
394
            a.low = inputs_float64[ inputNum ].low;
395
            a.high = inputs_float64[ inputNum ].high;
396
            function( a );
397
            inputNum = ( inputNum + 1 ) & ( numInputs_float64 - 1 );
398
        }
399
        count += minIterations;
400
    } while ( clock() - startClock < CLOCKS_PER_SEC );
401
    inputNum = 0;
402
    startClock = clock();
403
    for ( i = count; i; --i ) {
404
        a.low = inputs_float64[ inputNum ].low;
405
        a.high = inputs_float64[ inputNum ].high;
406
        function( a );
407
        inputNum = ( inputNum + 1 ) & ( numInputs_float64 - 1 );
408
    }
409
    endClock = clock();
410
    reportTime( count, endClock - startClock );
411
 
412
}
413
 
414
static void time_a_float64_z_float32( float32 function( float64 ) )
415
{
416
    clock_t startClock, endClock;
417
    int32 count, i;
418
    int8 inputNum;
419
    float64 a;
420
 
421
    count = 0;
422
    inputNum = 0;
423
    startClock = clock();
424
    do {
425
        for ( i = minIterations; i; --i ) {
426
            a.low = inputs_float64[ inputNum ].low;
427
            a.high = inputs_float64[ inputNum ].high;
428
            function( a );
429
            inputNum = ( inputNum + 1 ) & ( numInputs_float64 - 1 );
430
        }
431
        count += minIterations;
432
    } while ( clock() - startClock < CLOCKS_PER_SEC );
433
    inputNum = 0;
434
    startClock = clock();
435
    for ( i = count; i; --i ) {
436
        a.low = inputs_float64[ inputNum ].low;
437
        a.high = inputs_float64[ inputNum ].high;
438
        function( a );
439
        inputNum = ( inputNum + 1 ) & ( numInputs_float64 - 1 );
440
    }
441
    endClock = clock();
442
    reportTime( count, endClock - startClock );
443
 
444
}
445
 
446
static void time_az_float64( float64 function( float64 ) )
447
{
448
    clock_t startClock, endClock;
449
    int32 count, i;
450
    int8 inputNum;
451
    float64 a;
452
 
453
    count = 0;
454
    inputNum = 0;
455
    startClock = clock();
456
    do {
457
        for ( i = minIterations; i; --i ) {
458
            a.low = inputs_float64[ inputNum ].low;
459
            a.high = inputs_float64[ inputNum ].high;
460
            function( a );
461
            inputNum = ( inputNum + 1 ) & ( numInputs_float64 - 1 );
462
        }
463
        count += minIterations;
464
    } while ( clock() - startClock < CLOCKS_PER_SEC );
465
    inputNum = 0;
466
    startClock = clock();
467
    for ( i = count; i; --i ) {
468
        a.low = inputs_float64[ inputNum ].low;
469
        a.high = inputs_float64[ inputNum ].high;
470
        function( a );
471
        inputNum = ( inputNum + 1 ) & ( numInputs_float64 - 1 );
472
    }
473
    endClock = clock();
474
    reportTime( count, endClock - startClock );
475
 
476
}
477
 
478
static void time_ab_float64_z_flag( flag function( float64, float64 ) )
479
{
480
    clock_t startClock, endClock;
481
    int32 count, i;
482
    int8 inputNumA, inputNumB;
483
    float64 a, b;
484
 
485
    count = 0;
486
    inputNumA = 0;
487
    inputNumB = 0;
488
    startClock = clock();
489
    do {
490
        for ( i = minIterations; i; --i ) {
491
            a.low = inputs_float64[ inputNumA ].low;
492
            a.high = inputs_float64[ inputNumA ].high;
493
            b.low = inputs_float64[ inputNumB ].low;
494
            b.high = inputs_float64[ inputNumB ].high;
495
            function( a, b );
496
            inputNumA = ( inputNumA + 1 ) & ( numInputs_float64 - 1 );
497
            if ( inputNumA == 0 ) ++inputNumB;
498
            inputNumB = ( inputNumB + 1 ) & ( numInputs_float64 - 1 );
499
        }
500
        count += minIterations;
501
    } while ( clock() - startClock < CLOCKS_PER_SEC );
502
    inputNumA = 0;
503
    inputNumB = 0;
504
    startClock = clock();
505
    for ( i = count; i; --i ) {
506
        a.low = inputs_float64[ inputNumA ].low;
507
        a.high = inputs_float64[ inputNumA ].high;
508
        b.low = inputs_float64[ inputNumB ].low;
509
        b.high = inputs_float64[ inputNumB ].high;
510
        function( a, b );
511
        inputNumA = ( inputNumA + 1 ) & ( numInputs_float64 - 1 );
512
        if ( inputNumA == 0 ) ++inputNumB;
513
        inputNumB = ( inputNumB + 1 ) & ( numInputs_float64 - 1 );
514
    }
515
    endClock = clock();
516
    reportTime( count, endClock - startClock );
517
 
518
}
519
 
520
static void time_abz_float64( float64 function( float64, float64 ) )
521
{
522
    clock_t startClock, endClock;
523
    int32 count, i;
524
    int8 inputNumA, inputNumB;
525
    float64 a, b;
526
 
527
    count = 0;
528
    inputNumA = 0;
529
    inputNumB = 0;
530
    startClock = clock();
531
    do {
532
        for ( i = minIterations; i; --i ) {
533
            a.low = inputs_float64[ inputNumA ].low;
534
            a.high = inputs_float64[ inputNumA ].high;
535
            b.low = inputs_float64[ inputNumB ].low;
536
            b.high = inputs_float64[ inputNumB ].high;
537
            function( a, b );
538
            inputNumA = ( inputNumA + 1 ) & ( numInputs_float64 - 1 );
539
            if ( inputNumA == 0 ) ++inputNumB;
540
            inputNumB = ( inputNumB + 1 ) & ( numInputs_float64 - 1 );
541
        }
542
        count += minIterations;
543
    } while ( clock() - startClock < CLOCKS_PER_SEC );
544
    inputNumA = 0;
545
    inputNumB = 0;
546
    startClock = clock();
547
    for ( i = count; i; --i ) {
548
        a.low = inputs_float64[ inputNumA ].low;
549
        a.high = inputs_float64[ inputNumA ].high;
550
        b.low = inputs_float64[ inputNumB ].low;
551
        b.high = inputs_float64[ inputNumB ].high;
552
        function( a, b );
553
        inputNumA = ( inputNumA + 1 ) & ( numInputs_float64 - 1 );
554
        if ( inputNumA == 0 ) ++inputNumB;
555
        inputNumB = ( inputNumB + 1 ) & ( numInputs_float64 - 1 );
556
    }
557
    endClock = clock();
558
    reportTime( count, endClock - startClock );
559
 
560
}
561
 
562
static const struct {
563
    bits32 high, low;
564
} inputs_float64_pos[ numInputs_float64 ] = {
565
    { 0x422FFFC0, 0x08000000 },
566
    { 0x37E00004, 0x80000000 },
567
    { 0x73FD2546, 0x120B7935 },
568
    { 0x3FF00000, 0x00000000 },
569
    { 0x4E07F766, 0xF09588D6 },
570
    { 0x00000000, 0x00000000 },
571
    { 0x3FCE0004, 0x00000000 },
572
    { 0x0313B60F, 0x0032BED8 },
573
    { 0x41EFFFFF, 0xC0002000 },
574
    { 0x3FB3C75D, 0x224F2B0F },
575
    { 0x7FD00000, 0x004000FF },
576
    { 0x212FFF80, 0x00001FFF },
577
    { 0x3EE00000, 0x00FE0000 },
578
    { 0x00100000, 0x80000004 },
579
    { 0x41CFFFFE, 0x00000020 },
580
    { 0x40303FFF, 0xFFFFFFFD },
581
    { 0x3FD00000, 0x3FEFFFFF },
582
    { 0x3FD00000, 0x10000000 },
583
    { 0x37FC6B5C, 0x16CA55CF },
584
    { 0x413EEB94, 0x0B9D1301 },
585
    { 0x47E00200, 0x001FFFFF },
586
    { 0x47F00021, 0xFFFFFFFE },
587
    { 0x3FFFFFFF, 0xF80000FF },
588
    { 0x407FFFFF, 0xE00FFFFF },
589
    { 0x001497A6, 0x3740C5E8 },
590
    { 0x44BFFFE0, 0x001FFFFF },
591
    { 0x16FFDFFE, 0xFFFFFFFF },
592
    { 0x403FC000, 0x000001FE },
593
    { 0x7FD00000, 0x000001F6 },
594
    { 0x06404000, 0x02000000 },
595
    { 0x479CEE1E, 0x4F789FE0 },
596
    { 0x4237FFFF, 0xFFFFFDFE }
597
};
598
 
599
static void time_az_float64_pos( float64 function( float64 ) )
600
{
601
    clock_t startClock, endClock;
602
    int32 count, i;
603
    int8 inputNum;
604
    float64 a;
605
 
606
    count = 0;
607
    inputNum = 0;
608
    startClock = clock();
609
    do {
610
        for ( i = minIterations; i; --i ) {
611
            a.low = inputs_float64_pos[ inputNum ].low;
612
            a.high = inputs_float64_pos[ inputNum ].high;
613
            function( a );
614
            inputNum = ( inputNum + 1 ) & ( numInputs_float64 - 1 );
615
        }
616
        count += minIterations;
617
    } while ( clock() - startClock < CLOCKS_PER_SEC );
618
    inputNum = 0;
619
    startClock = clock();
620
    for ( i = count; i; --i ) {
621
        a.low = inputs_float64_pos[ inputNum ].low;
622
        a.high = inputs_float64_pos[ inputNum ].high;
623
        function( a );
624
        inputNum = ( inputNum + 1 ) & ( numInputs_float64 - 1 );
625
    }
626
    endClock = clock();
627
    reportTime( count, endClock - startClock );
628
 
629
}
630
 
631
enum {
632
    INT32_TO_FLOAT32 = 1,
633
    INT32_TO_FLOAT64,
634
    FLOAT32_TO_INT32,
635
    FLOAT32_TO_INT32_ROUND_TO_ZERO,
636
    FLOAT32_TO_FLOAT64,
637
    FLOAT32_ROUND_TO_INT,
638
    FLOAT32_ADD,
639
    FLOAT32_SUB,
640
    FLOAT32_MUL,
641
    FLOAT32_DIV,
642
    FLOAT32_REM,
643
    FLOAT32_SQRT,
644
    FLOAT32_EQ,
645
    FLOAT32_LE,
646
    FLOAT32_LT,
647
    FLOAT32_EQ_SIGNALING,
648
    FLOAT32_LE_QUIET,
649
    FLOAT32_LT_QUIET,
650
    FLOAT64_TO_INT32,
651
    FLOAT64_TO_INT32_ROUND_TO_ZERO,
652
    FLOAT64_TO_FLOAT32,
653
    FLOAT64_ROUND_TO_INT,
654
    FLOAT64_ADD,
655
    FLOAT64_SUB,
656
    FLOAT64_MUL,
657
    FLOAT64_DIV,
658
    FLOAT64_REM,
659
    FLOAT64_SQRT,
660
    FLOAT64_EQ,
661
    FLOAT64_LE,
662
    FLOAT64_LT,
663
    FLOAT64_EQ_SIGNALING,
664
    FLOAT64_LE_QUIET,
665
    FLOAT64_LT_QUIET,
666
    NUM_FUNCTIONS
667
};
668
 
669
static struct {
670
    char *name;
671
    int8 numInputs;
672
    flag roundingMode, tininessMode;
673
} functions[ NUM_FUNCTIONS ] = {
674
    { 0, 0, 0, 0 },
675
    { "int32_to_float32",                1, TRUE,  FALSE },
676
    { "int32_to_float64",                1, FALSE, FALSE },
677
    { "float32_to_int32",                1, TRUE,  FALSE },
678
    { "float32_to_int32_round_to_zero",  1, FALSE, FALSE },
679
    { "float32_to_float64",              1, FALSE, FALSE },
680
    { "float32_round_to_int",            1, TRUE,  FALSE },
681
    { "float32_add",                     2, TRUE,  FALSE },
682
    { "float32_sub",                     2, TRUE,  FALSE },
683
    { "float32_mul",                     2, TRUE,  FALSE },
684
    { "float32_div",                     2, TRUE,  FALSE },
685
    { "float32_rem",                     2, FALSE, FALSE },
686
    { "float32_sqrt",                    1, TRUE,  FALSE },
687
    { "float32_eq",                      2, FALSE, FALSE },
688
    { "float32_le",                      2, FALSE, FALSE },
689
    { "float32_lt",                      2, FALSE, FALSE },
690
    { "float32_eq_signaling",            2, FALSE, FALSE },
691
    { "float32_le_quiet",                2, FALSE, FALSE },
692
    { "float32_lt_quiet",                2, FALSE, FALSE },
693
    { "float64_to_int32",                1, TRUE,  FALSE },
694
    { "float64_to_int32_round_to_zero",  1, FALSE, FALSE },
695
    { "float64_to_float32",              1, TRUE,  TRUE, },
696
    { "float64_round_to_int",            1, TRUE,  FALSE },
697
    { "float64_add",                     2, TRUE,  FALSE },
698
    { "float64_sub",                     2, TRUE,  FALSE },
699
    { "float64_mul",                     2, TRUE,  TRUE, },
700
    { "float64_div",                     2, TRUE,  FALSE },
701
    { "float64_rem",                     2, FALSE, FALSE },
702
    { "float64_sqrt",                    1, TRUE,  FALSE },
703
    { "float64_eq",                      2, FALSE, FALSE },
704
    { "float64_le",                      2, FALSE, FALSE },
705
    { "float64_lt",                      2, FALSE, FALSE },
706
    { "float64_eq_signaling",            2, FALSE, FALSE },
707
    { "float64_le_quiet",                2, FALSE, FALSE },
708
    { "float64_lt_quiet",                2, FALSE, FALSE }
709
};
710
 
711
enum {
712
    ROUND_NEAREST_EVEN = 1,
713
    ROUND_TO_ZERO,
714
    ROUND_DOWN,
715
    ROUND_UP,
716
    NUM_ROUNDINGMODES
717
};
718
enum {
719
    TININESS_BEFORE_ROUNDING = 1,
720
    TININESS_AFTER_ROUNDING,
721
    NUM_TININESSMODES
722
};
723
 
724
static void
725
 timeFunctionVariety(
726
     uint8 functionCode, int8 roundingMode, int8 tininessMode )
727
{
728
    uint8 roundingCode;
729
    int8 tininessCode;
730
 
731
    functionName = functions[ functionCode ].name;
732
    switch ( roundingMode ) {
733
     case 0:
734
        roundingModeName = 0;
735
        roundingCode = float_round_nearest_even;
736
        break;
737
     case ROUND_NEAREST_EVEN:
738
        roundingModeName = "nearest_even";
739
        roundingCode = float_round_nearest_even;
740
        break;
741
     case ROUND_TO_ZERO:
742
        roundingModeName = "to_zero";
743
        roundingCode = float_round_to_zero;
744
        break;
745
     case ROUND_DOWN:
746
        roundingModeName = "down";
747
        roundingCode = float_round_down;
748
        break;
749
     case ROUND_UP:
750
        roundingModeName = "up";
751
        roundingCode = float_round_up;
752
        break;
753
    }
754
    float_rounding_mode = roundingCode;
755
    switch ( tininessMode ) {
756
     case 0:
757
        tininessModeName = 0;
758
        tininessCode = float_tininess_after_rounding;
759
        break;
760
     case TININESS_BEFORE_ROUNDING:
761
        tininessModeName = "before";
762
        tininessCode = float_tininess_before_rounding;
763
        break;
764
     case TININESS_AFTER_ROUNDING:
765
        tininessModeName = "after";
766
        tininessCode = float_tininess_after_rounding;
767
        break;
768
    }
769
    float_detect_tininess = tininessCode;
770
    switch ( functionCode ) {
771
     case INT32_TO_FLOAT32:
772
        time_a_int32_z_float32( int32_to_float32 );
773
        break;
774
     case INT32_TO_FLOAT64:
775
        time_a_int32_z_float64( int32_to_float64 );
776
        break;
777
     case FLOAT32_TO_INT32:
778
        time_a_float32_z_int32( float32_to_int32 );
779
        break;
780
     case FLOAT32_TO_INT32_ROUND_TO_ZERO:
781
        time_a_float32_z_int32( float32_to_int32_round_to_zero );
782
        break;
783
     case FLOAT32_TO_FLOAT64:
784
        time_a_float32_z_float64( float32_to_float64 );
785
        break;
786
     case FLOAT32_ROUND_TO_INT:
787
        time_az_float32( float32_round_to_int );
788
        break;
789
     case FLOAT32_ADD:
790
        time_abz_float32( float32_add );
791
        break;
792
     case FLOAT32_SUB:
793
        time_abz_float32( float32_sub );
794
        break;
795
     case FLOAT32_MUL:
796
        time_abz_float32( float32_mul );
797
        break;
798
     case FLOAT32_DIV:
799
        time_abz_float32( float32_div );
800
        break;
801
     case FLOAT32_REM:
802
        time_abz_float32( float32_rem );
803
        break;
804
     case FLOAT32_SQRT:
805
        time_az_float32_pos( float32_sqrt );
806
        break;
807
     case FLOAT32_EQ:
808
        time_ab_float32_z_flag( float32_eq );
809
        break;
810
     case FLOAT32_LE:
811
        time_ab_float32_z_flag( float32_le );
812
        break;
813
     case FLOAT32_LT:
814
        time_ab_float32_z_flag( float32_lt );
815
        break;
816
     case FLOAT32_EQ_SIGNALING:
817
        time_ab_float32_z_flag( float32_eq_signaling );
818
        break;
819
     case FLOAT32_LE_QUIET:
820
        time_ab_float32_z_flag( float32_le_quiet );
821
        break;
822
     case FLOAT32_LT_QUIET:
823
        time_ab_float32_z_flag( float32_lt_quiet );
824
        break;
825
     case FLOAT64_TO_INT32:
826
        time_a_float64_z_int32( float64_to_int32 );
827
        break;
828
     case FLOAT64_TO_INT32_ROUND_TO_ZERO:
829
        time_a_float64_z_int32( float64_to_int32_round_to_zero );
830
        break;
831
     case FLOAT64_TO_FLOAT32:
832
        time_a_float64_z_float32( float64_to_float32 );
833
        break;
834
     case FLOAT64_ROUND_TO_INT:
835
        time_az_float64( float64_round_to_int );
836
        break;
837
     case FLOAT64_ADD:
838
        time_abz_float64( float64_add );
839
        break;
840
     case FLOAT64_SUB:
841
        time_abz_float64( float64_sub );
842
        break;
843
     case FLOAT64_MUL:
844
        time_abz_float64( float64_mul );
845
        break;
846
     case FLOAT64_DIV:
847
        time_abz_float64( float64_div );
848
        break;
849
     case FLOAT64_REM:
850
        time_abz_float64( float64_rem );
851
        break;
852
     case FLOAT64_SQRT:
853
        time_az_float64_pos( float64_sqrt );
854
        break;
855
     case FLOAT64_EQ:
856
        time_ab_float64_z_flag( float64_eq );
857
        break;
858
     case FLOAT64_LE:
859
        time_ab_float64_z_flag( float64_le );
860
        break;
861
     case FLOAT64_LT:
862
        time_ab_float64_z_flag( float64_lt );
863
        break;
864
     case FLOAT64_EQ_SIGNALING:
865
        time_ab_float64_z_flag( float64_eq_signaling );
866
        break;
867
     case FLOAT64_LE_QUIET:
868
        time_ab_float64_z_flag( float64_le_quiet );
869
        break;
870
     case FLOAT64_LT_QUIET:
871
        time_ab_float64_z_flag( float64_lt_quiet );
872
        break;
873
    }
874
 
875
}
876
 
877
static void
878
 timeFunction( uint8 functionCode, int8 roundingModeIn, int8 tininessModeIn )
879
{
880
    int8 roundingMode, tininessMode;
881
 
882
    for ( roundingMode = 1;
883
          roundingMode < NUM_ROUNDINGMODES;
884
          ++roundingMode
885
        ) {
886
        if ( ! functions[ functionCode ].roundingMode ) {
887
            roundingMode = 0;
888
        }
889
        else if ( roundingModeIn ) {
890
            roundingMode = roundingModeIn;
891
        }
892
        for ( tininessMode = 1;
893
              tininessMode < NUM_TININESSMODES;
894
              ++tininessMode
895
            ) {
896
            if ( ! functions[ functionCode ].tininessMode ) {
897
                tininessMode = 0;
898
            }
899
            else if ( tininessModeIn ) {
900
                tininessMode = tininessModeIn;
901
            }
902
            timeFunctionVariety( functionCode, roundingMode, tininessMode );
903
            if ( tininessModeIn || ! tininessMode ) break;
904
        }
905
        if ( roundingModeIn || ! roundingMode ) break;
906
    }
907
 
908
}
909
 
910
main( int argc, char **argv )
911
{
912
    char *argPtr;
913
    flag functionArgument;
914
    uint8 functionCode;
915
    int8 operands, roundingMode, tininessMode;
916
 
917
    if ( argc <= 1 ) goto writeHelpMessage;
918
    functionArgument = FALSE;
919
    functionCode = 0;
920
    operands = 0;
921
    roundingMode = 0;
922
    tininessMode = 0;
923
    --argc;
924
    ++argv;
925
    while ( argc && ( argPtr = argv[ 0 ] ) ) {
926
        if ( argPtr[ 0 ] == '-' ) ++argPtr;
927
        if ( strcmp( argPtr, "help" ) == 0 ) {
928
 writeHelpMessage:
929
            fputs(
930
"timesoftfloat [<option>...] <function>\n"
931
"  <option>:  (* is default)\n"
932
"    -help            --Write this message and exit.\n"
933
"    -nearesteven     --Only time rounding to nearest/even.\n"
934
"    -tozero          --Only time rounding to zero.\n"
935
"    -down            --Only time rounding down.\n"
936
"    -up              --Only time rounding up.\n"
937
"    -tininessbefore  --Only time underflow tininess before rounding.\n"
938
"    -tininessafter   --Only time underflow tininess after rounding.\n"
939
"  <function>:\n"
940
"    int32_to_<float>                 <float>_add   <float>_eq\n"
941
"    <float>_to_int32                 <float>_sub   <float>_le\n"
942
"    <float>_to_int32_round_to_zero   <float>_mul   <float>_lt\n"
943
"    <float>_to_<float>               <float>_div   <float>_eq_signaling\n"
944
"    <float>_round_to_int             <float>_rem   <float>_le_quiet\n"
945
"    <float>_sqrt                                   <float>_lt_quiet\n"
946
"    -all1            --All 1-operand functions.\n"
947
"    -all2            --All 2-operand functions.\n"
948
"    -all             --All functions.\n"
949
"  <float>:\n"
950
"    float32          --Single precision.\n"
951
"    float64          --Double precision.\n",
952
                stdout
953
            );
954
            return EXIT_SUCCESS;
955
        }
956
        else if (    ( strcmp( argPtr, "nearesteven" ) == 0 )
957
                  || ( strcmp( argPtr, "nearest_even" ) == 0 ) ) {
958
            roundingMode = ROUND_NEAREST_EVEN;
959
        }
960
        else if (    ( strcmp( argPtr, "tozero" ) == 0 )
961
                  || ( strcmp( argPtr, "to_zero" ) == 0 ) ) {
962
            roundingMode = ROUND_TO_ZERO;
963
        }
964
        else if ( strcmp( argPtr, "down" ) == 0 ) {
965
            roundingMode = ROUND_DOWN;
966
        }
967
        else if ( strcmp( argPtr, "up" ) == 0 ) {
968
            roundingMode = ROUND_UP;
969
        }
970
        else if ( strcmp( argPtr, "tininessbefore" ) == 0 ) {
971
            tininessMode = TININESS_BEFORE_ROUNDING;
972
        }
973
        else if ( strcmp( argPtr, "tininessafter" ) == 0 ) {
974
            tininessMode = TININESS_AFTER_ROUNDING;
975
        }
976
        else if ( strcmp( argPtr, "all1" ) == 0 ) {
977
            functionArgument = TRUE;
978
            functionCode = 0;
979
            operands = 1;
980
        }
981
        else if ( strcmp( argPtr, "all2" ) == 0 ) {
982
            functionArgument = TRUE;
983
            functionCode = 0;
984
            operands = 2;
985
        }
986
        else if ( strcmp( argPtr, "all" ) == 0 ) {
987
            functionArgument = TRUE;
988
            functionCode = 0;
989
            operands = 0;
990
        }
991
        else {
992
            for ( functionCode = 1;
993
                  functionCode < NUM_FUNCTIONS;
994
                  ++functionCode
995
                ) {
996
                if ( strcmp( argPtr, functions[ functionCode ].name ) == 0 ) {
997
                    break;
998
                }
999
            }
1000
            if ( functionCode == NUM_FUNCTIONS ) {
1001
                fail( "Invalid option or function `%s'", argv[ 0 ] );
1002
            }
1003
            functionArgument = TRUE;
1004
        }
1005
        --argc;
1006
        ++argv;
1007
    }
1008
    if ( ! functionArgument ) fail( "Function argument required" );
1009
    if ( functionCode ) {
1010
        timeFunction( functionCode, roundingMode, tininessMode );
1011
    }
1012
    else if ( operands == 1 ) {
1013
        for ( functionCode = 1; functionCode < NUM_FUNCTIONS; ++functionCode
1014
            ) {
1015
            if ( functions[ functionCode ].numInputs == 1 ) {
1016
                timeFunction( functionCode, roundingMode, tininessMode );
1017
            }
1018
        }
1019
    }
1020
    else if ( operands == 2 ) {
1021
        for ( functionCode = 1; functionCode < NUM_FUNCTIONS; ++functionCode
1022
            ) {
1023
            if ( functions[ functionCode ].numInputs == 2 ) {
1024
                timeFunction( functionCode, roundingMode, tininessMode );
1025
            }
1026
        }
1027
    }
1028
    else {
1029
        for ( functionCode = 1; functionCode < NUM_FUNCTIONS; ++functionCode
1030
            ) {
1031
            timeFunction( functionCode, roundingMode, tininessMode );
1032
        }
1033
    }
1034
    return EXIT_SUCCESS;
1035
 
1036
}
1037
 

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.