1 //===- ScalarEvolutionAliasAnalysis.cpp - SCEV-based Alias Analysis -------===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 // 10 // This file defines the ScalarEvolutionAliasAnalysis pass, which implements a 11 // simple alias analysis implemented in terms of ScalarEvolution queries. 12 // 13 // ScalarEvolution has a more complete understanding of pointer arithmetic 14 // than BasicAliasAnalysis' collection of ad-hoc analyses. 15 // 16 //===----------------------------------------------------------------------===// 17 18 #include "llvm/Analysis/AliasAnalysis.h" 19 #include "llvm/Analysis/ScalarEvolutionExpressions.h" 20 #include "llvm/Analysis/Passes.h" 21 #include "llvm/Pass.h" 22 #include "llvm/Support/Compiler.h" 23 using namespace llvm; 24 25 namespace { 26 /// ScalarEvolutionAliasAnalysis - This is a simple alias analysis 27 /// implementation that uses ScalarEvolution to answer queries. 28 class VISIBILITY_HIDDEN ScalarEvolutionAliasAnalysis : public FunctionPass, 29 public AliasAnalysis { 30 ScalarEvolution *SE; 31 32 public: 33 static char ID; // Class identification, replacement for typeinfo 34 ScalarEvolutionAliasAnalysis() : FunctionPass(&ID), SE(0) {} 35 36 private: 37 virtual void getAnalysisUsage(AnalysisUsage &AU) const; 38 virtual bool runOnFunction(Function &F); 39 virtual AliasResult alias(const Value *V1, unsigned V1Size, 40 const Value *V2, unsigned V2Size); 41 42 Value *GetUnderlyingIdentifiedObject(const SCEV *S); 43 }; 44 } // End of anonymous namespace 45 46 // Register this pass... 47 char ScalarEvolutionAliasAnalysis::ID = 0; 48 static RegisterPass<ScalarEvolutionAliasAnalysis> 49 X("scev-aa", "ScalarEvolution-based Alias Analysis", false, true); 50 51 // Declare that we implement the AliasAnalysis interface 52 static RegisterAnalysisGroup<AliasAnalysis> Y(X); 53 54 FunctionPass *llvm::createScalarEvolutionAliasAnalysisPass() { 55 return new ScalarEvolutionAliasAnalysis(); 56 } 57 58 void 59 ScalarEvolutionAliasAnalysis::getAnalysisUsage(AnalysisUsage &AU) const { 60 AU.addRequiredTransitive<ScalarEvolution>(); 61 AU.setPreservesAll(); 62 AliasAnalysis::getAnalysisUsage(AU); 63 } 64 65 bool 66 ScalarEvolutionAliasAnalysis::runOnFunction(Function &F) { 67 InitializeAliasAnalysis(this); 68 SE = &getAnalysis<ScalarEvolution>(); 69 return false; 70 } 71 72 /// GetUnderlyingIdentifiedObject - Given an expression, try to find an 73 /// "identified object" (see AliasAnalysis::isIdentifiedObject) base 74 /// value. Return null is none was found. 75 Value * 76 ScalarEvolutionAliasAnalysis::GetUnderlyingIdentifiedObject(const SCEV *S) { 77 if (const SCEVAddRecExpr *AR = dyn_cast<SCEVAddRecExpr>(S)) { 78 // In an addrec, assume that the base will be in the start, rather 79 // than the step. 80 return GetUnderlyingIdentifiedObject(AR->getStart()); 81 } else if (const SCEVAddExpr *A = dyn_cast<SCEVAddExpr>(S)) { 82 // If there's a pointer operand, it'll be sorted at the end of the list. 83 const SCEV *Last = A->getOperand(A->getNumOperands()-1); 84 if (isa<PointerType>(Last->getType())) 85 return GetUnderlyingIdentifiedObject(Last); 86 } else if (const SCEVUnknown *U = dyn_cast<SCEVUnknown>(S)) { 87 // Determine if we've found an Identified object. 88 Value *V = U->getValue(); 89 if (isIdentifiedObject(V)) 90 return V; 91 } 92 // No Identified object found. 93 return 0; 94 } 95 96 AliasAnalysis::AliasResult 97 ScalarEvolutionAliasAnalysis::alias(const Value *A, unsigned ASize, 98 const Value *B, unsigned BSize) { 99 // This is ScalarEvolutionAliasAnalysis. Get the SCEVs! 100 const SCEV *AS = SE->getSCEV(const_cast<Value *>(A)); 101 const SCEV *BS = SE->getSCEV(const_cast<Value *>(B)); 102 103 // If they evaluate to the same expression, it's a MustAlias. 104 if (AS == BS) return MustAlias; 105 106 // If something is known about the difference between the two addresses, 107 // see if it's enough to prove a NoAlias. 108 if (SE->getEffectiveSCEVType(AS->getType()) == 109 SE->getEffectiveSCEVType(BS->getType())) { 110 unsigned BitWidth = SE->getTypeSizeInBits(AS->getType()); 111 APInt AI(BitWidth, ASize); 112 const SCEV *BA = SE->getMinusSCEV(BS, AS); 113 if (AI.ule(SE->getUnsignedRange(BA).getUnsignedMin())) { 114 APInt BI(BitWidth, BSize); 115 const SCEV *AB = SE->getMinusSCEV(AS, BS); 116 if (BI.ule(SE->getUnsignedRange(AB).getUnsignedMin())) 117 return NoAlias; 118 } 119 } 120 121 // If ScalarEvolution can find an underlying object, form a new query. 122 // The correctness of this depends on ScalarEvolution not recognizing 123 // inttoptr and ptrtoint operators. 124 Value *AO = GetUnderlyingIdentifiedObject(AS); 125 Value *BO = GetUnderlyingIdentifiedObject(BS); 126 if ((AO && AO != A) || (BO && BO != B)) 127 if (alias(AO ? AO : A, AO ? ~0u : ASize, 128 BO ? BO : B, BO ? ~0u : BSize) == NoAlias) 129 return NoAlias; 130 131 // Forward the query to the next analysis. 132 return AliasAnalysis::alias(A, ASize, B, BSize); 133 } 134