zahiraam updated this revision to Diff 417356.
zahiraam marked 2 inline comments as done.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D122155/new/

https://reviews.llvm.org/D122155

Files:
  clang/include/clang/Basic/DiagnosticFrontendKinds.td
  clang/include/clang/Basic/DiagnosticGroups.td
  clang/include/clang/Basic/DiagnosticSemaKinds.td
  clang/lib/Frontend/CompilerInvocation.cpp
  clang/lib/Sema/SemaAttr.cpp
  clang/test/Sema/eval-method-with-unsafe-math.c

Index: clang/test/Sema/eval-method-with-unsafe-math.c
===================================================================
--- /dev/null
+++ clang/test/Sema/eval-method-with-unsafe-math.c
@@ -0,0 +1,28 @@
+// RUN: %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -ffp-eval-method=source \
+// RUN: -verify %s
+
+// RUN: %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -fapprox-func -ffp-eval-method=source \
+// RUN: %s 2>&1 | FileCheck %s --check-prefix=WARN
+
+// RUN: %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math  -ffp-eval-method=source \
+// RUN: %s 2>&1 | FileCheck %s --check-prefix=WARN
+
+// RUN: %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -mreassociate -ffp-eval-method=source \
+// RUN: %s 2>&1 | FileCheck %s --check-prefix=WARN
+
+// expected-no-diagnostics
+
+float f1(float a, float b, float c) {
+  return a * b + c;
+  // WARN: setting the eval method via '-ffp-eval-method' has not effect when numeric results of floating-point calculations aren't value-safe.
+}
+
+float f2(float a, float b, float c) {
+#pragma clang fp eval_method(double)
+  // WARN: setting the eval method via the `pragma clang fp eval_method` has no effect when numeric results of floating-point calculations aren't value-safe.
+  return a * b + c;
+}
Index: clang/lib/Sema/SemaAttr.cpp
===================================================================
--- clang/lib/Sema/SemaAttr.cpp
+++ clang/lib/Sema/SemaAttr.cpp
@@ -486,6 +486,10 @@
     NewFPFeatures.setFPEvalMethodOverride(LangOptions::FEM_Extended);
     break;
   }
+  if (getLangOpts().ApproxFunc || getLangOpts().AllowFPReassoc ||
+      getLangOpts().AllowRecip)
+    Diag(Loc,
+         diag::warn_eval_method_setting_via_pragma_in_value_unsafe_context);
   FpPragmaStack.Act(Loc, PSK_Set, StringRef(), NewFPFeatures);
   CurFPFeatures = NewFPFeatures.applyOverrides(getLangOpts());
   PP.setCurrentFPEvalMethod(Loc, Value);
Index: clang/lib/Frontend/CompilerInvocation.cpp
===================================================================
--- clang/lib/Frontend/CompilerInvocation.cpp
+++ clang/lib/Frontend/CompilerInvocation.cpp
@@ -503,6 +503,18 @@
     Diags.Report(diag::warn_ignored_hip_only_option)
         << Args.getLastArg(OPT_gpu_max_threads_per_block_EQ)->getAsString(Args);
 
+  // When these options are used, the compiler is allowed to make
+  // transformation that may affect the final result. For example
+  // (x+y)+z is transformed to x+(y+z) but may not give the same
+  // final result; it's not value safe.
+  // Another example can be to simlify x/x to 1.0 but x could be 0.0, INF
+  // or NaN. Final result may then differ. Setting the eval method in this
+  // case has no effect.
+  if (Args.hasArg(OPT_ffp_eval_method_EQ) && (LangOpts.ApproxFunc ||
+      LangOpts.AllowFPReassoc || LangOpts.AllowRecip))
+    Diags.Report(
+        diag::warn_eval_method_setting_via_option_in_value_unsafe_context);
+
   // -cl-strict-aliasing needs to emit diagnostic in the case where CL > 1.0.
   // This option should be deprecated for CL > 1.0 because
   // this option was added for compatibility with OpenCL 1.0.
Index: clang/include/clang/Basic/DiagnosticSemaKinds.td
===================================================================
--- clang/include/clang/Basic/DiagnosticSemaKinds.td
+++ clang/include/clang/Basic/DiagnosticSemaKinds.td
@@ -6475,6 +6475,12 @@
   "comparing floating point with == or != is unsafe">,
   InGroup<DiagGroup<"float-equal">>, DefaultIgnore;
 
+def warn_eval_method_setting_via_pragma_in_value_unsafe_context : Warning<
+  "setting the eval method via the `pragma clang fp eval_method` "
+  "has no effect when numeric results of floating-point calculations aren't "
+  "value-safe.">,
+  InGroup<Pragmas>;
+
 def warn_remainder_division_by_zero : Warning<
   "%select{remainder|division}0 by zero is undefined">,
   InGroup<DivZero>;
Index: clang/include/clang/Basic/DiagnosticGroups.td
===================================================================
--- clang/include/clang/Basic/DiagnosticGroups.td
+++ clang/include/clang/Basic/DiagnosticGroups.td
@@ -124,6 +124,7 @@
 def UnsupportedNan : DiagGroup<"unsupported-nan">;
 def UnsupportedAbs : DiagGroup<"unsupported-abs">;
 def UnsupportedFPOpt : DiagGroup<"unsupported-floating-point-opt">;
+def IncompatibleFPOpts : DiagGroup<"incompatible-floating-point-opts">;
 def UnsupportedCB : DiagGroup<"unsupported-cb">;
 def UnsupportedGPOpt : DiagGroup<"unsupported-gpopt">;
 def UnsupportedTargetOpt : DiagGroup<"unsupported-target-opt">;
Index: clang/include/clang/Basic/DiagnosticFrontendKinds.td
===================================================================
--- clang/include/clang/Basic/DiagnosticFrontendKinds.td
+++ clang/include/clang/Basic/DiagnosticFrontendKinds.td
@@ -47,6 +47,10 @@
 def warn_fe_backend_unsupported_fp_exceptions : Warning<
     "overriding currently unsupported use of floating point exceptions "
     "on this target">, InGroup<UnsupportedFPOpt>;
+def warn_eval_method_setting_via_option_in_value_unsafe_context : Warning<
+    "setting the eval method via '-ffp-eval-method' has not effect when numeric "
+    "results of floating-point calculations aren't value-safe.">,
+    InGroup<IncompatibleFPOpts>;
 
 def remark_fe_backend_optimization_remark : Remark<"%0">, BackendInfo,
     InGroup<BackendOptimizationRemark>;
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to