summaryrefslogtreecommitdiffstats
path: root/clang/lib/CodeGen/CGExpr.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'clang/lib/CodeGen/CGExpr.cpp')
-rw-r--r--clang/lib/CodeGen/CGExpr.cpp27
1 files changed, 17 insertions, 10 deletions
diff --git a/clang/lib/CodeGen/CGExpr.cpp b/clang/lib/CodeGen/CGExpr.cpp
index 194eb412382..6e10a9dcf17 100644
--- a/clang/lib/CodeGen/CGExpr.cpp
+++ b/clang/lib/CodeGen/CGExpr.cpp
@@ -64,9 +64,12 @@ llvm::Value *CodeGenFunction::EmitCastToVoidPtr(llvm::Value *value) {
Address CodeGenFunction::CreateTempAlloca(llvm::Type *Ty, CharUnits Align,
const Twine &Name,
llvm::Value *ArraySize,
+ Address *AllocaAddr,
bool CastToDefaultAddrSpace) {
auto Alloca = CreateTempAlloca(Ty, Name, ArraySize);
Alloca->setAlignment(Align.getQuantity());
+ if (AllocaAddr)
+ *AllocaAddr = Address(Alloca, Align);
llvm::Value *V = Alloca;
// Alloca always returns a pointer in alloca address space, which may
// be different from the type defined by the language. For example,
@@ -125,16 +128,18 @@ Address CodeGenFunction::CreateIRTemp(QualType Ty, const Twine &Name) {
}
Address CodeGenFunction::CreateMemTemp(QualType Ty, const Twine &Name,
+ Address *Alloca,
bool CastToDefaultAddrSpace) {
// FIXME: Should we prefer the preferred type alignment here?
- return CreateMemTemp(Ty, getContext().getTypeAlignInChars(Ty), Name,
+ return CreateMemTemp(Ty, getContext().getTypeAlignInChars(Ty), Name, Alloca,
CastToDefaultAddrSpace);
}
Address CodeGenFunction::CreateMemTemp(QualType Ty, CharUnits Align,
- const Twine &Name,
+ const Twine &Name, Address *Alloca,
bool CastToDefaultAddrSpace) {
- return CreateTempAlloca(ConvertTypeForMem(Ty), Align, Name, nullptr,
+ return CreateTempAlloca(ConvertTypeForMem(Ty), Align, Name,
+ /*ArraySize=*/nullptr, Alloca,
CastToDefaultAddrSpace);
}
@@ -348,7 +353,8 @@ pushTemporaryCleanup(CodeGenFunction &CGF, const MaterializeTemporaryExpr *M,
static Address createReferenceTemporary(CodeGenFunction &CGF,
const MaterializeTemporaryExpr *M,
- const Expr *Inner) {
+ const Expr *Inner,
+ Address *Alloca = nullptr) {
auto &TCG = CGF.getTargetHooks();
switch (M->getStorageDuration()) {
case SD_FullExpression:
@@ -381,7 +387,7 @@ static Address createReferenceTemporary(CodeGenFunction &CGF,
return Address(C, alignment);
}
}
- return CGF.CreateMemTemp(Ty, "ref.tmp");
+ return CGF.CreateMemTemp(Ty, "ref.tmp", Alloca);
}
case SD_Thread:
case SD_Static:
@@ -458,7 +464,8 @@ EmitMaterializeTemporaryExpr(const MaterializeTemporaryExpr *M) {
}
// Create and initialize the reference temporary.
- Address Object = createReferenceTemporary(*this, M, E);
+ Address Alloca = Address::invalid();
+ Address Object = createReferenceTemporary(*this, M, E, &Alloca);
if (auto *Var = dyn_cast<llvm::GlobalVariable>(
Object.getPointer()->stripPointerCasts())) {
Object = Address(llvm::ConstantExpr::getBitCast(
@@ -477,13 +484,13 @@ EmitMaterializeTemporaryExpr(const MaterializeTemporaryExpr *M) {
case SD_Automatic:
case SD_FullExpression:
if (auto *Size = EmitLifetimeStart(
- CGM.getDataLayout().getTypeAllocSize(Object.getElementType()),
- Object.getPointer())) {
+ CGM.getDataLayout().getTypeAllocSize(Alloca.getElementType()),
+ Alloca.getPointer())) {
if (M->getStorageDuration() == SD_Automatic)
pushCleanupAfterFullExpr<CallLifetimeEnd>(NormalEHLifetimeMarker,
- Object, Size);
+ Alloca, Size);
else
- pushFullExprCleanup<CallLifetimeEnd>(NormalEHLifetimeMarker, Object,
+ pushFullExprCleanup<CallLifetimeEnd>(NormalEHLifetimeMarker, Alloca,
Size);
}
break;
OpenPOWER on IntegriCloud