[llvm] [EarlyCSE] Fix improper icmp simplification (PR #122043)
via llvm-commits
llvm-commits at lists.llvm.org
Tue Jan 7 18:49:11 PST 2025
llvmbot wrote:
<!--LLVM PR SUMMARY COMMENT-->
@llvm/pr-subscribers-llvm-analysis
Author: None (llvmssh)
<details>
<summary>Changes</summary>
When icmp's argument is a volatile instruction, we do not assume that icmp can be simplified.
---
Full diff: https://github.com/llvm/llvm-project/pull/122043.diff
2 Files Affected:
- (modified) llvm/lib/Analysis/InstructionSimplify.cpp (+15)
- (added) llvm/test/Transforms/EarlyCSE/icmp_with_volatile.ll (+40)
``````````diff
diff --git a/llvm/lib/Analysis/InstructionSimplify.cpp b/llvm/lib/Analysis/InstructionSimplify.cpp
index 515806428cbb29..db5156fcab9c1a 100644
--- a/llvm/lib/Analysis/InstructionSimplify.cpp
+++ b/llvm/lib/Analysis/InstructionSimplify.cpp
@@ -3726,6 +3726,21 @@ static Value *simplifyICmpInst(CmpPredicate Pred, Value *LHS, Value *RHS,
const SimplifyQuery &Q, unsigned MaxRecurse) {
assert(CmpInst::isIntPredicate(Pred) && "Not an integer compare!");
+ // volatile check
+ // %mark = load volatile ptr, ptr %1, align 8
+ // icmp eq ptr %mark, null
+ if (const auto LHSInstr = dyn_cast<Instruction>(LHS)) {
+ if (LHSInstr->isVolatile()) {
+ return nullptr;
+ }
+ }
+
+ if (const auto RHSInstr = dyn_cast<Instruction>(RHS)) {
+ if (RHSInstr->isVolatile()) {
+ return nullptr;
+ }
+ }
+
if (Constant *CLHS = dyn_cast<Constant>(LHS)) {
if (Constant *CRHS = dyn_cast<Constant>(RHS))
return ConstantFoldCompareInstOperands(Pred, CLHS, CRHS, Q.DL, Q.TLI);
diff --git a/llvm/test/Transforms/EarlyCSE/icmp_with_volatile.ll b/llvm/test/Transforms/EarlyCSE/icmp_with_volatile.ll
new file mode 100644
index 00000000000000..d85d56d50fb4a6
--- /dev/null
+++ b/llvm/test/Transforms/EarlyCSE/icmp_with_volatile.ll
@@ -0,0 +1,40 @@
+; RUN: opt < %s -S -passes=early-cse | FileCheck %s
+
+;When icmp's argument is a volatile instruction, we do not assume that icmp can
+;be simplified.
+define dso_local noundef i32 @_Z1funcv() {
+; CHECK-LABEL: @_Z1funcv(
+; CHECK-NEXT: %1 = alloca ptr, align 8
+; CHECK-NEXT: store volatile ptr null, ptr %1, align 8
+; CHECK-NEXT: %2 = load volatile ptr, ptr %1, align 8
+; CHECK-NEXT: %3 = ptrtoint ptr %2 to i64
+; CHECK-NEXT: %4 = and i64 %3, 1
+; CHECK-NEXT: %5 = icmp eq i64 %4, 0
+; CHECK-NEXT: %6 = zext i1 %5 to i32
+; CHECK-NEXT: ret i32 %6
+;
+ %1 = alloca ptr, align 8
+ store volatile ptr null, ptr %1, align 8
+ %2 = load volatile ptr, ptr %1, align 8
+ %3 = ptrtoint ptr %2 to i64
+ %4 = and i64 %3, 1
+ %5 = icmp eq i64 %4, 0
+ %6 = zext i1 %5 to i32
+ ret i32 %6
+}
+
+define dso_local noundef i32 @_Z2funcv() {
+; CHECK-LABEL: @_Z2funcv(
+; CHECK-NEXT: %1 = alloca ptr, align 8
+; CHECK-NEXT: store ptr null, ptr %1, align 8
+; CHECK-NEXT: ret i32 1
+;
+ %1 = alloca ptr, align 8
+ store ptr null, ptr %1, align 8
+ %2 = load ptr, ptr %1, align 8
+ %3 = ptrtoint ptr %2 to i64
+ %4 = and i64 %3, 1
+ %5 = icmp eq i64 %4, 0
+ %6 = zext i1 %5 to i32
+ ret i32 %6
+}
``````````
</details>
https://github.com/llvm/llvm-project/pull/122043
More information about the llvm-commits
mailing list