llvm.org GIT mirror llvm / 30aa8b1
Add a missed SCEV fold that is required to continue analyzing the IR produced by indvars through the scev expander. trunc(add x, y) --> add(trunc x, y). Currently SCEV largely folds the other way which is probably wrong, but preserved to minimize churn. Instcombine doesn't do this fold either, demonstrating a missed optz'n opportunity on code doing add+trunc+add. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@123838 91177308-0d34-0410-b5e6-96231b3b80d8 Nick Lewycky 9 years ago
2 changed file(s) with 23 addition(s) and 1 deletion(s). Raw diff Collapse all Expand all
817817 // trunc(zext(x)) --> zext(x) if widening or trunc(x) if narrowing
818818 if (const SCEVZeroExtendExpr *SZ = dyn_cast(Op))
819819 return getTruncateOrZeroExtend(SZ->getOperand(), Ty);
820
821 // trunc(x1+x2+...+xN) --> trunc(x1)+trunc(x2)+...+trunc(xN) if we can
822 // eliminate all the truncates.
823 if (const SCEVAddExpr *SA = dyn_cast(Op)) {
824 SmallVector Operands;
825 bool hasTrunc = false;
826 for (unsigned i = 0, e = SA->getNumOperands(); i != e && !hasTrunc; ++i) {
827 const SCEV *S = getTruncateExpr(SA->getOperand(i), Ty);
828 hasTrunc = isa(S);
829 Operands.push_back(S);
830 }
831 if (!hasTrunc)
832 return getAddExpr(Operands, false, false);
833 }
820834
821835 // If the input value is a chrec scev, truncate the chrec's operands.
822836 if (const SCEVAddRecExpr *AddRec = dyn_cast(Op)) {
0 ; RUN: opt -analyze -scalar-evolution %s -S | FileCheck %s
11
2 define i16 @test(i8 %x) {
2 define i16 @test1(i8 %x) {
33 %A = zext i8 %x to i12
44 %B = sext i12 %A to i16
55 ; CHECK: zext i8 %x to i16
66 ret i16 %B
77 }
8
9 define i8 @test2(i8 %x) {
10 %A = zext i8 %x to i16
11 %B = add i16 %A, 1025
12 %C = trunc i16 %B to i8
13 ; CHECK: (1 + %x)
14 ret i8 %C
15 }