Overhaul of Stmt allocation:
- Made allocation of Stmt objects using vanilla new/delete a *compiler
error* by making this new/delete "protected" within class Stmt.
- Now the only way to allocate Stmt objects is by using the new
operator that takes ASTContext& as an argument. This ensures that
all Stmt nodes are allocated from the same (pool) allocator.
- Naturally, these two changes required that *all* creation sites for
AST nodes use new (ASTContext&). This is a large patch, but the
majority of the changes are just this mechanical adjustment.
- The above changes also mean that AST nodes can no longer be
deallocated using 'delete'. Instead, one most do
StmtObject->Destroy(ASTContext&) or do
ASTContextObject.Deallocate(StmtObject) (the latter not running the
'Destroy' method).
Along the way I also...
- Made CompoundStmt allocate its array of Stmt* using the allocator in
ASTContext (previously it used std::vector). There are a whole
bunch of other Stmt classes that need to be similarly changed to
ensure that all memory allocated for ASTs comes from the allocator
in ASTContext.
- Added a new smart pointer ExprOwningPtr to Sema.h. This replaces
the uses of llvm::OwningPtr within Sema, as llvm::OwningPtr used
'delete' to free memory instead of a Stmt's 'Destroy' method.
Big thanks to Doug Gregor for helping with the acrobatics of making
'new/delete' private and the new smart pointer ExprOwningPtr!
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@63997 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/Sema/SemaDecl.cpp b/lib/Sema/SemaDecl.cpp
index bf16e1a..cdb6930 100644
--- a/lib/Sema/SemaDecl.cpp
+++ b/lib/Sema/SemaDecl.cpp
@@ -2260,7 +2260,7 @@
// If there is no declaration, there was an error parsing it. Just ignore
// the initializer.
if (RealDecl == 0) {
- delete Init;
+ Init->Destroy(Context);
return;
}
@@ -2697,8 +2697,10 @@
assert(FD == getCurFunctionDecl() && "Function parsing confused");
} else if (ObjCMethodDecl *MD = dyn_cast_or_null<ObjCMethodDecl>(dcl)) {
MD->setBody((Stmt*)Body);
- } else
+ } else {
+ Body->Destroy(Context);
return 0;
+ }
PopDeclContext();
// Verify and clean out per-function state.
@@ -2717,11 +2719,17 @@
// the function body so that they aren't leaked and that the AST is well
// formed.
if (Body) {
- L->setSubStmt(new NullStmt(L->getIdentLoc()));
- cast<CompoundStmt>(Body)->push_back(L);
+#if 0
+ // FIXME: Why do this? Having a 'push_back' in CompoundStmt is ugly,
+ // and the AST is malformed anyway. We should just blow away 'L'.
+ L->setSubStmt(new (Context) NullStmt(L->getIdentLoc()));
+ cast<CompoundStmt>(Body)->push_back(L);
+#else
+ L->Destroy(Context);
+#endif
} else {
// The whole function wasn't parsed correctly, just delete this.
- delete L;
+ L->Destroy(Context);
}
}
}
@@ -3516,7 +3524,7 @@
else
Diag(IdLoc, diag::err_redefinition) << Id;
Diag(PrevDecl->getLocation(), diag::note_previous_definition);
- delete Val;
+ Val->Destroy(Context);
return 0;
}
}
@@ -3530,7 +3538,7 @@
// C99 6.7.2.2p2: Make sure we have an integer constant expression.
SourceLocation ExpLoc;
if (VerifyIntegerConstantExpression(Val, &EnumVal)) {
- delete Val;
+ Val->Destroy(Context);
Val = 0; // Just forget about it.
} else {
EltTy = Val->getType();
@@ -3721,8 +3729,8 @@
// Adjust the Expr initializer and type.
if (ECD->getInitExpr())
- ECD->setInitExpr(new ImplicitCastExpr(NewTy, ECD->getInitExpr(),
- /*isLvalue=*/false));
+ ECD->setInitExpr(new (Context) ImplicitCastExpr(NewTy, ECD->getInitExpr(),
+ /*isLvalue=*/false));
if (getLangOptions().CPlusPlus)
// C++ [dcl.enum]p4: Following the closing brace of an
// enum-specifier, each enumerator has the type of its
@@ -3756,7 +3764,7 @@
!Val.isPowerOf2() ||
Val.getZExtValue() > 16) {
Diag(PragmaLoc, diag::warn_pragma_pack_invalid_alignment);
- delete Alignment;
+ Alignment->Destroy(Context);
return; // Ignore
}