teach sext optimization to handle truncs from types that are not

the dest of the sext.

llvm-svn: 93128
This commit is contained in:
Chris Lattner 2010-01-10 20:30:41 +00:00
parent ca53de1ab7
commit 18d753e05f
2 changed files with 30 additions and 3 deletions

View File

@ -799,6 +799,10 @@ static bool CanEvaluateSExtd(Value *V, const Type *Ty, TargetData *TD) {
if (!I->hasOneUse()) return false;
switch (I->getOpcode()) {
case Instruction::SExt: // sext(sext(x)) -> sext(x)
case Instruction::ZExt: // sext(zext(x)) -> zext(x)
case Instruction::Trunc: // sext(trunc(x)) -> trunc(x) or sext(x)
return true;
case Instruction::And:
case Instruction::Or:
case Instruction::Xor:
@ -813,9 +817,6 @@ static bool CanEvaluateSExtd(Value *V, const Type *Ty, TargetData *TD) {
//case Instruction::LShr: TODO
//case Instruction::Trunc: TODO
case Instruction::SExt: // sext(sext(x)) -> sext(x)
case Instruction::ZExt: // sext(zext(x)) -> zext(x)
return true;
case Instruction::Select:
return CanEvaluateSExtd(I->getOperand(1), Ty, TD) &&
CanEvaluateSExtd(I->getOperand(2), Ty, TD);

View File

@ -523,3 +523,29 @@ define i64 @test53(i32 %A) {
; CHECK-NEXT: %D = and i64 %C, 40186
; CHECK-NEXT: ret i64 %D
}
define i32 @test54(i64 %A) {
%B = trunc i64 %A to i16
%C = or i16 %B, -32574
%D = and i16 %C, -25350
%E = sext i16 %D to i32
ret i32 %E
; CHECK: @test54
; CHECK-NEXT: %B = trunc i64 %A to i32
; CHECK-NEXT: %C = or i32 %B, -32574
; CHECK-NEXT: %D = and i32 %C, -25350
; CHECK-NEXT: ret i32 %D
}
define i64 @test55(i32 %A) {
%B = trunc i32 %A to i16
%C = or i16 %B, -32574
%D = and i16 %C, -25350
%E = sext i16 %D to i64
ret i64 %E
; CHECK: @test55
; CHECK-NEXT: %B = zext i32 %A to i64
; CHECK-NEXT: %C = or i64 %B, -32574
; CHECK-NEXT: %D = and i64 %C, -25350
; CHECK-NEXT: ret i64 %D
}