diff --git a/llvm/lib/Analysis/InstructionSimplify.cpp b/llvm/lib/Analysis/InstructionSimplify.cpp index 7ed695e4c602..44de7e9e40c1 100644 --- a/llvm/lib/Analysis/InstructionSimplify.cpp +++ b/llvm/lib/Analysis/InstructionSimplify.cpp @@ -3019,15 +3019,19 @@ static Value *simplifyICmpWithBinOp(CmpInst::Predicate Pred, Value *LHS, return ConstantInt::getTrue(RHS->getContext()); } } - if (CIVal->isSignMask() && CI2Val->isOneValue()) { - if (Pred == ICmpInst::ICMP_UGT) - return ConstantInt::getFalse(RHS->getContext()); - if (Pred == ICmpInst::ICMP_ULE) - return ConstantInt::getTrue(RHS->getContext()); - } } } + // TODO: This is overly constrained. LHS can be any power-of-2. + // (1 << X) >u 0x8000 --> false + // (1 << X) <=u 0x8000 --> true + if (match(LHS, m_Shl(m_One(), m_Value())) && match(RHS, m_SignMask())) { + if (Pred == ICmpInst::ICMP_UGT) + return ConstantInt::getFalse(GetCompareTy(RHS)); + if (Pred == ICmpInst::ICMP_ULE) + return ConstantInt::getTrue(GetCompareTy(RHS)); + } + if (MaxRecurse && LBO && RBO && LBO->getOpcode() == RBO->getOpcode() && LBO->getOperand(1) == RBO->getOperand(1)) { switch (LBO->getOpcode()) { diff --git a/llvm/test/Transforms/InstSimplify/compare.ll b/llvm/test/Transforms/InstSimplify/compare.ll index d0bbe9ddfdde..edfca12a080c 100644 --- a/llvm/test/Transforms/InstSimplify/compare.ll +++ b/llvm/test/Transforms/InstSimplify/compare.ll @@ -1479,9 +1479,7 @@ define i1 @icmp_shl_1_V_ugt_2147483648(i32 %V) { define <2 x i1> @icmp_shl_1_ugt_signmask(<2 x i8> %V) { ; CHECK-LABEL: @icmp_shl_1_ugt_signmask( -; CHECK-NEXT: [[SHL:%.*]] = shl <2 x i8> , [[V:%.*]] -; CHECK-NEXT: [[CMP:%.*]] = icmp ugt <2 x i8> [[SHL]], -; CHECK-NEXT: ret <2 x i1> [[CMP]] +; CHECK-NEXT: ret <2 x i1> zeroinitializer ; %shl = shl <2 x i8> , %V %cmp = icmp ugt <2 x i8> %shl, @@ -1490,9 +1488,7 @@ define <2 x i1> @icmp_shl_1_ugt_signmask(<2 x i8> %V) { define <2 x i1> @icmp_shl_1_ugt_signmask_undef(<2 x i8> %V) { ; CHECK-LABEL: @icmp_shl_1_ugt_signmask_undef( -; CHECK-NEXT: [[SHL:%.*]] = shl <2 x i8> , [[V:%.*]] -; CHECK-NEXT: [[CMP:%.*]] = icmp ugt <2 x i8> [[SHL]], -; CHECK-NEXT: ret <2 x i1> [[CMP]] +; CHECK-NEXT: ret <2 x i1> zeroinitializer ; %shl = shl <2 x i8> , %V %cmp = icmp ugt <2 x i8> %shl, @@ -1501,9 +1497,7 @@ define <2 x i1> @icmp_shl_1_ugt_signmask_undef(<2 x i8> %V) { define <2 x i1> @icmp_shl_1_ugt_signmask_undef2(<2 x i8> %V) { ; CHECK-LABEL: @icmp_shl_1_ugt_signmask_undef2( -; CHECK-NEXT: [[SHL:%.*]] = shl <2 x i8> , [[V:%.*]] -; CHECK-NEXT: [[CMP:%.*]] = icmp ugt <2 x i8> [[SHL]], -; CHECK-NEXT: ret <2 x i1> [[CMP]] +; CHECK-NEXT: ret <2 x i1> zeroinitializer ; %shl = shl <2 x i8> , %V %cmp = icmp ugt <2 x i8> %shl, @@ -1521,9 +1515,7 @@ define i1 @icmp_shl_1_V_ule_2147483648(i32 %V) { define <2 x i1> @icmp_shl_1_ule_signmask(<2 x i8> %V) { ; CHECK-LABEL: @icmp_shl_1_ule_signmask( -; CHECK-NEXT: [[SHL:%.*]] = shl <2 x i8> , [[V:%.*]] -; CHECK-NEXT: [[CMP:%.*]] = icmp ule <2 x i8> [[SHL]], -; CHECK-NEXT: ret <2 x i1> [[CMP]] +; CHECK-NEXT: ret <2 x i1> ; %shl = shl <2 x i8> , %V %cmp = icmp ule <2 x i8> %shl, @@ -1532,9 +1524,7 @@ define <2 x i1> @icmp_shl_1_ule_signmask(<2 x i8> %V) { define <2 x i1> @icmp_shl_1_ule_signmask_undef(<2 x i8> %V) { ; CHECK-LABEL: @icmp_shl_1_ule_signmask_undef( -; CHECK-NEXT: [[SHL:%.*]] = shl <2 x i8> , [[V:%.*]] -; CHECK-NEXT: [[CMP:%.*]] = icmp ule <2 x i8> [[SHL]], -; CHECK-NEXT: ret <2 x i1> [[CMP]] +; CHECK-NEXT: ret <2 x i1> ; %shl = shl <2 x i8> , %V %cmp = icmp ule <2 x i8> %shl, @@ -1543,9 +1533,7 @@ define <2 x i1> @icmp_shl_1_ule_signmask_undef(<2 x i8> %V) { define <2 x i1> @icmp_shl_1_ule_signmask_undef2(<2 x i8> %V) { ; CHECK-LABEL: @icmp_shl_1_ule_signmask_undef2( -; CHECK-NEXT: [[SHL:%.*]] = shl <2 x i8> , [[V:%.*]] -; CHECK-NEXT: [[CMP:%.*]] = icmp ule <2 x i8> [[SHL]], -; CHECK-NEXT: ret <2 x i1> [[CMP]] +; CHECK-NEXT: ret <2 x i1> ; %shl = shl <2 x i8> , %V %cmp = icmp ule <2 x i8> %shl,