Skip to content

Commit 2014890

Browse files
authored
[SelectionDAG] Remove UnsafeFPMath in visitFP_ROUND (llvm#154768)
Remove `UnsafeFPMath` in `visitFP_ROUND` part, it blocks some bugfixes related to clang and the ultimate goal is to remove `resetTargetOptions` method in `TargetMachine`, see FIXME in `resetTargetOptions`. See also https://discourse.llvm.org/t/rfc-honor-pragmas-with-ffp-contract-fast https://discourse.llvm.org/t/allowfpopfusion-vs-sdnodeflags-hasallowcontract Now all UnsafeFPMath uses are eliminated in LLVMCodeGen
1 parent d8769bb commit 2014890

File tree

2 files changed

+46
-11
lines changed

2 files changed

+46
-11
lines changed

llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18983,7 +18983,9 @@ SDValue DAGCombiner::visitFP_ROUND(SDNode *N) {
1898318983
// single-step fp_round we want to fold to.
1898418984
// In other words, double rounding isn't the same as rounding.
1898518985
// Also, this is a value preserving truncation iff both fp_round's are.
18986-
if (DAG.getTarget().Options.UnsafeFPMath || N0IsTrunc)
18986+
if ((N->getFlags().hasAllowContract() &&
18987+
N0->getFlags().hasAllowContract()) ||
18988+
N0IsTrunc)
1898718989
return DAG.getNode(
1898818990
ISD::FP_ROUND, DL, VT, N0.getOperand(0),
1898918991
DAG.getIntPtrConstant(NIsTrunc && N0IsTrunc, DL, /*isTarget=*/true));

llvm/test/CodeGen/X86/fp-double-rounding.ll

Lines changed: 43 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,20 +1,53 @@
1-
; RUN: llc < %s | FileCheck %s --check-prefix=CHECK --check-prefix=SAFE
2-
; RUN: llc < %s -enable-unsafe-fp-math | FileCheck %s --check-prefix=CHECK --check-prefix=UNSAFE
1+
; RUN: llc < %s | FileCheck %s
32

43
target datalayout = "e-m:o-i64:64-f80:128-n8:16:32:64-S128"
54
target triple = "x86_64--"
65

6+
; CHECK-LABEL: double_rounding_safe:
7+
; CHECK: callq __trunctfdf2
8+
; CHECK-NEXT: cvtsd2ss %xmm0
9+
define void @double_rounding_safe(ptr %x, ptr %f) {
10+
entry:
11+
%x.fp128 = load fp128, ptr %x, align 16
12+
%x.double = fptrunc fp128 %x.fp128 to double
13+
%x.float = fptrunc double %x.double to float
14+
store float %x.float, ptr %f, align 4
15+
ret void
16+
}
17+
18+
; CHECK-LABEL: double_rounding_contract_fst:
19+
; CHECK: callq __trunctfdf2
20+
; CHECK-NEXT: cvtsd2ss %xmm0
21+
define void @double_rounding_contract_fst(ptr %x, ptr %f) {
22+
entry:
23+
%x.fp128 = load fp128, ptr %x, align 16
24+
%x.double = fptrunc contract fp128 %x.fp128 to double
25+
%x.float = fptrunc double %x.double to float
26+
store float %x.float, ptr %f, align 4
27+
ret void
28+
}
29+
30+
; CHECK-LABEL: double_rounding_contract_snd:
31+
; CHECK: callq __trunctfdf2
32+
; CHECK-NEXT: cvtsd2ss %xmm0
33+
define void @double_rounding_contract_snd(ptr %x, ptr %f) {
34+
entry:
35+
%x.fp128 = load fp128, ptr %x, align 16
36+
%x.double = fptrunc fp128 %x.fp128 to double
37+
%x.float = fptrunc contract double %x.double to float
38+
store float %x.float, ptr %f, align 4
39+
ret void
40+
}
41+
742
; CHECK-LABEL: double_rounding:
8-
; SAFE: callq __trunctfdf2
9-
; SAFE-NEXT: cvtsd2ss %xmm0
10-
; UNSAFE: callq __trunctfsf2
11-
; UNSAFE-NOT: cvt
43+
; CHECK: callq __trunctfsf2
44+
; CHECK-NOT: cvt
1245
define void @double_rounding(ptr %x, ptr %f) {
1346
entry:
14-
%0 = load fp128, ptr %x, align 16
15-
%1 = fptrunc fp128 %0 to double
16-
%2 = fptrunc double %1 to float
17-
store float %2, ptr %f, align 4
47+
%x.fp128 = load fp128, ptr %x, align 16
48+
%x.double = fptrunc contract fp128 %x.fp128 to double
49+
%x.float = fptrunc contract double %x.double to float
50+
store float %x.float, ptr %f, align 4
1851
ret void
1952
}
2053

0 commit comments

Comments
 (0)