mirror of
https://github.com/RPCS3/llvm.git
synced 2024-11-29 06:30:30 +00:00
generalize a transformation even more: we don't care whether the
input the the mul is a zext from bool, just that it is all zeros other than the low bit. This fixes some phase ordering issues that would cause us to miss some xforms in mul.ll when the worklist is visited differently. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@83794 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
0036e3a469
commit
d2c58366d8
@ -2781,20 +2781,18 @@ Instruction *InstCombiner::visitMul(BinaryOperator &I) {
|
||||
|
||||
// If one of the operands of the multiply is a cast from a boolean value, then
|
||||
// we know the bool is either zero or one, so this is a 'masking' multiply.
|
||||
// See if we can simplify things based on how the boolean was originally
|
||||
// formed.
|
||||
{
|
||||
Value *BoolCast = 0, *OtherOp = 0;
|
||||
if (ZExtInst *CI = dyn_cast<ZExtInst>(Op0))
|
||||
if (CI->getOperand(0)->getType() == Type::getInt1Ty(*Context))
|
||||
BoolCast = CI, OtherOp = I.getOperand(1);
|
||||
if (!BoolCast)
|
||||
if (ZExtInst *CI = dyn_cast<ZExtInst>(I.getOperand(1)))
|
||||
if (CI->getOperand(0)->getType() == Type::getInt1Ty(*Context))
|
||||
BoolCast = CI, OtherOp = Op0;
|
||||
// X * Y (where Y is 0 or 1) -> X & (0-Y)
|
||||
if (!isa<VectorType>(I.getType())) {
|
||||
// -2 is "-1 << 1" so it is all bits set except the low one.
|
||||
APInt Negative2(I.getType()->getPrimitiveSizeInBits(), -2, true);
|
||||
|
||||
Value *BoolCast = 0, *OtherOp = 0;
|
||||
if (MaskedValueIsZero(Op0, Negative2))
|
||||
BoolCast = Op0, OtherOp = I.getOperand(1);
|
||||
else if (MaskedValueIsZero(I.getOperand(1), Negative2))
|
||||
BoolCast = I.getOperand(1), OtherOp = Op0;
|
||||
|
||||
if (BoolCast) {
|
||||
// X * Y (where Y is 0 or 1) -> X & (0-Y)
|
||||
Value *V = Builder->CreateSub(Constant::getNullValue(I.getType()),
|
||||
BoolCast, "tmp");
|
||||
return BinaryOperator::CreateAnd(V, OtherOp);
|
||||
|
@ -105,5 +105,12 @@ define i32 @test16(i32 %b, i1 %c) {
|
||||
ret i32 %e
|
||||
}
|
||||
|
||||
; X * Y (when Y is 0 or 1) --> x & (0-Y)
|
||||
define i32 @test17(i32 %a, i32 %b) {
|
||||
%a.lobit = lshr i32 %a, 31
|
||||
%e = mul i32 %a.lobit, %b
|
||||
ret i32 %e
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user