Updated to fedora-glibc-20090427T1419
[glibc/history.git] / sysdeps / i386 / fpu / e_scalbl.S
blob3f67d0befb9e81b0b49f7d83d1873b2e20c8303a
1 /*
2  * Written by J.T. Conklin <jtc@netbsd.org>.
3  * Public domain.
4  *
5  * Adapted for `long double' by Ulrich Drepper <drepper@cygnus.com>.
6  *
7  * Correct handling of y==-inf <drepper@gnu>
8  */
10 #include <machine/asm.h>
12 RCSID("$NetBSD: $")
14 #ifdef __ELF__
15         .section .rodata
16 #else
17         .text
18 #endif
20         .align ALIGNARG(4)
21         ASM_TYPE_DIRECTIVE(zero_nan,@object)
22 zero_nan:
23         .double 0.0
24 nan:    .byte 0, 0, 0, 0, 0, 0, 0xff, 0x7f
25 minus_zero:
26         .byte 0, 0, 0, 0, 0, 0, 0, 0x80
27         .byte 0, 0, 0, 0, 0, 0, 0xff, 0x7f
28         ASM_SIZE_DIRECTIVE(zero_nan)
31 #ifdef PIC
32 #define MO(op) op##@GOTOFF(%ecx)
33 #define MOX(op,x,f) op##@GOTOFF(%ecx,x,f)
34 #else
35 #define MO(op) op
36 #define MOX(op,x,f) op(,x,f)
37 #endif
39         .text
40 ENTRY(__ieee754_scalbl)
41         fldt    16(%esp)
42         fxam
43         fnstsw
44         fldt    4(%esp)
45         andl    $0x4700, %eax
46         cmpl    $0x0700, %eax
47         je      1f
48         andl    $0x4500, %eax
49         cmpl    $0x0100, %eax
50         je      2f
51         fxam
52         fnstsw
53         andl    $0x4500, %eax
54         cmpl    $0x0100, %eax
55         je      3f
56         fld     %st(1)
57         frndint
58         fcomp   %st(2)
59         fnstsw
60         sahf
61         jne     4f
62         fscale
63         fstp    %st(1)
64         ret
66         /* y is -inf */
67 1:      fxam
68 #ifdef  PIC
69         LOAD_PIC_REG (cx)
70 #endif
71         fnstsw
72         movl    12(%esp), %edx
73         shrl    $5, %eax
74         fstp    %st
75         fstp    %st
76         andl    $0x8000, %edx
77         andl    $8, %eax
78         jnz     4f
79         shrl    $11, %edx
80         addl    %edx, %eax
81         fldl    MOX(zero_nan, %eax, 1)
82         ret
84         /* The result is NaN, but we must not raise an exception.
85            So use a variable.  */
86 2:      fstp    %st
87         fstp    %st
88 #ifdef  PIC
89         LOAD_PIC_REG (cx)
90 #endif
91         fldl    MO(nan)
92         ret
94         /* The first parameter is a NaN.  Return it.  */
95 3:      fstp    %st(1)
96         ret
98         /* Return NaN and raise the invalid exception.  */
99 4:      fstp    %st
100         fstp    %st
101         fldz
102         fdiv    %st
103         ret
104 END(__ieee754_scalbl)