diff options
| author | Chris Lattner <sabre@nondot.org> | 2005-01-14 00:20:05 +0000 | 
|---|---|---|
| committer | Chris Lattner <sabre@nondot.org> | 2005-01-14 00:20:05 +0000 | 
| commit | 4fa89827e29b29bb989993774749e3cd4fb9dd06 (patch) | |
| tree | 30b1aa139fc2c5c86853e31a40597c1195030b02 /llvm/lib/Transforms | |
| parent | d35d210ea08cc048f5faebcdf7df4d7634972321 (diff) | |
| download | bcm5719-llvm-4fa89827e29b29bb989993774749e3cd4fb9dd06.tar.gz bcm5719-llvm-4fa89827e29b29bb989993774749e3cd4fb9dd06.zip | |
if two gep comparisons only differ by one index, compare that index directly.
This allows us to better optimize begin() -> end() comparisons in common cases.
llvm-svn: 19542
Diffstat (limited to 'llvm/lib/Transforms')
| -rw-r--r-- | llvm/lib/Transforms/Scalar/InstructionCombining.cpp | 28 | 
1 files changed, 28 insertions, 0 deletions
| diff --git a/llvm/lib/Transforms/Scalar/InstructionCombining.cpp b/llvm/lib/Transforms/Scalar/InstructionCombining.cpp index e8f52d11573..948eb329040 100644 --- a/llvm/lib/Transforms/Scalar/InstructionCombining.cpp +++ b/llvm/lib/Transforms/Scalar/InstructionCombining.cpp @@ -2219,6 +2219,8 @@ Instruction *InstCombiner::FoldGEPSetCC(User *GEPLHS, Value *RHS,      if (AllZeros)        return FoldGEPSetCC(GEPRHS, GEPLHS->getOperand(0),                            SetCondInst::getSwappedCondition(Cond), I); + +    // If the other GEP has all zero indices, recurse.      AllZeros = true;      for (unsigned i = 1, e = GEPRHS->getNumOperands(); i != e; ++i)        if (!isa<Constant>(GEPRHS->getOperand(i)) || @@ -2229,6 +2231,32 @@ Instruction *InstCombiner::FoldGEPSetCC(User *GEPLHS, Value *RHS,      if (AllZeros)        return FoldGEPSetCC(GEPLHS, GEPRHS->getOperand(0), Cond, I); +    if (GEPLHS->getNumOperands() == GEPRHS->getNumOperands()) { +      // If the GEPs only differ by one index, compare it. +      unsigned NumDifferences = 0;  // Keep track of # differences. +      unsigned DiffOperand = 0;     // The operand that differs. +      for (unsigned i = 1, e = GEPRHS->getNumOperands(); i != e; ++i) +        if (GEPLHS->getOperand(i) != GEPRHS->getOperand(i)) { +          if (GEPLHS->getOperand(i)->getType() !=  +                     GEPRHS->getOperand(i)->getType()) { +            // Irreconsilable differences. +            NumDifferences = 2; +            break; +          } else { +            if (NumDifferences++) break; +            DiffOperand = i; +          } +        } + +      if (NumDifferences == 0)   // SAME GEP? +        return ReplaceInstUsesWith(I, // No comparison is needed here. +                                 ConstantBool::get(Cond == Instruction::SetEQ)); +      else if (NumDifferences == 1) { +        return new SetCondInst(Cond, GEPLHS->getOperand(DiffOperand), +                               GEPRHS->getOperand(DiffOperand)); +      } +    } +      // Only lower this if the setcc is the only user of the GEP or if we expect      // the result to fold to a constant!      if ((isa<ConstantExpr>(GEPLHS) || GEPLHS->hasOneUse()) && | 

