From c222f2aa27a5d3cbc4583d2ae8ee60d623aaacc4 Mon Sep 17 00:00:00 2001
From: Roberto Raggi <roberto.raggi@nokia.com>
Date: Wed, 17 Jun 2009 16:08:01 +0200
Subject: [PATCH] Some cleanup in the AST nodes.

---
 src/libs/cplusplus/CppDocument.cpp        |   4 +-
 src/shared/cplusplus/AST.cpp              |  52 +++--
 src/shared/cplusplus/AST.h                |  60 ++++--
 src/shared/cplusplus/ASTClone.cpp         |  54 ++----
 src/shared/cplusplus/ASTVisit.cpp         | 219 +++++++++++-----------
 src/shared/cplusplus/ASTVisitor.h         |   4 +
 src/shared/cplusplus/ASTfwd.h             |   2 +
 src/shared/cplusplus/CheckDeclaration.cpp |  23 +--
 src/shared/cplusplus/CheckDeclarator.cpp  |   6 +-
 src/shared/cplusplus/CheckSpecifier.cpp   |   5 +-
 src/shared/cplusplus/CheckStatement.cpp   |   4 +-
 src/shared/cplusplus/Parser.cpp           |  71 ++++---
 src/shared/cplusplus/Parser.h             |   4 +-
 src/shared/cplusplus/PrettyPrinter.cpp    |  28 ++-
 14 files changed, 298 insertions(+), 238 deletions(-)

diff --git a/src/libs/cplusplus/CppDocument.cpp b/src/libs/cplusplus/CppDocument.cpp
index bd93b8bb318..3f4e04066d5 100644
--- a/src/libs/cplusplus/CppDocument.cpp
+++ b/src/libs/cplusplus/CppDocument.cpp
@@ -326,8 +326,8 @@ void Document::check()
         return; // nothing to do.
 
     if (TranslationUnitAST *ast = _translationUnit->ast()->asTranslationUnit()) {
-        for (DeclarationAST *decl = ast->declarations; decl; decl = decl->next) {
-            semantic.check(decl, globals);
+        for (DeclarationListAST *decl = ast->declarations; decl; decl = decl->next) {
+            semantic.check(decl->declaration, globals);
         }
     } else if (ExpressionAST *ast = _translationUnit->ast()->asExpression()) {
         semantic.check(ast, globals);
diff --git a/src/shared/cplusplus/AST.cpp b/src/shared/cplusplus/AST.cpp
index 6e66060e403..39c37951168 100644
--- a/src/shared/cplusplus/AST.cpp
+++ b/src/shared/cplusplus/AST.cpp
@@ -356,10 +356,8 @@ unsigned CatchClauseAST::lastToken() const
         return statement->lastToken();
     else if (rparen_token)
         return rparen_token + 1;
-    for (DeclarationAST *it = exception_declaration; it; it = it->next) {
-        if (! it->next)
-            return it->lastToken();
-    }
+    if (exception_declaration)
+        return exception_declaration->lastToken();
     if (lparen_token)
         return lparen_token + 1;
 
@@ -377,7 +375,7 @@ unsigned ClassSpecifierAST::lastToken() const
     if (rbrace_token)
         return rbrace_token + 1;
 
-    for (DeclarationAST *it = member_specifiers; it; it = it->next) {
+    for (DeclarationListAST *it = member_specifiers; it; it = it->next) {
         if (! it->next)
             return it->lastToken();
     }
@@ -405,6 +403,21 @@ unsigned ClassSpecifierAST::lastToken() const
 }
 
 
+unsigned StatementListAST::firstToken() const
+{
+    return statement->firstToken();
+}
+
+unsigned StatementListAST::lastToken() const
+{
+    for (const StatementListAST *it = this; it; it = it->next) {
+        if (! it->next)
+            return it->statement->lastToken();
+    }
+
+    return 0;
+}
+
 unsigned CompoundStatementAST::firstToken() const
 {
     return lbrace_token;
@@ -415,9 +428,9 @@ unsigned CompoundStatementAST::lastToken() const
     if (rbrace_token)
         return rbrace_token + 1;
 
-    for (StatementAST *it = statements; it ; it = it->next) {
+    for (StatementListAST *it = statements; it; it = it->next) {
         if (! it->next)
-            return it->lastToken();
+            return it->statement->lastToken();
     }
 
     return lbrace_token + 1;
@@ -540,6 +553,20 @@ unsigned CtorInitializerAST::lastToken() const
     return colon_token + 1;
 }
 
+unsigned DeclarationListAST::firstToken() const
+{
+    return declaration->firstToken();
+}
+
+unsigned DeclarationListAST::lastToken() const
+{
+    for (const DeclarationListAST *it = this; it; it = it->next) {
+        if (! it->next)
+            return it->declaration->lastToken();
+    }
+
+    return 0;
+}
 
 unsigned DeclaratorAST::firstToken() const
 {
@@ -986,7 +1013,7 @@ unsigned LinkageBodyAST::lastToken() const
     if (rbrace_token)
         return rbrace_token + 1;
 
-    for (DeclarationAST *it = declarations; it; it = it->next) {
+    for (DeclarationListAST *it = declarations; it; it = it->next) {
         if (! it->next)
             return it->lastToken();
     }
@@ -1006,6 +1033,7 @@ unsigned LinkageSpecificationAST::lastToken() const
         return declaration->lastToken();
     else if (extern_type_token)
         return extern_type_token + 1;
+
     return extern_token + 1;
 }
 
@@ -1553,7 +1581,7 @@ unsigned TemplateDeclarationAST::lastToken() const
     else if (greater_token)
         return greater_token + 1;
 
-    for (DeclarationAST *it = template_parameters; it; it = it->next) {
+    for (DeclarationListAST *it = template_parameters; it; it = it->next) {
         if (! it->next)
             return it->lastToken();
     }
@@ -1609,9 +1637,9 @@ unsigned TemplateTypeParameterAST::lastToken() const
     else if (greater_token)
         return greater_token + 1;
 
-    for (DeclarationAST *it = template_parameters; it; it = it->next) {
+    for (DeclarationListAST *it = template_parameters; it; it = it->next) {
         if (! it->next)
-            return it->lastToken();
+            return it->declaration->lastToken();
     }
 
     if (less_token)
@@ -1652,7 +1680,7 @@ unsigned TranslationUnitAST::firstToken() const
 
 unsigned TranslationUnitAST::lastToken() const
 {
-    for (DeclarationAST *it = declarations; it; it = it->next) {
+    for (DeclarationListAST *it = declarations; it; it = it->next) {
         if (! it->next)
             return it->lastToken();
     }
diff --git a/src/shared/cplusplus/AST.h b/src/shared/cplusplus/AST.h
index 7dfcf4cc5fa..5869b1a14d6 100644
--- a/src/shared/cplusplus/AST.h
+++ b/src/shared/cplusplus/AST.h
@@ -303,9 +303,6 @@ protected:
 
 class CPLUSPLUS_EXPORT StatementAST: public AST
 {
-public:
-    StatementAST *next;
-
 public:
     virtual StatementAST *asStatement()
     { return this; }
@@ -324,9 +321,6 @@ public:
 
 class CPLUSPLUS_EXPORT DeclarationAST: public AST
 {
-public:
-    DeclarationAST *next;
-
 public:
     virtual DeclarationAST *asDeclaration()
     { return this; }
@@ -334,6 +328,25 @@ public:
     virtual DeclarationAST *clone(MemoryPool *pool) const = 0;
 };
 
+class CPLUSPLUS_EXPORT DeclarationListAST: public AST
+{
+public:
+    DeclarationAST *declaration;
+    DeclarationListAST *next;
+
+public:
+    virtual DeclarationListAST *asDeclarationList()
+    { return this; }
+
+    virtual unsigned firstToken() const;
+    virtual unsigned lastToken() const;
+
+    virtual DeclarationListAST *clone(MemoryPool *pool) const;
+
+protected:
+    virtual void accept0(ASTVisitor *visitor);
+};
+
 class CPLUSPLUS_EXPORT CoreDeclaratorAST: public AST
 {
 public:
@@ -378,7 +391,7 @@ protected:
     virtual void accept0(ASTVisitor *visitor);
 };
 
-class CPLUSPLUS_EXPORT ExpressionListAST: public ExpressionAST
+class CPLUSPLUS_EXPORT ExpressionListAST: public AST
 {
 public:
     unsigned comma_token;
@@ -601,7 +614,7 @@ public:
     unsigned colon_token;
     BaseSpecifierAST *base_clause;
     unsigned lbrace_token;
-    DeclarationAST *member_specifiers;
+    DeclarationListAST *member_specifiers;
     unsigned rbrace_token;
 
 public: // annotations
@@ -641,11 +654,30 @@ protected:
     virtual void accept0(ASTVisitor *visitor);
 };
 
+class CPLUSPLUS_EXPORT StatementListAST: public AST
+{
+public:
+    StatementAST *statement;
+    StatementListAST *next;
+
+public:
+    virtual StatementListAST *asStatementList()
+    { return this; }
+
+    virtual unsigned firstToken() const;
+    virtual unsigned lastToken() const;
+
+    virtual StatementListAST *clone(MemoryPool *pool) const;
+
+protected:
+    virtual void accept0(ASTVisitor *visitor);
+};
+
 class CPLUSPLUS_EXPORT CompoundStatementAST: public StatementAST
 {
 public:
     unsigned lbrace_token;
-    StatementAST *statements;
+    StatementListAST *statements;
     unsigned rbrace_token;
 
 public: // annotations
@@ -1201,7 +1233,7 @@ class CPLUSPLUS_EXPORT LinkageBodyAST: public DeclarationAST
 {
 public:
     unsigned lbrace_token;
-    DeclarationAST *declarations;
+    DeclarationListAST *declarations;
     unsigned rbrace_token;
 
 public:
@@ -1607,7 +1639,7 @@ protected:
 class CPLUSPLUS_EXPORT ParameterDeclarationClauseAST: public AST
 {
 public:
-    DeclarationAST *parameter_declarations;
+    DeclarationListAST *parameter_declarations;
     unsigned dot_dot_dot_token;
 
 public:
@@ -2107,7 +2139,7 @@ public:
     unsigned export_token;
     unsigned template_token;
     unsigned less_token;
-    DeclarationAST *template_parameters;
+    DeclarationListAST *template_parameters;
     unsigned greater_token;
     DeclarationAST *declaration;
 
@@ -2146,7 +2178,7 @@ protected:
 class CPLUSPLUS_EXPORT TranslationUnitAST: public AST
 {
 public:
-    DeclarationAST *declarations;
+    DeclarationListAST *declarations;
 
 public:
     virtual TranslationUnitAST *asTranslationUnit()
@@ -2255,7 +2287,7 @@ class CPLUSPLUS_EXPORT TemplateTypeParameterAST: public DeclarationAST
 public:
     unsigned template_token;
     unsigned less_token;
-    DeclarationAST *template_parameters;
+    DeclarationListAST *template_parameters;
     unsigned greater_token;
     unsigned class_token;
     NameAST *name;
diff --git a/src/shared/cplusplus/ASTClone.cpp b/src/shared/cplusplus/ASTClone.cpp
index 77e4a6488ae..a48f7b4c8bc 100644
--- a/src/shared/cplusplus/ASTClone.cpp
+++ b/src/shared/cplusplus/ASTClone.cpp
@@ -28,6 +28,7 @@
 **************************************************************************/
 
 #include "AST.h"
+#include "ASTVisitor.h"
 
 CPLUSPLUS_BEGIN_NAMESPACE
 
@@ -83,6 +84,15 @@ TypeofSpecifierAST *TypeofSpecifierAST::clone(MemoryPool *pool) const
     return ast;
 }
 
+DeclarationListAST *DeclarationListAST::clone(MemoryPool *pool) const
+{
+    DeclarationListAST *ast = new (pool) DeclarationListAST;
+    // copy DeclarationListAST
+    if (declaration) ast->declaration = declaration->clone(pool);
+    if (next) ast->next = next->clone(pool);
+    return ast;
+}
+
 DeclaratorAST *DeclaratorAST::clone(MemoryPool *pool) const
 {
     DeclaratorAST *ast = new (pool) DeclaratorAST;
@@ -99,7 +109,6 @@ DeclaratorAST *DeclaratorAST::clone(MemoryPool *pool) const
 ExpressionListAST *ExpressionListAST::clone(MemoryPool *pool) const
 {
     ExpressionListAST *ast = new (pool) ExpressionListAST;
-    // copy ExpressionAST
     // copy ExpressionListAST
     ast->comma_token = comma_token;
     if (expression) ast->expression = expression->clone(pool);
@@ -111,7 +120,6 @@ SimpleDeclarationAST *SimpleDeclarationAST::clone(MemoryPool *pool) const
 {
     SimpleDeclarationAST *ast = new (pool) SimpleDeclarationAST;
     // copy DeclarationAST
-    if (next) ast->next = next->clone(pool);
     // copy SimpleDeclarationAST
     ast->qt_invokable_token = qt_invokable_token;
     if (decl_specifier_seq) ast->decl_specifier_seq = decl_specifier_seq->clone(pool);
@@ -124,7 +132,6 @@ EmptyDeclarationAST *EmptyDeclarationAST::clone(MemoryPool *pool) const
 {
     EmptyDeclarationAST *ast = new (pool) EmptyDeclarationAST;
     // copy DeclarationAST
-    if (next) ast->next = next->clone(pool);
     // copy EmptyDeclarationAST
     ast->semicolon_token = semicolon_token;
     return ast;
@@ -134,7 +141,6 @@ AccessDeclarationAST *AccessDeclarationAST::clone(MemoryPool *pool) const
 {
     AccessDeclarationAST *ast = new (pool) AccessDeclarationAST;
     // copy DeclarationAST
-    if (next) ast->next = next->clone(pool);
     // copy AccessDeclarationAST
     ast->access_specifier_token = access_specifier_token;
     ast->slots_token = slots_token;
@@ -146,7 +152,6 @@ AsmDefinitionAST *AsmDefinitionAST::clone(MemoryPool *pool) const
 {
     AsmDefinitionAST *ast = new (pool) AsmDefinitionAST;
     // copy DeclarationAST
-    if (next) ast->next = next->clone(pool);
     // copy AsmDefinitionAST
     ast->asm_token = asm_token;
     ast->volatile_token = volatile_token;
@@ -236,7 +241,6 @@ CaseStatementAST *CaseStatementAST::clone(MemoryPool *pool) const
 {
     CaseStatementAST *ast = new (pool) CaseStatementAST;
     // copy StatementAST
-    if (next) ast->next = next->clone(pool);
     // copy CaseStatementAST
     ast->case_token = case_token;
     if (expression) ast->expression = expression->clone(pool);
@@ -245,11 +249,19 @@ CaseStatementAST *CaseStatementAST::clone(MemoryPool *pool) const
     return ast;
 }
 
+StatementListAST *StatementListAST::clone(MemoryPool *pool) const
+{
+    StatementListAST *ast = new (pool) StatementListAST;
+    // copy StatementListAST
+    if (statement) ast->statement = statement->clone(pool);
+    if (next) ast->next = next->clone(pool);
+    return ast;
+}
+
 CompoundStatementAST *CompoundStatementAST::clone(MemoryPool *pool) const
 {
     CompoundStatementAST *ast = new (pool) CompoundStatementAST;
     // copy StatementAST
-    if (next) ast->next = next->clone(pool);
     // copy CompoundStatementAST
     ast->lbrace_token = lbrace_token;
     if (statements) ast->statements = statements->clone(pool);
@@ -308,7 +320,6 @@ DeclarationStatementAST *DeclarationStatementAST::clone(MemoryPool *pool) const
 {
     DeclarationStatementAST *ast = new (pool) DeclarationStatementAST;
     // copy StatementAST
-    if (next) ast->next = next->clone(pool);
     // copy DeclarationStatementAST
     if (declaration) ast->declaration = declaration->clone(pool);
     return ast;
@@ -388,7 +399,6 @@ DoStatementAST *DoStatementAST::clone(MemoryPool *pool) const
 {
     DoStatementAST *ast = new (pool) DoStatementAST;
     // copy StatementAST
-    if (next) ast->next = next->clone(pool);
     // copy DoStatementAST
     ast->do_token = do_token;
     if (statement) ast->statement = statement->clone(pool);
@@ -451,7 +461,6 @@ ExceptionDeclarationAST *ExceptionDeclarationAST::clone(MemoryPool *pool) const
 {
     ExceptionDeclarationAST *ast = new (pool) ExceptionDeclarationAST;
     // copy DeclarationAST
-    if (next) ast->next = next->clone(pool);
     // copy ExceptionDeclarationAST
     if (type_specifier) ast->type_specifier = type_specifier->clone(pool);
     if (declarator) ast->declarator = declarator->clone(pool);
@@ -475,7 +484,6 @@ ExpressionOrDeclarationStatementAST *ExpressionOrDeclarationStatementAST::clone(
 {
     ExpressionOrDeclarationStatementAST *ast = new (pool) ExpressionOrDeclarationStatementAST;
     // copy StatementAST
-    if (next) ast->next = next->clone(pool);
     // copy ExpressionOrDeclarationStatementAST
     if (expression) ast->expression = expression->clone(pool);
     if (declaration) ast->declaration = declaration->clone(pool);
@@ -486,7 +494,6 @@ ExpressionStatementAST *ExpressionStatementAST::clone(MemoryPool *pool) const
 {
     ExpressionStatementAST *ast = new (pool) ExpressionStatementAST;
     // copy StatementAST
-    if (next) ast->next = next->clone(pool);
     // copy ExpressionStatementAST
     if (expression) ast->expression = expression->clone(pool);
     ast->semicolon_token = semicolon_token;
@@ -497,7 +504,6 @@ FunctionDefinitionAST *FunctionDefinitionAST::clone(MemoryPool *pool) const
 {
     FunctionDefinitionAST *ast = new (pool) FunctionDefinitionAST;
     // copy DeclarationAST
-    if (next) ast->next = next->clone(pool);
     // copy FunctionDefinitionAST
     ast->qt_invokable_token = qt_invokable_token;
     if (decl_specifier_seq) ast->decl_specifier_seq = decl_specifier_seq->clone(pool);
@@ -511,7 +517,6 @@ ForStatementAST *ForStatementAST::clone(MemoryPool *pool) const
 {
     ForStatementAST *ast = new (pool) ForStatementAST;
     // copy StatementAST
-    if (next) ast->next = next->clone(pool);
     // copy ForStatementAST
     ast->for_token = for_token;
     ast->lparen_token = lparen_token;
@@ -528,7 +533,6 @@ IfStatementAST *IfStatementAST::clone(MemoryPool *pool) const
 {
     IfStatementAST *ast = new (pool) IfStatementAST;
     // copy StatementAST
-    if (next) ast->next = next->clone(pool);
     // copy IfStatementAST
     ast->if_token = if_token;
     ast->lparen_token = lparen_token;
@@ -555,7 +559,6 @@ LabeledStatementAST *LabeledStatementAST::clone(MemoryPool *pool) const
 {
     LabeledStatementAST *ast = new (pool) LabeledStatementAST;
     // copy StatementAST
-    if (next) ast->next = next->clone(pool);
     // copy LabeledStatementAST
     ast->label_token = label_token;
     ast->colon_token = colon_token;
@@ -567,7 +570,6 @@ LinkageBodyAST *LinkageBodyAST::clone(MemoryPool *pool) const
 {
     LinkageBodyAST *ast = new (pool) LinkageBodyAST;
     // copy DeclarationAST
-    if (next) ast->next = next->clone(pool);
     // copy LinkageBodyAST
     ast->lbrace_token = lbrace_token;
     if (declarations) ast->declarations = declarations->clone(pool);
@@ -579,7 +581,6 @@ LinkageSpecificationAST *LinkageSpecificationAST::clone(MemoryPool *pool) const
 {
     LinkageSpecificationAST *ast = new (pool) LinkageSpecificationAST;
     // copy DeclarationAST
-    if (next) ast->next = next->clone(pool);
     // copy LinkageSpecificationAST
     ast->extern_token = extern_token;
     ast->extern_type_token = extern_type_token;
@@ -683,7 +684,6 @@ NamespaceAST *NamespaceAST::clone(MemoryPool *pool) const
 {
     NamespaceAST *ast = new (pool) NamespaceAST;
     // copy DeclarationAST
-    if (next) ast->next = next->clone(pool);
     // copy NamespaceAST
     ast->namespace_token = namespace_token;
     ast->identifier_token = identifier_token;
@@ -696,7 +696,6 @@ NamespaceAliasDefinitionAST *NamespaceAliasDefinitionAST::clone(MemoryPool *pool
 {
     NamespaceAliasDefinitionAST *ast = new (pool) NamespaceAliasDefinitionAST;
     // copy DeclarationAST
-    if (next) ast->next = next->clone(pool);
     // copy NamespaceAliasDefinitionAST
     ast->namespace_token = namespace_token;
     ast->namespace_name_token = namespace_name_token;
@@ -777,7 +776,6 @@ ParameterDeclarationAST *ParameterDeclarationAST::clone(MemoryPool *pool) const
 {
     ParameterDeclarationAST *ast = new (pool) ParameterDeclarationAST;
     // copy DeclarationAST
-    if (next) ast->next = next->clone(pool);
     // copy ParameterDeclarationAST
     if (type_specifier) ast->type_specifier = type_specifier->clone(pool);
     if (declarator) ast->declarator = declarator->clone(pool);
@@ -926,7 +924,6 @@ BreakStatementAST *BreakStatementAST::clone(MemoryPool *pool) const
 {
     BreakStatementAST *ast = new (pool) BreakStatementAST;
     // copy StatementAST
-    if (next) ast->next = next->clone(pool);
     // copy BreakStatementAST
     ast->break_token = break_token;
     ast->semicolon_token = semicolon_token;
@@ -937,7 +934,6 @@ ContinueStatementAST *ContinueStatementAST::clone(MemoryPool *pool) const
 {
     ContinueStatementAST *ast = new (pool) ContinueStatementAST;
     // copy StatementAST
-    if (next) ast->next = next->clone(pool);
     // copy ContinueStatementAST
     ast->continue_token = continue_token;
     ast->semicolon_token = semicolon_token;
@@ -948,7 +944,6 @@ GotoStatementAST *GotoStatementAST::clone(MemoryPool *pool) const
 {
     GotoStatementAST *ast = new (pool) GotoStatementAST;
     // copy StatementAST
-    if (next) ast->next = next->clone(pool);
     // copy GotoStatementAST
     ast->goto_token = goto_token;
     ast->identifier_token = identifier_token;
@@ -960,7 +955,6 @@ ReturnStatementAST *ReturnStatementAST::clone(MemoryPool *pool) const
 {
     ReturnStatementAST *ast = new (pool) ReturnStatementAST;
     // copy StatementAST
-    if (next) ast->next = next->clone(pool);
     // copy ReturnStatementAST
     ast->return_token = return_token;
     if (expression) ast->expression = expression->clone(pool);
@@ -1030,7 +1024,6 @@ SwitchStatementAST *SwitchStatementAST::clone(MemoryPool *pool) const
 {
     SwitchStatementAST *ast = new (pool) SwitchStatementAST;
     // copy StatementAST
-    if (next) ast->next = next->clone(pool);
     // copy SwitchStatementAST
     ast->switch_token = switch_token;
     ast->lparen_token = lparen_token;
@@ -1054,7 +1047,6 @@ TemplateDeclarationAST *TemplateDeclarationAST::clone(MemoryPool *pool) const
 {
     TemplateDeclarationAST *ast = new (pool) TemplateDeclarationAST;
     // copy DeclarationAST
-    if (next) ast->next = next->clone(pool);
     // copy TemplateDeclarationAST
     ast->export_token = export_token;
     ast->template_token = template_token;
@@ -1087,7 +1079,6 @@ TryBlockStatementAST *TryBlockStatementAST::clone(MemoryPool *pool) const
 {
     TryBlockStatementAST *ast = new (pool) TryBlockStatementAST;
     // copy StatementAST
-    if (next) ast->next = next->clone(pool);
     // copy TryBlockStatementAST
     ast->try_token = try_token;
     if (statement) ast->statement = statement->clone(pool);
@@ -1099,7 +1090,6 @@ CatchClauseAST *CatchClauseAST::clone(MemoryPool *pool) const
 {
     CatchClauseAST *ast = new (pool) CatchClauseAST;
     // copy StatementAST
-    if (next) ast->next = next->clone(pool);
     // copy CatchClauseAST
     ast->catch_token = catch_token;
     ast->lparen_token = lparen_token;
@@ -1124,7 +1114,6 @@ TypenameTypeParameterAST *TypenameTypeParameterAST::clone(MemoryPool *pool) cons
 {
     TypenameTypeParameterAST *ast = new (pool) TypenameTypeParameterAST;
     // copy DeclarationAST
-    if (next) ast->next = next->clone(pool);
     // copy TypenameTypeParameterAST
     ast->classkey_token = classkey_token;
     if (name) ast->name = name->clone(pool);
@@ -1137,7 +1126,6 @@ TemplateTypeParameterAST *TemplateTypeParameterAST::clone(MemoryPool *pool) cons
 {
     TemplateTypeParameterAST *ast = new (pool) TemplateTypeParameterAST;
     // copy DeclarationAST
-    if (next) ast->next = next->clone(pool);
     // copy TemplateTypeParameterAST
     ast->template_token = template_token;
     ast->less_token = less_token;
@@ -1164,7 +1152,6 @@ UsingAST *UsingAST::clone(MemoryPool *pool) const
 {
     UsingAST *ast = new (pool) UsingAST;
     // copy DeclarationAST
-    if (next) ast->next = next->clone(pool);
     // copy UsingAST
     ast->using_token = using_token;
     ast->typename_token = typename_token;
@@ -1177,7 +1164,6 @@ UsingDirectiveAST *UsingDirectiveAST::clone(MemoryPool *pool) const
 {
     UsingDirectiveAST *ast = new (pool) UsingDirectiveAST;
     // copy DeclarationAST
-    if (next) ast->next = next->clone(pool);
     // copy UsingDirectiveAST
     ast->using_token = using_token;
     ast->namespace_token = namespace_token;
@@ -1190,7 +1176,6 @@ WhileStatementAST *WhileStatementAST::clone(MemoryPool *pool) const
 {
     WhileStatementAST *ast = new (pool) WhileStatementAST;
     // copy StatementAST
-    if (next) ast->next = next->clone(pool);
     // copy WhileStatementAST
     ast->while_token = while_token;
     ast->lparen_token = lparen_token;
@@ -1213,7 +1198,6 @@ ObjCClassDeclarationAST *ObjCClassDeclarationAST::clone(MemoryPool *pool) const
 {
     ObjCClassDeclarationAST *ast = new (pool) ObjCClassDeclarationAST;
     // copy DeclarationAST
-    if (next) ast->next = next->clone(pool);
     // copy ObjCClassDeclarationAST
     if (attributes) ast->attributes = attributes->clone(pool);
     ast->class_token = class_token;
diff --git a/src/shared/cplusplus/ASTVisit.cpp b/src/shared/cplusplus/ASTVisit.cpp
index 808931e2988..c904e6d3f3d 100644
--- a/src/shared/cplusplus/ASTVisit.cpp
+++ b/src/shared/cplusplus/ASTVisit.cpp
@@ -37,7 +37,6 @@ void SimpleSpecifierAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit SimpleSpecifierAST
         // visit SpecifierAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -46,9 +45,9 @@ void AttributeSpecifierAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit AttributeSpecifierAST
-        accept(attributes, visitor);
+        for (AttributeAST *it = attributes; it; it = it->next)
+            accept(it, visitor);
         // visit SpecifierAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -57,8 +56,8 @@ void AttributeAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit AttributeAST
-        accept(expression_list, visitor);
-        accept(next, visitor);
+        for (ExpressionListAST *it = expression_list; it; it = it->next)
+            accept(it, visitor);
     }
     visitor->endVisit(this);
 }
@@ -69,7 +68,15 @@ void TypeofSpecifierAST::accept0(ASTVisitor *visitor)
         // visit TypeofSpecifierAST
         accept(expression, visitor);
         // visit SpecifierAST
-        accept(next, visitor);
+    }
+    visitor->endVisit(this);
+}
+
+void DeclarationListAST::accept0(ASTVisitor *visitor)
+{
+    if (visitor->visit(this)) {
+        // visit DeclarationListAST
+        accept(declaration, visitor);
     }
     visitor->endVisit(this);
 }
@@ -78,10 +85,13 @@ void DeclaratorAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit DeclaratorAST
-        accept(ptr_operators, visitor);
+        for (PtrOperatorAST *it = ptr_operators; it; it = it->next)
+            accept(it, visitor);
         accept(core_declarator, visitor);
-        accept(postfix_declarators, visitor);
-        accept(attributes, visitor);
+        for (PostfixDeclaratorAST *it = postfix_declarators; it; it = it->next)
+            accept(it, visitor);
+        for (SpecifierAST *it = attributes; it; it = it->next)
+            accept(it, visitor);
         accept(initializer, visitor);
     }
     visitor->endVisit(this);
@@ -92,8 +102,6 @@ void ExpressionListAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit ExpressionListAST
         accept(expression, visitor);
-        accept(next, visitor);
-        // visit ExpressionAST
     }
     visitor->endVisit(this);
 }
@@ -102,10 +110,11 @@ void SimpleDeclarationAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit SimpleDeclarationAST
-        accept(decl_specifier_seq, visitor);
-        accept(declarators, visitor);
+        for (SpecifierAST *it = decl_specifier_seq; it; it = it->next)
+            accept(it, visitor);
+        for (DeclaratorListAST *it = declarators; it; it = it->next)
+            accept(it, visitor);
         // visit DeclarationAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -115,7 +124,6 @@ void EmptyDeclarationAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit EmptyDeclarationAST
         // visit DeclarationAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -125,7 +133,6 @@ void AccessDeclarationAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit AccessDeclarationAST
         // visit DeclarationAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -135,7 +142,6 @@ void AsmDefinitionAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit AsmDefinitionAST
         // visit DeclarationAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -145,7 +151,6 @@ void BaseSpecifierAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit BaseSpecifierAST
         accept(name, visitor);
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -197,12 +202,14 @@ void ClassSpecifierAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit ClassSpecifierAST
-        accept(attributes, visitor);
+        for (SpecifierAST *it = attributes; it; it = it->next)
+            accept(it, visitor);
         accept(name, visitor);
-        accept(base_clause, visitor);
-        accept(member_specifiers, visitor);
+        for (BaseSpecifierAST *it = base_clause; it; it = it->next)
+            accept(it, visitor);
+        for (DeclarationListAST *it = member_specifiers; it; it = it->next)
+            accept(it, visitor);
         // visit SpecifierAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -214,7 +221,15 @@ void CaseStatementAST::accept0(ASTVisitor *visitor)
         accept(expression, visitor);
         accept(statement, visitor);
         // visit StatementAST
-        accept(next, visitor);
+    }
+    visitor->endVisit(this);
+}
+
+void StatementListAST::accept0(ASTVisitor *visitor)
+{
+    if (visitor->visit(this)) {
+        // visit StatementListAST
+        accept(statement, visitor);
     }
     visitor->endVisit(this);
 }
@@ -223,9 +238,9 @@ void CompoundStatementAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit CompoundStatementAST
-        accept(statements, visitor);
+        for (StatementListAST *it = statements; it; it = it->next)
+            accept(it, visitor);
         // visit StatementAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -234,7 +249,8 @@ void ConditionAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit ConditionAST
-        accept(type_specifier, visitor);
+        for (SpecifierAST *it = type_specifier; it; it = it->next)
+            accept(it, visitor);
         accept(declarator, visitor);
         // visit ExpressionAST
     }
@@ -268,7 +284,8 @@ void CtorInitializerAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit CtorInitializerAST
-        accept(member_initializers, visitor);
+        for (MemInitializerAST *it = member_initializers; it; it = it->next)
+            accept(it, visitor);
     }
     visitor->endVisit(this);
 }
@@ -279,7 +296,6 @@ void DeclarationStatementAST::accept0(ASTVisitor *visitor)
         // visit DeclarationStatementAST
         accept(declaration, visitor);
         // visit StatementAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -309,11 +325,11 @@ void FunctionDeclaratorAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit FunctionDeclaratorAST
         accept(parameters, visitor);
-        accept(cv_qualifier_seq, visitor);
+        for (SpecifierAST *it = cv_qualifier_seq; it; it = it->next)
+            accept(it, visitor);
         accept(exception_specification, visitor);
         accept(as_cpp_initializer, visitor);
         // visit PostfixDeclaratorAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -324,7 +340,6 @@ void ArrayDeclaratorAST::accept0(ASTVisitor *visitor)
         // visit ArrayDeclaratorAST
         accept(expression, visitor);
         // visit PostfixDeclaratorAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -334,7 +349,6 @@ void DeclaratorListAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit DeclaratorListAST
         accept(declarator, visitor);
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -356,7 +370,6 @@ void DoStatementAST::accept0(ASTVisitor *visitor)
         accept(statement, visitor);
         accept(expression, visitor);
         // visit StatementAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -367,7 +380,6 @@ void NamedTypeSpecifierAST::accept0(ASTVisitor *visitor)
         // visit NamedTypeSpecifierAST
         accept(name, visitor);
         // visit SpecifierAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -378,7 +390,6 @@ void ElaboratedTypeSpecifierAST::accept0(ASTVisitor *visitor)
         // visit ElaboratedTypeSpecifierAST
         accept(name, visitor);
         // visit SpecifierAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -388,9 +399,9 @@ void EnumSpecifierAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit EnumSpecifierAST
         accept(name, visitor);
-        accept(enumerators, visitor);
+        for (EnumeratorAST *it = enumerators; it; it = it->next)
+            accept(it, visitor);
         // visit SpecifierAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -400,7 +411,6 @@ void EnumeratorAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit EnumeratorAST
         accept(expression, visitor);
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -409,10 +419,10 @@ void ExceptionDeclarationAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit ExceptionDeclarationAST
-        accept(type_specifier, visitor);
+        for (SpecifierAST *it = type_specifier; it; it = it->next)
+            accept(it, visitor);
         accept(declarator, visitor);
         // visit DeclarationAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -421,7 +431,8 @@ void ExceptionSpecificationAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit ExceptionSpecificationAST
-        accept(type_ids, visitor);
+        for (ExpressionListAST *it = type_ids; it; it = it->next)
+            accept(it, visitor);
     }
     visitor->endVisit(this);
 }
@@ -433,7 +444,6 @@ void ExpressionOrDeclarationStatementAST::accept0(ASTVisitor *visitor)
         accept(expression, visitor);
         accept(declaration, visitor);
         // visit StatementAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -444,7 +454,6 @@ void ExpressionStatementAST::accept0(ASTVisitor *visitor)
         // visit ExpressionStatementAST
         accept(expression, visitor);
         // visit StatementAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -453,12 +462,12 @@ void FunctionDefinitionAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit FunctionDefinitionAST
-        accept(decl_specifier_seq, visitor);
+        for (SpecifierAST *it = decl_specifier_seq; it; it = it->next)
+            accept(it, visitor);
         accept(declarator, visitor);
         accept(ctor_initializer, visitor);
         accept(function_body, visitor);
         // visit DeclarationAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -472,7 +481,6 @@ void ForStatementAST::accept0(ASTVisitor *visitor)
         accept(expression, visitor);
         accept(statement, visitor);
         // visit StatementAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -485,7 +493,6 @@ void IfStatementAST::accept0(ASTVisitor *visitor)
         accept(statement, visitor);
         accept(else_statement, visitor);
         // visit StatementAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -494,7 +501,8 @@ void ArrayInitializerAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit ArrayInitializerAST
-        accept(expression_list, visitor);
+        for (ExpressionListAST *it = expression_list; it; it = it->next)
+            accept(it, visitor);
         // visit ExpressionAST
     }
     visitor->endVisit(this);
@@ -506,7 +514,6 @@ void LabeledStatementAST::accept0(ASTVisitor *visitor)
         // visit LabeledStatementAST
         accept(statement, visitor);
         // visit StatementAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -515,9 +522,9 @@ void LinkageBodyAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit LinkageBodyAST
-        accept(declarations, visitor);
+        for (DeclarationListAST *it = declarations; it; it = it->next)
+            accept(it, visitor);
         // visit DeclarationAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -528,7 +535,6 @@ void LinkageSpecificationAST::accept0(ASTVisitor *visitor)
         // visit LinkageSpecificationAST
         accept(declaration, visitor);
         // visit DeclarationAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -539,7 +545,6 @@ void MemInitializerAST::accept0(ASTVisitor *visitor)
         // visit MemInitializerAST
         accept(name, visitor);
         accept(expression, visitor);
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -549,7 +554,6 @@ void NestedNameSpecifierAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit NestedNameSpecifierAST
         accept(class_or_namespace_name, visitor);
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -558,7 +562,8 @@ void QualifiedNameAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit QualifiedNameAST
-        accept(nested_name_specifier, visitor);
+        for (NestedNameSpecifierAST *it = nested_name_specifier; it; it = it->next)
+            accept(it, visitor);
         accept(unqualified_name, visitor);
         // visit NameAST
         // visit ExpressionAST
@@ -581,8 +586,10 @@ void ConversionFunctionIdAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit ConversionFunctionIdAST
-        accept(type_specifier, visitor);
-        accept(ptr_operators, visitor);
+        for (SpecifierAST *it = type_specifier; it; it = it->next)
+            accept(it, visitor);
+        for (PtrOperatorAST *it = ptr_operators; it; it = it->next)
+            accept(it, visitor);
         // visit NameAST
         // visit ExpressionAST
     }
@@ -613,7 +620,8 @@ void TemplateIdAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit TemplateIdAST
-        accept(template_arguments, visitor);
+        for (TemplateArgumentListAST *it = template_arguments; it; it = it->next)
+            accept(it, visitor);
         // visit NameAST
         // visit ExpressionAST
     }
@@ -624,10 +632,10 @@ void NamespaceAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit NamespaceAST
-        accept(attributes, visitor);
+        for (SpecifierAST *it = attributes; it; it = it->next)
+            accept(it, visitor);
         accept(linkage_body, visitor);
         // visit DeclarationAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -638,7 +646,6 @@ void NamespaceAliasDefinitionAST::accept0(ASTVisitor *visitor)
         // visit NamespaceAliasDefinitionAST
         accept(name, visitor);
         // visit DeclarationAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -647,7 +654,8 @@ void NewPlacementAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit NewPlacementAST
-        accept(expression_list, visitor);
+        for (ExpressionListAST *it = expression_list; it; it = it->next)
+            accept(it, visitor);
     }
     visitor->endVisit(this);
 }
@@ -657,7 +665,6 @@ void NewArrayDeclaratorAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit NewArrayDeclaratorAST
         accept(expression, visitor);
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -688,9 +695,12 @@ void NewTypeIdAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit NewTypeIdAST
-        accept(type_specifier, visitor);
-        accept(ptr_operators, visitor);
-        accept(new_array_declarators, visitor);
+        for (SpecifierAST *it = type_specifier; it; it = it->next)
+            accept(it, visitor);
+        for (PtrOperatorAST *it = ptr_operators; it; it = it->next)
+            accept(it, visitor);
+        for (NewArrayDeclaratorAST *it = new_array_declarators; it; it = it->next)
+            accept(it, visitor);
     }
     visitor->endVisit(this);
 }
@@ -707,11 +717,11 @@ void ParameterDeclarationAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit ParameterDeclarationAST
-        accept(type_specifier, visitor);
+        for (SpecifierAST *it = type_specifier; it; it = it->next)
+            accept(it, visitor);
         accept(declarator, visitor);
         accept(expression, visitor);
         // visit DeclarationAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -720,7 +730,8 @@ void ParameterDeclarationClauseAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit ParameterDeclarationClauseAST
-        accept(parameter_declarations, visitor);
+        for (DeclarationListAST *it = parameter_declarations; it; it = it->next)
+            accept(it, visitor);
     }
     visitor->endVisit(this);
 }
@@ -729,9 +740,9 @@ void CallAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit CallAST
-        accept(expression_list, visitor);
+        for (ExpressionListAST *it = expression_list; it; it = it->next)
+            accept(it, visitor);
         // visit PostfixAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -742,7 +753,6 @@ void ArrayAccessAST::accept0(ASTVisitor *visitor)
         // visit ArrayAccessAST
         accept(expression, visitor);
         // visit PostfixAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -752,7 +762,6 @@ void PostIncrDecrAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit PostIncrDecrAST
         // visit PostfixAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -763,7 +772,6 @@ void MemberAccessAST::accept0(ASTVisitor *visitor)
         // visit MemberAccessAST
         accept(member_name, visitor);
         // visit PostfixAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -783,7 +791,8 @@ void TypenameCallExpressionAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit TypenameCallExpressionAST
         accept(name, visitor);
-        accept(expression_list, visitor);
+        for (ExpressionListAST *it = expression_list; it; it = it->next)
+            accept(it, visitor);
         // visit ExpressionAST
     }
     visitor->endVisit(this);
@@ -793,8 +802,10 @@ void TypeConstructorCallAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit TypeConstructorCallAST
-        accept(type_specifier, visitor);
-        accept(expression_list, visitor);
+        for (SpecifierAST *it = type_specifier; it; it = it->next)
+            accept(it, visitor);
+        for (ExpressionListAST *it = expression_list; it; it = it->next)
+            accept(it, visitor);
         // visit ExpressionAST
     }
     visitor->endVisit(this);
@@ -805,7 +816,8 @@ void PostfixExpressionAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit PostfixExpressionAST
         accept(base_expression, visitor);
-        accept(postfix_expressions, visitor);
+        for (PostfixAST *it = postfix_expressions; it; it = it->next)
+            accept(it, visitor);
         // visit ExpressionAST
     }
     visitor->endVisit(this);
@@ -815,10 +827,11 @@ void PointerToMemberAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit PointerToMemberAST
-        accept(nested_name_specifier, visitor);
-        accept(cv_qualifier_seq, visitor);
+        for (NestedNameSpecifierAST *it = nested_name_specifier; it; it = it->next)
+            accept(it, visitor);
+        for (SpecifierAST *it = cv_qualifier_seq; it; it = it->next)
+            accept(it, visitor);
         // visit PtrOperatorAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -827,9 +840,9 @@ void PointerAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit PointerAST
-        accept(cv_qualifier_seq, visitor);
+        for (SpecifierAST *it = cv_qualifier_seq; it; it = it->next)
+            accept(it, visitor);
         // visit PtrOperatorAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -839,7 +852,6 @@ void ReferenceAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit ReferenceAST
         // visit PtrOperatorAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -849,7 +861,6 @@ void BreakStatementAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit BreakStatementAST
         // visit StatementAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -859,7 +870,6 @@ void ContinueStatementAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit ContinueStatementAST
         // visit StatementAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -869,7 +879,6 @@ void GotoStatementAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit GotoStatementAST
         // visit StatementAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -880,7 +889,6 @@ void ReturnStatementAST::accept0(ASTVisitor *visitor)
         // visit ReturnStatementAST
         accept(expression, visitor);
         // visit StatementAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -936,7 +944,6 @@ void StringLiteralAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit StringLiteralAST
-        accept(next, visitor);
         // visit ExpressionAST
     }
     visitor->endVisit(this);
@@ -949,7 +956,6 @@ void SwitchStatementAST::accept0(ASTVisitor *visitor)
         accept(condition, visitor);
         accept(statement, visitor);
         // visit StatementAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -959,7 +965,6 @@ void TemplateArgumentListAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit TemplateArgumentListAST
         accept(template_argument, visitor);
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -968,10 +973,10 @@ void TemplateDeclarationAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit TemplateDeclarationAST
-        accept(template_parameters, visitor);
+        for (DeclarationListAST *it = template_parameters; it; it = it->next)
+            accept(it, visitor);
         accept(declaration, visitor);
         // visit DeclarationAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -990,7 +995,8 @@ void TranslationUnitAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit TranslationUnitAST
-        accept(declarations, visitor);
+        for (DeclarationListAST *it = declarations; it; it = it->next)
+            accept(it, visitor);
     }
     visitor->endVisit(this);
 }
@@ -1000,9 +1006,9 @@ void TryBlockStatementAST::accept0(ASTVisitor *visitor)
     if (visitor->visit(this)) {
         // visit TryBlockStatementAST
         accept(statement, visitor);
-        accept(catch_clause_seq, visitor);
+        for (CatchClauseAST *it = catch_clause_seq; it; it = it->next)
+            accept(it, visitor);
         // visit StatementAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -1013,9 +1019,7 @@ void CatchClauseAST::accept0(ASTVisitor *visitor)
         // visit CatchClauseAST
         accept(exception_declaration, visitor);
         accept(statement, visitor);
-        accept(next, visitor);
         // visit StatementAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -1024,7 +1028,8 @@ void TypeIdAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit TypeIdAST
-        accept(type_specifier, visitor);
+        for (SpecifierAST *it = type_specifier; it; it = it->next)
+            accept(it, visitor);
         accept(declarator, visitor);
         // visit ExpressionAST
     }
@@ -1038,7 +1043,6 @@ void TypenameTypeParameterAST::accept0(ASTVisitor *visitor)
         accept(name, visitor);
         accept(type_id, visitor);
         // visit DeclarationAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -1047,11 +1051,11 @@ void TemplateTypeParameterAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit TemplateTypeParameterAST
-        accept(template_parameters, visitor);
+        for (DeclarationListAST *it = template_parameters; it; it = it->next)
+            accept(it, visitor);
         accept(name, visitor);
         accept(type_id, visitor);
         // visit DeclarationAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -1072,7 +1076,6 @@ void UsingAST::accept0(ASTVisitor *visitor)
         // visit UsingAST
         accept(name, visitor);
         // visit DeclarationAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -1083,7 +1086,6 @@ void UsingDirectiveAST::accept0(ASTVisitor *visitor)
         // visit UsingDirectiveAST
         accept(name, visitor);
         // visit DeclarationAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -1095,7 +1097,6 @@ void WhileStatementAST::accept0(ASTVisitor *visitor)
         accept(condition, visitor);
         accept(statement, visitor);
         // visit StatementAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -1104,7 +1105,6 @@ void IdentifierListAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit IdentifierListAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
@@ -1113,10 +1113,11 @@ void ObjCClassDeclarationAST::accept0(ASTVisitor *visitor)
 {
     if (visitor->visit(this)) {
         // visit ObjCClassDeclarationAST
-        accept(attributes, visitor);
-        accept(identifier_list, visitor);
+        for (SpecifierAST *it = attributes; it; it = it->next)
+            accept(it, visitor);
+        for (IdentifierListAST *it = identifier_list; it; it = it->next)
+            accept(it, visitor);
         // visit DeclarationAST
-        accept(next, visitor);
     }
     visitor->endVisit(this);
 }
diff --git a/src/shared/cplusplus/ASTVisitor.h b/src/shared/cplusplus/ASTVisitor.h
index 71c8c2fb892..45c8d89efc7 100644
--- a/src/shared/cplusplus/ASTVisitor.h
+++ b/src/shared/cplusplus/ASTVisitor.h
@@ -171,6 +171,7 @@ public:
     virtual bool visit(SimpleNameAST *) { return true; }
     virtual bool visit(SimpleSpecifierAST *) { return true; }
     virtual bool visit(SizeofExpressionAST *) { return true; }
+    virtual bool visit(StatementListAST *) { return true; }
     virtual bool visit(StringLiteralAST *) { return true; }
     virtual bool visit(SwitchStatementAST *) { return true; }
     virtual bool visit(TemplateArgumentListAST *) { return true; }
@@ -197,6 +198,8 @@ public:
     virtual bool visit(IdentifierListAST *) { return true; }
     virtual bool visit(ObjCClassDeclarationAST *) { return true; }
 
+    virtual bool visit(DeclarationListAST *) { return true; }
+    virtual void endVisit(DeclarationListAST *) { }
 
 
     virtual void endVisit(AccessDeclarationAST *) { }
@@ -276,6 +279,7 @@ public:
     virtual void endVisit(SimpleNameAST *) { }
     virtual void endVisit(SimpleSpecifierAST *) { }
     virtual void endVisit(SizeofExpressionAST *) { }
+    virtual void endVisit(StatementListAST *) { }
     virtual void endVisit(StringLiteralAST *) { }
     virtual void endVisit(SwitchStatementAST *) { }
     virtual void endVisit(TemplateArgumentListAST *) { }
diff --git a/src/shared/cplusplus/ASTfwd.h b/src/shared/cplusplus/ASTfwd.h
index 71287c98ac4..0f4d9581bfb 100644
--- a/src/shared/cplusplus/ASTfwd.h
+++ b/src/shared/cplusplus/ASTfwd.h
@@ -83,6 +83,7 @@ class CoreDeclaratorAST;
 class CppCastExpressionAST;
 class CtorInitializerAST;
 class DeclarationAST;
+class DeclarationListAST;
 class DeclarationStatementAST;
 class DeclaratorAST;
 class DeclaratorIdAST;
@@ -143,6 +144,7 @@ class SimpleSpecifierAST;
 class SizeofExpressionAST;
 class SpecifierAST;
 class StatementAST;
+class StatementListAST;
 class StringLiteralAST;
 class SwitchStatementAST;
 class TemplateArgumentListAST;
diff --git a/src/shared/cplusplus/CheckDeclaration.cpp b/src/shared/cplusplus/CheckDeclaration.cpp
index 42004bcc8ea..79392bf4e76 100644
--- a/src/shared/cplusplus/CheckDeclaration.cpp
+++ b/src/shared/cplusplus/CheckDeclaration.cpp
@@ -311,27 +311,20 @@ bool CheckDeclaration::visit(FunctionDefinitionAST *ast)
     semantic()->switchMethodKey(previousMethodKey);
     semantic()->switchVisibility(previousVisibility);
 
-    if (ast->next && ast->next->asEmptyDeclaration()) {
-        translationUnit()->warning(ast->next->firstToken(),
-                                   "unnecessary semicolon after function block");
-    }
-
     return false;
 }
 
 bool CheckDeclaration::visit(LinkageBodyAST *ast)
 {
-    for (DeclarationAST *decl = ast->declarations; decl; decl = decl->next) {
-       semantic()->check(decl, _scope);
+    for (DeclarationListAST *decl = ast->declarations; decl; decl = decl->next) {
+       semantic()->check(decl->declaration, _scope);
     }
     return false;
 }
 
 bool CheckDeclaration::visit(LinkageSpecificationAST *ast)
 {
-    for (DeclarationAST *decl = ast->declaration; decl; decl = decl->next) {
-        semantic()->check(decl, _scope);
-    }
+    semantic()->check(ast->declaration, _scope);
     return false;
 }
 
@@ -352,11 +345,6 @@ bool CheckDeclaration::visit(NamespaceAST *ast)
     _scope->enterSymbol(ns);
     semantic()->check(ast->linkage_body, ns->members()); // ### we'll do the merge later.
 
-    if (ast->next && ast->next->asEmptyDeclaration()) {
-        translationUnit()->warning(ast->next->firstToken(),
-                                   "unnecessary semicolon after namespace");
-    }
-
     return false;
 }
 
@@ -389,9 +377,8 @@ bool CheckDeclaration::visit(ParameterDeclarationAST *ast)
 bool CheckDeclaration::visit(TemplateDeclarationAST *ast)
 {
     Scope *previousScope = switchScope(new Scope(_scope->owner()));
-    for (DeclarationAST *param = ast->template_parameters; param;
-            param = param->next) {
-       semantic()->check(param, _scope);
+    for (DeclarationListAST *param = ast->template_parameters; param; param = param->next) {
+       semantic()->check(param->declaration, _scope);
     }
 
     Scope *templateParameters = switchScope(previousScope);
diff --git a/src/shared/cplusplus/CheckDeclarator.cpp b/src/shared/cplusplus/CheckDeclarator.cpp
index 225754521cf..aaf324cc214 100644
--- a/src/shared/cplusplus/CheckDeclarator.cpp
+++ b/src/shared/cplusplus/CheckDeclarator.cpp
@@ -162,9 +162,9 @@ bool CheckDeclarator::visit(FunctionDeclaratorAST *ast)
     fun->setReturnType(_fullySpecifiedType);
 
     if (ast->parameters) {
-        DeclarationAST *parameter_declarations = ast->parameters->parameter_declarations;
-        for (DeclarationAST *decl = parameter_declarations; decl; decl = decl->next) {
-            semantic()->check(decl, fun->arguments());
+        DeclarationListAST *parameter_declarations = ast->parameters->parameter_declarations;
+        for (DeclarationListAST *decl = parameter_declarations; decl; decl = decl->next) {
+            semantic()->check(decl->declaration, fun->arguments());
         }
 
         if (ast->parameters->dot_dot_dot_token)
diff --git a/src/shared/cplusplus/CheckSpecifier.cpp b/src/shared/cplusplus/CheckSpecifier.cpp
index 3f3fffb580d..c112561f168 100644
--- a/src/shared/cplusplus/CheckSpecifier.cpp
+++ b/src/shared/cplusplus/CheckSpecifier.cpp
@@ -335,9 +335,8 @@ bool CheckSpecifier::visit(ClassSpecifierAST *ast)
     int previousVisibility = semantic()->switchVisibility(visibility);
     int previousMethodKey = semantic()->switchMethodKey(Function::NormalMethod);
 
-    for (DeclarationAST *member = ast->member_specifiers;
-            member; member = member->next) {
-        semantic()->check(member, klass->members());
+    for (DeclarationListAST *member = ast->member_specifiers; member; member = member->next) {
+        semantic()->check(member->declaration, klass->members());
     }
 
     (void) semantic()->switchMethodKey(previousMethodKey);
diff --git a/src/shared/cplusplus/CheckStatement.cpp b/src/shared/cplusplus/CheckStatement.cpp
index 06651fae75a..433dc5c8730 100644
--- a/src/shared/cplusplus/CheckStatement.cpp
+++ b/src/shared/cplusplus/CheckStatement.cpp
@@ -104,8 +104,8 @@ bool CheckStatement::visit(CompoundStatementAST *ast)
     ast->symbol = block;
     _scope->enterSymbol(block);
     Scope *previousScope = switchScope(block->members());
-    for (StatementAST *it = ast->statements; it; it = it->next) {
-        semantic()->check(it, _scope);
+    for (StatementListAST *it = ast->statements; it; it = it->next) {
+        semantic()->check(it->statement, _scope);
     }
     (void) switchScope(previousScope);
     return false;
diff --git a/src/shared/cplusplus/Parser.cpp b/src/shared/cplusplus/Parser.cpp
index 4f38bbe726f..a2c0d2edda5 100644
--- a/src/shared/cplusplus/Parser.cpp
+++ b/src/shared/cplusplus/Parser.cpp
@@ -353,14 +353,17 @@ bool Parser::parseName(NameAST *&node, bool acceptTemplateId)
 bool Parser::parseTranslationUnit(TranslationUnitAST *&node)
 {
     TranslationUnitAST *ast = new (_pool) TranslationUnitAST;
-    DeclarationAST **decl = &ast->declarations;
+    DeclarationListAST **decl = &ast->declarations;
 
     while (LA()) {
         unsigned start_declaration = cursor();
 
-        if (parseDeclaration(*decl)) {
-            if (*decl)
-                decl = &(*decl)->next;
+        DeclarationAST *declaration = 0;
+
+        if (parseDeclaration(declaration)) {
+            *decl = new (_pool) DeclarationListAST;
+            (*decl)->declaration = declaration;
+            decl = &(*decl)->next;
         } else {
             rewind(start_declaration + 1);
             skipUntilDeclaration();
@@ -469,16 +472,18 @@ bool Parser::parseLinkageBody(DeclarationAST *&node)
     if (LA() == T_LBRACE) {
         LinkageBodyAST *ast = new (_pool) LinkageBodyAST;
         ast->lbrace_token = consumeToken();
-        DeclarationAST **declaration_ptr = &ast->declarations;
+        DeclarationListAST **declaration_ptr = &ast->declarations;
 
         while (int tk = LA()) {
             if (tk == T_RBRACE)
                 break;
 
             unsigned start_declaration = cursor();
-            if (parseDeclaration(*declaration_ptr)) {
-                if (*declaration_ptr) // ### remove me
-                    declaration_ptr = &(*declaration_ptr)->next;
+            DeclarationAST *declaration = 0;
+            if (parseDeclaration(declaration)) {
+                *declaration_ptr = new (_pool) DeclarationListAST;
+                (*declaration_ptr)->declaration = declaration;
+                declaration_ptr = &(*declaration_ptr)->next;
             } else {
                 rewind(start_declaration + 1);
                 skipUntilDeclaration();
@@ -1179,16 +1184,24 @@ bool Parser::parseEnumSpecifier(SpecifierAST *&node)
     return false;
 }
 
-bool Parser::parseTemplateParameterList(DeclarationAST *&node)
+bool Parser::parseTemplateParameterList(DeclarationListAST *&node)
 {
-    DeclarationAST **template_parameter_ptr = &node;
-    if (parseTemplateParameter(*template_parameter_ptr)) {
+    DeclarationListAST **template_parameter_ptr = &node;
+    DeclarationAST *declaration = 0;
+    if (parseTemplateParameter(declaration)) {
+        *template_parameter_ptr = new (_pool) DeclarationListAST;
+        (*template_parameter_ptr)->declaration = declaration;
         template_parameter_ptr = &(*template_parameter_ptr)->next;
+
         while (LA() == T_COMMA) {
             consumeToken(); // XXX Store this token somewhere
 
-            if (parseTemplateParameter(*template_parameter_ptr))
+            declaration = 0;
+            if (parseTemplateParameter(declaration)) {
+                *template_parameter_ptr = new (_pool) DeclarationListAST;
+                (*template_parameter_ptr)->declaration = declaration;
                 template_parameter_ptr = &(*template_parameter_ptr)->next;
+            }
         }
         return true;
     }
@@ -1272,7 +1285,7 @@ bool Parser::parseTypeId(ExpressionAST *&node)
 
 bool Parser::parseParameterDeclarationClause(ParameterDeclarationClauseAST *&node)
 {
-    DeclarationAST *parameter_declarations = 0;
+    DeclarationListAST *parameter_declarations = 0;
     if (LA() != T_DOT_DOT_DOT)
         parseParameterDeclarationList(parameter_declarations);
     unsigned dot_dot_dot_token = 0;
@@ -1288,10 +1301,13 @@ bool Parser::parseParameterDeclarationClause(ParameterDeclarationClauseAST *&nod
     return true;
 }
 
-bool Parser::parseParameterDeclarationList(DeclarationAST *&node)
+bool Parser::parseParameterDeclarationList(DeclarationListAST *&node)
 {
-    DeclarationAST **parameter_declaration_ptr = &node;
-    if (parseParameterDeclaration(*parameter_declaration_ptr)) {
+    DeclarationListAST **parameter_declaration_ptr = &node;
+    DeclarationAST *declaration = 0;
+    if (parseParameterDeclaration(declaration)) {
+        *parameter_declaration_ptr = new (_pool) DeclarationListAST;
+        (*parameter_declaration_ptr)->declaration = declaration;
         parameter_declaration_ptr = &(*parameter_declaration_ptr)->next;
         while (LA() == T_COMMA) {
             consumeToken();
@@ -1299,8 +1315,12 @@ bool Parser::parseParameterDeclarationList(DeclarationAST *&node)
             if (LA() == T_DOT_DOT_DOT)
                 break;
 
-            if (parseParameterDeclaration(*parameter_declaration_ptr))
+            declaration = 0;
+            if (parseParameterDeclaration(declaration)) {
+                *parameter_declaration_ptr = new (_pool) DeclarationListAST;
+                (*parameter_declaration_ptr)->declaration = declaration;
                 parameter_declaration_ptr = &(*parameter_declaration_ptr)->next;
+            }
         }
         return true;
     }
@@ -1381,7 +1401,7 @@ bool Parser::parseClassSpecifier(SpecifierAST *&node)
         if (LA() == T_LBRACE)
             ast->lbrace_token = consumeToken();
 
-        DeclarationAST **declaration_ptr = &ast->member_specifiers;
+        DeclarationListAST **declaration_ptr = &ast->member_specifiers;
         while (int tk = LA()) {
             if (tk == T_RBRACE) {
                 ast->rbrace_token = consumeToken();
@@ -1389,9 +1409,11 @@ bool Parser::parseClassSpecifier(SpecifierAST *&node)
             }
 
             unsigned start_declaration = cursor();
-            if (parseMemberSpecification(*declaration_ptr)) {
-                if (*declaration_ptr)
-                    declaration_ptr = &(*declaration_ptr)->next;
+            DeclarationAST *declaration = 0;
+            if (parseMemberSpecification(declaration)) {
+                *declaration_ptr = new (_pool) DeclarationListAST;
+                (*declaration_ptr)->declaration = declaration;
+                declaration_ptr = &(*declaration_ptr)->next;
             } else {
                 rewind(start_declaration + 1);
                 skipUntilDeclaration();
@@ -2097,16 +2119,19 @@ bool Parser::parseCompoundStatement(StatementAST *&node)
     if (LA() == T_LBRACE) {
         CompoundStatementAST *ast = new (_pool) CompoundStatementAST;
         ast->lbrace_token = consumeToken();
-        StatementAST **statement_ptr = &ast->statements;
+        StatementListAST **statement_ptr = &ast->statements;
         while (int tk = LA()) {
             if (tk == T_RBRACE)
                 break;
 
             unsigned start_statement = cursor();
-            if (! parseStatement(*statement_ptr)) {
+            StatementAST *statement = 0;
+            if (! parseStatement(statement)) {
                 rewind(start_statement + 1);
                 skipUntilStatement();
             } else {
+                *statement_ptr = new (_pool) StatementListAST;
+                (*statement_ptr)->statement = statement;
                 statement_ptr = &(*statement_ptr)->next;
             }
         }
diff --git a/src/shared/cplusplus/Parser.h b/src/shared/cplusplus/Parser.h
index b069320c48c..330bb84b3d7 100644
--- a/src/shared/cplusplus/Parser.h
+++ b/src/shared/cplusplus/Parser.h
@@ -156,7 +156,7 @@ public:
     bool parseOperatorFunctionId(NameAST *&node);
     bool parseParameterDeclaration(DeclarationAST *&node);
     bool parseParameterDeclarationClause(ParameterDeclarationClauseAST *&node);
-    bool parseParameterDeclarationList(DeclarationAST *&node);
+    bool parseParameterDeclarationList(DeclarationListAST *&node);
     bool parsePmExpression(ExpressionAST *&node);
     bool parseTypeidExpression(ExpressionAST *&node);
     bool parseTypenameCallExpression(ExpressionAST *&node);
@@ -178,7 +178,7 @@ public:
     bool parseTemplateArgumentList(TemplateArgumentListAST *&node);
     bool parseTemplateDeclaration(DeclarationAST *&node);
     bool parseTemplateParameter(DeclarationAST *&node);
-    bool parseTemplateParameterList(DeclarationAST *&node);
+    bool parseTemplateParameterList(DeclarationListAST *&node);
     bool parseThrowExpression(ExpressionAST *&node);
     bool parseTryBlockStatement(StatementAST *&node);
     bool parseCatchClause(CatchClauseAST *&node);
diff --git a/src/shared/cplusplus/PrettyPrinter.cpp b/src/shared/cplusplus/PrettyPrinter.cpp
index e1979523625..fd274c47d48 100644
--- a/src/shared/cplusplus/PrettyPrinter.cpp
+++ b/src/shared/cplusplus/PrettyPrinter.cpp
@@ -286,10 +286,8 @@ bool PrettyPrinter::visit(ClassSpecifierAST *ast)
     outToken(ast->lbrace_token);
     if (ast->member_specifiers) {
         indent();
-        if (ast->member_specifiers) {
-            for (DeclarationAST *it = ast->member_specifiers; it; it = it->next) {
-                accept(it);
-            }
+        for (DeclarationListAST *it = ast->member_specifiers; it; it = it->next) {
+            accept(it->declaration);
         }
         deindent();
     }
@@ -302,7 +300,7 @@ bool PrettyPrinter::visit(CompoundStatementAST *ast)
     outToken(ast->lbrace_token);
     if (ast->statements) {
         indent();
-        for (StatementAST *it = ast->statements; it; it = it->next) {
+        for (StatementListAST *it = ast->statements; it; it = it->next) {
             accept(it);
         }
         deindent();
@@ -624,8 +622,8 @@ bool PrettyPrinter::visit(LinkageBodyAST *ast)
     outToken(ast->lbrace_token);
     if (ast->declarations) {
         indent();
-        for (DeclarationAST *it = ast->declarations; it; it = it->next) {
-            accept(it);
+        for (DeclarationListAST *it = ast->declarations; it; it = it->next) {
+            accept(it->declaration);
         }
         deindent();
     }
@@ -806,9 +804,9 @@ bool PrettyPrinter::visit(ParameterDeclarationAST *ast)
 
 bool PrettyPrinter::visit(ParameterDeclarationClauseAST *ast)
 {
-    for (DeclarationAST *it = ast->parameter_declarations; it; it = it->next) {
+    for (DeclarationListAST *it = ast->parameter_declarations; it; it = it->next) {
         // XXX handle the comma tokens correctly
-        accept(it);
+        accept(it->declaration);
     }
     return false;
 }
@@ -943,9 +941,9 @@ bool PrettyPrinter::visit(TemplateDeclarationAST *ast)
     outToken(ast->template_token);
     outToken(ast->less_token);
     if (ast->template_parameters) {
-        for (DeclarationAST *it = ast->template_parameters; it; it = it->next) {
+        for (DeclarationListAST *it = ast->template_parameters; it; it = it->next) {
             // XXX handle the comma tokens correctly
-            accept(it);
+            accept(it->declaration);
         }
     }
     outToken(ast->greater_token);
@@ -972,9 +970,9 @@ bool PrettyPrinter::visit(TemplateTypeParameterAST *ast)
     outToken(ast->template_token);
     outToken(ast->less_token);
     if (ast->template_parameters) {
-        for (DeclarationAST *it = ast->template_parameters; it; it = it->next) {
+        for (DeclarationListAST *it = ast->template_parameters; it; it = it->next) {
             // XXX handle the comma tokens correctly
-            accept(it);
+            accept(it->declaration);
         }
     }
     outToken(ast->greater_token);
@@ -1002,8 +1000,8 @@ bool PrettyPrinter::visit(ThrowExpressionAST *ast)
 
 bool PrettyPrinter::visit(TranslationUnitAST *ast)
 {
-    for (DeclarationAST *it = ast->declarations; it; it = it->next) {
-        accept(it);
+    for (DeclarationListAST *it = ast->declarations; it; it = it->next) {
+        accept(it->declaration);
     }
     return false;
 }
-- 
GitLab