[llvm-branch-commits] [llvm] ValueTracking: x - floor(x) cannot introduce overflow (PR #189003)
via llvm-branch-commits
llvm-branch-commits at lists.llvm.org
Fri Mar 27 06:56:16 PDT 2026
llvmbot wrote:
<!--LLVM PR SUMMARY COMMENT-->
@llvm/pr-subscribers-backend-amdgpu
Author: Matt Arsenault (arsenm)
<details>
<summary>Changes</summary>
This returns a value with an absolute value less than 1 so it
should be possible to propagate no-infs.
---
Full diff: https://github.com/llvm/llvm-project/pull/189003.diff
2 Files Affected:
- (modified) llvm/lib/Analysis/ValueTracking.cpp (+9-1)
- (modified) llvm/test/Transforms/Attributor/nofpclass-fmul.ll (+42)
``````````diff
diff --git a/llvm/lib/Analysis/ValueTracking.cpp b/llvm/lib/Analysis/ValueTracking.cpp
index eca4b98b21226..7f6b0c27d7518 100644
--- a/llvm/lib/Analysis/ValueTracking.cpp
+++ b/llvm/lib/Analysis/ValueTracking.cpp
@@ -4977,7 +4977,15 @@ static constexpr KnownFPClass::MinMaxKind getMinMaxKind(Intrinsic::ID IID) {
/// \return true if this is a floating point value that is known to have a
/// magnitude smaller than 1. i.e., fabs(X) <= 1.0
static bool isAbsoluteValueLessEqualOne(const Value *V) {
- // TODO: Handle frexp and x - floor(x)?
+ // TODO: Handle frexp
+ // TODO: Other rounding intrinsics?
+
+ // fabs(x - floor(x)) <= 1
+ const Value *SubFloorX;
+ if (match(V, m_FSub(m_Value(SubFloorX),
+ m_Intrinsic<Intrinsic::floor>(m_Deferred(SubFloorX)))))
+ return true;
+
return match(V, m_Intrinsic<Intrinsic::amdgcn_trig_preop>(m_Value())) ||
match(V, m_Intrinsic<Intrinsic::amdgcn_fract>(m_Value()));
}
diff --git a/llvm/test/Transforms/Attributor/nofpclass-fmul.ll b/llvm/test/Transforms/Attributor/nofpclass-fmul.ll
index db2cb9ed9c2ba..1b1cf60a33500 100644
--- a/llvm/test/Transforms/Attributor/nofpclass-fmul.ll
+++ b/llvm/test/Transforms/Attributor/nofpclass-fmul.ll
@@ -910,3 +910,45 @@ define float @ret_fmul__not_inf__neg1.5(float nofpclass(inf) %x) {
%mul = fmul float %x, -1.5
ret float %mul
}
+
+define float @ret_fmul__not_inf__fsub_floor_pat(float nofpclass(inf) %x, float %y) {
+; CHECK-LABEL: define nofpclass(inf) float @ret_fmul__not_inf__fsub_floor_pat(
+; CHECK-SAME: float nofpclass(inf) [[X:%.*]], float [[Y:%.*]]) #[[ATTR0]] {
+; CHECK-NEXT: [[FLOOR_Y:%.*]] = call float @llvm.floor.f32(float [[Y]]) #[[ATTR2]]
+; CHECK-NEXT: [[Y_SUB_FLOOR_Y:%.*]] = fsub float [[Y]], [[FLOOR_Y]]
+; CHECK-NEXT: [[MUL:%.*]] = fmul float [[X]], [[Y_SUB_FLOOR_Y]]
+; CHECK-NEXT: ret float [[MUL]]
+;
+ %floor.y = call float @llvm.floor.f32(float %y)
+ %y.sub.floor.y = fsub float %y, %floor.y
+ %mul = fmul float %x, %y.sub.floor.y
+ ret float %mul
+}
+
+define float @ret_fmul__not_inf__fsub_floor_pat_commute(float nofpclass(inf) %x, float %y) {
+; CHECK-LABEL: define nofpclass(inf) float @ret_fmul__not_inf__fsub_floor_pat_commute(
+; CHECK-SAME: float nofpclass(inf) [[X:%.*]], float [[Y:%.*]]) #[[ATTR0]] {
+; CHECK-NEXT: [[FLOOR_Y:%.*]] = call float @llvm.floor.f32(float [[Y]]) #[[ATTR2]]
+; CHECK-NEXT: [[Y_SUB_FLOOR_Y:%.*]] = fsub float [[Y]], [[FLOOR_Y]]
+; CHECK-NEXT: [[MUL:%.*]] = fmul float [[Y_SUB_FLOOR_Y]], [[X]]
+; CHECK-NEXT: ret float [[MUL]]
+;
+ %floor.y = call float @llvm.floor.f32(float %y)
+ %y.sub.floor.y = fsub float %y, %floor.y
+ %mul = fmul float %y.sub.floor.y, %x
+ ret float %mul
+}
+
+define float @ret_fmul__not_inf__fsub_floor_pat_wrong_floor_val(float nofpclass(inf) %x, float %y, float %z) {
+; CHECK-LABEL: define float @ret_fmul__not_inf__fsub_floor_pat_wrong_floor_val(
+; CHECK-SAME: float nofpclass(inf) [[X:%.*]], float [[Y:%.*]], float [[Z:%.*]]) #[[ATTR0]] {
+; CHECK-NEXT: [[FLOOR_Y:%.*]] = call float @llvm.floor.f32(float [[Z]]) #[[ATTR2]]
+; CHECK-NEXT: [[Y_SUB_FLOOR_Y:%.*]] = fsub float [[Y]], [[FLOOR_Y]]
+; CHECK-NEXT: [[MUL:%.*]] = fmul float [[X]], [[Y_SUB_FLOOR_Y]]
+; CHECK-NEXT: ret float [[MUL]]
+;
+ %floor.y = call float @llvm.floor.f32(float %z)
+ %y.sub.floor.y = fsub float %y, %floor.y
+ %mul = fmul float %x, %y.sub.floor.y
+ ret float %mul
+}
``````````
</details>
https://github.com/llvm/llvm-project/pull/189003
More information about the llvm-branch-commits
mailing list