Skip to content

[InstCombine] Compare icmp inttoptr, inttoptr values directly #107012

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

Merged
merged 2 commits into from
Sep 24, 2024

Conversation

citymarina
Copy link
Contributor

InstCombine already has some rules for icmp ptrtoint, ptrtoint to drop the casts and compare the source values. This change adds the same for the reverse case with inttoptr.

@llvmbot
Copy link
Member

llvmbot commented Sep 2, 2024

@llvm/pr-subscribers-llvm-transforms

Author: Marina Taylor (citymarina)

Changes

InstCombine already has some rules for icmp ptrtoint, ptrtoint to drop the casts and compare the source values. This change adds the same for the reverse case with inttoptr.


Full diff: https://github.com/llvm/llvm-project/pull/107012.diff

2 Files Affected:

  • (modified) llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp (+21-5)
  • (modified) llvm/test/Transforms/InstCombine/icmp.ll (+19)
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
index 8e8d472a5df1d3..af60b1886fc72e 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
@@ -6081,12 +6081,12 @@ Instruction *InstCombinerImpl::foldICmpWithCastOp(ICmpInst &ICmp) {
 
   // Turn icmp (ptrtoint x), (ptrtoint/c) into a compare of the input if the
   // integer type is the same size as the pointer type.
-  auto CompatibleSizes = [&](Type *SrcTy, Type *DestTy) {
-    if (isa<VectorType>(SrcTy)) {
-      SrcTy = cast<VectorType>(SrcTy)->getElementType();
-      DestTy = cast<VectorType>(DestTy)->getElementType();
+  auto CompatibleSizes = [&](Type *PtrTy, Type *IntTy) {
+    if (isa<VectorType>(PtrTy)) {
+      PtrTy = cast<VectorType>(PtrTy)->getElementType();
+      IntTy = cast<VectorType>(IntTy)->getElementType();
     }
-    return DL.getPointerTypeSizeInBits(SrcTy) == DestTy->getIntegerBitWidth();
+    return DL.getPointerTypeSizeInBits(PtrTy) == IntTy->getIntegerBitWidth();
   };
   if (CastOp0->getOpcode() == Instruction::PtrToInt &&
       CompatibleSizes(SrcTy, DestTy)) {
@@ -6103,6 +6103,22 @@ Instruction *InstCombinerImpl::foldICmpWithCastOp(ICmpInst &ICmp) {
       return new ICmpInst(ICmp.getPredicate(), Op0Src, NewOp1);
   }
 
+  // Do the same in the other direction for icmp (inttoptr x), (inttoptr/c).
+  if (CastOp0->getOpcode() == Instruction::IntToPtr &&
+      CompatibleSizes(DestTy, SrcTy)) {
+    Value *NewOp1 = nullptr;
+    if (auto *IntToPtrOp1 = dyn_cast<IntToPtrInst>(ICmp.getOperand(1))) {
+      Value *IntSrc = IntToPtrOp1->getOperand(0);
+      if (IntSrc->getType() == Op0Src->getType())
+        NewOp1 = IntToPtrOp1->getOperand(0);
+    } else if (auto *RHSC = dyn_cast<Constant>(ICmp.getOperand(1))) {
+      NewOp1 = ConstantExpr::getPtrToInt(RHSC, SrcTy);
+    }
+
+    if (NewOp1)
+      return new ICmpInst(ICmp.getPredicate(), Op0Src, NewOp1);
+  }
+
   if (Instruction *R = foldICmpWithTrunc(ICmp))
     return R;
 
diff --git a/llvm/test/Transforms/InstCombine/icmp.ll b/llvm/test/Transforms/InstCombine/icmp.ll
index e492055fea8b8d..b3cce3548a949e 100644
--- a/llvm/test/Transforms/InstCombine/icmp.ll
+++ b/llvm/test/Transforms/InstCombine/icmp.ll
@@ -5326,3 +5326,22 @@ define i1 @pr94897(i32 range(i32 -2147483648, 0) %x) {
   %cmp = icmp ugt i32 %shl, -50331648
   ret i1 %cmp
 }
+
+define i1 @test_icmp_inttoptr(i64 %x, i64 %y) {
+; CHECK-LABEL: @test_icmp_inttoptr(
+; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i64 [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT:    ret i1 [[CMP]]
+  %xptr = inttoptr i64 %x to ptr
+  %yptr = inttoptr i64 %y to ptr
+  %cmp = icmp eq ptr %xptr, %yptr
+  ret i1 %cmp
+}
+
+define i1 @test_icmp_inttoptr_constant(i64 %x) {
+; CHECK-LABEL: @test_icmp_inttoptr_constant(
+; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i64 [[X:%.*]], 42
+; CHECK-NEXT:    ret i1 [[CMP]]
+  %xptr = inttoptr i64 %x to ptr
+  %cmp = icmp eq ptr %xptr, inttoptr (i64 42 to ptr)
+  ret i1 %cmp
+}

@fhahn fhahn requested review from dtcxzyw and XChy September 2, 2024 19:27
@nikic
Copy link
Contributor

nikic commented Sep 2, 2024

Please see https://llvm.org/docs/InstCombineContributorGuide.html, esp. the bit about pre-committing tests.

@citymarina
Copy link
Contributor Author

Oh wow, that contributor guide looks really thorough. Thank you for writing it!

Copy link
Member

@dtcxzyw dtcxzyw left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

My last attempt #77832 broke hwasan buildbot. @vitalybuka Can you check this patch?

@citymarina
Copy link
Contributor Author

citymarina commented Sep 6, 2024

Oh wow, that contributor guide looks really thorough. Thank you for writing it!

I've read through the guide carefully and hopefully this revision meets the expectations better. I appreciate the clear instructions!

@vitalybuka vitalybuka removed their request for review September 6, 2024 21:29
@citymarina
Copy link
Contributor Author

Ping

@nikic
Copy link
Contributor

nikic commented Sep 23, 2024

I think the open question here is:

My last attempt #77832 broke hwasan buildbot. @vitalybuka Can you check this patch?

But maybe we can just land this and see what happens.

@citymarina
Copy link
Contributor Author

I think the open question here is:

My last attempt #77832 broke hwasan buildbot. @vitalybuka Can you check this patch?

But maybe we can just land this and see what happens.

I interpreted @vitalybuka's removing themself from the review to indicate no plans to test this, but if that was incorrect let me know.

InstCombine already has some rules for `icmp ptrtoint, ptrtoint` to
drop the casts and compare the source values. This change adds the
same for the reverse case with `inttoptr`.
Copy link
Member

@XChy XChy left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Look reasonable to me

@dtcxzyw
Copy link
Member

dtcxzyw commented Sep 24, 2024

I think the open question here is:

My last attempt #77832 broke hwasan buildbot. @vitalybuka Can you check this patch?

But maybe we can just land this and see what happens.

Agree.

Copy link
Member

@dtcxzyw dtcxzyw left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LG

@nikic nikic merged commit 5cd0900 into llvm:main Sep 24, 2024
8 checks passed
@nikic
Copy link
Contributor

nikic commented Sep 24, 2024

Looks like the hwasan build bot with this commit passed: https://lab.llvm.org/buildbot/#/builders/55/builds/2229

@vitalybuka
Copy link
Collaborator

My last attempt #77832 broke hwasan buildbot. @vitalybuka Can you check this patch?

Sorry, I don't expert in this code, so I removed myself, assuming I am accidentally here. I didn't noticed testing request.
In general if you confident, it's fine to land and wait, because even for owner of the bot testing there is some hassle.

@citymarina citymarina deleted the icmp-inttoptr branch October 7, 2024 13:43
citymarina added a commit to swiftlang/llvm-project that referenced this pull request Oct 9, 2024
…#107012)

InstCombine already has some rules for `icmp ptrtoint, ptrtoint` to drop
the casts and compare the source values. This change adds the same for
the reverse case with `inttoptr`.

(cherry picked from commit 5cd0900)

Editor's note: two test cases were changed during the cherry-pick.
They were of the form:
-; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i64 [[Y:%.*]], [[TMP1]]
+; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i64 [[TMP1]], [[Y:%.*]]
I assume that between stable/20240723 and this landing, the
canonical order of these icmps was changed.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

8 participants