[llvm] [GVN] Replace cmp with not instruction if inv cmp is found (PR #223171)

Nikita Popov via llvm-commits llvm-commits at lists.llvm.org
Tue Sep 29 05:39:37 PDT 2026


================
@@ -3445,18 +3451,36 @@ bool GVNPass::processInstruction(Instruction *I) {
     }
   }
 
-  // If the number we were assigned was a brand new VN, then we don't
-  // need to do a lookup to see if the number already exists
-  // somewhere in the domtree: it can't!
-  if (Num >= NextNum) {
-    LeaderTable.insert(Num, I, I->getParent());
-    return false;
-  }
-
   // Perform fast-path value-number based elimination of values inherited from
-  // dominators.
-  Value *Repl = findLeader(I->getParent(), Num);
+  // dominators, unless the number we were assigned was a brand new VN, then
+  // we don't need to do a lookup to see if the number already exists somewhere
+  // in the domtree: it can't!
+  Value *Repl = Num < NextNum ? findLeader(I->getParent(), Num) : nullptr;
   if (!Repl) {
+    // Substitute cmp instruction with not if possible.
+    if (CmpInst *Cmp = dyn_cast<CmpInst>(I)) {
+      uint32_t NotNum =
+          VN.lookupCmp(Cmp->getOpcode(), Cmp->getInversePredicate(),
+                       Cmp->getOperand(0), Cmp->getOperand(1));
+      if (NotNum != 0) {
+        Value *NotRepl = findLeader(I->getParent(), NotNum);
+        auto FlagCheck = [&]() {
+          if (auto *ICmp = dyn_cast<ICmpInst>(NotRepl))
+            return !ICmp->hasSameSign() ||
+                   ICmp->hasSameSign() == cast<ICmpInst>(I)->hasSameSign();
+          return cast<FPMathOperator>(NotRepl)->getFastMathFlags() ==
+                 cast<FPMathOperator>(I)->getFastMathFlags();
+        };
----------------
nikic wrote:

Yes, it should use andIRFlags. Or patchReplacementInstruction, but it will come down to andIRFlags for icmp/fcmp.

https://github.com/llvm/llvm-project/pull/223171


More information about the llvm-commits mailing list