From 7bd839f42ba5100cd48dead581fdcad9523d0dee Mon Sep 17 00:00:00 2001 From: Evgeny Astigeevich Date: Tue, 3 Oct 2017 12:00:40 +0000 Subject: [PATCH] [InlineCost, NFC] Extract code dealing with inbounds GEPs from visitGetElementPtr into a function The code responsible for analysis of inbounds GEPs is extracted into a separate function: CallAnalyzer::canFoldInboundsGEP. With the patch SROA enabling/disabling code is localized at one place instead of spreading across the code of CallAnalyzer::visitGetElementPtr. Differential Revision: https://reviews.llvm.org/D38233 git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@314787 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Analysis/InlineCost.cpp | 53 ++++++++++++++++++++------------------------- 1 file changed, 24 insertions(+), 29 deletions(-) diff --git a/lib/Analysis/InlineCost.cpp b/lib/Analysis/InlineCost.cpp index 2ee75c83d70..db89fc2181a 100644 --- a/lib/Analysis/InlineCost.cpp +++ b/lib/Analysis/InlineCost.cpp @@ -172,6 +172,7 @@ class CallAnalyzer : public InstVisitor { void accumulateSROACost(DenseMap::iterator CostIt, int InstructionCost); bool isGEPFree(GetElementPtrInst &GEP); + bool canFoldInboundsGEP(GetElementPtrInst &I); bool accumulateGEPOffset(GEPOperator &GEP, APInt &Offset); bool simplifyCallSite(Function *F, CallSite CS); template @@ -431,40 +432,34 @@ bool CallAnalyzer::visitPHI(PHINode &I) { return true; } +/// \brief Check we can fold GEPs of constant-offset call site argument pointers. +/// This requires target data and inbounds GEPs. +/// +/// \return true if the specified GEP can be folded. +bool CallAnalyzer::canFoldInboundsGEP(GetElementPtrInst &I) { + // Check if we have a base + offset for the pointer. + std::pair BaseAndOffset = + ConstantOffsetPtrs.lookup(I.getPointerOperand()); + if (!BaseAndOffset.first) + return false; + + // Check if the offset of this GEP is constant, and if so accumulate it + // into Offset. + if (!accumulateGEPOffset(cast(I), BaseAndOffset.second)) + return false; + + // Add the result as a new mapping to Base + Offset. + ConstantOffsetPtrs[&I] = BaseAndOffset; + + return true; +} + bool CallAnalyzer::visitGetElementPtr(GetElementPtrInst &I) { Value *SROAArg; DenseMap::iterator CostIt; bool SROACandidate = lookupSROAArgAndCost(I.getPointerOperand(), SROAArg, CostIt); - // Try to fold GEPs of constant-offset call site argument pointers. This - // requires target data and inbounds GEPs. - if (I.isInBounds()) { - // Check if we have a base + offset for the pointer. - Value *Ptr = I.getPointerOperand(); - std::pair BaseAndOffset = ConstantOffsetPtrs.lookup(Ptr); - if (BaseAndOffset.first) { - // Check if the offset of this GEP is constant, and if so accumulate it - // into Offset. - if (!accumulateGEPOffset(cast(I), BaseAndOffset.second)) { - // Non-constant GEPs aren't folded, and disable SROA. - if (SROACandidate) - disableSROA(CostIt); - return isGEPFree(I); - } - - // Add the result as a new mapping to Base + Offset. - ConstantOffsetPtrs[&I] = BaseAndOffset; - - // Also handle SROA candidates here, we already know that the GEP is - // all-constant indexed. - if (SROACandidate) - SROAArgValues[&I] = SROAArg; - - return true; - } - } - // Lambda to check whether a GEP's indices are all constant. auto IsGEPOffsetConstant = [&](GetElementPtrInst &GEP) { for (User::op_iterator I = GEP.idx_begin(), E = GEP.idx_end(); I != E; ++I) @@ -473,7 +468,7 @@ bool CallAnalyzer::visitGetElementPtr(GetElementPtrInst &I) { return true; }; - if (IsGEPOffsetConstant(I)) { + if ((I.isInBounds() && canFoldInboundsGEP(I)) || IsGEPOffsetConstant(I)) { if (SROACandidate) SROAArgValues[&I] = SROAArg; -- 2.11.0