VirtualBox

source: vbox/trunk/src/libs/softfloat-3e/testfloat/source/genCases_f32.c@ 107044

Last change on this file since 107044 was 94551, checked in by vboxsync, 3 years ago

libs/softfloat: Copied TestFloat-3e from vendor branch and to testfloat subdir. bugref:9898

  • Property svn:eol-style set to native
File size: 18.2 KB
Line 
1
2/*============================================================================
3
4This C source file is part of TestFloat, Release 3e, a package of programs for
5testing the correctness of floating-point arithmetic complying with the IEEE
6Standard for Floating-Point, by John R. Hauser.
7
8Copyright 2011, 2012, 2013, 2014 The Regents of the University of California.
9All rights reserved.
10
11Redistribution and use in source and binary forms, with or without
12modification, are permitted provided that the following conditions are met:
13
14 1. Redistributions of source code must retain the above copyright notice,
15 this list of conditions, and the following disclaimer.
16
17 2. Redistributions in binary form must reproduce the above copyright notice,
18 this list of conditions, and the following disclaimer in the documentation
19 and/or other materials provided with the distribution.
20
21 3. Neither the name of the University nor the names of its contributors may
22 be used to endorse or promote products derived from this software without
23 specific prior written permission.
24
25THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS "AS IS", AND ANY
26EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
27WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE, ARE
28DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE FOR ANY
29DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
30(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
31LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
32ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
33(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
34SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
35
36=============================================================================*/
37
38#include <stdbool.h>
39#include <stdint.h>
40#include "platform.h"
41#include "random.h"
42#include "softfloat.h"
43#include "genCases.h"
44
45struct sequence {
46 int expNum, term1Num, term2Num;
47 bool done;
48};
49
50union ui32_f32 { uint32_t ui; float32_t f; };
51
52enum {
53 f32NumQIn = 22,
54 f32NumQOut = 50,
55 f32NumP1 = 4,
56 f32NumP2 = 88
57};
58static const uint32_t f32QIn[f32NumQIn] = {
59 0x00000000, /* positive, subnormal */
60 0x00800000, /* positive, -126 */
61 0x33800000, /* positive, -24 */
62 0x3E800000, /* positive, -2 */
63 0x3F000000, /* positive, -1 */
64 0x3F800000, /* positive, 0 */
65 0x40000000, /* positive, 1 */
66 0x40800000, /* positive, 2 */
67 0x4B800000, /* positive, 24 */
68 0x7F000000, /* positive, 127 */
69 0x7F800000, /* positive, infinity or NaN */
70 0x80000000, /* negative, subnormal */
71 0x80800000, /* negative, -126 */
72 0xB3800000, /* negative, -24 */
73 0xBE800000, /* negative, -2 */
74 0xBF000000, /* negative, -1 */
75 0xBF800000, /* negative, 0 */
76 0xC0000000, /* negative, 1 */
77 0xC0800000, /* negative, 2 */
78 0xCB800000, /* negative, 24 */
79 0xFE800000, /* negative, 126 */
80 0xFF800000 /* negative, infinity or NaN */
81};
82static const uint32_t f32QOut[f32NumQOut] = {
83 0x00000000, /* positive, subnormal */
84 0x00800000, /* positive, -126 */
85 0x01000000, /* positive, -125 */
86 0x33800000, /* positive, -24 */
87 0x3D800000, /* positive, -4 */
88 0x3E000000, /* positive, -3 */
89 0x3E800000, /* positive, -2 */
90 0x3F000000, /* positive, -1 */
91 0x3F800000, /* positive, 0 */
92 0x40000000, /* positive, 1 */
93 0x40800000, /* positive, 2 */
94 0x41000000, /* positive, 3 */
95 0x41800000, /* positive, 4 */
96 0x4B800000, /* positive, 24 */
97 0x4E000000, /* positive, 29 */
98 0x4E800000, /* positive, 30 */
99 0x4F000000, /* positive, 31 */
100 0x4F800000, /* positive, 32 */
101 0x5E000000, /* positive, 61 */
102 0x5E800000, /* positive, 62 */
103 0x5F000000, /* positive, 63 */
104 0x5F800000, /* positive, 64 */
105 0x7E800000, /* positive, 126 */
106 0x7F000000, /* positive, 127 */
107 0x7F800000, /* positive, infinity or NaN */
108 0x80000000, /* negative, subnormal */
109 0x80800000, /* negative, -126 */
110 0x81000000, /* negative, -125 */
111 0xB3800000, /* negative, -24 */
112 0xBD800000, /* negative, -4 */
113 0xBE000000, /* negative, -3 */
114 0xBE800000, /* negative, -2 */
115 0xBF000000, /* negative, -1 */
116 0xBF800000, /* negative, 0 */
117 0xC0000000, /* negative, 1 */
118 0xC0800000, /* negative, 2 */
119 0xC1000000, /* negative, 3 */
120 0xC1800000, /* negative, 4 */
121 0xCB800000, /* negative, 24 */
122 0xCE000000, /* negative, 29 */
123 0xCE800000, /* negative, 30 */
124 0xCF000000, /* negative, 31 */
125 0xCF800000, /* negative, 32 */
126 0xDE000000, /* negative, 61 */
127 0xDE800000, /* negative, 62 */
128 0xDF000000, /* negative, 63 */
129 0xDF800000, /* negative, 64 */
130 0xFE800000, /* negative, 126 */
131 0xFF000000, /* negative, 127 */
132 0xFF800000 /* negative, infinity or NaN */
133};
134static const uint32_t f32P1[f32NumP1] = {
135 0x00000000,
136 0x00000001,
137 0x007FFFFF,
138 0x007FFFFE
139};
140static const uint32_t f32P2[f32NumP2] = {
141 0x00000000,
142 0x00000001,
143 0x00000002,
144 0x00000004,
145 0x00000008,
146 0x00000010,
147 0x00000020,
148 0x00000040,
149 0x00000080,
150 0x00000100,
151 0x00000200,
152 0x00000400,
153 0x00000800,
154 0x00001000,
155 0x00002000,
156 0x00004000,
157 0x00008000,
158 0x00010000,
159 0x00020000,
160 0x00040000,
161 0x00080000,
162 0x00100000,
163 0x00200000,
164 0x00400000,
165 0x00600000,
166 0x00700000,
167 0x00780000,
168 0x007C0000,
169 0x007E0000,
170 0x007F0000,
171 0x007F8000,
172 0x007FC000,
173 0x007FE000,
174 0x007FF000,
175 0x007FF800,
176 0x007FFC00,
177 0x007FFE00,
178 0x007FFF00,
179 0x007FFF80,
180 0x007FFFC0,
181 0x007FFFE0,
182 0x007FFFF0,
183 0x007FFFF8,
184 0x007FFFFC,
185 0x007FFFFE,
186 0x007FFFFF,
187 0x007FFFFD,
188 0x007FFFFB,
189 0x007FFFF7,
190 0x007FFFEF,
191 0x007FFFDF,
192 0x007FFFBF,
193 0x007FFF7F,
194 0x007FFEFF,
195 0x007FFDFF,
196 0x007FFBFF,
197 0x007FF7FF,
198 0x007FEFFF,
199 0x007FDFFF,
200 0x007FBFFF,
201 0x007F7FFF,
202 0x007EFFFF,
203 0x007DFFFF,
204 0x007BFFFF,
205 0x0077FFFF,
206 0x006FFFFF,
207 0x005FFFFF,
208 0x003FFFFF,
209 0x001FFFFF,
210 0x000FFFFF,
211 0x0007FFFF,
212 0x0003FFFF,
213 0x0001FFFF,
214 0x0000FFFF,
215 0x00007FFF,
216 0x00003FFF,
217 0x00001FFF,
218 0x00000FFF,
219 0x000007FF,
220 0x000003FF,
221 0x000001FF,
222 0x000000FF,
223 0x0000007F,
224 0x0000003F,
225 0x0000001F,
226 0x0000000F,
227 0x00000007,
228 0x00000003
229};
230
231static const uint_fast64_t f32NumQInP1 = f32NumQIn * f32NumP1;
232static const uint_fast64_t f32NumQOutP1 = f32NumQOut * f32NumP1;
233
234static float32_t f32NextQInP1( struct sequence *sequencePtr )
235{
236 int expNum, sigNum;
237 union ui32_f32 uZ;
238
239 expNum = sequencePtr->expNum;
240 sigNum = sequencePtr->term1Num;
241 uZ.ui = f32QIn[expNum] | f32P1[sigNum];
242 ++sigNum;
243 if ( f32NumP1 <= sigNum ) {
244 sigNum = 0;
245 ++expNum;
246 if ( f32NumQIn <= expNum ) {
247 expNum = 0;
248 sequencePtr->done = true;
249 }
250 sequencePtr->expNum = expNum;
251 }
252 sequencePtr->term1Num = sigNum;
253 return uZ.f;
254
255}
256
257static float32_t f32NextQOutP1( struct sequence *sequencePtr )
258{
259 int expNum, sigNum;
260 union ui32_f32 uZ;
261
262 expNum = sequencePtr->expNum;
263 sigNum = sequencePtr->term1Num;
264 uZ.ui = f32QOut[expNum] | f32P1[sigNum];
265 ++sigNum;
266 if ( f32NumP1 <= sigNum ) {
267 sigNum = 0;
268 ++expNum;
269 if ( f32NumQOut <= expNum ) {
270 expNum = 0;
271 sequencePtr->done = true;
272 }
273 sequencePtr->expNum = expNum;
274 }
275 sequencePtr->term1Num = sigNum;
276 return uZ.f;
277
278}
279
280static const uint_fast64_t f32NumQInP2 = f32NumQIn * f32NumP2;
281static const uint_fast64_t f32NumQOutP2 = f32NumQOut * f32NumP2;
282
283static float32_t f32NextQInP2( struct sequence *sequencePtr )
284{
285 int expNum, sigNum;
286 union ui32_f32 uZ;
287
288 expNum = sequencePtr->expNum;
289 sigNum = sequencePtr->term1Num;
290 uZ.ui = f32QIn[expNum] | f32P2[sigNum];
291 ++sigNum;
292 if ( f32NumP2 <= sigNum ) {
293 sigNum = 0;
294 ++expNum;
295 if ( f32NumQIn <= expNum ) {
296 expNum = 0;
297 sequencePtr->done = true;
298 }
299 sequencePtr->expNum = expNum;
300 }
301 sequencePtr->term1Num = sigNum;
302 return uZ.f;
303
304}
305
306static float32_t f32NextQOutP2( struct sequence *sequencePtr )
307{
308 int expNum, sigNum;
309 union ui32_f32 uZ;
310
311 expNum = sequencePtr->expNum;
312 sigNum = sequencePtr->term1Num;
313 uZ.ui = f32QOut[expNum] | f32P2[sigNum];
314 ++sigNum;
315 if ( f32NumP2 <= sigNum ) {
316 sigNum = 0;
317 ++expNum;
318 if ( f32NumQOut <= expNum ) {
319 expNum = 0;
320 sequencePtr->done = true;
321 }
322 sequencePtr->expNum = expNum;
323 }
324 sequencePtr->term1Num = sigNum;
325 return uZ.f;
326
327}
328
329static float32_t f32RandomQOutP3( void )
330{
331 union ui32_f32 uZ;
332
333 uZ.ui =
334 f32QOut[randomN_ui8( f32NumQOut )]
335 | ((f32P2[randomN_ui8( f32NumP2 )] + f32P2[randomN_ui8( f32NumP2 )])
336 & 0x007FFFFF);
337 return uZ.f;
338
339}
340
341static float32_t f32RandomQOutPInf( void )
342{
343 union ui32_f32 uZ;
344
345 uZ.ui = f32QOut[randomN_ui8( f32NumQOut )] | (random_ui32() & 0x007FFFFF);
346 return uZ.f;
347
348}
349
350enum { f32NumQInfWeightMasks = 7 };
351static const uint32_t f32QInfWeightMasks[f32NumQInfWeightMasks] = {
352 0xFF800000,
353 0xFF800000,
354 0xBF800000,
355 0x9F800000,
356 0x8F800000,
357 0x87800000,
358 0x83800000
359};
360static const uint32_t f32QInfWeightOffsets[f32NumQInfWeightMasks] = {
361 0x00000000,
362 0x00000000,
363 0x20000000,
364 0x30000000,
365 0x38000000,
366 0x3C000000,
367 0x3E000000
368};
369
370static float32_t f32RandomQInfP3( void )
371{
372 int weightMaskNum;
373 union ui32_f32 uZ;
374
375 weightMaskNum = randomN_ui8( f32NumQInfWeightMasks );
376 uZ.ui =
377 (((uint_fast32_t) random_ui16()<<16
378 & f32QInfWeightMasks[weightMaskNum])
379 + f32QInfWeightOffsets[weightMaskNum])
380 | ((f32P2[randomN_ui8( f32NumP2 )] + f32P2[randomN_ui8( f32NumP2 )])
381 & 0x007FFFFF);
382 return uZ.f;
383
384}
385
386static float32_t f32RandomQInfPInf( void )
387{
388 int weightMaskNum;
389 union ui32_f32 uZ;
390
391 weightMaskNum = randomN_ui8( f32NumQInfWeightMasks );
392 uZ.ui =
393 (random_ui32() & (f32QInfWeightMasks[weightMaskNum] | 0x007FFFFF))
394 + f32QInfWeightOffsets[weightMaskNum];
395 return uZ.f;
396
397}
398
399static float32_t f32Random( void )
400{
401
402 switch ( random_ui8() & 7 ) {
403 case 0:
404 case 1:
405 case 2:
406 return f32RandomQOutP3();
407 case 3:
408 return f32RandomQOutPInf();
409 case 4:
410 case 5:
411 case 6:
412 return f32RandomQInfP3();
413 case 7:
414 return f32RandomQInfPInf();
415 }
416
417}
418
419static struct sequence sequenceA, sequenceB, sequenceC;
420static float32_t currentA, currentB, currentC;
421static int subcase;
422
423float32_t genCases_f32_a, genCases_f32_b, genCases_f32_c;
424
425void genCases_f32_a_init( void )
426{
427
428 sequenceA.expNum = 0;
429 sequenceA.term1Num = 0;
430 sequenceA.term2Num = 0;
431 sequenceA.done = false;
432 subcase = 0;
433 genCases_total =
434 (genCases_level == 1) ? 3 * f32NumQOutP1 : 2 * f32NumQOutP2;
435 genCases_done = false;
436
437}
438
439void genCases_f32_a_next( void )
440{
441
442 if ( genCases_level == 1 ) {
443 switch ( subcase ) {
444 case 0:
445 case 1:
446 genCases_f32_a = f32Random();
447 break;
448 case 2:
449 genCases_f32_a = f32NextQOutP1( &sequenceA );
450 genCases_done = sequenceA.done;
451 subcase = -1;
452 break;
453 }
454 } else {
455 switch ( subcase ) {
456 case 0:
457 genCases_f32_a = f32Random();
458 break;
459 case 1:
460 genCases_f32_a = f32NextQOutP2( &sequenceA );
461 genCases_done = sequenceA.done;
462 subcase = -1;
463 break;
464 }
465 }
466 ++subcase;
467
468}
469
470void genCases_f32_ab_init( void )
471{
472
473 sequenceA.expNum = 0;
474 sequenceA.term1Num = 0;
475 sequenceA.term2Num = 0;
476 sequenceA.done = false;
477 sequenceB.expNum = 0;
478 sequenceB.term1Num = 0;
479 sequenceB.term2Num = 0;
480 sequenceB.done = false;
481 subcase = 0;
482 if ( genCases_level == 1 ) {
483 genCases_total = 6 * f32NumQInP1 * f32NumQInP1;
484 currentA = f32NextQInP1( &sequenceA );
485 } else {
486 genCases_total = 2 * f32NumQInP2 * f32NumQInP2;
487 currentA = f32NextQInP2( &sequenceA );
488 }
489 genCases_done = false;
490
491}
492
493void genCases_f32_ab_next( void )
494{
495
496 if ( genCases_level == 1 ) {
497 switch ( subcase ) {
498 case 0:
499 if ( sequenceB.done ) {
500 sequenceB.done = false;
501 currentA = f32NextQInP1( &sequenceA );
502 }
503 currentB = f32NextQInP1( &sequenceB );
504 case 2:
505 case 4:
506 genCases_f32_a = f32Random();
507 genCases_f32_b = f32Random();
508 break;
509 case 1:
510 genCases_f32_a = currentA;
511 genCases_f32_b = f32Random();
512 break;
513 case 3:
514 genCases_f32_a = f32Random();
515 genCases_f32_b = currentB;
516 break;
517 case 5:
518 genCases_f32_a = currentA;
519 genCases_f32_b = currentB;
520 genCases_done = sequenceA.done & sequenceB.done;
521 subcase = -1;
522 break;
523 }
524 } else {
525 switch ( subcase ) {
526 case 0:
527 genCases_f32_a = f32Random();
528 genCases_f32_b = f32Random();
529 break;
530 case 1:
531 if ( sequenceB.done ) {
532 sequenceB.done = false;
533 currentA = f32NextQInP2( &sequenceA );
534 }
535 genCases_f32_a = currentA;
536 genCases_f32_b = f32NextQInP2( &sequenceB );
537 genCases_done = sequenceA.done & sequenceB.done;
538 subcase = -1;
539 break;
540 }
541 }
542 ++subcase;
543
544}
545
546void genCases_f32_abc_init( void )
547{
548
549 sequenceA.expNum = 0;
550 sequenceA.term1Num = 0;
551 sequenceA.term2Num = 0;
552 sequenceA.done = false;
553 sequenceB.expNum = 0;
554 sequenceB.term1Num = 0;
555 sequenceB.term2Num = 0;
556 sequenceB.done = false;
557 sequenceC.expNum = 0;
558 sequenceC.term1Num = 0;
559 sequenceC.term2Num = 0;
560 sequenceC.done = false;
561 subcase = 0;
562 if ( genCases_level == 1 ) {
563 genCases_total = 9 * f32NumQInP1 * f32NumQInP1 * f32NumQInP1;
564 currentA = f32NextQInP1( &sequenceA );
565 currentB = f32NextQInP1( &sequenceB );
566 } else {
567 genCases_total = 2 * f32NumQInP2 * f32NumQInP2 * f32NumQInP2;
568 currentA = f32NextQInP2( &sequenceA );
569 currentB = f32NextQInP2( &sequenceB );
570 }
571 genCases_done = false;
572
573}
574
575void genCases_f32_abc_next( void )
576{
577
578 if ( genCases_level == 1 ) {
579 switch ( subcase ) {
580 case 0:
581 if ( sequenceC.done ) {
582 sequenceC.done = false;
583 if ( sequenceB.done ) {
584 sequenceB.done = false;
585 currentA = f32NextQInP1( &sequenceA );
586 }
587 currentB = f32NextQInP1( &sequenceB );
588 }
589 currentC = f32NextQInP1( &sequenceC );
590 genCases_f32_a = f32Random();
591 genCases_f32_b = f32Random();
592 genCases_f32_c = currentC;
593 break;
594 case 1:
595 genCases_f32_a = currentA;
596 genCases_f32_b = currentB;
597 genCases_f32_c = f32Random();
598 break;
599 case 2:
600 genCases_f32_a = f32Random();
601 genCases_f32_b = f32Random();
602 genCases_f32_c = f32Random();
603 break;
604 case 3:
605 genCases_f32_a = f32Random();
606 genCases_f32_b = currentB;
607 genCases_f32_c = currentC;
608 break;
609 case 4:
610 genCases_f32_a = currentA;
611 genCases_f32_b = f32Random();
612 genCases_f32_c = f32Random();
613 break;
614 case 5:
615 genCases_f32_a = f32Random();
616 genCases_f32_b = currentB;
617 genCases_f32_c = f32Random();
618 break;
619 case 6:
620 genCases_f32_a = currentA;
621 genCases_f32_b = f32Random();
622 genCases_f32_c = currentC;
623 break;
624 case 7:
625 genCases_f32_a = f32Random();
626 genCases_f32_b = f32Random();
627 genCases_f32_c = f32Random();
628 break;
629 case 8:
630 genCases_f32_a = currentA;
631 genCases_f32_b = currentB;
632 genCases_f32_c = currentC;
633 genCases_done = sequenceA.done & sequenceB.done & sequenceC.done;
634 subcase = -1;
635 break;
636 }
637 } else {
638 switch ( subcase ) {
639 case 0:
640 genCases_f32_a = f32Random();
641 genCases_f32_b = f32Random();
642 genCases_f32_c = f32Random();
643 break;
644 case 1:
645 if ( sequenceC.done ) {
646 sequenceC.done = false;
647 if ( sequenceB.done ) {
648 sequenceB.done = false;
649 currentA = f32NextQInP2( &sequenceA );
650 }
651 currentB = f32NextQInP2( &sequenceB );
652 }
653 genCases_f32_a = currentA;
654 genCases_f32_b = currentB;
655 genCases_f32_c = f32NextQInP2( &sequenceC );
656 genCases_done = sequenceA.done & sequenceB.done & sequenceC.done;
657 subcase = -1;
658 break;
659 }
660 }
661 ++subcase;
662
663}
664
Note: See TracBrowser for help on using the repository browser.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette