aboutsummaryrefslogtreecommitdiff
path: root/gcc/d/decl.cc
diff options
context:
space:
mode:
authorIain Buclaw <ibuclaw@gdcproject.org>2019-04-21 07:03:32 +0000
committerIain Buclaw <ibuclaw@gcc.gnu.org>2019-04-21 07:03:32 +0000
commite64deb7447955c4d513a1fb5f9e4c553ca64545c (patch)
tree5702c70a0dee4087eda5ed6068828e5fd6351fb6 /gcc/d/decl.cc
parentf452f0d67f1a5a0da4e1e15026c5a9c322c2f5b7 (diff)
downloadgcc-e64deb7447955c4d513a1fb5f9e4c553ca64545c.zip
gcc-e64deb7447955c4d513a1fb5f9e4c553ca64545c.tar.gz
gcc-e64deb7447955c4d513a1fb5f9e4c553ca64545c.tar.bz2
d: Use semanticRun to prevent declaration pass from running multiple times.
This shouldn't happen during normal traversal of the AST provided from the front-end, however as there are some cases where declarations need to be visited out of order, such as what is being done in PR d/89017, it then becomes necessary to guard against this. gcc/d/ChangeLog: 2019-04-21 Iain Buclaw <ibuclaw@gdcproject.org> * decl.cc (DeclVisitor::visit(Import)): Set semanticRun after completion, guard against being called more than once. (DeclVisitor::visit(StructDeclaration)): Likewise. (DeclVisitor::visit(ClassDeclaration)): Likewise. (DeclVisitor::visit(InterfaceDeclaration)): Likewise. (DeclVisitor::visit(VarDeclaration)): Likewise. (DeclVisitor::visit(TypeInfoDeclaration)): Likewise. From-SVN: r270478
Diffstat (limited to 'gcc/d/decl.cc')
-rw-r--r--gcc/d/decl.cc29
1 files changed, 29 insertions, 0 deletions
diff --git a/gcc/d/decl.cc b/gcc/d/decl.cc
index f6c8639..26de272 100644
--- a/gcc/d/decl.cc
+++ b/gcc/d/decl.cc
@@ -152,6 +152,9 @@ public:
void visit (Import *d)
{
+ if (d->semanticRun >= PASSobj)
+ return;
+
/* Implements import declarations by telling the debug back-end we are
importing the NAMESPACE_DECL of the module or IMPORTED_DECL of the
declaration into the current lexical scope CONTEXT. NAME is set if
@@ -193,6 +196,8 @@ public:
debug_hooks->imported_module_or_decl (decl, name, context,
false, false);
}
+
+ d->semanticRun = PASSobj;
}
/* Expand any local variables found in tuples. */
@@ -349,6 +354,9 @@ public:
void visit (StructDeclaration *d)
{
+ if (d->semanticRun >= PASSobj)
+ return;
+
if (d->type->ty == Terror)
{
error_at (make_location_t (d->loc),
@@ -400,6 +408,8 @@ public:
if (d->xhash)
d->xhash->accept (this);
+
+ d->semanticRun = PASSobj;
}
/* Finish semantic analysis of functions in vtbl for class CD. */
@@ -477,6 +487,9 @@ public:
void visit (ClassDeclaration *d)
{
+ if (d->semanticRun >= PASSobj)
+ return;
+
if (d->type->ty == Terror)
{
error_at (make_location_t (d->loc),
@@ -542,6 +555,8 @@ public:
tree ctype = TREE_TYPE (build_ctype (d->type));
if (TYPE_NAME (ctype))
d_pushdecl (TYPE_NAME (ctype));
+
+ d->semanticRun = PASSobj;
}
/* Write out compiler generated TypeInfo and vtables for the given interface
@@ -549,6 +564,9 @@ public:
void visit (InterfaceDeclaration *d)
{
+ if (d->semanticRun >= PASSobj)
+ return;
+
if (d->type->ty == Terror)
{
error_at (make_location_t (d->loc),
@@ -581,6 +599,8 @@ public:
tree ctype = TREE_TYPE (build_ctype (d->type));
if (TYPE_NAME (ctype))
d_pushdecl (TYPE_NAME (ctype));
+
+ d->semanticRun = PASSobj;
}
/* Write out compiler generated TypeInfo and initializer for the given
@@ -630,6 +650,9 @@ public:
void visit (VarDeclaration *d)
{
+ if (d->semanticRun >= PASSobj)
+ return;
+
if (d->type->ty == Terror)
{
error_at (make_location_t (d->loc),
@@ -755,6 +778,8 @@ public:
}
}
}
+
+ d->semanticRun = PASSobj;
}
/* Generate and compile a static TypeInfo declaration, but only if it is
@@ -762,12 +787,16 @@ public:
void visit (TypeInfoDeclaration *d)
{
+ if (d->semanticRun >= PASSobj)
+ return;
+
if (speculative_type_p (d->tinfo))
return;
tree t = get_typeinfo_decl (d);
DECL_INITIAL (t) = layout_typeinfo (d);
d_finish_decl (t);
+ d->semanticRun = PASSobj;
}
/* Finish up a function declaration and compile it all the way