Assembly Language for Beginners

(Jeff_L) #1

1.25. UNIONS


RNG_state=RNG_state*RNG_a+RNG_c;
return RNG_state;
};


// FPU PRNG definitions and routines:


union uint32_t_float
{
uint32_t i;
float f;
};


float float_rand()
{
union uint32_t_float tmp;
tmp.i=my_rand() & 0x007fffff | 0x3F800000;
return tmp.f-1;
};


// test


int main()
{
my_srand(time(NULL)); // PRNG initialization


for (int i=0; i<100; i++)
printf ("%f\n", float_rand());

return 0;
};


x86


Listing 1.355: Optimizing MSVC 2010

$SG4238 DB '%f', 0aH, 00H


__real@3ff0000000000000 DQ 03ff0000000000000r ; 1


tv130 = -4
_tmp$ = -4
?float_rand@@YAMXZ PROC
push ecx
call ?my_rand@@YAIXZ
; EAX=pseudorandom value
and eax, 8388607 ; 007fffffH
or eax, 1065353216 ; 3f800000H
; EAX=pseudorandom value & 0x007fffff | 0x3f800000
; store it into local stack:
mov DWORD PTR _tmp$[esp+4], eax
; reload it as float point number:
fld DWORD PTR _tmp$[esp+4]
; subtract 1.0:
fsub QWORD PTR __real@3ff0000000000000
; store value we got into local stack and reload it:
fstp DWORD PTR tv130[esp+4] ; \ these instructions are redundant
fld DWORD PTR tv130[esp+4] ; /
pop ecx
ret 0
?float_rand@@YAMXZ ENDP


_main PROC
push esi
xor eax, eax
call _time
push eax
call ?my_srand@@YAXI@Z
add esp, 4

Free download pdf