3 #include "parsetree/ParseTree.h"
4 #include "parsetree/ParseTreeVisitor.h"
8 using pty =
Node::Type;
13 ast::ClassDecl* ptv::visitClassDeclaration(
Node* node) {
14 sem.ResetFieldScope();
15 check_node_type(node, pty::ClassDeclaration);
16 check_num_children(node, 5, 5);
21 auto name = visitIdentifier(node
->child(1
));
23 auto super = visitSuperOpt(node
->child(2
));
25 ast::pmr_vector<ast::ReferenceType*> interfaces;
26 visitListPattern<pty::InterfaceTypeList, ast::ReferenceType*,
true>(
27 node->child(3), interfaces);
29 ast::pmr_vector<ast::Decl*> classBodyDeclarations;
30 visitListPattern<pty::ClassBodyDeclarationList, ast::Decl*,
true>(
31 node->child(4), classBodyDeclarations);
33 return sem.BuildClassDecl(modifiers,
38 classBodyDeclarations);
42 if(node ==
nullptr)
return nullptr;
43 check_node_type(node, pty::SuperOpt);
44 check_num_children(node, 1, 1);
45 return visitReferenceType(node
->child(0
));
50 return visitReferenceType(node);
54 ast::
Decl* ptv::visit<pty::ClassBodyDeclarationList>(
Node* node) {
57 case pty::FieldDeclaration:
58 return visitFieldDeclaration(node);
59 case pty::MethodDeclaration:
60 return visitMethodDeclaration(node);
61 case pty::ConstructorDeclaration:
62 return visitConstructorDeclaration(node);
70 ast::FieldDecl* ptv::visitFieldDeclaration(
Node* node) {
71 check_node_type(node, pty::FieldDeclaration);
72 check_num_children(node, 3, 3);
74 auto modifiers = visitModifierList(node
->child(0
));
78 if(decl.init) decl.init->setScope(sem.CurrentFieldScopeID());
79 return sem.BuildFieldDecl(modifiers, decl.loc, decl.type, decl.name, decl.init);
84 ast::MethodDecl* ptv::visitMethodDeclaration(
Node* node) {
85 check_node_type(node, pty::MethodDeclaration);
86 check_num_children(node, 2, 2);
93 check_node_type(pt_header, pty::MethodHeader);
94 check_num_children(pt_header, 3, 4);
96 ast::
Type* type =
nullptr;
98 ast::pmr_vector<ast::VarDecl*> params;
99 Node* nameNode =
nullptr;
102 modifiers = visitModifierList(pt_header
->child(0
));
106 name = visitIdentifier(pt_header
->child(1
));
109 visitListPattern<pty::FormalParameterList, ast::VarDecl*,
true>(
110 pt_header->child(2), params);
113 modifiers = visitModifierList(pt_header
->child(0
));
117 name = visitIdentifier(pt_header
->child(2
));
120 visitListPattern<pty::FormalParameterList, ast::VarDecl*,
true>(
121 pt_header->child(3), params);
126 ast::
Stmt* body =
nullptr;
127 if(pt_body !=
nullptr) {
128 body = visitBlock(pt_body);
132 auto ast = sem.BuildMethodDecl(
133 modifiers, nameNode->location(), name, type, params,
false, body);
134 ast->addDecls(sem.getAllLexicalDecls());
138 ast::MethodDecl* ptv::visitConstructorDeclaration(
Node* node) {
139 check_node_type(node, pty::ConstructorDeclaration);
140 check_num_children(node, 4, 4);
146 auto modifiers = visitModifierList(node
->child(0
));
149 auto name = visitIdentifier(nameNode);
151 ast::pmr_vector<ast::VarDecl*> params;
152 visitListPattern<pty::FormalParameterList, ast::VarDecl*,
true>(node->child(2),
155 ast::
Stmt* body =
nullptr;
160 auto ast = sem.BuildMethodDecl(
161 modifiers, nameNode->location(), name,
nullptr, params,
true, body);
162 ast->addDecls(sem.getAllLexicalDecls());
167 ast::
VarDecl* ptv::visit<pty::FormalParameterList>(
Node* node) {
168 check_node_type(node, pty::FormalParameter);
169 check_num_children(node, 2, 2);
174 auto name = visitIdentifier(nameNode);
176 return sem.BuildVarDecl(type, nameNode
->location(), name, sem.NextScopeID());
181 ast::InterfaceDecl* ptv::visitInterfaceDeclaration(
Node* node) {
182 sem.ResetFieldScope();
183 check_node_type(node, pty::InterfaceDeclaration);
184 check_num_children(node, 4, 4);
189 auto name = visitIdentifier(node
->child(1
));
191 ast::pmr_vector<ast::ReferenceType*> extends;
192 visitListPattern<pty::InterfaceTypeList, ast::ReferenceType*,
true>(
193 node->child(2), extends);
195 ast::pmr_vector<ast::Decl*> interfaceBodyDeclarations;
196 visitListPattern<pty::InterfaceMemberDeclarationList, ast::Decl*,
true>(
197 node->child(3), interfaceBodyDeclarations);
199 return sem.BuildInterfaceDecl(modifiers,
200 nameNode->location(),
203 interfaceBodyDeclarations);
207 ast::
Decl* ptv::visit<pty::InterfaceMemberDeclarationList>(
Node* node) {
208 return visitAbstractMethodDeclaration(node);
213 ast::MethodDecl* ptv::visitAbstractMethodDeclaration(
Node* node) {
214 check_node_type(node, pty::AbstractMethodDeclaration);
215 check_num_children(node, 3, 4);
221 ast::
Type* type =
nullptr;
223 ast::pmr_vector<ast::VarDecl*> params;
224 Node* nameNode =
nullptr;
227 modifiers = visitModifierList(node
->child(0
));
234 visitListPattern<pty::FormalParameterList, ast::VarDecl*,
true>(
235 node->child(2), params);
238 modifiers = visitModifierList(node
->child(0
));
245 visitListPattern<pty::FormalParameterList, ast::VarDecl*,
true>(
246 node->child(3), params);
251 auto ast = sem.BuildMethodDecl(
252 modifiers, nameNode->location(), name, type, params,
false,
nullptr);
253 ast->addDecls(sem.getAllLexicalDecls());