forked from OSchip/llvm-project
Emit the destructor epilogue in a cleanup block so a return from a destructor body still calls the epilogue.
llvm-svn: 83397
This commit is contained in:
parent
36d1b14dde
commit
6b7378bbe1
|
@ -233,11 +233,30 @@ void CodeGenFunction::GenerateCode(GlobalDecl GD,
|
|||
// FIXME: Support CXXTryStmt here, too.
|
||||
if (const CompoundStmt *S = FD->getCompoundBody()) {
|
||||
StartFunction(GD, FD->getResultType(), Fn, Args, S->getLBracLoc());
|
||||
const CXXDestructorDecl *DD = dyn_cast<CXXDestructorDecl>(FD);
|
||||
llvm::BasicBlock *DtorEpilogue = 0;
|
||||
if (DD) {
|
||||
DtorEpilogue = createBasicBlock("dtor.epilogue");
|
||||
|
||||
PushCleanupBlock(DtorEpilogue);
|
||||
}
|
||||
|
||||
if (const CXXConstructorDecl *CD = dyn_cast<CXXConstructorDecl>(FD))
|
||||
EmitCtorPrologue(CD, GD.getCtorType());
|
||||
EmitStmt(S);
|
||||
if (const CXXDestructorDecl *DD = dyn_cast<CXXDestructorDecl>(FD))
|
||||
|
||||
if (DD) {
|
||||
CleanupBlockInfo Info = PopCleanupBlock();
|
||||
|
||||
assert(Info.CleanupBlock == DtorEpilogue && "Block mismatch!");
|
||||
EmitBlock(DtorEpilogue);
|
||||
EmitDtorEpilogue(DD, GD.getDtorType());
|
||||
|
||||
if (Info.SwitchBlock)
|
||||
EmitBlock(Info.SwitchBlock);
|
||||
if (Info.EndBlock)
|
||||
EmitBlock(Info.EndBlock);
|
||||
}
|
||||
FinishFunction(S->getRBracLoc());
|
||||
} else if (FD->isImplicit()) {
|
||||
const CXXRecordDecl *ClassDecl =
|
||||
|
|
|
@ -30,7 +30,12 @@ struct N : M, P {
|
|||
P p;
|
||||
};
|
||||
|
||||
struct O : B {
|
||||
~O() { return; }
|
||||
};
|
||||
|
||||
int main() {
|
||||
N n1;
|
||||
N n2;
|
||||
O o;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue