diff options
| author | Artur Pilipenko <apilipenko@azulsystems.com> | 2015-06-08 11:58:13 +0000 |
|---|---|---|
| committer | Artur Pilipenko <apilipenko@azulsystems.com> | 2015-06-08 11:58:13 +0000 |
| commit | 7fad7e57e8137a2e6c6d8c21fe92d436a053b2f1 (patch) | |
| tree | 789235442663959cf2c82b6c3ea22066404f0c85 /llvm/lib | |
| parent | 1c5ad681d7be4192b9d9f88f2821d7f9cd258a63 (diff) | |
| download | bcm5719-llvm-7fad7e57e8137a2e6c6d8c21fe92d436a053b2f1.tar.gz bcm5719-llvm-7fad7e57e8137a2e6c6d8c21fe92d436a053b2f1.zip | |
Minor refactoring of GEP handling in isDereferenceablePointer
For GEP instructions isDereferenceablePointer checks that all indices are constant and within bounds. Replace this index calculation logic to a call to accumulateConstantOffset. Separated from the http://reviews.llvm.org/D9791
Reviewed By: sanjoy
Differential Revision: http://reviews.llvm.org/D9874
llvm-svn: 239299
Diffstat (limited to 'llvm/lib')
| -rw-r--r-- | llvm/lib/Analysis/ValueTracking.cpp | 43 |
1 files changed, 15 insertions, 28 deletions
diff --git a/llvm/lib/Analysis/ValueTracking.cpp b/llvm/lib/Analysis/ValueTracking.cpp index a55712c6296..c4f046340fc 100644 --- a/llvm/lib/Analysis/ValueTracking.cpp +++ b/llvm/lib/Analysis/ValueTracking.cpp @@ -2967,38 +2967,25 @@ static bool isDereferenceablePointer(const Value *V, const DataLayout &DL, // For GEPs, determine if the indexing lands within the allocated object. if (const GEPOperator *GEP = dyn_cast<GEPOperator>(V)) { + Type *VTy = GEP->getType(); + Type *Ty = VTy->getPointerElementType(); + const Value *Base = GEP->getPointerOperand(); + // Conservatively require that the base pointer be fully dereferenceable. - if (!Visited.insert(GEP->getOperand(0)).second) + if (!Visited.insert(Base).second) return false; - if (!isDereferenceablePointer(GEP->getOperand(0), DL, CtxI, + if (!isDereferenceablePointer(Base, DL, CtxI, DT, TLI, Visited)) return false; - // Check the indices. - gep_type_iterator GTI = gep_type_begin(GEP); - for (User::const_op_iterator I = GEP->op_begin()+1, - E = GEP->op_end(); I != E; ++I) { - Value *Index = *I; - Type *Ty = *GTI++; - // Struct indices can't be out of bounds. - if (isa<StructType>(Ty)) - continue; - ConstantInt *CI = dyn_cast<ConstantInt>(Index); - if (!CI) - return false; - // Zero is always ok. - if (CI->isZero()) - continue; - // Check to see that it's within the bounds of an array. - ArrayType *ATy = dyn_cast<ArrayType>(Ty); - if (!ATy) - return false; - if (CI->getValue().getActiveBits() > 64) - return false; - if (CI->getZExtValue() >= ATy->getNumElements()) - return false; - } - // Indices check out; this is dereferenceable. - return true; + + APInt Offset(DL.getPointerTypeSizeInBits(VTy), 0); + if (!GEP->accumulateConstantOffset(DL, Offset)) + return false; + + // Check if the load is within the bounds of the underlying object. + uint64_t LoadSize = DL.getTypeStoreSize(Ty); + Type *BaseType = Base->getType()->getPointerElementType(); + return (Offset + LoadSize).ule(DL.getTypeAllocSize(BaseType)); } // For gc.relocate, look through relocations |

