// Shift the address back by one element.
llvm::Value *negativeOne = llvm::ConstantInt::get(SizeTy, -1, true);
- llvm::Value *element = Builder.CreateInBoundsGEP(elementPast, negativeOne,
- "arraydestroy.element");
+ llvm::Value *element = Builder.CreateInBoundsGEP(
+ elementPast->getType()->getPointerElementType(), elementPast, negativeOne,
+ "arraydestroy.element");
if (useEHCleanup)
pushRegularPartialArrayCleanup(begin, element, elementType, elementAlign,
llvm::Value *zero = llvm::ConstantInt::get(CGF.SizeTy, 0);
SmallVector<llvm::Value*,4> gepIndices(arrayDepth+1, zero);
- begin = CGF.Builder.CreateInBoundsGEP(begin, gepIndices, "pad.arraybegin");
- end = CGF.Builder.CreateInBoundsGEP(end, gepIndices, "pad.arrayend");
+ llvm::Type *elemTy = begin->getType()->getPointerElementType();
+ begin = CGF.Builder.CreateInBoundsGEP(
+ elemTy, begin, gepIndices, "pad.arraybegin");
+ end = CGF.Builder.CreateInBoundsGEP(
+ elemTy, end, gepIndices, "pad.arrayend");
}
// Destroy the array. We don't ever need an EH cleanup because we
LValue Start = CGF.EmitLValueForFieldInitialization(DestLV, *Field);
llvm::Value *Zero = llvm::ConstantInt::get(CGF.PtrDiffTy, 0);
llvm::Value *IdxStart[] = { Zero, Zero };
- llvm::Value *ArrayStart =
- Builder.CreateInBoundsGEP(ArrayPtr.getPointer(), IdxStart, "arraystart");
+ llvm::Value *ArrayStart = Builder.CreateInBoundsGEP(
+ ArrayPtr.getElementType(), ArrayPtr.getPointer(), IdxStart, "arraystart");
CGF.EmitStoreThroughLValue(RValue::get(ArrayStart), Start);
++Field;
ArrayType->getElementType())) {
// End pointer.
llvm::Value *IdxEnd[] = { Zero, Size };
- llvm::Value *ArrayEnd =
- Builder.CreateInBoundsGEP(ArrayPtr.getPointer(), IdxEnd, "arrayend");
+ llvm::Value *ArrayEnd = Builder.CreateInBoundsGEP(
+ ArrayPtr.getElementType(), ArrayPtr.getPointer(), IdxEnd, "arrayend");
CGF.EmitStoreThroughLValue(RValue::get(ArrayEnd), EndOrLength);
} else if (Ctx.hasSameType(Field->getType(), Ctx.getSizeType())) {
// Length.
// down a level.
llvm::Value *zero = llvm::ConstantInt::get(CGF.SizeTy, 0);
llvm::Value *indices[] = { zero, zero };
- llvm::Value *begin =
- Builder.CreateInBoundsGEP(DestPtr.getPointer(), indices, "arrayinit.begin");
+ llvm::Value *begin = Builder.CreateInBoundsGEP(
+ DestPtr.getElementType(), DestPtr.getPointer(), indices,
+ "arrayinit.begin");
CharUnits elementSize = CGF.getContext().getTypeSizeInChars(elementType);
CharUnits elementAlign =
DestPtr.getAlignment().alignmentOfArrayElement(elementSize);
+ llvm::Type *llvmElementType = begin->getType()->getPointerElementType();
// Consider initializing the array by copying from a global. For this to be
// more efficient than per-element initialization, the size of the elements
for (uint64_t i = 0; i != NumInitElements; ++i) {
// Advance to the next element.
if (i > 0) {
- element = Builder.CreateInBoundsGEP(element, one, "arrayinit.element");
+ element = Builder.CreateInBoundsGEP(
+ llvmElementType, element, one, "arrayinit.element");
// Tell the cleanup that it needs to destroy up to this
// element. TODO: some of these stores can be trivially
// Advance to the start of the rest of the array.
if (NumInitElements) {
- element = Builder.CreateInBoundsGEP(element, one, "arrayinit.start");
+ element = Builder.CreateInBoundsGEP(
+ llvmElementType, element, one, "arrayinit.start");
if (endOfInit.isValid()) Builder.CreateStore(element, endOfInit);
}
// Compute the end of the array.
- llvm::Value *end = Builder.CreateInBoundsGEP(begin,
- llvm::ConstantInt::get(CGF.SizeTy, NumArrayElements),
- "arrayinit.end");
+ llvm::Value *end = Builder.CreateInBoundsGEP(
+ llvmElementType, begin,
+ llvm::ConstantInt::get(CGF.SizeTy, NumArrayElements), "arrayinit.end");
llvm::BasicBlock *entryBB = Builder.GetInsertBlock();
llvm::BasicBlock *bodyBB = CGF.createBasicBlock("arrayinit.body");
}
// Move on to the next element.
- llvm::Value *nextElement =
- Builder.CreateInBoundsGEP(currentElement, one, "arrayinit.next");
+ llvm::Value *nextElement = Builder.CreateInBoundsGEP(
+ llvmElementType, currentElement, one, "arrayinit.next");
// Tell the EH cleanup that we finished with the last element.
if (endOfInit.isValid()) Builder.CreateStore(nextElement, endOfInit);
// destPtr is an array*. Construct an elementType* by drilling down a level.
llvm::Value *zero = llvm::ConstantInt::get(CGF.SizeTy, 0);
llvm::Value *indices[] = {zero, zero};
- llvm::Value *begin = Builder.CreateInBoundsGEP(destPtr.getPointer(), indices,
- "arrayinit.begin");
+ llvm::Value *begin = Builder.CreateInBoundsGEP(
+ destPtr.getElementType(), destPtr.getPointer(), indices,
+ "arrayinit.begin");
// Prepare to special-case multidimensional array initialization: we avoid
// emitting multiple destructor loops in that case.
llvm::PHINode *index =
Builder.CreatePHI(zero->getType(), 2, "arrayinit.index");
index->addIncoming(zero, entryBB);
- llvm::Value *element = Builder.CreateInBoundsGEP(begin, index);
+ llvm::Value *element = Builder.CreateInBoundsGEP(
+ begin->getType()->getPointerElementType(), begin, index);
// Prepare for a cleanup.
QualType::DestructionKind dtorKind = elementType.isDestructedType();
PollyIRBuilder &Builder,
std::string ArrayName) {
assert(GlobalDescriptor && "invalid global descriptor given");
+ Type *Ty = GlobalDescriptor->getType()->getPointerElementType();
Value *endIdx[4] = {Builder.getInt64(0), Builder.getInt32(3),
Builder.getInt64(0), Builder.getInt32(2)};
- Value *endPtr = Builder.CreateInBoundsGEP(GlobalDescriptor, endIdx,
+ Value *endPtr = Builder.CreateInBoundsGEP(Ty, GlobalDescriptor, endIdx,
ArrayName + "_end_ptr");
Type *type = cast<GEPOperator>(endPtr)->getResultElementType();
assert(isa<IntegerType>(type) && "expected type of end to be integral");
Value *beginIdx[4] = {Builder.getInt64(0), Builder.getInt32(3),
Builder.getInt64(0), Builder.getInt32(1)};
- Value *beginPtr = Builder.CreateInBoundsGEP(GlobalDescriptor, beginIdx,
+ Value *beginPtr = Builder.CreateInBoundsGEP(Ty, GlobalDescriptor, beginIdx,
ArrayName + "_begin_ptr");
Value *begin = Builder.CreateLoad(type, beginPtr, ArrayName + "_begin");