1 ; RUN: llc < %s | FileCheck %s
3 target datalayout = "e-m:o-i64:64-f80:128-n8:16:32:64-S128"
4 target triple = "x86_64-apple-macosx10.10.0"
6 define void @test_copysign_const_magnitude_d(double %X) {
7 ; CHECK: [[SIGNMASK:L.+]]:
8 ; CHECK-NEXT: .quad -9223372036854775808 ## double -0.000000e+00
9 ; CHECK-NEXT: .quad 0 ## double 0.000000e+00
10 ; CHECK: [[ZERO:L.+]]:
11 ; CHECK-NEXT: .space 16
12 ; CHECK: [[ONE:L.+]]:
13 ; CHECK-NEXT: .quad 4607182418800017408 ## double 1.000000e+00
14 ; CHECK-NEXT: .quad 0 ## double 0.000000e+00
15 ; CHECK-LABEL: test_copysign_const_magnitude_d:
17 ; CHECK: id
18 %iX = call double @id_d(double %X)
20 ; CHECK-NEXT: andpd [[SIGNMASK]](%rip), %xmm0
21 %d0 = call double @copysign(double 0.000000e+00, double %iX)
23 ; CHECK-NEXT: id
24 %id0 = call double @id_d(double %d0)
26 ; CHECK-NEXT: andpd [[SIGNMASK]](%rip), %xmm0
27 ; CHECK-NEXT: orpd [[ZERO]](%rip), %xmm0
28 %dn0 = call double @copysign(double -0.000000e+00, double %id0)
30 ; CHECK-NEXT: id
31 %idn0 = call double @id_d(double %dn0)
33 ; CHECK-NEXT: andpd [[SIGNMASK]](%rip), %xmm0
34 ; CHECK-NEXT: orpd [[ONE]](%rip), %xmm0
35 %d1 = call double @copysign(double 1.000000e+00, double %idn0)
37 ; CHECK-NEXT: id
38 %id1 = call double @id_d(double %d1)
40 ; CHECK-NEXT: andpd [[SIGNMASK]](%rip), %xmm0
41 ; CHECK-NEXT: orpd [[ONE]](%rip), %xmm0
42 %dn1 = call double @copysign(double -1.000000e+00, double %id1)
44 ; CHECK-NEXT: id
45 %idn1 = call double @id_d(double %dn1)
47 ; CHECK: retq
48 ret void
49 }
51 define void @test_copysign_const_magnitude_f(float %X) {
52 ; CHECK: [[SIGNMASK:L.+]]:
53 ; CHECK-NEXT: .long 2147483648 ## float -0.000000e+00
54 ; CHECK-NEXT: .long 0 ## float 0.000000e+00
55 ; CHECK-NEXT: .long 0 ## float 0.000000e+00
56 ; CHECK-NEXT: .long 0 ## float 0.000000e+00
57 ; CHECK: [[ZERO:L.+]]:
58 ; CHECK-NEXT: .space 16
59 ; CHECK: [[ONE:L.+]]:
60 ; CHECK-NEXT: .long 1065353216 ## float 1.000000e+00
61 ; CHECK-NEXT: .long 0 ## float 0.000000e+00
62 ; CHECK-NEXT: .long 0 ## float 0.000000e+00
63 ; CHECK-NEXT: .long 0 ## float 0.000000e+00
64 ; CHECK-LABEL: test_copysign_const_magnitude_f:
66 ; CHECK: id
67 %iX = call float @id_f(float %X)
69 ; CHECK-NEXT: andps [[SIGNMASK]](%rip), %xmm0
70 %d0 = call float @copysignf(float 0.000000e+00, float %iX)
72 ; CHECK-NEXT: id
73 %id0 = call float @id_f(float %d0)
75 ; CHECK-NEXT: andps [[SIGNMASK]](%rip), %xmm0
76 ; CHECK-NEXT: orps [[ZERO]](%rip), %xmm0
77 %dn0 = call float @copysignf(float -0.000000e+00, float %id0)
79 ; CHECK-NEXT: id
80 %idn0 = call float @id_f(float %dn0)
82 ; CHECK-NEXT: andps [[SIGNMASK]](%rip), %xmm0
83 ; CHECK-NEXT: orps [[ONE]](%rip), %xmm0
84 %d1 = call float @copysignf(float 1.000000e+00, float %idn0)
86 ; CHECK-NEXT: id
87 %id1 = call float @id_f(float %d1)
89 ; CHECK-NEXT: andps [[SIGNMASK]](%rip), %xmm0
90 ; CHECK-NEXT: orps [[ONE]](%rip), %xmm0
91 %dn1 = call float @copysignf(float -1.000000e+00, float %id1)
93 ; CHECK-NEXT: id
94 %idn1 = call float @id_f(float %dn1)
96 ; CHECK: retq
97 ret void
98 }
100 declare double @copysign(double, double) nounwind readnone
101 declare float @copysignf(float, float) nounwind readnone
103 ; Dummy identity functions, so we always have xmm0, and prevent optimizations.
104 declare double @id_d(double)
105 declare float @id_f(float)