mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2024-08-19 19:29:31 +00:00
* Further cleanup.
* Test for whether bits are shifted out during the optzn. If so, the fold is illegal, though it can be handled explicitly for setne/seteq This fixes the miscompilation of 254.gap last night, which was a latent bug exposed by other optimizer improvements. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@15085 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
97a296f743
commit
f0cacc0ae7
@ -1471,22 +1471,40 @@ Instruction *InstCombiner::visitSetCondInst(BinaryOperator &I) {
|
||||
if (ShAmt) {
|
||||
bool CanFold = Shift->getOpcode() != Instruction::Shr ||
|
||||
Shift->getType()->isUnsigned();
|
||||
if (!CanFold &&
|
||||
if (!CanFold) {
|
||||
// To test for the bad case of the signed shr, see if any
|
||||
// of the bits shifted in could be tested after the mask.
|
||||
ConstantExpr::getAnd(ConstantExpr::getShl(ConstantInt::getAllOnesValue(Ty), ConstantUInt::get(Type::UByteTy, Ty->getPrimitiveSize()*8-ShAmt->getValue())), AndCST)->isNullValue()) {
|
||||
CanFold = true;
|
||||
Constant *OShAmt = ConstantUInt::get(Type::UByteTy,
|
||||
Ty->getPrimitiveSize()*8-ShAmt->getValue());
|
||||
Constant *ShVal =
|
||||
ConstantExpr::getShl(ConstantInt::getAllOnesValue(Ty), OShAmt);
|
||||
if (ConstantExpr::getAnd(ShVal, AndCST)->isNullValue())
|
||||
CanFold = true;
|
||||
}
|
||||
|
||||
if (CanFold) {
|
||||
unsigned ShiftOp = Shift->getOpcode() == Instruction::Shl
|
||||
? Instruction::Shr : Instruction::Shl;
|
||||
I.setOperand(1, ConstantExpr::get(ShiftOp, CI, ShAmt));
|
||||
LHSI->setOperand(1,ConstantExpr::get(ShiftOp,AndCST,ShAmt));
|
||||
LHSI->setOperand(0, Shift->getOperand(0));
|
||||
WorkList.push_back(Shift); // Shift is dead.
|
||||
AddUsesToWorkList(I);
|
||||
return &I;
|
||||
Constant *NewCst = ConstantExpr::get(ShiftOp, CI, ShAmt);
|
||||
|
||||
// Check to see if we are shifting out any of the bits being
|
||||
// compared.
|
||||
if (ConstantExpr::get(Shift->getOpcode(), NewCst, ShAmt) != CI){
|
||||
// If we shifted bits out, the fold is not going to work out.
|
||||
// As a special case, check to see if this means that the
|
||||
// result is always true or false now.
|
||||
if (I.getOpcode() == Instruction::SetEQ)
|
||||
return ReplaceInstUsesWith(I, ConstantBool::False);
|
||||
if (I.getOpcode() == Instruction::SetNE)
|
||||
return ReplaceInstUsesWith(I, ConstantBool::True);
|
||||
} else {
|
||||
I.setOperand(1, NewCst);
|
||||
LHSI->setOperand(1, ConstantExpr::get(ShiftOp, AndCST,ShAmt));
|
||||
LHSI->setOperand(0, Shift->getOperand(0));
|
||||
WorkList.push_back(Shift); // Shift is dead.
|
||||
AddUsesToWorkList(I);
|
||||
return &I;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user