• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1; RUN: llc -O3 -mtriple=x86_64-pc-linux < %s | FileCheck --check-prefix=COMMON --check-prefix=NO-FMA --check-prefix=FMACALL64 --check-prefix=FMACALL32 %s
2; RUN: llc -O3 -mtriple=x86_64-pc-linux -mattr=+fma < %s | FileCheck -check-prefix=COMMON --check-prefix=HAS-FMA --check-prefix=FMA64 --check-prefix=FMA32 %s
3
4; Verify that constants aren't folded to inexact results when the rounding mode
5; is unknown.
6;
7; double f1() {
8;   // Because 0.1 cannot be represented exactly, this shouldn't be folded.
9;   return 1.0/10.0;
10; }
11;
12; CHECK-LABEL: f1
13; COMMON: divsd
14define double @f1() {
15entry:
16  %div = call double @llvm.experimental.constrained.fdiv.f64(
17                                               double 1.000000e+00,
18                                               double 1.000000e+01,
19                                               metadata !"round.dynamic",
20                                               metadata !"fpexcept.strict")
21  ret double %div
22}
23
24; Verify that 'a - 0' isn't simplified to 'a' when the rounding mode is unknown.
25;
26; double f2(double a) {
27;   // Because the result of '0 - 0' is negative zero if rounding mode is
28;   // downward, this shouldn't be simplified.
29;   return a - 0;
30; }
31;
32; CHECK-LABEL: f2
33; COMMON:  subsd
34define double @f2(double %a) {
35entry:
36  %sub = call double @llvm.experimental.constrained.fsub.f64(
37                                               double %a,
38                                               double 0.000000e+00,
39                                               metadata !"round.dynamic",
40                                               metadata !"fpexcept.strict")
41  ret double %sub
42}
43
44; Verify that '-((-a)*b)' isn't simplified to 'a*b' when the rounding mode is
45; unknown.
46;
47; double f3(double a, double b) {
48;   // Because the intermediate value involved in this calculation may require
49;   // rounding, this shouldn't be simplified.
50;   return -((-a)*b);
51; }
52;
53; CHECK-LABEL: f3:
54; COMMON:  subsd
55; COMMON:  mulsd
56; COMMON:  subsd
57define double @f3(double %a, double %b) {
58entry:
59  %sub = call double @llvm.experimental.constrained.fsub.f64(
60                                               double -0.000000e+00, double %a,
61                                               metadata !"round.dynamic",
62                                               metadata !"fpexcept.strict")
63  %mul = call double @llvm.experimental.constrained.fmul.f64(
64                                               double %sub, double %b,
65                                               metadata !"round.dynamic",
66                                               metadata !"fpexcept.strict")
67  %ret = call double @llvm.experimental.constrained.fsub.f64(
68                                               double -0.000000e+00,
69                                               double %mul,
70                                               metadata !"round.dynamic",
71                                               metadata !"fpexcept.strict")
72  ret double %ret
73}
74
75; Verify that FP operations are not performed speculatively when FP exceptions
76; are not being ignored.
77;
78; double f4(int n, double a) {
79;   // Because a + 1 may overflow, this should not be simplified.
80;   if (n > 0)
81;     return a + 1.0;
82;   return a;
83; }
84;
85;
86; CHECK-LABEL: f4:
87; COMMON: testl
88; COMMON: jle
89; COMMON: addsd
90define double @f4(i32 %n, double %a) {
91entry:
92  %cmp = icmp sgt i32 %n, 0
93  br i1 %cmp, label %if.then, label %if.end
94
95if.then:
96  %add = call double @llvm.experimental.constrained.fadd.f64(
97                                               double 1.000000e+00, double %a,
98                                               metadata !"round.dynamic",
99                                               metadata !"fpexcept.strict")
100  br label %if.end
101
102if.end:
103  %a.0 = phi double [%add, %if.then], [ %a, %entry ]
104  ret double %a.0
105}
106
107; Verify that sqrt(42.0) isn't simplified when the rounding mode is unknown.
108; CHECK-LABEL: f5
109; COMMON:  sqrtsd
110define double @f5() {
111entry:
112  %result = call double @llvm.experimental.constrained.sqrt.f64(double 42.0,
113                                               metadata !"round.dynamic",
114                                               metadata !"fpexcept.strict")
115  ret double %result
116}
117
118; Verify that pow(42.1, 3.0) isn't simplified when the rounding mode is unknown.
119; CHECK-LABEL: f6
120; COMMON:  pow
121define double @f6() {
122entry:
123  %result = call double @llvm.experimental.constrained.pow.f64(double 42.1,
124                                               double 3.0,
125                                               metadata !"round.dynamic",
126                                               metadata !"fpexcept.strict")
127  ret double %result
128}
129
130; Verify that powi(42.1, 3) isn't simplified when the rounding mode is unknown.
131; CHECK-LABEL: f7
132; COMMON:  powi
133define double @f7() {
134entry:
135  %result = call double @llvm.experimental.constrained.powi.f64(double 42.1,
136                                               i32 3,
137                                               metadata !"round.dynamic",
138                                               metadata !"fpexcept.strict")
139  ret double %result
140}
141
142; Verify that sin(42.0) isn't simplified when the rounding mode is unknown.
143; CHECK-LABEL: f8
144; COMMON:  sin
145define double @f8() {
146entry:
147  %result = call double @llvm.experimental.constrained.sin.f64(double 42.0,
148                                               metadata !"round.dynamic",
149                                               metadata !"fpexcept.strict")
150  ret double %result
151}
152
153; Verify that cos(42.0) isn't simplified when the rounding mode is unknown.
154; CHECK-LABEL: f9
155; COMMON:  cos
156define double @f9() {
157entry:
158  %result = call double @llvm.experimental.constrained.cos.f64(double 42.0,
159                                               metadata !"round.dynamic",
160                                               metadata !"fpexcept.strict")
161  ret double %result
162}
163
164; Verify that exp(42.0) isn't simplified when the rounding mode is unknown.
165; CHECK-LABEL: f10
166; COMMON:  exp
167define double @f10() {
168entry:
169  %result = call double @llvm.experimental.constrained.exp.f64(double 42.0,
170                                               metadata !"round.dynamic",
171                                               metadata !"fpexcept.strict")
172  ret double %result
173}
174
175; Verify that exp2(42.1) isn't simplified when the rounding mode is unknown.
176; CHECK-LABEL: f11
177; COMMON:  exp2
178define double @f11() {
179entry:
180  %result = call double @llvm.experimental.constrained.exp2.f64(double 42.1,
181                                               metadata !"round.dynamic",
182                                               metadata !"fpexcept.strict")
183  ret double %result
184}
185
186; Verify that log(42.0) isn't simplified when the rounding mode is unknown.
187; CHECK-LABEL: f12
188; COMMON:  log
189define double @f12() {
190entry:
191  %result = call double @llvm.experimental.constrained.log.f64(double 42.0,
192                                               metadata !"round.dynamic",
193                                               metadata !"fpexcept.strict")
194  ret double %result
195}
196
197; Verify that log10(42.0) isn't simplified when the rounding mode is unknown.
198; CHECK-LABEL: f13
199; COMMON:  log10
200define double @f13() {
201entry:
202  %result = call double @llvm.experimental.constrained.log10.f64(double 42.0,
203                                               metadata !"round.dynamic",
204                                               metadata !"fpexcept.strict")
205  ret double %result
206}
207
208; Verify that log2(42.0) isn't simplified when the rounding mode is unknown.
209; CHECK-LABEL: f14
210; COMMON:  log2
211define double @f14() {
212entry:
213  %result = call double @llvm.experimental.constrained.log2.f64(double 42.0,
214                                               metadata !"round.dynamic",
215                                               metadata !"fpexcept.strict")
216  ret double %result
217}
218
219; Verify that rint(42.1) isn't simplified when the rounding mode is unknown.
220; CHECK-LABEL: f15
221; NO-FMA:  rint
222; HAS-FMA: vroundsd
223define double @f15() {
224entry:
225  %result = call double @llvm.experimental.constrained.rint.f64(double 42.1,
226                                               metadata !"round.dynamic",
227                                               metadata !"fpexcept.strict")
228  ret double %result
229}
230
231; Verify that nearbyint(42.1) isn't simplified when the rounding mode is
232; unknown.
233; CHECK-LABEL: f16
234; NO-FMA:  nearbyint
235; HAS-FMA: vroundsd
236define double @f16() {
237entry:
238  %result = call double @llvm.experimental.constrained.nearbyint.f64(
239                                               double 42.1,
240                                               metadata !"round.dynamic",
241                                               metadata !"fpexcept.strict")
242  ret double %result
243}
244
245; Verify that fma(3.5) isn't simplified when the rounding mode is
246; unknown.
247; CHECK-LABEL: f17
248; FMACALL32: jmp fmaf  # TAILCALL
249; FMA32: vfmadd213ss
250define float @f17() {
251entry:
252  %result = call float @llvm.experimental.constrained.fma.f32(
253                                               float 3.5,
254                                               float 3.5,
255                                               float 3.5,
256                                               metadata !"round.dynamic",
257                                               metadata !"fpexcept.strict")
258  ret float %result
259}
260
261; Verify that fma(42.1) isn't simplified when the rounding mode is
262; unknown.
263; CHECK-LABEL: f18
264; FMACALL64: jmp fma  # TAILCALL
265; FMA64: vfmadd213sd
266define double @f18() {
267entry:
268  %result = call double @llvm.experimental.constrained.fma.f64(
269                                               double 42.1,
270                                               double 42.1,
271                                               double 42.1,
272                                               metadata !"round.dynamic",
273                                               metadata !"fpexcept.strict")
274  ret double %result
275}
276
277@llvm.fp.env = thread_local global i8 zeroinitializer, section "llvm.metadata"
278declare double @llvm.experimental.constrained.fdiv.f64(double, double, metadata, metadata)
279declare double @llvm.experimental.constrained.fmul.f64(double, double, metadata, metadata)
280declare double @llvm.experimental.constrained.fadd.f64(double, double, metadata, metadata)
281declare double @llvm.experimental.constrained.fsub.f64(double, double, metadata, metadata)
282declare double @llvm.experimental.constrained.sqrt.f64(double, metadata, metadata)
283declare double @llvm.experimental.constrained.pow.f64(double, double, metadata, metadata)
284declare double @llvm.experimental.constrained.powi.f64(double, i32, metadata, metadata)
285declare double @llvm.experimental.constrained.sin.f64(double, metadata, metadata)
286declare double @llvm.experimental.constrained.cos.f64(double, metadata, metadata)
287declare double @llvm.experimental.constrained.exp.f64(double, metadata, metadata)
288declare double @llvm.experimental.constrained.exp2.f64(double, metadata, metadata)
289declare double @llvm.experimental.constrained.log.f64(double, metadata, metadata)
290declare double @llvm.experimental.constrained.log10.f64(double, metadata, metadata)
291declare double @llvm.experimental.constrained.log2.f64(double, metadata, metadata)
292declare double @llvm.experimental.constrained.rint.f64(double, metadata, metadata)
293declare double @llvm.experimental.constrained.nearbyint.f64(double, metadata, metadata)
294declare float @llvm.experimental.constrained.fma.f32(float, float, float, metadata, metadata)
295declare double @llvm.experimental.constrained.fma.f64(double, double, double, metadata, metadata)
296