-
Notifications
You must be signed in to change notification settings - Fork 13.7k
[ConstantFolding] Add support for llvm.atan in constant folding. #143416
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
@llvm/pr-subscribers-llvm-transforms Author: Craig Topper (topperc) ChangesFixes #143360 Full diff: https://github.com/llvm/llvm-project/pull/143416.diff 2 Files Affected:
diff --git a/llvm/lib/Analysis/ConstantFolding.cpp b/llvm/lib/Analysis/ConstantFolding.cpp
index 7dd7f413783c9..23ea6966fbf6c 100644
--- a/llvm/lib/Analysis/ConstantFolding.cpp
+++ b/llvm/lib/Analysis/ConstantFolding.cpp
@@ -1672,6 +1672,7 @@ bool llvm::canConstantFoldCallTo(const CallBase *Call, const Function *F) {
case Intrinsic::sincos:
case Intrinsic::sinh:
case Intrinsic::cosh:
+ case Intrinsic::atan:
case Intrinsic::pow:
case Intrinsic::powi:
case Intrinsic::ldexp:
@@ -2538,6 +2539,8 @@ static Constant *ConstantFoldScalarCall1(StringRef Name,
return ConstantFoldFP(sinh, APF, Ty);
case Intrinsic::cosh:
return ConstantFoldFP(cosh, APF, Ty);
+ case Intrinsic::atan:
+ return ConstantFoldFP(atan, APF, Ty);
case Intrinsic::sqrt:
return ConstantFoldFP(sqrt, APF, Ty);
case Intrinsic::amdgcn_cos:
diff --git a/llvm/test/Transforms/InstSimplify/ConstProp/atan-intrinsic.ll b/llvm/test/Transforms/InstSimplify/ConstProp/atan-intrinsic.ll
new file mode 100644
index 0000000000000..d824d6d35643d
--- /dev/null
+++ b/llvm/test/Transforms/InstSimplify/ConstProp/atan-intrinsic.ll
@@ -0,0 +1,88 @@
+; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 5
+; RUN: opt -S -passes=instsimplify < %s | FileCheck %s
+
+define double @test_atan_0() {
+; CHECK-LABEL: define double @test_atan_0() {
+; CHECK-NEXT: ret double 0.000000e+00
+;
+ %result = call double @llvm.atan.f64(double 0.0)
+ ret double %result
+}
+
+define double @test_atan_one() {
+; CHECK-LABEL: define double @test_atan_one() {
+; CHECK-NEXT: ret double 0x3FE921FB54442D18
+;
+ %res = call double @llvm.atan.f64(double 1.0)
+ ret double %res
+}
+
+define <2 x double> @test_atan_v2() {
+; CHECK-LABEL: define <2 x double> @test_atan_v2() {
+; CHECK-NEXT: ret <2 x double> zeroinitializer
+;
+ %result = call <2 x double> @llvm.atan.v2f64(<2 x double> zeroinitializer)
+ ret <2 x double> %result
+}
+
+define double @test_atan_neg0() {
+; CHECK-LABEL: define double @test_atan_neg0() {
+; CHECK-NEXT: ret double -0.000000e+00
+;
+ %res = call double @llvm.atan.f64(double -0.0)
+ ret double %res
+}
+
+define double @test_atan_poison() {
+; CHECK-LABEL: define double @test_atan_poison() {
+; CHECK-NEXT: [[RES:%.*]] = call double @llvm.atan.f64(double poison)
+; CHECK-NEXT: ret double [[RES]]
+;
+ %res = call double @llvm.atan.f64(double poison)
+ ret double %res
+}
+
+define double @test_atan_undef() {
+; CHECK-LABEL: define double @test_atan_undef() {
+; CHECK-NEXT: [[RES:%.*]] = call double @llvm.atan.f64(double undef)
+; CHECK-NEXT: ret double [[RES]]
+;
+ %res = call double @llvm.atan.f64(double undef)
+ ret double %res
+}
+
+define double @test_atan_snan() {
+; CHECK-LABEL: define double @test_atan_snan() {
+; CHECK-NEXT: [[RES:%.*]] = call double @llvm.atan.f64(double 0x7FF0000000000001)
+; CHECK-NEXT: ret double [[RES]]
+;
+ %res = call double @llvm.atan.f64(double 0x7ff0000000000001)
+ ret double %res
+}
+
+define double @test_atan_qnan() {
+; CHECK-LABEL: define double @test_atan_qnan() {
+; CHECK-NEXT: [[RES:%.*]] = call double @llvm.atan.f64(double 0x7FF8000000000000)
+; CHECK-NEXT: ret double [[RES]]
+;
+ %res = call double @llvm.atan.f64(double 0x7ff8000000000000)
+ ret double %res
+}
+
+define double @test_atan_pos_inf() {
+; CHECK-LABEL: define double @test_atan_pos_inf() {
+; CHECK-NEXT: [[RES:%.*]] = call double @llvm.atan.f64(double 0x7FF0000000000000)
+; CHECK-NEXT: ret double [[RES]]
+;
+ %res = call double @llvm.atan.f64(double 0x7ff0000000000000)
+ ret double %res
+}
+
+define double @test_atan_neg_inf() {
+; CHECK-LABEL: define double @test_atan_neg_inf() {
+; CHECK-NEXT: [[RES:%.*]] = call double @llvm.atan.f64(double 0xFFF0000000000000)
+; CHECK-NEXT: ret double [[RES]]
+;
+ %res = call double @llvm.atan.f64(double 0xfff0000000000000)
+ ret double %res
+}
|
@llvm/pr-subscribers-llvm-analysis Author: Craig Topper (topperc) ChangesFixes #143360 Full diff: https://github.com/llvm/llvm-project/pull/143416.diff 2 Files Affected:
diff --git a/llvm/lib/Analysis/ConstantFolding.cpp b/llvm/lib/Analysis/ConstantFolding.cpp
index 7dd7f413783c9..23ea6966fbf6c 100644
--- a/llvm/lib/Analysis/ConstantFolding.cpp
+++ b/llvm/lib/Analysis/ConstantFolding.cpp
@@ -1672,6 +1672,7 @@ bool llvm::canConstantFoldCallTo(const CallBase *Call, const Function *F) {
case Intrinsic::sincos:
case Intrinsic::sinh:
case Intrinsic::cosh:
+ case Intrinsic::atan:
case Intrinsic::pow:
case Intrinsic::powi:
case Intrinsic::ldexp:
@@ -2538,6 +2539,8 @@ static Constant *ConstantFoldScalarCall1(StringRef Name,
return ConstantFoldFP(sinh, APF, Ty);
case Intrinsic::cosh:
return ConstantFoldFP(cosh, APF, Ty);
+ case Intrinsic::atan:
+ return ConstantFoldFP(atan, APF, Ty);
case Intrinsic::sqrt:
return ConstantFoldFP(sqrt, APF, Ty);
case Intrinsic::amdgcn_cos:
diff --git a/llvm/test/Transforms/InstSimplify/ConstProp/atan-intrinsic.ll b/llvm/test/Transforms/InstSimplify/ConstProp/atan-intrinsic.ll
new file mode 100644
index 0000000000000..d824d6d35643d
--- /dev/null
+++ b/llvm/test/Transforms/InstSimplify/ConstProp/atan-intrinsic.ll
@@ -0,0 +1,88 @@
+; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 5
+; RUN: opt -S -passes=instsimplify < %s | FileCheck %s
+
+define double @test_atan_0() {
+; CHECK-LABEL: define double @test_atan_0() {
+; CHECK-NEXT: ret double 0.000000e+00
+;
+ %result = call double @llvm.atan.f64(double 0.0)
+ ret double %result
+}
+
+define double @test_atan_one() {
+; CHECK-LABEL: define double @test_atan_one() {
+; CHECK-NEXT: ret double 0x3FE921FB54442D18
+;
+ %res = call double @llvm.atan.f64(double 1.0)
+ ret double %res
+}
+
+define <2 x double> @test_atan_v2() {
+; CHECK-LABEL: define <2 x double> @test_atan_v2() {
+; CHECK-NEXT: ret <2 x double> zeroinitializer
+;
+ %result = call <2 x double> @llvm.atan.v2f64(<2 x double> zeroinitializer)
+ ret <2 x double> %result
+}
+
+define double @test_atan_neg0() {
+; CHECK-LABEL: define double @test_atan_neg0() {
+; CHECK-NEXT: ret double -0.000000e+00
+;
+ %res = call double @llvm.atan.f64(double -0.0)
+ ret double %res
+}
+
+define double @test_atan_poison() {
+; CHECK-LABEL: define double @test_atan_poison() {
+; CHECK-NEXT: [[RES:%.*]] = call double @llvm.atan.f64(double poison)
+; CHECK-NEXT: ret double [[RES]]
+;
+ %res = call double @llvm.atan.f64(double poison)
+ ret double %res
+}
+
+define double @test_atan_undef() {
+; CHECK-LABEL: define double @test_atan_undef() {
+; CHECK-NEXT: [[RES:%.*]] = call double @llvm.atan.f64(double undef)
+; CHECK-NEXT: ret double [[RES]]
+;
+ %res = call double @llvm.atan.f64(double undef)
+ ret double %res
+}
+
+define double @test_atan_snan() {
+; CHECK-LABEL: define double @test_atan_snan() {
+; CHECK-NEXT: [[RES:%.*]] = call double @llvm.atan.f64(double 0x7FF0000000000001)
+; CHECK-NEXT: ret double [[RES]]
+;
+ %res = call double @llvm.atan.f64(double 0x7ff0000000000001)
+ ret double %res
+}
+
+define double @test_atan_qnan() {
+; CHECK-LABEL: define double @test_atan_qnan() {
+; CHECK-NEXT: [[RES:%.*]] = call double @llvm.atan.f64(double 0x7FF8000000000000)
+; CHECK-NEXT: ret double [[RES]]
+;
+ %res = call double @llvm.atan.f64(double 0x7ff8000000000000)
+ ret double %res
+}
+
+define double @test_atan_pos_inf() {
+; CHECK-LABEL: define double @test_atan_pos_inf() {
+; CHECK-NEXT: [[RES:%.*]] = call double @llvm.atan.f64(double 0x7FF0000000000000)
+; CHECK-NEXT: ret double [[RES]]
+;
+ %res = call double @llvm.atan.f64(double 0x7ff0000000000000)
+ ret double %res
+}
+
+define double @test_atan_neg_inf() {
+; CHECK-LABEL: define double @test_atan_neg_inf() {
+; CHECK-NEXT: [[RES:%.*]] = call double @llvm.atan.f64(double 0xFFF0000000000000)
+; CHECK-NEXT: ret double [[RES]]
+;
+ %res = call double @llvm.atan.f64(double 0xfff0000000000000)
+ ret double %res
+}
|
You can test this locally with the following command:git diff -U0 --pickaxe-regex -S '([^a-zA-Z0-9#_-]undef[^a-zA-Z0-9_-]|UndefValue::get)' 'HEAD~1' HEAD llvm/test/Transforms/InstSimplify/ConstProp/atan-intrinsic.ll llvm/lib/Analysis/ConstantFolding.cpp The following files introduce new uses of undef:
Undef is now deprecated and should only be used in the rare cases where no replacement is possible. For example, a load of uninitialized memory yields In tests, avoid using For example, this is considered a bad practice: define void @fn() {
...
br i1 undef, ...
} Please use the following instead: define void @fn(i1 %cond) {
...
br i1 %cond, ...
} Please refer to the Undefined Behavior Manual for more information. |
@nikic The testcase is failing for https://lab.llvm.org/buildbot/#/builders/64/builds/4143 The affected test is:
This bot is generating:
instead of |
|
I think the constant folding just calls the native libm function linked with the compiler. |
Which we really shouldn't be doing, I know @andykaylor has filed an issue on that in the past. The sooner we can get llvm-libc hand-in-hand with APFloat integration, the better. |
The issue I had (and I seem to be in the minority in caring about this) is that when we constant fold a transcendental function by calling the libm function, we run the risk of getting a different answer than we would have gotten if the call had been evaluated at runtime if the user binary is linked with a different math library than the compiler. That's a problem of bitwise reproducibility of results. If the math library linked with the compiler is simply returning an incorrect result (as seems to be the case here) that's a much bigger problem, but it's a problem for the library. |
Testcase from llvm#143416 is causing the AIX bot to be red. XFAIL for now till issue can be resolved.
I would like to xfail this tc for now so we can bring the aix bot back to green. |
Testcase from #143416 is causing the AIX bot to be red. XFAIL for now till issue can be resolved.
Testcase from llvm/llvm-project#143416 is causing the AIX bot to be red. XFAIL for now till issue can be resolved.
PR to add special handling for -/+0.0: #143962 |
Fixes #143360