From ad80c2d9ed1a348deaacdf11aa17c40382a97ac7 Mon Sep 17 00:00:00 2001 From: David Blaikie Date: Thu, 7 May 2015 17:28:58 +0000 Subject: [PATCH] Recommit r236670: [opaque pointer type] Pass explicit pointer type through GEP constant folding"" Clang regressions were caused by more stringent assertion checking introduced by this change. Small fix needed to clang has been committed in r236751. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@236752 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/IR/ConstantFold.cpp | 30 +++++++++++++++++++++++------- lib/IR/ConstantFold.h | 4 ++++ lib/IR/Constants.cpp | 12 +++++++----- lib/Transforms/IPO/GlobalOpt.cpp | 6 ++---- 4 files changed, 36 insertions(+), 16 deletions(-) diff --git a/lib/IR/ConstantFold.cpp b/lib/IR/ConstantFold.cpp index 2a524937391..8afb3e489de 100644 --- a/lib/IR/ConstantFold.cpp +++ b/lib/IR/ConstantFold.cpp @@ -2028,7 +2028,7 @@ static bool isIndexInRangeOfSequentialType(const SequentialType *STy, } template -static Constant *ConstantFoldGetElementPtrImpl(Constant *C, +static Constant *ConstantFoldGetElementPtrImpl(Type *PointeeTy, Constant *C, bool inBounds, ArrayRef Idxs) { if (Idxs.empty()) return C; @@ -2165,9 +2165,9 @@ static Constant *ConstantFoldGetElementPtrImpl(Constant *C, // factored out into preceding dimensions. bool Unknown = false; SmallVector NewIdxs; - Type *Ty = C->getType(); - Type *Prev = nullptr; - for (unsigned i = 0, e = Idxs.size(); i != e; + Type *Ty = PointeeTy; + Type *Prev = C->getType(); + for (unsigned i = 1, e = Idxs.size(); i != e; Prev = Ty, Ty = cast(Ty)->getTypeAtIndex(Idxs[i]), ++i) { if (ConstantInt *CI = dyn_cast(Idxs[i])) { if (isa(Ty) || isa(Ty)) @@ -2229,7 +2229,7 @@ static Constant *ConstantFoldGetElementPtrImpl(Constant *C, if (!Unknown && !inBounds) if (auto *GV = dyn_cast(C)) if (!GV->hasExternalWeakLinkage() && isInBoundsIndices(Idxs)) - return ConstantExpr::getInBoundsGetElementPtr(nullptr, C, Idxs); + return ConstantExpr::getInBoundsGetElementPtr(PointeeTy, C, Idxs); return nullptr; } @@ -2237,11 +2237,27 @@ static Constant *ConstantFoldGetElementPtrImpl(Constant *C, Constant *llvm::ConstantFoldGetElementPtr(Constant *C, bool inBounds, ArrayRef Idxs) { - return ConstantFoldGetElementPtrImpl(C, inBounds, Idxs); + return ConstantFoldGetElementPtrImpl( + cast(C->getType()->getScalarType())->getElementType(), C, + inBounds, Idxs); } Constant *llvm::ConstantFoldGetElementPtr(Constant *C, bool inBounds, ArrayRef Idxs) { - return ConstantFoldGetElementPtrImpl(C, inBounds, Idxs); + return ConstantFoldGetElementPtrImpl( + cast(C->getType()->getScalarType())->getElementType(), C, + inBounds, Idxs); +} + +Constant *llvm::ConstantFoldGetElementPtr(Type *Ty, Constant *C, + bool inBounds, + ArrayRef Idxs) { + return ConstantFoldGetElementPtrImpl(Ty, C, inBounds, Idxs); +} + +Constant *llvm::ConstantFoldGetElementPtr(Type *Ty, Constant *C, + bool inBounds, + ArrayRef Idxs) { + return ConstantFoldGetElementPtrImpl(Ty, C, inBounds, Idxs); } diff --git a/lib/IR/ConstantFold.h b/lib/IR/ConstantFold.h index a516abe024e..42a9c6ba908 100644 --- a/lib/IR/ConstantFold.h +++ b/lib/IR/ConstantFold.h @@ -51,6 +51,10 @@ namespace llvm { ArrayRef Idxs); Constant *ConstantFoldGetElementPtr(Constant *C, bool inBounds, ArrayRef Idxs); + Constant *ConstantFoldGetElementPtr(Type *Ty, Constant *C, bool inBounds, + ArrayRef Idxs); + Constant *ConstantFoldGetElementPtr(Type *Ty, Constant *C, bool inBounds, + ArrayRef Idxs); } // End llvm namespace #endif diff --git a/lib/IR/Constants.cpp b/lib/IR/Constants.cpp index 20a5206c230..b598c2807ce 100644 --- a/lib/IR/Constants.cpp +++ b/lib/IR/Constants.cpp @@ -2015,14 +2015,16 @@ Constant *ConstantExpr::getSelect(Constant *C, Constant *V1, Constant *V2, Constant *ConstantExpr::getGetElementPtr(Type *Ty, Constant *C, ArrayRef Idxs, bool InBounds, Type *OnlyIfReducedTy) { - if (Constant *FC = ConstantFoldGetElementPtr(C, InBounds, Idxs)) - return FC; // Fold a few common cases. - if (!Ty) Ty = cast(C->getType()->getScalarType())->getElementType(); else - assert(Ty == - cast(C->getType()->getScalarType())->getElementType()); + assert( + Ty == + cast(C->getType()->getScalarType())->getContainedType(0u)); + + if (Constant *FC = ConstantFoldGetElementPtr(Ty, C, InBounds, Idxs)) + return FC; // Fold a few common cases. + // Get the result type of the getelementptr! Type *DestTy = GetElementPtrInst::getIndexedType(Ty, Idxs); assert(DestTy && "GEP indices invalid!"); diff --git a/lib/Transforms/IPO/GlobalOpt.cpp b/lib/Transforms/IPO/GlobalOpt.cpp index b8c4f5da39e..cc4a79fa67d 100644 --- a/lib/Transforms/IPO/GlobalOpt.cpp +++ b/lib/Transforms/IPO/GlobalOpt.cpp @@ -564,7 +564,7 @@ static GlobalVariable *SRAGlobal(GlobalVariable *GV, const DataLayout &DL) { if (Val >= NewGlobals.size()) Val = 0; // Out of bound array access. Value *NewPtr = NewGlobals[Val]; - Type *NewTy = NewGlobals[Val]->getType(); + Type *NewTy = NewGlobals[Val]->getValueType(); // Form a shorter GEP if needed. if (GEP->getNumOperands() > 3) { @@ -575,7 +575,6 @@ static GlobalVariable *SRAGlobal(GlobalVariable *GV, const DataLayout &DL) { Idxs.push_back(CE->getOperand(i)); NewPtr = ConstantExpr::getGetElementPtr(NewTy, cast(NewPtr), Idxs); - NewTy = GetElementPtrInst::getIndexedType(NewTy, Idxs); } else { GetElementPtrInst *GEPI = cast(GEP); SmallVector Idxs; @@ -583,8 +582,7 @@ static GlobalVariable *SRAGlobal(GlobalVariable *GV, const DataLayout &DL) { for (unsigned i = 3, e = GEPI->getNumOperands(); i != e; ++i) Idxs.push_back(GEPI->getOperand(i)); NewPtr = GetElementPtrInst::Create( - NewPtr->getType()->getPointerElementType(), NewPtr, Idxs, - GEPI->getName() + "." + Twine(Val), GEPI); + NewTy, NewPtr, Idxs, GEPI->getName() + "." + Twine(Val), GEPI); } } GEP->replaceAllUsesWith(NewPtr); -- 2.34.1