implement a TODO by teaching jump threading about "xor x, 1".

llvm-svn: 86739
This commit is contained in:
Chris Lattner 2009-11-10 22:39:16 +00:00
parent 3ad2645430
commit 9518fbb54e
2 changed files with 53 additions and 2 deletions

View File

@ -299,8 +299,20 @@ ComputeValueKnownInPredecessors(Value *V, BasicBlock *BB,PredValueInfo &Result){
return !Result.empty();
}
// TODO: Should handle the NOT form of XOR.
// Handle the NOT form of XOR.
if (I->getOpcode() == Instruction::Xor &&
isa<ConstantInt>(I->getOperand(1)) &&
cast<ConstantInt>(I->getOperand(1))->isOne()) {
ComputeValueKnownInPredecessors(I->getOperand(0), BB, Result);
if (Result.empty())
return false;
// Invert the known values.
for (unsigned i = 0, e = Result.size(); i != e; ++i)
Result[i].first =
cast<ConstantInt>(ConstantExpr::getNot(Result[i].first));
return true;
}
}
// Handle compare with phi operand, where the PHI is defined in this block.

View File

@ -245,3 +245,42 @@ Y:
ret i32 2
}
;;; Verify that we can handle constraint propagation through "xor x, 1".
define i32 @test9(i1 %cond, i1 %cond2) {
Entry:
; CHECK: @test9
%v1 = call i32 @f1()
br i1 %cond, label %Merge, label %F1
; CHECK: Entry:
; CHECK-NEXT: %v1 = call i32 @f1()
; CHECK-NEXT: br i1 %cond, label %F2, label %Merge
F1:
%v2 = call i32 @f2()
br label %Merge
Merge:
%B = phi i32 [%v1, %Entry], [%v2, %F1]
%M = icmp eq i32 %B, %v1
%M1 = xor i1 %M, 1
%N = icmp eq i32 %B, 47
%O = and i1 %M1, %N
br i1 %O, label %T2, label %F2
; CHECK: Merge:
; CHECK-NOT: phi
; CHECK-NEXT: %v2 = call i32 @f2()
T2:
%Q = zext i1 %M to i32
ret i32 %Q
F2:
ret i32 %B
; CHECK: F2:
; CHECK-NEXT: phi i32
}