this repo has no description
1// float scalbnf( float x, int n );
2// float ldexpf( float x, int n );
3// float scalblnf( float x, long int n );
4//
5// Returns x * 2^n computed efficiently, without undue over/underflow.
6//
7// -- Stephen Canon, January 2010
8
9
10.text
11.globl _scalblnf
12.globl _scalbnf
13.globl _ldexpf
14
15#if defined __x86_64__
16
17 #define n %edi
18 #define ln %rdi
19
20.align 4
21_scalblnf:
22 cvtss2sd %xmm0, %xmm0 // (double)x
23 mov $300, %rdx
24 cmp %rdx, ln // if n > 300
25 cmovg %rdx, ln // n == 300
26 neg %rdx
27 cmp %rdx, ln // if n < -300
28 cmovl %rdx, ln // n == -300
29 jmp L_common
30
31.align 4
32_scalbnf:
33_ldexpf:
34 cvtss2sd %xmm0, %xmm0 // (double)x
35 mov $300, %edx
36 cmp %edx, n // if n > 300
37 cmovg %edx, n // n == 300
38 neg %edx
39 cmp %edx, n // if n < -300
40 cmovl %edx, n // n == -300
41L_common:
42 add $0x3ff, n //
43 shl $52, ln // (double)2^n
44 movd ln, %xmm1
45 mulsd %xmm1, %xmm0 // (double)(x * 2^n)
46 cvtsd2ss %xmm0, %xmm0 // x * 2^n
47 ret
48
49#elif defined __i386__
50
51 #define n %eax
52
53.align 4
54_scalblnf:
55_scalbnf:
56_ldexpf:
57 cvtss2sd 4(%esp), %xmm0 // (double)x
58 mov 8(%esp), n
59 mov $300, %edx
60 cmp %edx, n // if n > 300
61 cmovg %edx, n // n == 300
62 neg %edx
63 cmp %edx, n // if n < -300
64 cmovl %edx, n // n == -300
65 add $0x3ff, n //
66 movd n, %xmm1
67 psllq $52, %xmm1 // (double)2^n
68 mulsd %xmm1, %xmm0 // (double)(x * 2^n)
69 cvtsd2ss %xmm0, %xmm0 // x * 2^n
70 movss %xmm0, 4(%esp)
71 flds 4(%esp)
72 ret
73
74#else
75 #error "This implementation supports 32- and 64-bit Intel only"
76#endif