mibintc created this revision.
mibintc added reviewers: rjmccall, scanon.
Herald added a project: clang.
mibintc marked 3 inline comments as done.
mibintc added a comment.

added some inline explanation



================
Comment at: clang/lib/Frontend/CompilerInvocation.cpp:2943
+  if (Opts.FastRelaxedMath)
+    Opts.setDefaultFPContractMode(LangOptions::FPM_Fast);
   Opts.HexagonQdsp6Compat = Args.hasArg(OPT_mqdsp6_compat);
----------------
I changed this because the FAST version of this test 
clang/test/CodeGenOpenCL/relaxed-fpmath.cl wants the 'fast' attribute on the 
instruction dump.  All the LLVM FMF bits must be set for the fast attribute 
print.  By default, the value for OpenCL is ffp-contract=on


================
Comment at: clang/lib/Sema/SemaAttr.cpp:460
   case PFC_Push:
-    Action = Sema::PSK_Push_Set;
-    FpPragmaStack.Act(Loc, Action, StringRef(), 
NewFPFeatures.getAsOpaqueInt());
+    if (FpPragmaStack.Stack.empty()) {
+      FpPragmaStack.Act(Loc, Sema::PSK_Set, StringRef(),
----------------
When i was adding a test, I realized that pragma float_control(push) then pop 
wasn't working as expected. If the stack is empty, which is most of the time, 
first need to push the current fp features onto the stack so they can be 
restored at the pop


================
Comment at: clang/test/CodeGen/constrained-math-builtins.c:157
 
-  // CHECK: call contract float @llvm.experimental.constrained.fmuladd.f32
+  // CHECK: call float @llvm.experimental.constrained.fmuladd.f32
   // CHECK: fneg
----------------
most of the test changes here are just a revert of the test changes from the 
original patch for float_control


Previously, the IRBuilder.FMF.allowContract was initialized to true if either 
(ffp-contract=fast or ffp-contract=on) ; with this patch that bit will only be 
set if ffp-contract=fast.  This problem was pointed out by michele.scandale in 
a reply to https://reviews.llvm.org/D72841


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D79903

Files:
  clang/lib/CodeGen/CGExprScalar.cpp
  clang/lib/Frontend/CompilerInvocation.cpp
  clang/lib/Sema/SemaAttr.cpp
  clang/test/CodeGen/constrained-math-builtins.c
  clang/test/CodeGen/fp-contract-on-pragma.cpp
  clang/test/CodeGen/fp-contract-pragma.cpp
  clang/test/CodeGen/fp-floatcontrol-class.cpp
  clang/test/CodeGen/fp-floatcontrol-pragma.cpp
  clang/test/CodeGen/fp-floatcontrol-stack.cpp
  clang/test/CodeGenOpenCL/relaxed-fpmath.cl
  clang/test/CodeGenOpenCL/single-precision-constant.cl

Index: clang/test/CodeGenOpenCL/single-precision-constant.cl
===================================================================
--- clang/test/CodeGenOpenCL/single-precision-constant.cl
+++ clang/test/CodeGenOpenCL/single-precision-constant.cl
@@ -1,6 +1,6 @@
 // RUN: %clang_cc1 %s -cl-single-precision-constant -emit-llvm -o - | FileCheck %s
 
 float fn(float f) {
-  // CHECK: tail call contract float @llvm.fmuladd.f32(float %f, float 2.000000e+00, float 1.000000e+00)
+  // CHECK: tail call float @llvm.fmuladd.f32(float %f, float 2.000000e+00, float 1.000000e+00)
   return f*2. + 1.;
 }
Index: clang/test/CodeGenOpenCL/relaxed-fpmath.cl
===================================================================
--- clang/test/CodeGenOpenCL/relaxed-fpmath.cl
+++ clang/test/CodeGenOpenCL/relaxed-fpmath.cl
@@ -8,12 +8,12 @@
 float spscalardiv(float a, float b) {
   // CHECK: @spscalardiv(
 
-  // NORMAL: fdiv contract float
+  // NORMAL: fdiv float
   // FAST: fdiv fast float
-  // FINITE: fdiv nnan ninf contract float
-  // UNSAFE: fdiv nnan nsz contract float
-  // MAD: fdiv contract float
-  // NOSIGNED: fdiv nsz contract float
+  // FINITE: fdiv nnan ninf float
+  // UNSAFE: fdiv nnan nsz float
+  // MAD: fdiv float
+  // NOSIGNED: fdiv nsz float
   return a / b;
 }
 // CHECK: attributes
Index: clang/test/CodeGen/fp-floatcontrol-stack.cpp
===================================================================
--- clang/test/CodeGen/fp-floatcontrol-stack.cpp
+++ clang/test/CodeGen/fp-floatcontrol-stack.cpp
@@ -9,7 +9,7 @@
 float fun_default FUN(1)
 //CHECK-LABEL: define {{.*}} @_Z11fun_defaultf{{.*}}
 #if DEFAULT
-//CHECK-DDEFAULT: call contract float @llvm.fmuladd{{.*}}
+//CHECK-DDEFAULT: call float @llvm.fmuladd{{.*}}
 #endif
 #if EBSTRICT
 // Note that backend wants constrained intrinsics used
@@ -37,7 +37,7 @@
 //CHECK-DEBSTRICT: llvm.experimental.constrained.fmuladd{{.*}}tonearest{{.*}}strict
 #endif
 #if NOHONOR
-//CHECK-NOHONOR: nnan ninf contract float {{.*}}llvm.experimental.constrained.fmuladd{{.*}}tonearest{{.*}}strict
+//CHECK-NOHONOR: nnan ninf float {{.*}}llvm.experimental.constrained.fmuladd{{.*}}tonearest{{.*}}strict
 #endif
 #if FAST
 //Not possible to enable float_control(except) in FAST mode.
@@ -49,13 +49,13 @@
         float exc_pop FUN(5)
 //CHECK-LABEL: define {{.*}} @_Z7exc_popf{{.*}}
 #if DEFAULT
-//CHECK-DDEFAULT: call contract float @llvm.fmuladd{{.*}}
+//CHECK-DDEFAULT: call float @llvm.fmuladd{{.*}}
 #endif
 #if EBSTRICT
 //CHECK-DEBSTRICT: llvm.experimental.constrained.fmuladd{{.*}}tonearest{{.*}}strict
 #endif
 #if NOHONOR
-//CHECK-NOHONOR: call nnan ninf contract float @llvm.fmuladd{{.*}}
+//CHECK-NOHONOR: call nnan ninf float @llvm.fmuladd{{.*}}
 #endif
 #if FAST
 //CHECK-FAST: fmul fast float
@@ -66,13 +66,13 @@
             float exc_off FUN(5)
 //CHECK-LABEL: define {{.*}} @_Z7exc_offf{{.*}}
 #if DEFAULT
-//CHECK-DDEFAULT: call contract float @llvm.fmuladd{{.*}}
+//CHECK-DDEFAULT: call float @llvm.fmuladd{{.*}}
 #endif
 #if EBSTRICT
-//CHECK-DEBSTRICT: call contract float @llvm.fmuladd{{.*}}
+//CHECK-DEBSTRICT: call float @llvm.fmuladd{{.*}}
 #endif
 #if NOHONOR
-//CHECK-NOHONOR: call nnan ninf contract float @llvm.fmuladd{{.*}}
+//CHECK-NOHONOR: call nnan ninf float @llvm.fmuladd{{.*}}
 #endif
 #if FAST
 //CHECK-FAST: fmul fast float
@@ -83,30 +83,30 @@
                 float precise_on FUN(3)
 //CHECK-LABEL: define {{.*}} @_Z10precise_onf{{.*}}
 #if DEFAULT
-//CHECK-DDEFAULT: contract float {{.*}}llvm.fmuladd{{.*}}
+//CHECK-DDEFAULT: float {{.*}}llvm.fmuladd{{.*}}
 #endif
 #if EBSTRICT
-//CHECK-DEBSTRICT: contract float {{.*}}llvm.fmuladd{{.*}}
+//CHECK-DEBSTRICT: float {{.*}}llvm.fmuladd{{.*}}
 #endif
 #if NOHONOR
 // If precise is pushed then all fast-math should be off!
-//CHECK-NOHONOR: call contract float {{.*}}llvm.fmuladd{{.*}}
+//CHECK-NOHONOR: call float {{.*}}llvm.fmuladd{{.*}}
 #endif
 #if FAST
-//CHECK-FAST: contract float {{.*}}llvm.fmuladd{{.*}}
+//CHECK-FAST: float {{.*}}llvm.fmuladd{{.*}}
 #endif
 
 #pragma float_control(pop)
                     float precise_pop FUN(3)
 //CHECK-LABEL: define {{.*}} @_Z11precise_popf{{.*}}
 #if DEFAULT
-//CHECK-DDEFAULT: contract float {{.*}}llvm.fmuladd{{.*}}
+//CHECK-DDEFAULT: float {{.*}}llvm.fmuladd{{.*}}
 #endif
 #if EBSTRICT
-//CHECK-DEBSTRICT: contract float {{.*}}llvm.fmuladd{{.*}}
+//CHECK-DEBSTRICT: float {{.*}}llvm.fmuladd{{.*}}
 #endif
 #if NOHONOR
-//CHECK-NOHONOR: call nnan ninf contract float @llvm.fmuladd{{.*}}
+//CHECK-NOHONOR: call nnan ninf float @llvm.fmuladd{{.*}}
 #endif
 #if FAST
 //CHECK-FAST: fmul fast float
@@ -143,14 +143,14 @@
 //CHECK-DDEFAULT: llvm.fmuladd{{.*}}
 #endif
 #if EBSTRICT
-//CHECK-DEBSTRICT: contract float {{.*}}llvm.fmuladd{{.*}}
+//CHECK-DEBSTRICT: float {{.*}}llvm.fmuladd{{.*}}
 #endif
 #if NOHONOR
 // fast math should be off, and contract should be on
-//CHECK-NOHONOR: contract float {{.*}}llvm.fmuladd{{.*}}
+//CHECK-NOHONOR: float {{.*}}llvm.fmuladd{{.*}}
 #endif
 #if FAST
-//CHECK-FAST: contract float {{.*}}llvm.fmuladd{{.*}}
+//CHECK-FAST: float {{.*}}llvm.fmuladd{{.*}}
 #endif
 
 #pragma float_control(push)
@@ -160,13 +160,13 @@
 //CHECK-DDEFAULT: llvm.fmuladd{{.*}}
 #endif
 #if EBSTRICT
-//CHECK-DEBSTRICT: contract float {{.*}}llvm.fmuladd{{.*}}
+//CHECK-DEBSTRICT: float {{.*}}llvm.fmuladd{{.*}}
 #endif
 #if NOHONOR
-//CHECK-NOHONOR: contract float {{.*}}llvm.fmuladd{{.*}}
+//CHECK-NOHONOR: float {{.*}}llvm.fmuladd{{.*}}
 #endif
 #if FAST
-//CHECK-FAST: contract float {{.*}}llvm.fmuladd{{.*}}
+//CHECK-FAST: float {{.*}}llvm.fmuladd{{.*}}
 #endif
 
 #pragma float_control(precise, off)
@@ -197,13 +197,13 @@
 //CHECK-DDEFAULT: llvm.fmuladd{{.*}}
 #endif
 #if EBSTRICT
-//CHECK-DEBSTRICT: contract float {{.*}}llvm.fmuladd{{.*}}
+//CHECK-DEBSTRICT: float {{.*}}llvm.fmuladd{{.*}}
 #endif
 #if NOHONOR
-//CHECK-NOHONOR: contract float {{.*}}llvm.fmuladd{{.*}}
+//CHECK-NOHONOR: float {{.*}}llvm.fmuladd{{.*}}
 #endif
 #if FAST
-//CHECK-FAST: contract float {{.*}}llvm.fmuladd{{.*}}
+//CHECK-FAST: float {{.*}}llvm.fmuladd{{.*}}
 #endif
 
 #ifndef FAST
@@ -217,14 +217,14 @@
   float z = 2 + y() * 7;
 //CHECK-LABEL: define {{.*}} void @_ZN2ONC2Ev{{.*}}
 #if DEFAULT
-//CHECK-DDEFAULT: call contract float {{.*}}llvm.fmuladd
+//CHECK-DDEFAULT: call float {{.*}}llvm.fmuladd
 #endif
 #if EBSTRICT
 //Currently, same as default [command line options not considered]
-//CHECK-DEBSTRICT: call contract float {{.*}}llvm.fmuladd
+//CHECK-DEBSTRICT: call float {{.*}}llvm.fmuladd
 #endif
 #if NOHONOR
-//CHECK-NOHONOR: call nnan ninf contract float @llvm.fmuladd{{.*}}
+//CHECK-NOHONOR: call nnan ninf float @llvm.fmuladd{{.*}}
 #endif
 #if FAST
 //CHECK-FAST: fmul fast float
@@ -237,13 +237,13 @@
   float w = 2 + y() * 7;
 //CHECK-LABEL: define {{.*}} void @_ZN3OFFC2Ev{{.*}}
 #if DEFAULT
-//CHECK-DDEFAULT: call contract float {{.*}}llvm.fmuladd
+//CHECK-DDEFAULT: call float {{.*}}llvm.fmuladd
 #endif
 #if EBSTRICT
-//CHECK-DEBSTRICT: call contract float {{.*}}llvm.fmuladd
+//CHECK-DEBSTRICT: call float {{.*}}llvm.fmuladd
 #endif
 #if NOHONOR
-//CHECK-NOHONOR: call nnan ninf contract float @llvm.fmuladd{{.*}}
+//CHECK-NOHONOR: call nnan ninf float @llvm.fmuladd{{.*}}
 #endif
 #if FAST
 //CHECK-FAST: fmul fast float
Index: clang/test/CodeGen/fp-floatcontrol-pragma.cpp
===================================================================
--- clang/test/CodeGen/fp-floatcontrol-pragma.cpp
+++ clang/test/CodeGen/fp-floatcontrol-pragma.cpp
@@ -1,6 +1,68 @@
 // RUN: %clang_cc1 -DEXCEPT=1 -fcxx-exceptions -triple x86_64-linux-gnu -emit-llvm -o - %s | FileCheck -check-prefix=CHECK-NS %s
 // RUN: %clang_cc1 -triple x86_64-linux-gnu -emit-llvm -o - %s | FileCheck %s
 // RUN: %clang_cc1 -verify -DFENV_ON=1 -triple x86_64-linux-gnu -emit-llvm -o - %s | FileCheck %s
+// RUN: %clang_cc1 -triple %itanium_abi_triple -O3 -emit-llvm -o - %s | FileCheck -check-prefix=CHECK-O3 %s
+
+// Verify float_control(precise, off) enables fast math flags on fp operations.
+float fp_precise_1(float a, float b, float c) {
+// CHECK-O3: _Z12fp_precise_1fff
+// CHECK-O3: %[[M:.+]] = fmul fast float{{.*}}
+// CHECK-O3: fadd fast float %[[M]], %c
+#pragma float_control(precise, off)
+  return a * b + c;
+}
+
+// Is float_control state cleared on exiting compound statements?
+float fp_precise_2(float a, float b, float c) {
+  // CHECK-O3: _Z12fp_precise_2fff
+  // CHECK-O3: %[[M:.+]] = fmul float{{.*}}
+  // CHECK-O3: fadd float %[[M]], %c
+  {
+#pragma float_control(precise, off)
+  }
+  return a * b + c;
+}
+
+// Does float_control survive template instantiation?
+class Foo {};
+Foo operator+(Foo, Foo);
+
+template <typename T>
+T template_muladd(T a, T b, T c) {
+#pragma float_control(precise, off)
+  return a * b + c;
+}
+
+float fp_precise_3(float a, float b, float c) {
+  // CHECK-O3: _Z12fp_precise_3fff
+  // CHECK-O3: %[[M:.+]] = fmul fast float{{.*}}
+  // CHECK-O3: fadd fast float %[[M]], %c
+  return template_muladd<float>(a, b, c);
+}
+
+template <typename T>
+class fp_precise_4 {
+  float method(float a, float b, float c) {
+#pragma float_control(precise, off)
+    return a * b + c;
+  }
+};
+
+template class fp_precise_4<int>;
+// CHECK-O3: _ZN12fp_precise_4IiE6methodEfff
+// CHECK-O3: %[[M:.+]] = fmul fast float{{.*}}
+// CHECK-O3: fadd fast float %[[M]], %c
+
+// Check file-scoped float_control
+#pragma float_control(push)
+#pragma float_control(precise, off)
+float fp_precise_5(float a, float b, float c) {
+  // CHECK-O3: _Z12fp_precise_5fff
+  // CHECK-O3: %[[M:.+]] = fmul fast float{{.*}}
+  // CHECK-O3: fadd fast float %[[M]], %c
+  return a * b + c;
+}
+#pragma float_control(pop)
 
 float fff(float x, float y) {
 // CHECK-LABEL: define float @_Z3fffff{{.*}}
@@ -41,6 +103,14 @@
   return z;
 }
 
+float fma_test2(float a, float b, float c) {
+// CHECK-LABEL define float @_Z9fma_test2fff{{.*}}
+#pragma float_control(precise, off)
+  float x = a * b + c;
+  //CHECK: fmuladd
+  return x;
+}
+
 float fma_test1(float a, float b, float c) {
 // CHECK-LABEL define float @_Z9fma_test1fff{{.*}}
 #pragma float_control(precise, on)
@@ -90,7 +160,7 @@
 // CHECK-NS: define {{.*}}exc_off{{.*}}
   {} try {
     x = 1.0 / zero; /* division by zero, the result unused */
-//CHECK-NS: fdiv contract double
+//CHECK-NS: fdiv double
   } catch (...) {}
   return zero;
 }
Index: clang/test/CodeGen/fp-floatcontrol-class.cpp
===================================================================
--- clang/test/CodeGen/fp-floatcontrol-class.cpp
+++ clang/test/CodeGen/fp-floatcontrol-class.cpp
@@ -8,13 +8,13 @@
 class ON {
   float w = 2 + y() * z();
   // CHECK-LABEL: define {{.*}} @_ZN2ONC2Ev{{.*}}
-  //CHECK: call contract float {{.*}}llvm.fmuladd
+  //CHECK: call float {{.*}}llvm.fmuladd
 };
 ON on;
 #pragma float_control(except, off)
 class OFF {
   float w = 2 + y() * z();
   // CHECK-LABEL: define {{.*}} @_ZN3OFFC2Ev{{.*}}
-  //CHECK: call contract float {{.*}}llvm.fmuladd
+  //CHECK: call float {{.*}}llvm.fmuladd
 };
 OFF off;
Index: clang/test/CodeGen/fp-contract-pragma.cpp
===================================================================
--- clang/test/CodeGen/fp-contract-pragma.cpp
+++ clang/test/CodeGen/fp-contract-pragma.cpp
@@ -2,9 +2,9 @@
 
 // Is FP_CONTRACT honored in a simple case?
 float fp_contract_1(float a, float b, float c) {
-  // CHECK: _Z13fp_contract_1fff
-  // CHECK: tail call contract float @llvm.fmuladd
-#pragma STDC FP_CONTRACT ON
+// CHECK: _Z13fp_contract_1fff
+// CHECK: tail call float @llvm.fmuladd
+  #pragma STDC FP_CONTRACT ON
   return a * b + c;
 }
 
@@ -30,8 +30,8 @@
 }
 
 float fp_contract_3(float a, float b, float c) {
-  // CHECK: _Z13fp_contract_3fff
-  // CHECK: tail call contract float @llvm.fmuladd
+// CHECK: _Z13fp_contract_3fff
+// CHECK: tail call float @llvm.fmuladd
   return template_muladd<float>(a, b, c);
 }
 
@@ -44,13 +44,13 @@
 
 template class fp_contract_4<int>;
 // CHECK: _ZN13fp_contract_4IiE6methodEfff
-// CHECK: tail call contract float @llvm.fmuladd
+// CHECK: tail call float @llvm.fmuladd
 
 // Check file-scoped FP_CONTRACT
 #pragma STDC FP_CONTRACT ON
 float fp_contract_5(float a, float b, float c) {
-  // CHECK: _Z13fp_contract_5fff
-  // CHECK: tail call contract float @llvm.fmuladd
+// CHECK: _Z13fp_contract_5fff
+// CHECK: tail call float @llvm.fmuladd
   return a * b + c;
 }
 
@@ -67,25 +67,25 @@
 // https://llvm.org/bugs/show_bug.cgi?id=25719
 
 float fp_contract_7(float a, float b, float c) {
-  // CHECK: _Z13fp_contract_7fff
-  // CHECK:  %[[M:.+]] = fmul contract float %b, 2.000000e+00
-  // CHECK-NEXT: fsub contract float %[[M]], %c
-#pragma STDC FP_CONTRACT ON
+// CHECK: _Z13fp_contract_7fff
+// CHECK:  %[[M:.+]] = fmul float %b, 2.000000e+00
+// CHECK-NEXT: fsub float %[[M]], %c
+  #pragma STDC FP_CONTRACT ON
   return (a = 2 * b) - c;
 }
 
 float fp_contract_8(float a, float b, float c) {
-  // CHECK: _Z13fp_contract_8fff
-  // CHECK: fneg contract float %c
-  // CHECK: tail call contract float @llvm.fmuladd
-#pragma STDC FP_CONTRACT ON
+// CHECK: _Z13fp_contract_8fff
+// CHECK: fneg float %c
+// CHECK: tail call float @llvm.fmuladd
+  #pragma STDC FP_CONTRACT ON
   return a * b - c;
 }
 
 float fp_contract_9(float a, float b, float c) {
-  // CHECK: _Z13fp_contract_9fff
-  // CHECK: fneg contract float %a
-  // CHECK: tail call contract float @llvm.fmuladd
-#pragma STDC FP_CONTRACT ON
+// CHECK: _Z13fp_contract_9fff
+// CHECK: fneg float %a
+// CHECK: tail call float @llvm.fmuladd
+  #pragma STDC FP_CONTRACT ON
   return c - a * b;
 }
Index: clang/test/CodeGen/fp-contract-on-pragma.cpp
===================================================================
--- clang/test/CodeGen/fp-contract-on-pragma.cpp
+++ clang/test/CodeGen/fp-contract-on-pragma.cpp
@@ -3,7 +3,7 @@
 // Is FP_CONTRACT honored in a simple case?
 float fp_contract_1(float a, float b, float c) {
 // CHECK: _Z13fp_contract_1fff
-// CHECK: tail call contract float @llvm.fmuladd
+// CHECK: tail call float @llvm.fmuladd
 #pragma clang fp contract(on)
   return a * b + c;
 }
@@ -31,7 +31,7 @@
 
 float fp_contract_3(float a, float b, float c) {
   // CHECK: _Z13fp_contract_3fff
-  // CHECK: tail call contract float @llvm.fmuladd
+  // CHECK: tail call float @llvm.fmuladd
   return template_muladd<float>(a, b, c);
 }
 
@@ -45,13 +45,13 @@
 
 template class fp_contract_4<int>;
 // CHECK: _ZN13fp_contract_4IiE6methodEfff
-// CHECK: tail call contract float @llvm.fmuladd
+// CHECK: tail call float @llvm.fmuladd
 
 // Check file-scoped FP_CONTRACT
 #pragma clang fp contract(on)
 float fp_contract_5(float a, float b, float c) {
   // CHECK: _Z13fp_contract_5fff
-  // CHECK: tail call contract float @llvm.fmuladd
+  // CHECK: tail call float @llvm.fmuladd
   return a * b + c;
 }
 
@@ -69,8 +69,8 @@
 
 float fp_contract_7(float a, float b, float c) {
 // CHECK: _Z13fp_contract_7fff
-// CHECK:  %[[M:.+]] = fmul contract float %b, 2.000000e+00
-// CHECK-NEXT: fsub contract float %[[M]], %c
+// CHECK:  %[[M:.+]] = fmul float %b, 2.000000e+00
+// CHECK-NEXT: fsub float %[[M]], %c
 #pragma clang fp contract(on)
   return (a = 2 * b) - c;
 }
Index: clang/test/CodeGen/constrained-math-builtins.c
===================================================================
--- clang/test/CodeGen/constrained-math-builtins.c
+++ clang/test/CodeGen/constrained-math-builtins.c
@@ -154,9 +154,9 @@
   (double)f * f - f;
   (long double)-f * f + f;
 
-  // CHECK: call contract float @llvm.experimental.constrained.fmuladd.f32
+  // CHECK: call float @llvm.experimental.constrained.fmuladd.f32
   // CHECK: fneg
-  // CHECK: call contract double @llvm.experimental.constrained.fmuladd.f64
+  // CHECK: call double @llvm.experimental.constrained.fmuladd.f64
   // CHECK: fneg
-  // CHECK: call contract x86_fp80 @llvm.experimental.constrained.fmuladd.f80
+  // CHECK: call x86_fp80 @llvm.experimental.constrained.fmuladd.f80
 };
Index: clang/lib/Sema/SemaAttr.cpp
===================================================================
--- clang/lib/Sema/SemaAttr.cpp
+++ clang/lib/Sema/SemaAttr.cpp
@@ -457,8 +457,12 @@
     FpPragmaStack.Act(Loc, Action, StringRef(), NewValue);
     break;
   case PFC_Push:
-    Action = Sema::PSK_Push_Set;
-    FpPragmaStack.Act(Loc, Action, StringRef(), NewFPFeatures.getAsOpaqueInt());
+    if (FpPragmaStack.Stack.empty()) {
+      FpPragmaStack.Act(Loc, Sema::PSK_Set, StringRef(),
+                        CurFPFeatures.getAsOpaqueInt());
+    }
+    FpPragmaStack.Act(Loc, Sema::PSK_Push_Set, StringRef(),
+                      NewFPFeatures.getAsOpaqueInt());
     break;
   case PFC_Pop:
     if (FpPragmaStack.Stack.empty()) {
Index: clang/lib/Frontend/CompilerInvocation.cpp
===================================================================
--- clang/lib/Frontend/CompilerInvocation.cpp
+++ clang/lib/Frontend/CompilerInvocation.cpp
@@ -2939,6 +2939,8 @@
   Opts.NoBitFieldTypeAlign = Args.hasArg(OPT_fno_bitfield_type_align);
   Opts.SinglePrecisionConstants = Args.hasArg(OPT_cl_single_precision_constant);
   Opts.FastRelaxedMath = Args.hasArg(OPT_cl_fast_relaxed_math);
+  if (Opts.FastRelaxedMath)
+    Opts.setDefaultFPContractMode(LangOptions::FPM_Fast);
   Opts.HexagonQdsp6Compat = Args.hasArg(OPT_mqdsp6_compat);
   Opts.FakeAddressSpaceMap = Args.hasArg(OPT_ffake_address_space_map);
   Opts.ParseUnknownAnytype = Args.hasArg(OPT_funknown_anytype);
Index: clang/lib/CodeGen/CGExprScalar.cpp
===================================================================
--- clang/lib/CodeGen/CGExprScalar.cpp
+++ clang/lib/CodeGen/CGExprScalar.cpp
@@ -223,8 +223,7 @@
   FMF.setNoSignedZeros(FPFeatures.noSignedZeros());
   FMF.setAllowReciprocal(FPFeatures.allowReciprocalMath());
   FMF.setApproxFunc(FPFeatures.allowApproximateFunctions());
-  FMF.setAllowContract(FPFeatures.allowFPContractAcrossStatement() ||
-                       FPFeatures.allowFPContractWithinStatement());
+  FMF.setAllowContract(FPFeatures.allowFPContractAcrossStatement());
 }
 
 /// Propagate fast-math flags from \p Op to the instruction in \p V.
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to