From 30af2e31917021f68a3d16ee71335f048c9e6235 Mon Sep 17 00:00:00 2001 From: Sanjay Patel Date: Thu, 29 Dec 2022 14:23:25 -0500 Subject: [PATCH] [InstCombine] avoid miscompile in sinkNotIntoLogicalOp() Fixes #59704 --- llvm/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp | 6 ++++++ llvm/test/Transforms/InstCombine/sink-not-into-logical-and.ll | 6 ++++-- 2 files changed, 10 insertions(+), 2 deletions(-) diff --git a/llvm/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp b/llvm/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp index 93bb120..47f8c14 100644 --- a/llvm/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp +++ b/llvm/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp @@ -3668,6 +3668,12 @@ bool InstCombinerImpl::sinkNotIntoLogicalOp(Instruction &I) { Value *Op0, *Op1; if (!match(&I, m_LogicalOp(m_Value(Op0), m_Value(Op1)))) return false; + + // If this logic op has not been simplified yet, just bail out and let that + // happen first. Otherwise, the code below may wrongly invert. + if (Op0 == Op1) + return false; + Instruction::BinaryOps NewOpc = match(&I, m_LogicalAnd()) ? Instruction::Or : Instruction::And; bool IsBinaryOp = isa(I); diff --git a/llvm/test/Transforms/InstCombine/sink-not-into-logical-and.ll b/llvm/test/Transforms/InstCombine/sink-not-into-logical-and.ll index 7917e7c..8998be5 100644 --- a/llvm/test/Transforms/InstCombine/sink-not-into-logical-and.ll +++ b/llvm/test/Transforms/InstCombine/sink-not-into-logical-and.ll @@ -204,16 +204,18 @@ define i1 @t11(i32 %v0, i32 %v1, i32 %v2, i32 %v3, i1 %v4, i1 %v5) { ret i1 %i4 } -; FIXME: This is a miscompile. +; This would miscompile by not handling the unsimplified select correctly. define i1 @PR59704(i1 %c, i1 %b, i64 %arg) { ; CHECK-LABEL: @PR59704( ; CHECK-NEXT: entry: ; CHECK-NEXT: br i1 [[C:%.*]], label [[IF:%.*]], label [[JOIN:%.*]] ; CHECK: if: +; CHECK-NEXT: [[CMP_NOT:%.*]] = icmp eq i64 [[ARG:%.*]], 0 ; CHECK-NEXT: br label [[JOIN]] ; CHECK: join: -; CHECK-NEXT: ret i1 true +; CHECK-NEXT: [[PHI:%.*]] = phi i1 [ true, [[ENTRY:%.*]] ], [ [[CMP_NOT]], [[IF]] ] +; CHECK-NEXT: ret i1 [[PHI]] ; entry: br i1 %c, label %if, label %join -- 2.7.4