1 // =================================
  2 // Copyright (c) 2020 Seppo Laakko
  3 // Distributed under the MIT license
  4 // =================================
  5 
  6 #include <sngcm/ast/Node.hpp>
  7 #include <sngcm/ast/AstWriter.hpp>
  8 #include <sngcm/ast/AstReader.hpp>
  9 #include <sngcm/ast/BasicType.hpp>
 10 #include <sngcm/ast/Literal.hpp>
 11 #include <sngcm/ast/CompileUnit.hpp>
 12 #include <sngcm/ast/Identifier.hpp>
 13 #include <sngcm/ast/Typedef.hpp>
 14 #include <sngcm/ast/Constant.hpp>
 15 #include <sngcm/ast/Enumeration.hpp>
 16 #include <sngcm/ast/TypeExpr.hpp>
 17 #include <sngcm/ast/Expression.hpp>
 18 #include <sngcm/ast/Parameter.hpp>
 19 #include <sngcm/ast/Template.hpp>
 20 #include <sngcm/ast/Delegate.hpp>
 21 #include <sngcm/ast/Statement.hpp>
 22 #include <sngcm/ast/Function.hpp>
 23 #include <sngcm/ast/Class.hpp>
 24 #include <sngcm/ast/Interface.hpp>
 25 #include <sngcm/ast/Concept.hpp>
 26 #include <sngcm/ast/GlobalVariable.hpp>
 27 #include <sngcm/ast/Comment.hpp>
 28 #include <algorithm>
 29 
 30 namespace sngcm { namespace ast {
 31 
 32 const char* nodeTypeStr[] =
 33 {
 34     "boolNode", "sbyteNode", "byteNode", "shortNode", "ushortNode", "intNode", "uintNode", "longNode", "ulongNode", "floatNode", "doubleNode", "charNode", "wcharNode", "ucharNode", "voidNode", 
 35     "booleanLiteralNode", "sbyteLiteralNode", "byteLiteralNode", "shortLiteralNode", "ushortLiteralNode", "intLiteralNode", "uintLiteralNode", "longLiteralNode", "ulongLiteralNode", 
 36     "floatLiteralNode", "doubleLiteralNode", "charLiteralNode", "wcharLiteralNode", "ucharLiteralNode", "stringLiteralNode", "wstringLiteralNode", "ustringLiteralNode", "nullLiteralNode", "arrayLiteralNode", 
 37     "structuredLiteralNode", 
 38     "compileUnitNode", "namespaceNode", "aliasNode", "namespaceImportNode", "identifierNode", "templateIdNode", "functionNode", 
 39     "classNode", "thisInitializerNode", "baseInitializerNode", "memberInitializerNode", "staticConstructorNode", "constructorNode", "destructorNode", "memberFunctionNode", "conversionFunctionNode", 
 40     "memberVariableNode", 
 41     "interfaceNode", "delegateNode", "classDelegateNode", 
 42     "parenthesizedConstraintNode", "disjunctiveConstraintNode", "conjunctiveConstraintNode", "whereConstraintNode", "predicateConstraintNode", "isConstraintNode", "multiParamConstraintNode", "typeNameConstraintNode", 
 43     "constructorConstraintNode", "destructorConstraintNode", "memberFunctionConstraintNode", "functionConstraintNode", 
 44     "sameConstraintNode", "derivedConstraintNode", "convertibleConstraintNode", "explicitlyConvertibleConstraintNode", "commonConstraintNode", "nonreferenceTypeConstraintNode", 
 45     "axiomStatementNode", "axiomNode", "conceptIdNode", "conceptNode", 
 46     "sameConceptNode", "derivedConceptNode", "convertibleConceptNode", "ecxplicitlyConvertibleConceptNode", "commonConceptNode", "nonreferenceTypeConceptNode", 
 47     "labelNode", "compoundStatementNode", "returnStatementNode", "ifStatementNode", "whileStatementNode", "doStatementNode", "forStatementNode", "breakStatementNode", "continueStatementNode", 
 48     "gotoStatementNode", "constructionStatementNode", "deleteStatementNode", "destroyStatementNode", "assignmentStatementNode", "expressionStatementNode", "emptyStatementNode", 
 49     "rangeForStatementNode", "switchStatementNode", "caseStatementNode", "defaultStatementNode", "gotoCaseStatementNode", 
 50     "gotoDefaultStatementNode", "throwStatementNode", "catchNode", "tryStatementNode", "assertStatementNode", 
 51     "typedefNode", "constantNode", "enumTypeNode", "enumConstantNode", "parameterNode", "templateParameterNode", 
 52     "constNode", "refNode", "arrayNode", 
 53     "dotNode", "arrowNode", "equivalenceNode", "implicationNode", "disjunctionNode", "conjunctionNode", "bitOrNode", "bitXorNode", "bitAndNode", "equalNode", "notEqualNode", "lessNode", "greaterNode", 
 54     "lessOrEqualNode", "greaterOrEqualNode", "shiftLeftNode", "shiftRightNode", 
 55     "addNode", "subNode", "mulNode", "divNode", "remNode", "notNode", "unaryPlusNode", "unaryMinusNode", "prefixIncrementNode", "prefixDecrementNode", "complementNode", "derefNode", "addrOfNode", 
 56     "isNode", "asNode", "indexingNode", "invokeNode", "postfixIncrementNode", "postfixDecrementNode", "sizeOfNode", "typeNameNode", "typeIdNode", "castNode", "constructNode", "newNode", "thisNode", "baseNode", 
 57     "conditionalCompilationDisjunctionNode", "conditionalCompilationConjunctionNode", "conditionalCompilationNotNode", "conditionalCompilationPrimaryNode", "conditionalCompilationPartNode", 
 58     "conditionalCompilationStatementNode", "uuidLiteralNode", "cursorIdNode", "parenthesizedExpressionNode", "globalVariableNode", "parenthesizedCondCompExpressionNode", "labeledStatementNode", 
 59     "commentNode", 
 60     "maxNode"
 61 };
 62 
 63 std::string NodeTypeStr(NodeType nodeType)
 64 {
 65     return nodeTypeStr[static_cast<size_t>(nodeType)];
 66 }
 67 
 68 Node::Node(NodeType nodeType_, const Span& span_) : nodeType(nodeType_), span(span_), parent(nullptr)
 69 {
 70 }
 71 
 72 Node::~Node()
 73 {
 74 }
 75 
 76 void Node::SetParent(Node* parent_)
 77 {
 78     parent = parent_;
 79 }
 80 
 81 void Node::Write(AstWriter& writer)
 82 {
 83 }
 84 
 85 void Node::Read(AstReader& reader)
 86 {
 87 }
 88 
 89 void Node::SetFullSpan()
 90 {
 91 }
 92 
 93 UnaryNode::UnaryNode(NodeType nodeType_, const Span& span_) : Node(nodeType_, span_), subject()
 94 {
 95 }
 96 
 97 UnaryNode::UnaryNode(NodeType nodeType_, const Span& span_, Node* subject_) : Node(nodeType_, span_), subject(subject_)
 98 {
 99 }
100 
101 void UnaryNode::Write(AstWriter& writer)
102 {
103     Node::Write(writer);
104     writer.Write(subject.get());
105 }
106 
107 void UnaryNode::Read(AstReader& reader)
108 {
109     Node::Read(reader);
110     subject.reset(reader.ReadNode());
111     subject->SetParent(this);
112 }
113 
114 void UnaryNode::SetFullSpan()
115 {
116     if (subject)
117     {
118         const Span& thisSpan = GetSpan();
119         subject->SetFullSpan();
120         const Span& childSpan = subject->GetSpan();
121         SetSpanStart(std::min(thisSpan.start, childSpan.start));
122         SetSpanEnd(std::max(thisSpan.end, childSpan.end));
123     }
124 }
125 
126 BinaryNode::BinaryNode(NodeType nodeType, const Span& span_) : Node(nodeType, span_), left(), right()
127 {
128 }
129 
130 BinaryNode::BinaryNode(NodeType nodeType, const Span& span_, Node* left_, Node* right_) : Node(nodeType, span_), left(left_), right(right_)
131 {
132     left->SetParent(this);
133     right->SetParent(this);
134 }
135 
136 void BinaryNode::Write(AstWriter& writer)
137 {
138     Node::Write(writer);
139     writer.Write(left.get());
140     writer.Write(right.get());
141 }
142 
143 void BinaryNode::Read(AstReader& reader)
144 {
145     Node::Read(reader);
146     left.reset(reader.ReadNode());
147     left->SetParent(this);
148     right.reset(reader.ReadNode());
149     right->SetParent(this);
150 }
151 
152 void BinaryNode::SetFullSpan()
153 {
154     const Span& thisSpan = GetSpan();
155     left->SetFullSpan();
156     right->SetFullSpan();
157     const Span& leftSpan = left->GetSpan();
158     const Span& rightSpan = right->GetSpan();
159     SetSpanStart(std::min(thisSpan.start, std::min(leftSpan.start, rightSpan.start)));
160     SetSpanEnd(std::max(thisSpan.end, std::max(leftSpan.end, rightSpan.end)));
161 }
162 
163 NodeCreator::NodeCreator()
164 {
165 }
166 
167 NodeCreator::~NodeCreator()
168 {
169 }
170 
171 template<typename T>
172 class ConcreteNodeCreator : public NodeCreator
173 {
174 public:
175     ConcreteNodeCreator() : NodeCreator() {}
176     ConcreteNodeCreator(const ConcreteNodeCreator&) = delete;
177     ConcreteNodeCreator& operator=(const ConcreteNodeCreator&) = delete;
178     Node* CreateNode(const Span& span) override
179     {
180         return new T(span);
181     }
182 };
183 
184 std::unique_ptr<NodeFactory> NodeFactory::instance;
185 
186 void NodeFactory::Init()
187 {
188     instance.reset(new NodeFactory());
189 }
190 
191 void NodeFactory::Done()
192 {
193     instance.reset();
194 }
195 
196 NodeFactory::NodeFactory()
197 {
198     creators.resize(static_cast<size_t>(NodeType::maxNode));
199 
200     Register(NodeType::boolNode, new ConcreteNodeCreator<BoolNode>());
201     Register(NodeType::sbyteNode, new ConcreteNodeCreator<SByteNode>());
202     Register(NodeType::byteNode, new ConcreteNodeCreator<ByteNode>());
203     Register(NodeType::shortNode, new ConcreteNodeCreator<ShortNode>());
204     Register(NodeType::ushortNode, new ConcreteNodeCreator<UShortNode>());
205     Register(NodeType::intNode, new ConcreteNodeCreator<IntNode>());
206     Register(NodeType::uintNode, new ConcreteNodeCreator<UIntNode>());
207     Register(NodeType::longNode, new ConcreteNodeCreator<LongNode>());
208     Register(NodeType::ulongNode, new ConcreteNodeCreator<ULongNode>());
209     Register(NodeType::floatNode, new ConcreteNodeCreator<FloatNode>());
210     Register(NodeType::doubleNode, new ConcreteNodeCreator<DoubleNode>());
211     Register(NodeType::charNode, new ConcreteNodeCreator<CharNode>());
212     Register(NodeType::wcharNode, new ConcreteNodeCreator<WCharNode>());
213     Register(NodeType::ucharNode, new ConcreteNodeCreator<UCharNode>());
214     Register(NodeType::voidNode, new ConcreteNodeCreator<VoidNode>());
215 
216     Register(NodeType::booleanLiteralNode, new ConcreteNodeCreator<BooleanLiteralNode>());
217     Register(NodeType::sbyteLiteralNode, new ConcreteNodeCreator<SByteLiteralNode>());
218     Register(NodeType::byteLiteralNode, new ConcreteNodeCreator<ByteLiteralNode>());
219     Register(NodeType::shortLiteralNode, new ConcreteNodeCreator<ShortLiteralNode>());
220     Register(NodeType::ushortLiteralNode, new ConcreteNodeCreator<UShortLiteralNode>());
221     Register(NodeType::intLiteralNode, new ConcreteNodeCreator<IntLiteralNode>());
222     Register(NodeType::uintLiteralNode, new ConcreteNodeCreator<UIntLiteralNode>());
223     Register(NodeType::longLiteralNode, new ConcreteNodeCreator<LongLiteralNode>());
224     Register(NodeType::ulongLiteralNode, new ConcreteNodeCreator<ULongLiteralNode>());
225     Register(NodeType::floatLiteralNode, new ConcreteNodeCreator<FloatLiteralNode>());
226     Register(NodeType::doubleLiteralNode, new ConcreteNodeCreator<DoubleLiteralNode>());
227     Register(NodeType::charLiteralNode, new ConcreteNodeCreator<CharLiteralNode>());
228     Register(NodeType::wcharLiteralNode, new ConcreteNodeCreator<WCharLiteralNode>());
229     Register(NodeType::ucharLiteralNode, new ConcreteNodeCreator<UCharLiteralNode>());
230     Register(NodeType::stringLiteralNode, new ConcreteNodeCreator<StringLiteralNode>());
231     Register(NodeType::wstringLiteralNode, new ConcreteNodeCreator<WStringLiteralNode>());
232     Register(NodeType::ustringLiteralNode, new ConcreteNodeCreator<UStringLiteralNode>());
233     Register(NodeType::nullLiteralNode, new ConcreteNodeCreator<NullLiteralNode>());
234     Register(NodeType::arrayLiteralNode, new ConcreteNodeCreator<ArrayLiteralNode>());
235     Register(NodeType::structuredLiteralNode, new ConcreteNodeCreator<StructuredLiteralNode>());
236 
237     Register(NodeType::compileUnitNode, new ConcreteNodeCreator<CompileUnitNode>());
238     Register(NodeType::namespaceNode, new ConcreteNodeCreator<NamespaceNode>());
239     Register(NodeType::aliasNode, new ConcreteNodeCreator<AliasNode>());
240     Register(NodeType::namespaceImportNode, new ConcreteNodeCreator<NamespaceImportNode>());
241     Register(NodeType::identifierNode, new ConcreteNodeCreator<IdentifierNode>());
242     Register(NodeType::templateIdNode, new ConcreteNodeCreator<TemplateIdNode>());
243     Register(NodeType::functionNode, new ConcreteNodeCreator<FunctionNode>());
244     Register(NodeType::classNode, new ConcreteNodeCreator<ClassNode>());
245     Register(NodeType::thisInitializerNode, new ConcreteNodeCreator<ThisInitializerNode>());
246     Register(NodeType::baseInitializerNode, new ConcreteNodeCreator<BaseInitializerNode>());
247     Register(NodeType::memberInitializerNode, new ConcreteNodeCreator<MemberInitializerNode>());
248     Register(NodeType::staticConstructorNode, new ConcreteNodeCreator<StaticConstructorNode>());
249     Register(NodeType::constructorNode, new ConcreteNodeCreator<ConstructorNode>());
250     Register(NodeType::destructorNode, new ConcreteNodeCreator<DestructorNode>());
251     Register(NodeType::memberFunctionNode, new ConcreteNodeCreator<MemberFunctionNode>());
252     Register(NodeType::conversionFunctionNode, new ConcreteNodeCreator<ConversionFunctionNode>());
253     Register(NodeType::memberVariableNode, new ConcreteNodeCreator<MemberVariableNode>());
254     Register(NodeType::interfaceNode, new ConcreteNodeCreator<InterfaceNode>());
255     Register(NodeType::delegateNode, new ConcreteNodeCreator<DelegateNode>());
256     Register(NodeType::classDelegateNode, new ConcreteNodeCreator<ClassDelegateNode>());
257 
258     Register(NodeType::parenthesizedConstraintNode, new ConcreteNodeCreator<ParenthesizedConstraintNode>());
259     Register(NodeType::disjunctiveConstraintNode, new ConcreteNodeCreator<DisjunctiveConstraintNode>());
260     Register(NodeType::conjunctiveConstraintNode, new ConcreteNodeCreator<ConjunctiveConstraintNode>());
261     Register(NodeType::whereConstraintNode, new ConcreteNodeCreator<WhereConstraintNode>());
262     Register(NodeType::predicateConstraintNode, new ConcreteNodeCreator<PredicateConstraintNode>());
263     Register(NodeType::isConstraintNode, new ConcreteNodeCreator<IsConstraintNode>());
264     Register(NodeType::multiParamConstraintNode, new ConcreteNodeCreator<MultiParamConstraintNode>());
265     Register(NodeType::typeNameConstraintNode, new ConcreteNodeCreator<TypeNameConstraintNode>());
266     Register(NodeType::constructorConstraintNode, new ConcreteNodeCreator<ConstructorConstraintNode>());
267     Register(NodeType::destructorConstraintNode, new ConcreteNodeCreator<DestructorConstraintNode>());
268     Register(NodeType::memberFunctionConstraintNode, new ConcreteNodeCreator<MemberFunctionConstraintNode>());
269     Register(NodeType::functionConstraintNode, new ConcreteNodeCreator<FunctionConstraintNode>());
270     Register(NodeType::sameConstraintNode, new ConcreteNodeCreator<SameConstraintNode>());
271     Register(NodeType::derivedConstraintNode, new ConcreteNodeCreator<DerivedConstraintNode>());
272     Register(NodeType::convertibleConstraintNode, new ConcreteNodeCreator<ConvertibleConstraintNode>());
273     Register(NodeType::explicitlyConvertibleConstraintNode, new ConcreteNodeCreator<ExplicitlyConvertibleConstraintNode>());
274     Register(NodeType::commonConstraintNode, new ConcreteNodeCreator<CommonConstraintNode>());
275     Register(NodeType::nonreferenceTypeConstraintNode, new ConcreteNodeCreator<NonreferenceTypeConstraintNode>());
276     Register(NodeType::axiomStatementNode, new ConcreteNodeCreator<AxiomStatementNode>());
277     Register(NodeType::axiomNode, new ConcreteNodeCreator<AxiomNode>());
278     Register(NodeType::conceptIdNode, new ConcreteNodeCreator<ConceptIdNode>());
279     Register(NodeType::conceptNode, new ConcreteNodeCreator<ConceptNode>());
280     Register(NodeType::sameConceptNode, new ConcreteNodeCreator<SameConceptNode>());
281     Register(NodeType::derivedConceptNode, new ConcreteNodeCreator<DerivedConceptNode>());
282     Register(NodeType::convertibleConceptNode, new ConcreteNodeCreator<ConvertibleConceptNode>());
283     Register(NodeType::explicitlyConvertibleConceptNode, new ConcreteNodeCreator<ExplicitlyConvertibleConceptNode>());
284     Register(NodeType::commonConceptNode, new ConcreteNodeCreator<CommonConceptNode>());
285     Register(NodeType::nonreferenceTypeConceptNode, new ConcreteNodeCreator<NonreferenceTypeConceptNode>());
286 
287     Register(NodeType::labelNode, new ConcreteNodeCreator<LabelNode>());
288     Register(NodeType::labeledStatementNode, new ConcreteNodeCreator<LabeledStatementNode>());
289     Register(NodeType::compoundStatementNode, new ConcreteNodeCreator<CompoundStatementNode>());
290     Register(NodeType::returnStatementNode, new ConcreteNodeCreator<ReturnStatementNode>());
291     Register(NodeType::ifStatementNode, new ConcreteNodeCreator<IfStatementNode>());
292     Register(NodeType::whileStatementNode, new ConcreteNodeCreator<WhileStatementNode>());
293     Register(NodeType::doStatementNode, new ConcreteNodeCreator<DoStatementNode>());
294     Register(NodeType::forStatementNode, new ConcreteNodeCreator<ForStatementNode>());
295     Register(NodeType::breakStatementNode, new ConcreteNodeCreator<BreakStatementNode>());
296     Register(NodeType::continueStatementNode, new ConcreteNodeCreator<ContinueStatementNode>());
297     Register(NodeType::gotoStatementNode, new ConcreteNodeCreator<GotoStatementNode>());
298     Register(NodeType::constructionStatementNode, new ConcreteNodeCreator<ConstructionStatementNode>());
299     Register(NodeType::deleteStatementNode, new ConcreteNodeCreator<DeleteStatementNode>());
300     Register(NodeType::destroyStatementNode, new ConcreteNodeCreator<DestroyStatementNode>());
301     Register(NodeType::assignmentStatementNode, new ConcreteNodeCreator<AssignmentStatementNode>());
302     Register(NodeType::expressionStatementNode, new ConcreteNodeCreator<ExpressionStatementNode>());
303     Register(NodeType::emptyStatementNode, new ConcreteNodeCreator<EmptyStatementNode>());
304     Register(NodeType::rangeForStatementNode, new ConcreteNodeCreator<RangeForStatementNode>());
305     Register(NodeType::switchStatementNode, new ConcreteNodeCreator<SwitchStatementNode>());
306     Register(NodeType::caseStatementNode, new ConcreteNodeCreator<CaseStatementNode>());
307     Register(NodeType::defaultStatementNode, new ConcreteNodeCreator<DefaultStatementNode>());
308     Register(NodeType::gotoCaseStatementNode, new ConcreteNodeCreator<GotoCaseStatementNode>());
309     Register(NodeType::gotoDefaultStatementNode, new ConcreteNodeCreator<GotoDefaultStatementNode>());
310     Register(NodeType::throwStatementNode, new ConcreteNodeCreator<ThrowStatementNode>());
311     Register(NodeType::catchNode, new ConcreteNodeCreator<CatchNode>());
312     Register(NodeType::tryStatementNode, new ConcreteNodeCreator<TryStatementNode>());
313     Register(NodeType::assertStatementNode, new ConcreteNodeCreator<AssertStatementNode>());
314 
315     Register(NodeType::typedefNode, new ConcreteNodeCreator<TypedefNode>());
316     Register(NodeType::constantNode, new ConcreteNodeCreator<ConstantNode>());
317     Register(NodeType::enumTypeNode, new ConcreteNodeCreator<EnumTypeNode>());
318     Register(NodeType::enumConstantNode, new ConcreteNodeCreator<EnumConstantNode>());
319     Register(NodeType::parameterNode, new ConcreteNodeCreator<ParameterNode>());
320     Register(NodeType::templateParameterNode, new ConcreteNodeCreator<TemplateParameterNode>());
321 
322     Register(NodeType::constNode, new ConcreteNodeCreator<ConstNode>());
323     Register(NodeType::lvalueRefNode, new ConcreteNodeCreator<LValueRefNode>());
324     Register(NodeType::rvalueRefNode, new ConcreteNodeCreator<RValueRefNode>());
325     Register(NodeType::pointerNode, new ConcreteNodeCreator<PointerNode>());
326     Register(NodeType::dotNode, new ConcreteNodeCreator<DotNode>());
327     Register(NodeType::arrowNode, new ConcreteNodeCreator<ArrowNode>());
328     Register(NodeType::arrayNode, new ConcreteNodeCreator<ArrayNode>());
329 
330     Register(NodeType::equivalenceNode, new ConcreteNodeCreator<EquivalenceNode>());
331     Register(NodeType::implicationNode, new ConcreteNodeCreator<ImplicationNode>());
332     Register(NodeType::disjunctionNode, new ConcreteNodeCreator<DisjunctionNode>());
333     Register(NodeType::conjunctionNode, new ConcreteNodeCreator<ConjunctionNode>());
334     Register(NodeType::bitOrNode, new ConcreteNodeCreator<BitOrNode>());
335     Register(NodeType::bitXorNode, new ConcreteNodeCreator<BitXorNode>());
336     Register(NodeType::bitAndNode, new ConcreteNodeCreator<BitAndNode>());
337     Register(NodeType::equalNode, new ConcreteNodeCreator<EqualNode>());
338     Register(NodeType::notEqualNode, new ConcreteNodeCreator<NotEqualNode>());
339     Register(NodeType::lessNode, new ConcreteNodeCreator<LessNode>());
340     Register(NodeType::greaterNode, new ConcreteNodeCreator<GreaterNode>());
341     Register(NodeType::lessOrEqualNode, new ConcreteNodeCreator<LessOrEqualNode>());
342     Register(NodeType::greaterOrEqualNode, new ConcreteNodeCreator<GreaterOrEqualNode>());
343     Register(NodeType::shiftLeftNode, new ConcreteNodeCreator<ShiftLeftNode>());
344     Register(NodeType::shiftRightNode, new ConcreteNodeCreator<ShiftRightNode>());
345     Register(NodeType::addNode, new ConcreteNodeCreator<AddNode>());
346     Register(NodeType::subNode, new ConcreteNodeCreator<SubNode>());
347     Register(NodeType::mulNode, new ConcreteNodeCreator<MulNode>());
348     Register(NodeType::divNode, new ConcreteNodeCreator<DivNode>());
349     Register(NodeType::remNode, new ConcreteNodeCreator<RemNode>());
350     Register(NodeType::notNode, new ConcreteNodeCreator<NotNode>());
351     Register(NodeType::unaryPlusNode, new ConcreteNodeCreator<UnaryPlusNode>());
352     Register(NodeType::unaryMinusNode, new ConcreteNodeCreator<UnaryMinusNode>());
353     Register(NodeType::prefixIncrementNode, new ConcreteNodeCreator<PrefixIncrementNode>());
354     Register(NodeType::prefixDecrementNode, new ConcreteNodeCreator<PrefixDecrementNode>());
355     Register(NodeType::complementNode, new ConcreteNodeCreator<ComplementNode>());
356     Register(NodeType::derefNode, new ConcreteNodeCreator<DerefNode>());
357     Register(NodeType::addrOfNode, new ConcreteNodeCreator<AddrOfNode>());
358     Register(NodeType::isNode, new ConcreteNodeCreator<IsNode>());
359     Register(NodeType::asNode, new ConcreteNodeCreator<AsNode>());
360     Register(NodeType::indexingNode, new ConcreteNodeCreator<IndexingNode>());
361     Register(NodeType::invokeNode, new ConcreteNodeCreator<InvokeNode>());
362     Register(NodeType::postfixIncrementNode, new ConcreteNodeCreator<PostfixIncrementNode>());
363     Register(NodeType::postfixDecrementNode, new ConcreteNodeCreator<PostfixDecrementNode>());
364     Register(NodeType::sizeOfNode, new ConcreteNodeCreator<SizeOfNode>());
365     Register(NodeType::typeNameNode, new ConcreteNodeCreator<TypeNameNode>());
366     Register(NodeType::typeIdNode, new ConcreteNodeCreator<TypeIdNode>());
367     Register(NodeType::castNode, new ConcreteNodeCreator<CastNode>());
368     Register(NodeType::constructNode, new ConcreteNodeCreator<ConstructNode>());
369     Register(NodeType::newNode, new ConcreteNodeCreator<NewNode>());
370     Register(NodeType::thisNode, new ConcreteNodeCreator<ThisNode>());
371     Register(NodeType::baseNode, new ConcreteNodeCreator<BaseNode>());
372     Register(NodeType::conditionalCompilationDisjunctionNode, new ConcreteNodeCreator<ConditionalCompilationDisjunctionNode>());
373     Register(NodeType::conditionalCompilationConjunctionNode, new ConcreteNodeCreator<ConditionalCompilationConjunctionNode>());
374     Register(NodeType::conditionalCompilationNotNode, new ConcreteNodeCreator<ConditionalCompilationNotNode>());
375     Register(NodeType::conditionalCompilationPrimaryNode, new ConcreteNodeCreator<ConditionalCompilationPrimaryNode>());
376     Register(NodeType::conditionalCompilationPartNode, new ConcreteNodeCreator<ConditionalCompilationPartNode>());
377     Register(NodeType::parenthesizedCondCompExpressionNode, new ConcreteNodeCreator<ParenthesizedConditionalCompilationExpressionNode>());
378     Register(NodeType::conditionalCompilationStatementNode, new ConcreteNodeCreator<ConditionalCompilationStatementNode>());
379     Register(NodeType::uuidLiteralNode, new ConcreteNodeCreator<UuidLiteralNode>());
380     Register(NodeType::cursorIdNode, new ConcreteNodeCreator<CursorIdNode>());
381     Register(NodeType::parenthesizedExpressionNode, new ConcreteNodeCreator<ParenthesizedExpressionNode>());
382     Register(NodeType::globalVariableNode, new ConcreteNodeCreator<GlobalVariableNode>());
383     Register(NodeType::commentNode, new ConcreteNodeCreator<CommentNode>());
384 }
385 
386 void NodeFactory::Register(NodeType nodeType, NodeCreator* creator)
387 {
388     creators[static_cast<size_t>(nodeType)] = std::unique_ptr<NodeCreator>(creator);
389 }
390 
391 Node* NodeFactory::CreateNode(NodeType nodeType, const Span& span)
392 {
393     const std::std::unique_ptr<NodeCreator>&creator=creators[static_cast<size_t>(nodeType)];
394     if (creator)
395     {
396         Node* value = creator->CreateNode(span);
397         if (value)
398         {
399             return value;
400         }
401         else
402         {
403             throw std::runtime_error("could not create node");
404         }
405     }
406     else
407     {
408         throw std::runtime_error("no creator for node type '" + NodeTypeStr(nodeType) + "'");
409     }
410 }
411 
412 void NodeInit()
413 {
414     NodeFactory::Init();
415 }
416 
417 void NodeDone()
418 {
419     NodeFactory::Done();
420 }
421 
422 } } // namespace sngcm::ast