summaryrefslogtreecommitdiffstats
path: root/llvm/lib/Analysis/ScalarEvolution.cpp
diff options
context:
space:
mode:
authorNicola Zaghen <nicola.zaghen@imgtec.com>2019-12-13 09:55:45 +0000
committerNicola Zaghen <nicola.zaghen@imgtec.com>2019-12-13 14:30:21 +0000
commit97572775d2fe088d8059b3a9423f6d8539fafe33 (patch)
tree634e93ae8cbc9e4d7691d65a864bc61dfe689026 /llvm/lib/Analysis/ScalarEvolution.cpp
parent56adcebfda84009b2825e69f71068685360abed7 (diff)
downloadbcm5719-llvm-97572775d2fe088d8059b3a9423f6d8539fafe33.tar.gz
bcm5719-llvm-97572775d2fe088d8059b3a9423f6d8539fafe33.zip
Reland [DataLayout] Fix occurrences that size and range of pointers are assumed to be the same.
GEP index size can be specified in the DataLayout, introduced in D42123. However, there were still places in which getIndexSizeInBits was used interchangeably with getPointerSizeInBits. This notably caused issues with Instcombine's visitPtrToInt; but the unit tests was incorrect, so this remained undiscovered. This fixes the buildbot failures. Differential Revision: https://reviews.llvm.org/D68328 Patch by Joseph Faulls!
Diffstat (limited to 'llvm/lib/Analysis/ScalarEvolution.cpp')
-rw-r--r--llvm/lib/Analysis/ScalarEvolution.cpp25
1 files changed, 18 insertions, 7 deletions
diff --git a/llvm/lib/Analysis/ScalarEvolution.cpp b/llvm/lib/Analysis/ScalarEvolution.cpp
index d635afb0a29..8fcea5d4cd3 100644
--- a/llvm/lib/Analysis/ScalarEvolution.cpp
+++ b/llvm/lib/Analysis/ScalarEvolution.cpp
@@ -3495,7 +3495,7 @@ ScalarEvolution::getGEPExpr(GEPOperator *GEP,
const SCEV *BaseExpr = getSCEV(GEP->getPointerOperand());
// getSCEV(Base)->getType() has the same address space as Base->getType()
// because SCEV::getType() preserves the address space.
- Type *IntPtrTy = getEffectiveSCEVType(BaseExpr->getType());
+ Type *IntIdxTy = getEffectiveSCEVType(BaseExpr->getType());
// FIXME(PR23527): Don't blindly transfer the inbounds flag from the GEP
// instruction to its SCEV, because the Instruction may be guarded by control
// flow and the no-overflow bits may not be valid for the expression in any
@@ -3504,7 +3504,7 @@ ScalarEvolution::getGEPExpr(GEPOperator *GEP,
SCEV::NoWrapFlags Wrap = GEP->isInBounds() ? SCEV::FlagNSW
: SCEV::FlagAnyWrap;
- const SCEV *TotalOffset = getZero(IntPtrTy);
+ const SCEV *TotalOffset = getZero(IntIdxTy);
// The array size is unimportant. The first thing we do on CurTy is getting
// its element type.
Type *CurTy = ArrayType::get(GEP->getSourceElementType(), 0);
@@ -3514,7 +3514,7 @@ ScalarEvolution::getGEPExpr(GEPOperator *GEP,
// For a struct, add the member offset.
ConstantInt *Index = cast<SCEVConstant>(IndexExpr)->getValue();
unsigned FieldNo = Index->getZExtValue();
- const SCEV *FieldOffset = getOffsetOfExpr(IntPtrTy, STy, FieldNo);
+ const SCEV *FieldOffset = getOffsetOfExpr(IntIdxTy, STy, FieldNo);
// Add the field offset to the running total offset.
TotalOffset = getAddExpr(TotalOffset, FieldOffset);
@@ -3525,9 +3525,9 @@ ScalarEvolution::getGEPExpr(GEPOperator *GEP,
// Update CurTy to its element type.
CurTy = cast<SequentialType>(CurTy)->getElementType();
// For an array, add the element offset, explicitly scaled.
- const SCEV *ElementSize = getSizeOfExpr(IntPtrTy, CurTy);
+ const SCEV *ElementSize = getSizeOfExpr(IntIdxTy, CurTy);
// Getelementptr indices are signed.
- IndexExpr = getTruncateOrSignExtend(IndexExpr, IntPtrTy);
+ IndexExpr = getTruncateOrSignExtend(IndexExpr, IntIdxTy);
// Multiply the index by the element size to compute the element offset.
const SCEV *LocalOffset = getMulExpr(IndexExpr, ElementSize, Wrap);
@@ -3786,7 +3786,7 @@ uint64_t ScalarEvolution::getTypeSizeInBits(Type *Ty) const {
/// Return a type with the same bitwidth as the given type and which represents
/// how SCEV will treat the given type, for which isSCEVable must return
-/// true. For pointer types, this is the pointer-sized integer type.
+/// true. For pointer types, this is the pointer index sized integer type.
Type *ScalarEvolution::getEffectiveSCEVType(Type *Ty) const {
assert(isSCEVable(Ty) && "Type is not SCEVable!");
@@ -3795,7 +3795,7 @@ Type *ScalarEvolution::getEffectiveSCEVType(Type *Ty) const {
// The only other support type is pointer.
assert(Ty->isPointerTy() && "Unexpected non-pointer non-integer type!");
- return getDataLayout().getIntPtrType(Ty);
+ return getDataLayout().getIndexType(Ty);
}
Type *ScalarEvolution::getWiderType(Type *T1, Type *T2) const {
@@ -5717,6 +5717,8 @@ ScalarEvolution::getRangeRef(const SCEV *S,
if (SignHint == ScalarEvolution::HINT_RANGE_UNSIGNED) {
// For a SCEVUnknown, ask ValueTracking.
KnownBits Known = computeKnownBits(U->getValue(), DL, 0, &AC, nullptr, &DT);
+ if (Known.getBitWidth() != BitWidth)
+ Known = Known.zextOrTrunc(BitWidth, true);
// If Known does not result in full-set, intersect with it.
if (Known.getMinValue() != Known.getMaxValue() + 1)
ConservativeResult = ConservativeResult.intersectWith(
@@ -5726,6 +5728,15 @@ ScalarEvolution::getRangeRef(const SCEV *S,
assert(SignHint == ScalarEvolution::HINT_RANGE_SIGNED &&
"generalize as needed!");
unsigned NS = ComputeNumSignBits(U->getValue(), DL, 0, &AC, nullptr, &DT);
+ // If the pointer size is larger than the index size type, this can cause
+ // NS to be larger than BitWidth. So compensate for this.
+ if (U->getType()->isPointerTy()) {
+ unsigned ptrSize = DL.getPointerTypeSizeInBits(U->getType());
+ int ptrIdxDiff = ptrSize - BitWidth;
+ if (ptrIdxDiff > 0 && ptrSize > BitWidth && NS > (unsigned)ptrIdxDiff)
+ NS -= ptrIdxDiff;
+ }
+
if (NS > 1)
ConservativeResult = ConservativeResult.intersectWith(
ConstantRange(APInt::getSignedMinValue(BitWidth).ashr(NS - 1),
OpenPOWER on IntegriCloud