source: src/AST/Convert.cpp@ f685679

ADT arm-eh ast-experimental cleanup-dtors enum forall-pointer-decay jacob/cs343-translation jenkins-sandbox new-ast new-ast-unique-expr pthread-emulation qualifiedEnum
Last change on this file since f685679 was f685679, checked in by Andrew Beach <ajbeach@…>, 7 years ago

Translation can go both ways without crashing. Don't seem to be the inverse of each other.

  • Property mode set to 100644
File size: 70.9 KB
Line 
1//
2// Cforall Version 1.0.0 Copyright (C) 2019 University of Waterloo
3//
4// The contents of this file are covered under the licence agreement in the
5// file "LICENCE" distributed with Cforall.
6//
7// Convert.cpp -- Convert between the new and old syntax trees.
8//
9// Author : Thierry Delisle
10// Created On : Thu May 09 15::37::05 2019
11// Last Modified By : Andrew Beach
12// Last Modified On : Thu May 23 16:59:00 2019
13// Update Count : 6
14//
15
16#include "Convert.hpp"
17
18#include <unordered_map>
19
20#include "AST/Attribute.hpp"
21#include "AST/Decl.hpp"
22#include "AST/Expr.hpp"
23#include "AST/Init.hpp"
24#include "AST/Stmt.hpp"
25#include "AST/TypeSubstitution.hpp"
26
27#include "SynTree/Attribute.h"
28#include "SynTree/Declaration.h"
29#include "SynTree/TypeSubstitution.h"
30
31//================================================================================================
32// Utilities
33template<template <class...> class C>
34struct to {
35 template<typename T>
36 static auto from( T && v ) -> C< typename T::value_type > {
37 C< typename T::value_type > l;
38 std::move(std::begin(v), std::end(v), std::back_inserter(l));
39 return l;
40 }
41};
42
43//================================================================================================
44class ConverterNewToOld : public ast::Visitor {
45 BaseSyntaxNode * node = nullptr;
46 using Cache = std::unordered_map< const ast::Node *, BaseSyntaxNode * >;
47 Cache cache;
48
49 template<typename T>
50 struct Getter {
51 ConverterNewToOld & visitor;
52
53 template<typename U, enum ast::Node::ref_type R>
54 T * accept1( const ast::ptr_base<U, R> & ptr ) {
55 if ( ! ptr ) return nullptr;
56 ptr->accept( visitor );
57 T * ret = strict_dynamic_cast< T * >( visitor.node );
58 visitor.node = nullptr;
59 return ret;
60 }
61
62 template<typename U>
63 std::list< T * > acceptL( const U & container ) {
64 std::list< T * > ret;
65 for (auto ptr : container ) {
66 ret.emplace_back( accept1( ptr ) );
67 }
68 return ret;
69 }
70 };
71
72 template<typename T>
73 Getter<T> get() {
74 return Getter<T>{ *this };
75 }
76
77 Label makeLabel(Statement * labelled, const ast::Label& label) {
78 return Label(
79 label.name,
80 labelled,
81 get<Attribute>().acceptL(label.attributes)
82 );
83 }
84
85 template<template <class...> class C>
86 std::list<Label> makeLabelL(Statement * labelled, const C<ast::Label>& labels) {
87 std::list<Label> ret;
88 for (auto label : labels) {
89 ret.push_back( makeLabel(labelled, label) );
90 }
91 return ret;
92 }
93
94 /// get new qualifiers from old type
95 Type::Qualifiers cv( const ast::Type * ty ) { return { ty->qualifiers.val }; }
96
97 /// returns true and sets `node` if in cache
98 bool inCache( const ast::Node * node ) {
99 auto it = cache.find( node );
100 if ( it == cache.end() ) return false;
101 this->node = it->second;
102 return true;
103 }
104
105public:
106 Declaration * decl( const ast::Decl * declNode ) {
107 return get<Declaration>().accept1( ast::ptr<ast::Decl>( declNode ) );
108 }
109
110private:
111 void declPostamble( Declaration * decl, const ast::Decl * node ) {
112 decl->location = node->location;
113 // name comes from constructor
114 // linkage comes from constructor
115 decl->extension = node->extension;
116 decl->uniqueId = node->uniqueId;
117 // storageClasses comes from constructor
118 this->node = decl;
119 }
120
121 const ast::DeclWithType * declWithTypePostamble (
122 DeclarationWithType * decl, const ast::DeclWithType * node ) {
123 cache.emplace( node, decl );
124 decl->mangleName = node->mangleName;
125 decl->scopeLevel = node->scopeLevel;
126 decl->asmName = get<Expression>().accept1( node->asmName );
127 // attributes comes from constructor
128 decl->isDeleted = node->isDeleted;
129 // fs comes from constructor
130 declPostamble( decl, node );
131 return nullptr;
132 }
133
134 const ast::DeclWithType * visit( const ast::ObjectDecl * node ) override final {
135 if ( inCache( node ) ) return nullptr;
136 auto decl = new ObjectDecl(
137 node->name,
138 Type::StorageClasses( node->storage.val ),
139 LinkageSpec::Spec( node->linkage.val ),
140 get<Expression>().accept1( node->bitfieldWidth ),
141 get<Type>().accept1( node->type ),
142 get<Initializer>().accept1( node->init ),
143 get<Attribute>().acceptL( node->attributes ),
144 Type::FuncSpecifiers( node->funcSpec.val )
145 );
146 return declWithTypePostamble( decl, node );
147 }
148
149 const ast::DeclWithType * visit( const ast::FunctionDecl * node ) override final {
150 if ( inCache( node ) ) return nullptr;
151 auto decl = new FunctionDecl(
152 node->name,
153 Type::StorageClasses( node->storage.val ),
154 LinkageSpec::Spec( node->linkage.val ),
155 get<FunctionType>().accept1( node->type ),
156 get<CompoundStmt>().accept1( node->stmts ),
157 get<Attribute>().acceptL( node->attributes ),
158 Type::FuncSpecifiers( node->funcSpec.val )
159 );
160 decl->withExprs = get<Expression>().acceptL( node->withExprs );
161 return declWithTypePostamble( decl, node );
162 }
163
164 const ast::Decl * namedTypePostamble( NamedTypeDecl * decl, const ast::NamedTypeDecl * node ) {
165 // base comes from constructor
166 decl->parameters = get<TypeDecl>().acceptL( node->params );
167 decl->assertions = get<DeclarationWithType>().acceptL( node->assertions );
168 declPostamble( decl, node );
169 return nullptr;
170 }
171
172 const ast::Decl * visit( const ast::TypeDecl * node ) override final {
173 if ( inCache( node ) ) return nullptr;
174 auto decl = new TypeDecl(
175 node->name,
176 Type::StorageClasses( node->storage.val ),
177 get<Type>().accept1( node->base ),
178 (TypeDecl::Kind)(unsigned)node->kind,
179 node->sized,
180 get<Type>().accept1( node->init )
181 );
182 cache.emplace( node, decl );
183 return namedTypePostamble( decl, node );
184 }
185
186 const ast::Decl * visit( const ast::TypedefDecl * node ) override final {
187 auto decl = new TypedefDecl(
188 node->name,
189 node->location,
190 Type::StorageClasses( node->storage.val ),
191 get<Type>().accept1( node->base ),
192 LinkageSpec::Spec( node->linkage.val )
193 );
194 return namedTypePostamble( decl, node );
195 }
196
197 const ast::Decl * aggregatePostamble( AggregateDecl * decl, const ast::AggregateDecl * node ) {
198 cache.emplace( node, decl );
199 decl->members = get<Declaration>().acceptL( node->members );
200 decl->parameters = get<TypeDecl>().acceptL( node->params );
201 decl->body = node->body;
202 // attributes come from constructor
203 decl->parent = get<AggregateDecl>().accept1( node->parent );
204 declPostamble( decl, node );
205 return nullptr;
206 }
207
208 const ast::Decl * visit( const ast::StructDecl * node ) override final {
209 if ( inCache( node ) ) return nullptr;
210 auto decl = new StructDecl(
211 node->name,
212 node->kind,
213 get<Attribute>().acceptL( node->attributes ),
214 LinkageSpec::Spec( node->linkage.val )
215 );
216 return aggregatePostamble( decl, node );
217 }
218
219 const ast::Decl * visit( const ast::UnionDecl * node ) override final {
220 if ( inCache( node ) ) return nullptr;
221 auto decl = new UnionDecl(
222 node->name,
223 get<Attribute>().acceptL( node->attributes ),
224 LinkageSpec::Spec( node->linkage.val )
225 );
226 return aggregatePostamble( decl, node );
227 }
228
229 const ast::Decl * visit( const ast::EnumDecl * node ) override final {
230 if ( inCache( node ) ) return nullptr;
231 auto decl = new EnumDecl(
232 node->name,
233 get<Attribute>().acceptL( node->attributes ),
234 LinkageSpec::Spec( node->linkage.val )
235 );
236 return aggregatePostamble( decl, node );
237 }
238
239 const ast::Decl * visit( const ast::TraitDecl * node ) override final {
240 if ( inCache( node ) ) return nullptr;
241 auto decl = new TraitDecl(
242 node->name,
243 {},
244 LinkageSpec::Spec( node->linkage.val )
245 );
246 return aggregatePostamble( decl, node );
247 }
248
249 const ast::AsmDecl * visit( const ast::AsmDecl * node ) override final {
250 auto decl = new AsmDecl( get<AsmStmt>().accept1( node->stmt ) );
251 declPostamble( decl, node );
252 return nullptr;
253 }
254
255 const ast::StaticAssertDecl * visit( const ast::StaticAssertDecl * node ) override final {
256 auto decl = new StaticAssertDecl(
257 get<Expression>().accept1( node->cond ),
258 get<ConstantExpr>().accept1( node->msg )
259 );
260 declPostamble( decl, node );
261 return nullptr;
262 }
263
264 const ast::Stmt * stmtPostamble( Statement * stmt, const ast::Stmt * node ) {
265 cache.emplace( node, stmt );
266 stmt->location = node->location;
267 stmt->labels = makeLabelL( stmt, node->labels );
268 this->node = stmt;
269 return nullptr;
270 }
271
272 const ast::CompoundStmt * visit( const ast::CompoundStmt * node ) override final {
273 if ( inCache( node ) ) return nullptr;
274 auto stmt = new CompoundStmt( get<Statement>().acceptL( node->kids ) );
275 stmtPostamble( stmt, node );
276 return nullptr;
277 }
278
279 const ast::Stmt * visit( const ast::ExprStmt * node ) override final {
280 if ( inCache( node ) ) return nullptr;
281 auto stmt = new ExprStmt( nullptr );
282 cache.emplace( node, stmt );
283 stmt->expr = get<Expression>().accept1( node->expr );
284 return stmtPostamble( stmt, node );
285 }
286
287 const ast::Stmt * visit( const ast::AsmStmt * node ) override final {
288 if ( inCache( node ) ) return nullptr;
289 auto stmt = new AsmStmt(
290 node->isVolatile,
291 get<Expression>().accept1( node->instruction ),
292 get<Expression>().acceptL( node->output ),
293 get<Expression>().acceptL( node->input ),
294 get<ConstantExpr>().acceptL( node->clobber ),
295 makeLabelL( nullptr, node->gotoLabels ) // What are these labelling?
296 );
297 return stmtPostamble( stmt, node );
298 }
299
300 const ast::Stmt * visit( const ast::DirectiveStmt * node ) override final {
301 if ( inCache( node ) ) return nullptr;
302 auto stmt = new DirectiveStmt( node->directive );
303 return stmtPostamble( stmt, node );
304 }
305
306 const ast::Stmt * visit( const ast::IfStmt * node ) override final {
307 if ( inCache( node ) ) return nullptr;
308 auto stmt = new IfStmt(
309 get<Expression>().accept1( node->cond ),
310 get<Statement>().accept1( node->thenPart ),
311 get<Statement>().accept1( node->elsePart ),
312 get<Statement>().acceptL( node->inits )
313 );
314 return stmtPostamble( stmt, node );
315 }
316
317 const ast::Stmt * visit( const ast::SwitchStmt * node ) override final {
318 if ( inCache( node ) ) return nullptr;
319 auto stmt = new SwitchStmt(
320 get<Expression>().accept1( node->cond ),
321 get<Statement>().acceptL( node->stmts )
322 );
323 return stmtPostamble( stmt, node );
324 }
325
326 const ast::Stmt * visit( const ast::CaseStmt * node ) override final {
327 if ( inCache( node ) ) return nullptr;
328 auto stmt = new CaseStmt(
329 get<Expression>().accept1( node->cond ),
330 get<Statement>().acceptL( node->stmts ),
331 node->isDefault()
332 );
333 return stmtPostamble( stmt, node );
334 }
335
336 const ast::Stmt * visit( const ast::WhileStmt * node ) override final {
337 if ( inCache( node ) ) return nullptr;
338 auto inits = get<Statement>().acceptL( node->inits );
339 auto stmt = new WhileStmt(
340 get<Expression>().accept1( node->cond ),
341 get<Statement>().accept1( node->body ),
342 inits,
343 node->isDoWhile
344 );
345 return stmtPostamble( stmt, node );
346 }
347
348 const ast::Stmt * visit( const ast::ForStmt * node ) override final {
349 if ( inCache( node ) ) return nullptr;
350 auto stmt = new ForStmt(
351 get<Statement>().acceptL( node->inits ),
352 get<Expression>().accept1( node->cond ),
353 get<Expression>().accept1( node->inc ),
354 get<Statement>().accept1( node->body )
355 );
356 return stmtPostamble( stmt, node );
357 }
358
359 const ast::Stmt * visit( const ast::BranchStmt * node ) override final {
360 if ( inCache( node ) ) return nullptr;
361 BranchStmt * stmt;
362 if (node->computedTarget) {
363 stmt = new BranchStmt( get<Expression>().accept1( node->computedTarget ),
364 BranchStmt::Goto );
365 } else {
366 BranchStmt::Type type;
367 switch (node->kind) {
368 #define CASE(n) \
369 case ast::BranchStmt::n: \
370 type = BranchStmt::n; \
371 break
372 CASE(Goto);
373 CASE(Break);
374 CASE(Continue);
375 CASE(FallThrough);
376 CASE(FallThroughDefault);
377 #undef CASE
378 default:
379 assertf(false, "Invalid ast::BranchStmt::Kind: %d\n", node->kind);
380 }
381
382 // The labels here are also weird.
383 stmt = new BranchStmt( makeLabel( nullptr, node->originalTarget ), type );
384 stmt->target = makeLabel( stmt, node->target );
385 }
386 return stmtPostamble( stmt, node );
387 }
388
389 const ast::Stmt * visit( const ast::ReturnStmt * node ) override final {
390 if ( inCache( node ) ) return nullptr;
391 auto stmt = new ReturnStmt( get<Expression>().accept1( node->expr ) );
392 return stmtPostamble( stmt, node );
393 }
394
395 const ast::Stmt * visit( const ast::ThrowStmt * node ) override final {
396 if ( inCache( node ) ) return nullptr;
397 ThrowStmt::Kind kind;
398 switch (node->kind) {
399 case ast::ThrowStmt::Terminate:
400 kind = ThrowStmt::Terminate;
401 break;
402 case ast::ThrowStmt::Resume:
403 kind = ThrowStmt::Resume;
404 break;
405 default:
406 assertf(false, "Invalid ast::ThrowStmt::Kind: %d\n", node->kind);
407 }
408 auto stmt = new ThrowStmt(
409 kind,
410 get<Expression>().accept1( node->expr ),
411 get<Expression>().accept1( node->target )
412 );
413 return stmtPostamble( stmt, node );
414 }
415
416 const ast::Stmt * visit( const ast::TryStmt * node ) override final {
417 if ( inCache( node ) ) return nullptr;
418 auto handlers = get<CatchStmt>().acceptL( node->handlers );
419 auto stmt = new TryStmt(
420 get<CompoundStmt>().accept1( node->body ),
421 handlers,
422 get<FinallyStmt>().accept1( node->finally )
423 );
424 return stmtPostamble( stmt, node );
425 }
426
427 const ast::Stmt * visit( const ast::CatchStmt * node ) override final {
428 if ( inCache( node ) ) return nullptr;
429 CatchStmt::Kind kind;
430 switch (node->kind) {
431 case ast::CatchStmt::Terminate:
432 kind = CatchStmt::Terminate;
433 break;
434 case ast::CatchStmt::Resume:
435 kind = CatchStmt::Resume;
436 break;
437 default:
438 assertf(false, "Invalid ast::CatchStmt::Kind: %d\n", node->kind);
439 }
440 auto stmt = new CatchStmt(
441 kind,
442 get<Declaration>().accept1( node->decl ),
443 get<Expression>().accept1( node->cond ),
444 get<Statement>().accept1( node->body )
445 );
446 return stmtPostamble( stmt, node );
447 }
448
449 const ast::Stmt * visit( const ast::FinallyStmt * node ) override final {
450 if ( inCache( node ) ) return nullptr;
451 auto stmt = new FinallyStmt( get<CompoundStmt>().accept1( node->body ) );
452 return stmtPostamble( stmt, node );
453 }
454
455 const ast::Stmt * visit( const ast::WaitForStmt * node ) override final {
456 if ( inCache( node ) ) return nullptr;
457 auto stmt = new WaitForStmt;
458 stmt->clauses.reserve( node->clauses.size() );
459 for ( auto clause : node->clauses ) {
460 stmt->clauses.push_back({{
461 get<Expression>().accept1( clause.target.func ),
462 get<Expression>().acceptL( clause.target.args ),
463 },
464 get<Statement>().accept1( clause.stmt ),
465 get<Expression>().accept1( clause.cond ),
466 });
467 }
468 stmt->timeout = {
469 get<Expression>().accept1( node->timeout.time ),
470 get<Statement>().accept1( node->timeout.stmt ),
471 get<Expression>().accept1( node->timeout.cond ),
472 };
473 stmt->orelse = {
474 get<Statement>().accept1( node->orElse.stmt ),
475 get<Expression>().accept1( node->orElse.cond ),
476 };
477 return stmtPostamble( stmt, node );
478 }
479
480 const ast::Stmt * visit( const ast::WithStmt * node ) override final {
481 if ( inCache( node ) ) return nullptr;
482 auto stmt = new WithStmt(
483 get<Expression>().acceptL( node->exprs ),
484 get<Statement>().accept1( node->stmt )
485 );
486 return stmtPostamble( stmt, node );
487 }
488
489 const ast::NullStmt * visit( const ast::NullStmt * node ) override final {
490 if ( inCache( node ) ) return nullptr;
491 auto stmt = new NullStmt();
492 stmtPostamble( stmt, node );
493 return nullptr;
494 }
495
496 const ast::Stmt * visit( const ast::DeclStmt * node ) override final {
497 if ( inCache( node ) ) return nullptr;
498 auto stmt = new DeclStmt( get<Declaration>().accept1( node->decl ) );
499 return stmtPostamble( stmt, node );
500 }
501
502 const ast::Stmt * visit( const ast::ImplicitCtorDtorStmt * node ) override final {
503 if ( inCache( node ) ) return nullptr;
504 auto stmt = new ImplicitCtorDtorStmt{
505 get<Statement>().accept1( node->callStmt )
506 };
507 return stmtPostamble( stmt, node );
508 }
509
510 TypeSubstitution * convertTypeSubstitution(const ast::TypeSubstitution * src) {
511
512 if (!src) return nullptr;
513
514 TypeSubstitution *rslt = new TypeSubstitution();
515
516 for (decltype(src->begin()) src_i = src->begin(); src_i != src->end(); src_i++) {
517 rslt->add( src_i->first,
518 get<Type>().accept1(src_i->second) );
519 }
520
521 for (decltype(src->beginVar()) src_i = src->beginVar(); src_i != src->endVar(); src_i++) {
522 rslt->addVar( src_i->first,
523 get<Expression>().accept1(src_i->second) );
524 }
525
526 return rslt;
527 }
528
529 void convertInferUnion(std::map<UniqueId,ParamEntry> &tgtInferParams,
530 std::vector<UniqueId> &tgtResnSlots,
531 const ast::Expr::InferUnion &srcInferred ) {
532
533 assert( tgtInferParams.empty() );
534 assert( tgtResnSlots.empty() );
535
536 if ( srcInferred.mode == ast::Expr::InferUnion::Params ) {
537 const ast::InferredParams &srcParams = srcInferred.inferParamsConst();
538 for (auto srcParam : srcParams) {
539 tgtInferParams[srcParam.first] = ParamEntry(
540 srcParam.second.decl,
541 get<Type>().accept1(srcParam.second.actualType),
542 get<Type>().accept1(srcParam.second.formalType),
543 get<Expression>().accept1(srcParam.second.expr)
544 );
545 }
546 } else if ( srcInferred.mode == ast::Expr::InferUnion::Slots ) {
547 const ast::ResnSlots &srcSlots = srcInferred.resnSlotsConst();
548 for (auto srcSlot : srcSlots) {
549 tgtResnSlots.push_back(srcSlot);
550 }
551 }
552 }
553
554 Expression * visitBaseExpr_skipResultType(const ast::Expr * src, Expression * tgt) {
555
556 tgt->location = src->location;
557 tgt->env = convertTypeSubstitution(src->env);
558 tgt->extension = src->extension;
559
560 convertInferUnion(tgt->inferParams, tgt->resnSlots, src->inferred);
561 return tgt;
562 }
563
564 Expression * visitBaseExpr(const ast::Expr * src, Expression * tgt) {
565
566 tgt->result = get<Type>().accept1(src->result);
567 return visitBaseExpr_skipResultType(src, tgt);
568 }
569
570 const ast::Expr * visit( const ast::ApplicationExpr * node ) override final {
571 auto expr = visitBaseExpr( node,
572 new ApplicationExpr(
573 get<Expression>().accept1(node->func),
574 get<Expression>().acceptL(node->args)
575 )
576 );
577 this->node = expr;
578 return nullptr;
579 }
580
581 const ast::Expr * visit( const ast::UntypedExpr * node ) override final {
582 auto expr = visitBaseExpr( node,
583 new UntypedExpr(
584 get<Expression>().accept1(node->func),
585 get<Expression>().acceptL(node->args)
586 )
587 );
588 this->node = expr;
589 return nullptr;
590 }
591
592 const ast::Expr * visit( const ast::NameExpr * node ) override final {
593 auto expr = visitBaseExpr( node,
594 new NameExpr(
595 node->name
596 )
597 );
598 this->node = expr;
599 return nullptr;
600 }
601
602 const ast::Expr * visit( const ast::AddressExpr * node ) override final {
603 auto expr = visitBaseExpr( node,
604 new AddressExpr(
605 get<Expression>().accept1(node->arg)
606 )
607 );
608 this->node = expr;
609 return nullptr;
610 }
611
612 const ast::Expr * visit( const ast::LabelAddressExpr * node ) override final {
613 auto expr = visitBaseExpr( node,
614 new LabelAddressExpr(
615 makeLabel(nullptr, node->arg)
616 )
617 );
618 this->node = expr;
619 return nullptr;
620 }
621
622 const ast::Expr * visit( const ast::CastExpr * node ) override final {
623 auto expr = visitBaseExpr( node,
624 new CastExpr(
625 get<Expression>().accept1(node->arg),
626 (node->isGenerated == ast::GeneratedCast)
627 )
628 );
629 this->node = expr;
630 return nullptr;
631 }
632
633 const ast::Expr * visit( const ast::KeywordCastExpr * node ) override final {
634 KeywordCastExpr::Target castTarget = KeywordCastExpr::NUMBER_OF_TARGETS;
635 switch (node->target) {
636 case ast::KeywordCastExpr::Coroutine:
637 castTarget = KeywordCastExpr::Coroutine;
638 break;
639 case ast::KeywordCastExpr::Thread:
640 castTarget = KeywordCastExpr::Thread;
641 break;
642 case ast::KeywordCastExpr::Monitor:
643 castTarget = KeywordCastExpr::Monitor;
644 break;
645 default:
646 break;
647 }
648 assert ( castTarget < KeywordCastExpr::NUMBER_OF_TARGETS );
649 auto expr = visitBaseExpr( node,
650 new KeywordCastExpr(
651 get<Expression>().accept1(node->arg),
652 castTarget
653 )
654 );
655 this->node = expr;
656 return nullptr;
657 }
658
659 const ast::Expr * visit( const ast::VirtualCastExpr * node ) override final {
660 auto expr = visitBaseExpr_skipResultType( node,
661 new VirtualCastExpr(
662 get<Expression>().accept1(node->arg),
663 get<Type>().accept1(node->result)
664 )
665 );
666 this->node = expr;
667 return nullptr;
668 }
669
670 const ast::Expr * visit( const ast::UntypedMemberExpr * node ) override final {
671 auto expr = visitBaseExpr( node,
672 new UntypedMemberExpr(
673 get<Expression>().accept1(node->member),
674 get<Expression>().accept1(node->aggregate)
675 )
676 );
677 this->node = expr;
678 return nullptr;
679 }
680
681 const ast::Expr * visit( const ast::MemberExpr * node ) override final {
682 auto expr = visitBaseExpr( node,
683 new MemberExpr(
684 inCache(node->member) ?
685 dynamic_cast<DeclarationWithType *>(this->node) :
686 get<DeclarationWithType>().accept1(node->member),
687 get<Expression>().accept1(node->aggregate)
688 )
689 );
690 this->node = expr;
691 return nullptr;
692 }
693
694 const ast::Expr * visit( const ast::VariableExpr * node ) override final {
695 auto expr = visitBaseExpr( node,
696 new VariableExpr(
697 inCache(node->var) ?
698 dynamic_cast<DeclarationWithType *>(this->node) :
699 get<DeclarationWithType>().accept1(node->var)
700 )
701 );
702 this->node = expr;
703 return nullptr;
704 }
705
706 bool isIntlikeConstantType(const ast::Type *t) {
707 if ( const ast::BasicType * basicType = dynamic_cast< const ast::BasicType * >( t ) ) {
708 if ( basicType->isInteger() ) {
709 return true;
710 }
711 } else if ( dynamic_cast< const ast::OneType * >( t ) ) {
712 return true;
713 } else if ( dynamic_cast< const ast::ZeroType * >( t ) ) {
714 return true;
715 } else if ( dynamic_cast< const ast::PointerType * >( t ) ) {
716 // null pointer constants, with zero int-values
717 return true;
718 }
719 return false;
720 }
721
722 bool isFloatlikeConstantType(const ast::Type *t) {
723 if ( const ast::BasicType * bty = dynamic_cast< const ast::BasicType * >( t ) ) {
724 if ( ! bty->isInteger() ) {
725 return true;
726 }
727 }
728 return false;
729 }
730
731 bool isStringlikeConstantType(const ast::Type *t) {
732 if ( const ast::ArrayType * aty = dynamic_cast< const ast::ArrayType * >( t ) ) {
733 if ( const ast::BasicType * bty = aty->base.as<ast::BasicType>() ) {
734 if ( bty->kind == ast::BasicType::Kind::Char ) {
735 return true;
736 }
737 }
738 }
739 return false;
740 }
741
742 const ast::Expr * visit( const ast::ConstantExpr * node ) override final {
743 ConstantExpr *rslt = nullptr;
744 if (isIntlikeConstantType(node->result)) {
745 rslt = new ConstantExpr(Constant(
746 get<Type>().accept1(node->result),
747 node->rep,
748 (unsigned long long) node->intValue()
749 ));
750 } else if (isFloatlikeConstantType(node->result)) {
751 rslt = new ConstantExpr(Constant(
752 get<Type>().accept1(node->result),
753 node->rep,
754 (double) node->floatValue()
755 ));
756 } else if (isStringlikeConstantType(node->result)) {
757 rslt = new ConstantExpr(Constant::from_string(
758 node->rep
759 ));
760 }
761 assert(rslt);
762 auto expr = visitBaseExpr( node, rslt );
763 this->node = expr;
764 return nullptr;
765 }
766
767 const ast::Expr * visit( const ast::SizeofExpr * node ) override final {
768 assert (node->expr || node->type);
769 assert (! (node->expr && node->type));
770 SizeofExpr *rslt;
771 if (node->expr) {
772 rslt = new SizeofExpr(
773 get<Expression>().accept1(node->expr)
774 );
775 assert (!rslt->isType);
776 }
777 if (node->type) {
778 rslt = new SizeofExpr(
779 get<Type>().accept1(node->type)
780 );
781 assert (rslt->isType);
782 }
783 auto expr = visitBaseExpr( node, rslt );
784 this->node = expr;
785 return nullptr;
786 }
787
788 const ast::Expr * visit( const ast::AlignofExpr * node ) override final {
789 assert (node->expr || node->type);
790 assert (! (node->expr && node->type));
791 AlignofExpr *rslt;
792 if (node->expr) {
793 rslt = new AlignofExpr(
794 get<Expression>().accept1(node->expr)
795 );
796 assert (!rslt->isType);
797 }
798 if (node->type) {
799 rslt = new AlignofExpr(
800 get<Type>().accept1(node->type)
801 );
802 assert (rslt->isType);
803 }
804 auto expr = visitBaseExpr( node, rslt );
805 this->node = expr;
806 return nullptr;
807 }
808
809 const ast::Expr * visit( const ast::UntypedOffsetofExpr * node ) override final {
810 auto expr = visitBaseExpr( node,
811 new UntypedOffsetofExpr(
812 get<Type>().accept1(node->type),
813 node->member
814 )
815 );
816 this->node = expr;
817 return nullptr;
818 }
819
820 const ast::Expr * visit( const ast::OffsetofExpr * node ) override final {
821 auto expr = visitBaseExpr( node,
822 new OffsetofExpr(
823 get<Type>().accept1(node->type),
824 inCache(node->member) ?
825 dynamic_cast<DeclarationWithType *>(this->node) :
826 get<DeclarationWithType>().accept1(node->member)
827 )
828 );
829 this->node = expr;
830 return nullptr;
831 }
832
833 const ast::Expr * visit( const ast::OffsetPackExpr * node ) override final {
834 auto expr = visitBaseExpr( node,
835 new OffsetPackExpr(
836 get<StructInstType>().accept1(node->type)
837 )
838 );
839 this->node = expr;
840 return nullptr;
841 }
842
843 const ast::Expr * visit( const ast::LogicalExpr * node ) override final {
844 assert (node->isAnd == ast::LogicalFlag::AndExpr ||
845 node->isAnd == ast::LogicalFlag::OrExpr );
846 auto expr = visitBaseExpr( node,
847 new LogicalExpr(
848 get<Expression>().accept1(node->arg1),
849 get<Expression>().accept1(node->arg2),
850 (node->isAnd == ast::LogicalFlag::AndExpr)
851 )
852 );
853 this->node = expr;
854 return nullptr;
855 }
856
857 const ast::Expr * visit( const ast::ConditionalExpr * node ) override final {
858 auto expr = visitBaseExpr( node,
859 new ConditionalExpr(
860 get<Expression>().accept1(node->arg1),
861 get<Expression>().accept1(node->arg2),
862 get<Expression>().accept1(node->arg3)
863 )
864 );
865 this->node = expr;
866 return nullptr;
867 }
868
869 const ast::Expr * visit( const ast::CommaExpr * node ) override final {
870 auto expr = visitBaseExpr( node,
871 new CommaExpr(
872 get<Expression>().accept1(node->arg1),
873 get<Expression>().accept1(node->arg2)
874 )
875 );
876 this->node = expr;
877 return nullptr;
878 }
879
880 const ast::Expr * visit( const ast::TypeExpr * node ) override final {
881 auto expr = visitBaseExpr( node,
882 new TypeExpr(
883 get<Type>().accept1(node->type)
884 )
885 );
886 this->node = expr;
887 return nullptr;
888 }
889
890 const ast::Expr * visit( const ast::AsmExpr * node ) override final {
891 auto expr = visitBaseExpr( node,
892 new AsmExpr(
893 get<Expression>().accept1(node->inout),
894 get<Expression>().accept1(node->constraint),
895 get<Expression>().accept1(node->operand)
896 )
897 );
898 this->node = expr;
899 return nullptr;
900 }
901
902 const ast::Expr * visit( const ast::ImplicitCopyCtorExpr * node ) override final {
903 auto rslt = new ImplicitCopyCtorExpr(
904 get<ApplicationExpr>().accept1(node->callExpr)
905 );
906
907 rslt->tempDecls = get<ObjectDecl>().acceptL(node->tempDecls);
908 rslt->returnDecls = get<ObjectDecl>().acceptL(node->returnDecls);
909 rslt->dtors = get<Expression>().acceptL(node->dtors);
910
911 auto expr = visitBaseExpr( node, rslt );
912 this->node = expr;
913 return nullptr;
914 }
915
916 const ast::Expr * visit( const ast::ConstructorExpr * node ) override final {
917 auto expr = visitBaseExpr( node,
918 new ConstructorExpr(
919 get<Expression>().accept1(node->callExpr)
920 )
921 );
922 this->node = expr;
923 return nullptr;
924 }
925
926 const ast::Expr * visit( const ast::CompoundLiteralExpr * node ) override final {
927 auto expr = visitBaseExpr_skipResultType( node,
928 new CompoundLiteralExpr(
929 get<Type>().accept1(node->result),
930 get<Initializer>().accept1(node->init)
931 )
932 );
933 this->node = expr;
934 return nullptr;
935 }
936
937 const ast::Expr * visit( const ast::RangeExpr * node ) override final {
938 auto expr = visitBaseExpr( node,
939 new RangeExpr(
940 get<Expression>().accept1(node->low),
941 get<Expression>().accept1(node->high)
942 )
943 );
944 this->node = expr;
945 return nullptr;
946 }
947
948 const ast::Expr * visit( const ast::UntypedTupleExpr * node ) override final {
949 auto expr = visitBaseExpr( node,
950 new UntypedTupleExpr(
951 get<Expression>().acceptL(node->exprs)
952 )
953 );
954 this->node = expr;
955 return nullptr;
956 }
957
958 const ast::Expr * visit( const ast::TupleExpr * node ) override final {
959 auto expr = visitBaseExpr( node,
960 new UntypedTupleExpr(
961 get<Expression>().acceptL(node->exprs)
962 )
963 );
964 this->node = expr;
965 return nullptr;
966 }
967
968 const ast::Expr * visit( const ast::TupleIndexExpr * node ) override final {
969 auto expr = visitBaseExpr( node,
970 new TupleIndexExpr(
971 get<Expression>().accept1(node->tuple),
972 node->index
973 )
974 );
975 this->node = expr;
976 return nullptr;
977 }
978
979 const ast::Expr * visit( const ast::TupleAssignExpr * node ) override final {
980 auto expr = visitBaseExpr( node,
981 new TupleAssignExpr(
982 get<StmtExpr>().accept1(node->stmtExpr)
983 )
984 );
985 this->node = expr;
986 return nullptr;
987 }
988
989 const ast::Expr * visit( const ast::StmtExpr * node ) override final {
990 auto rslt = new StmtExpr(
991 get<CompoundStmt>().accept1(node->stmts)
992 );
993
994 rslt->returnDecls = get<ObjectDecl>().acceptL(node->returnDecls);
995 rslt->dtors = get<Expression>().acceptL(node->dtors);
996
997 auto expr = visitBaseExpr( node, rslt );
998 this->node = expr;
999 return nullptr;
1000 }
1001
1002 const ast::Expr * visit( const ast::UniqueExpr * node ) override final {
1003 auto rslt = new UniqueExpr(
1004 get<Expression>().accept1(node->expr)
1005 );
1006
1007 rslt->object = get<ObjectDecl> ().accept1(node->object);
1008 rslt->var = get<VariableExpr>().accept1(node->var);
1009
1010 auto expr = visitBaseExpr( node, rslt );
1011 this->node = expr;
1012 return nullptr;
1013 }
1014
1015 const ast::Expr * visit( const ast::UntypedInitExpr * node ) override final {
1016 std::list<InitAlternative> initAlts;
1017 for (auto ia : node->initAlts) {
1018 initAlts.push_back(InitAlternative(
1019 get<Type> ().accept1(ia.type),
1020 get<Designation>().accept1(ia.designation)
1021 ));
1022 }
1023 auto expr = visitBaseExpr( node,
1024 new UntypedInitExpr(
1025 get<Expression>().accept1(node->expr),
1026 initAlts
1027 )
1028 );
1029 this->node = expr;
1030 return nullptr;
1031 }
1032
1033 const ast::Expr * visit( const ast::InitExpr * node ) override final {
1034 auto expr = visitBaseExpr( node,
1035 new InitExpr(
1036 get<Expression>().accept1(node->expr),
1037 get<Designation>().accept1(node->designation)
1038 )
1039 );
1040 this->node = expr;
1041 return nullptr;
1042 }
1043
1044 const ast::Expr * visit( const ast::DeletedExpr * node ) override final {
1045 auto expr = visitBaseExpr( node,
1046 new DeletedExpr(
1047 get<Expression>().accept1(node->expr),
1048 inCache(node->deleteStmt) ?
1049 this->node :
1050 get<BaseSyntaxNode>().accept1(node->deleteStmt)
1051 )
1052 );
1053 this->node = expr;
1054 return nullptr;
1055 }
1056
1057 const ast::Expr * visit( const ast::DefaultArgExpr * node ) override final {
1058 auto expr = visitBaseExpr( node,
1059 new DefaultArgExpr(
1060 get<Expression>().accept1(node->expr)
1061 )
1062 );
1063 this->node = expr;
1064 return nullptr;
1065 }
1066
1067 const ast::Expr * visit( const ast::GenericExpr * node ) override final {
1068 std::list<GenericExpr::Association> associations;
1069 for (auto association : node->associations) {
1070 associations.push_back(GenericExpr::Association(
1071 get<Type> ().accept1(association.type),
1072 get<Expression>().accept1(association.expr)
1073 ));
1074 }
1075 auto expr = visitBaseExpr( node,
1076 new GenericExpr(
1077 get<Expression>().accept1(node->control),
1078 associations
1079 )
1080 );
1081 this->node = expr;
1082 return nullptr;
1083 }
1084
1085 const ast::Type * visit( const ast::VoidType * node ) override final {
1086 this->node = new VoidType{ cv( node ) };
1087 return nullptr;
1088 }
1089
1090 const ast::Type * visit( const ast::BasicType * node ) override final {
1091 this->node = new BasicType{ cv( node ), (BasicType::Kind)(unsigned)node->kind };
1092 return nullptr;
1093 }
1094
1095 const ast::Type * visit( const ast::PointerType * node ) override final {
1096 this->node = new PointerType{
1097 cv( node ),
1098 get<Type>().accept1( node->base ),
1099 get<Expression>().accept1( node->dimension ),
1100 (bool)node->isVarLen,
1101 (bool)node->isStatic
1102 };
1103 return nullptr;
1104 }
1105
1106 const ast::Type * visit( const ast::ArrayType * node ) override final {
1107 this->node = new ArrayType{
1108 cv( node ),
1109 get<Type>().accept1( node->base ),
1110 get<Expression>().accept1( node->dimension ),
1111 (bool)node->isVarLen,
1112 (bool)node->isStatic
1113 };
1114 return nullptr;
1115 }
1116
1117 const ast::Type * visit( const ast::ReferenceType * node ) override final {
1118 this->node = new ReferenceType{
1119 cv( node ),
1120 get<Type>().accept1( node->base )
1121 };
1122 return nullptr;
1123 }
1124
1125 const ast::Type * visit( const ast::QualifiedType * node ) override final {
1126 this->node = new QualifiedType{
1127 cv( node ),
1128 get<Type>().accept1( node->parent ),
1129 get<Type>().accept1( node->child )
1130 };
1131 return nullptr;
1132 }
1133
1134 const ast::Type * visit( const ast::FunctionType * node ) override final {
1135 auto ty = new FunctionType {
1136 cv( node ),
1137 (bool)node->isVarArgs
1138 };
1139 ty->returnVals = get<DeclarationWithType>().acceptL( node->returns );
1140 ty->parameters = get<DeclarationWithType>().acceptL( node->params );
1141 ty->forall = get<TypeDecl>().acceptL( node->forall );
1142 this->node = ty;
1143 return nullptr;
1144 }
1145
1146 void postvisit( const ast::ReferenceToType * old, ReferenceToType * ty ) {
1147 ty->forall = get<TypeDecl>().acceptL( old->forall );
1148 ty->parameters = get<Expression>().acceptL( old->params );
1149 ty->hoistType = old->hoistType;
1150 }
1151
1152 const ast::Type * visit( const ast::StructInstType * node ) override final {
1153 StructInstType * ty;
1154 if ( node->base ) {
1155 ty = new StructInstType{
1156 cv( node ),
1157 get<StructDecl>().accept1( node->base ),
1158 get<Attribute>().acceptL( node->attributes )
1159 };
1160 } else {
1161 ty = new StructInstType{
1162 cv( node ),
1163 node->name,
1164 get<Attribute>().acceptL( node->attributes )
1165 };
1166 }
1167 postvisit( node, ty );
1168 this->node = ty;
1169 return nullptr;
1170 }
1171
1172 const ast::Type * visit( const ast::UnionInstType * node ) override final {
1173 UnionInstType * ty;
1174 if ( node->base ) {
1175 ty = new UnionInstType{
1176 cv( node ),
1177 get<UnionDecl>().accept1( node->base ),
1178 get<Attribute>().acceptL( node->attributes )
1179 };
1180 } else {
1181 ty = new UnionInstType{
1182 cv( node ),
1183 node->name,
1184 get<Attribute>().acceptL( node->attributes )
1185 };
1186 }
1187 postvisit( node, ty );
1188 this->node = ty;
1189 return nullptr;
1190 }
1191
1192 const ast::Type * visit( const ast::EnumInstType * node ) override final {
1193 EnumInstType * ty;
1194 if ( node->base ) {
1195 ty = new EnumInstType{
1196 cv( node ),
1197 get<EnumDecl>().accept1( node->base ),
1198 get<Attribute>().acceptL( node->attributes )
1199 };
1200 } else {
1201 ty = new EnumInstType{
1202 cv( node ),
1203 node->name,
1204 get<Attribute>().acceptL( node->attributes )
1205 };
1206 }
1207 postvisit( node, ty );
1208 this->node = ty;
1209 return nullptr;
1210 }
1211
1212 const ast::Type * visit( const ast::TraitInstType * node ) override final {
1213 TraitInstType * ty;
1214 if ( node->base ) {
1215 ty = new TraitInstType{
1216 cv( node ),
1217 get<TraitDecl>().accept1( node->base ),
1218 get<Attribute>().acceptL( node->attributes )
1219 };
1220 } else {
1221 ty = new TraitInstType{
1222 cv( node ),
1223 node->name,
1224 get<Attribute>().acceptL( node->attributes )
1225 };
1226 }
1227 postvisit( node, ty );
1228 this->node = ty;
1229 return nullptr;
1230 }
1231
1232 const ast::Type * visit( const ast::TypeInstType * node ) override final {
1233 TypeInstType * ty;
1234 if ( node->base ) {
1235 ty = new TypeInstType{
1236 cv( node ),
1237 node->name,
1238 get<TypeDecl>().accept1( node->base ),
1239 get<Attribute>().acceptL( node->attributes )
1240 };
1241 } else {
1242 ty = new TypeInstType{
1243 cv( node ),
1244 node->name,
1245 node->kind == ast::TypeVar::Ftype,
1246 get<Attribute>().acceptL( node->attributes )
1247 };
1248 }
1249 postvisit( node, ty );
1250 this->node = ty;
1251 return nullptr;
1252 }
1253
1254 const ast::Type * visit( const ast::TupleType * node ) override final {
1255 this->node = new TupleType{
1256 cv( node ),
1257 get<Type>().acceptL( node->types )
1258 // members generated by TupleType c'tor
1259 };
1260 return nullptr;
1261 }
1262
1263 const ast::Type * visit( const ast::TypeofType * node ) override final {
1264 this->node = new TypeofType{
1265 cv( node ),
1266 get<Expression>().accept1( node->expr ),
1267 (bool)node->kind
1268 };
1269 return nullptr;
1270 }
1271
1272 const ast::Type * visit( const ast::VarArgsType * node ) override final {
1273 this->node = new VarArgsType{ cv( node ) };
1274 return nullptr;
1275 }
1276
1277 const ast::Type * visit( const ast::ZeroType * node ) override final {
1278 this->node = new ZeroType{ cv( node ) };
1279 return nullptr;
1280 }
1281
1282 const ast::Type * visit( const ast::OneType * node ) override final {
1283 this->node = new OneType{ cv( node ) };
1284 return nullptr;
1285 }
1286
1287 const ast::Type * visit( const ast::GlobalScopeType * ) override final {
1288 this->node = new GlobalScopeType{};
1289 return nullptr;
1290 }
1291
1292 const ast::Designation * visit( const ast::Designation * node ) override final {
1293 auto designation = new Designation( get<Expression>().acceptL( node->designators ) );
1294 designation->location = node->location;
1295 this->node = designation;
1296 return nullptr;
1297 }
1298
1299 const ast::Init * visit( const ast::SingleInit * node ) override final {
1300 auto init = new SingleInit(
1301 get<Expression>().accept1( node->value ),
1302 ast::MaybeConstruct == node->maybeConstructed
1303 );
1304 init->location = node->location;
1305 this->node = init;
1306 return nullptr;
1307 }
1308
1309 const ast::Init * visit( const ast::ListInit * node ) override final {
1310 auto init = new ListInit(
1311 get<Initializer>().acceptL( node->initializers ),
1312 get<Designation>().acceptL( node->designations ),
1313 ast::MaybeConstruct == node->maybeConstructed
1314 );
1315 init->location = node->location;
1316 this->node = init;
1317 return nullptr;
1318 }
1319
1320 const ast::Init * visit( const ast::ConstructorInit * node ) override final {
1321 auto init = new ConstructorInit(
1322 get<Statement>().accept1( node->ctor ),
1323 get<Statement>().accept1( node->dtor ),
1324 get<Initializer>().accept1( node->init )
1325 );
1326 init->location = node->location;
1327 this->node = init;
1328 return nullptr;
1329 }
1330
1331 const ast::Attribute * visit( const ast::Attribute * node ) override final {
1332 auto attr = new Attribute(
1333 node->name,
1334 get<Expression>().acceptL(node->params)
1335 );
1336 this->node = attr;
1337 return nullptr;
1338 }
1339
1340 const ast::TypeSubstitution * visit( const ast::TypeSubstitution * node ) override final {
1341 // Handled by convertTypeSubstitution helper instead.
1342 // TypeSubstitution is not a node in the old model, so the conversion result wouldn't fit in this->node.
1343 assert( 0 );
1344 (void)node;
1345 return nullptr;
1346 }
1347};
1348
1349std::list< Declaration * > convert( const std::list< ast::ptr< ast::Decl > > && translationUnit ) {
1350 ConverterNewToOld c;
1351 std::list< Declaration * > decls;
1352 for(auto d : translationUnit) {
1353 decls.emplace_back( c.decl( d ) );
1354 }
1355 return decls;
1356}
1357
1358//================================================================================================
1359
1360class ConverterOldToNew : public Visitor {
1361public:
1362 ast::Decl * decl() {
1363 return strict_dynamic_cast< ast::Decl * >( node );
1364 }
1365private:
1366 /// conversion output
1367 ast::Node * node;
1368 /// cache of nodes that might be referenced by readonly<> for de-duplication
1369 std::unordered_map< BaseSyntaxNode *, ast::Node * > cache;
1370
1371 // Local Utilities:
1372
1373 template<typename NewT, typename OldT>
1374 NewT * getAccept1( OldT old ) {
1375 if ( ! old ) return nullptr;
1376 old->accept(*this);
1377 return strict_dynamic_cast< NewT * >( node );
1378 }
1379
1380# define GET_ACCEPT_1(child, type) \
1381 getAccept1< ast::type, decltype( old->child ) >( old->child )
1382
1383 template<typename NewT, typename OldC>
1384 std::vector< ast::ptr<NewT> > getAcceptV( OldC& old ) {
1385 std::vector< ast::ptr<NewT> > ret;
1386 ret.reserve( old.size() );
1387 for ( auto a : old ) {
1388 a->accept( *this );
1389 ret.emplace_back( strict_dynamic_cast< NewT * >(node) );
1390 }
1391 return ret;
1392 }
1393
1394# define GET_ACCEPT_V(child, type) \
1395 getAcceptV< ast::type, decltype( old->child ) >( old->child )
1396
1397 ast::Label make_label(Label* old) {
1398 return ast::Label(
1399 old->labelled->location,
1400 old->name,
1401 GET_ACCEPT_V(attributes, Attribute)
1402 );
1403 }
1404
1405 template<template <class...> class C>
1406 C<ast::Label> make_labels(C<Label> olds) {
1407 C<ast::Label> ret;
1408 for (auto oldn : olds) {
1409 ret.push_back( make_label( &oldn ) );
1410 }
1411 return ret;
1412 }
1413
1414# define GET_LABELS_V(labels) \
1415 to<std::vector>::from( make_labels( std::move( labels ) ) )
1416
1417 static ast::CV::Qualifiers cv( Type * ty ) { return { ty->get_qualifiers().val }; }
1418
1419 /// returns true and sets `node` if in cache
1420 bool inCache( BaseSyntaxNode * old ) {
1421 auto it = cache.find( old );
1422 if ( it == cache.end() ) return false;
1423 node = it->second;
1424 return true;
1425 }
1426
1427 // Now all the visit functions:
1428
1429 virtual void visit( ObjectDecl * old ) override final {
1430 if ( inCache( old ) ) return;
1431 auto decl = new ast::ObjectDecl(
1432 old->location,
1433 old->name,
1434 GET_ACCEPT_1(type, Type),
1435 GET_ACCEPT_1(init, Init),
1436 { old->get_storageClasses().val },
1437 { old->linkage.val },
1438 GET_ACCEPT_1(bitfieldWidth, Expr),
1439 GET_ACCEPT_V(attributes, Attribute),
1440 { old->get_funcSpec().val }
1441 );
1442 cache.emplace( old, decl );
1443 decl->scopeLevel = old->scopeLevel;
1444 decl->mangleName = old->mangleName;
1445 decl->isDeleted = old->isDeleted;
1446 decl->uniqueId = old->uniqueId;
1447 decl->extension = old->extension;
1448
1449 this->node = decl;
1450 }
1451
1452 virtual void visit( FunctionDecl * old ) override final {
1453 if ( inCache( old ) ) return;
1454 auto decl = new ast::FunctionDecl{
1455 old->location,
1456 old->name,
1457 GET_ACCEPT_1(type, FunctionType),
1458 GET_ACCEPT_1(statements, CompoundStmt),
1459 { old->storageClasses.val },
1460 { old->linkage.val },
1461 GET_ACCEPT_V(attributes, Attribute),
1462 { old->get_funcSpec().val }
1463 };
1464 cache.emplace( old, decl );
1465 decl->scopeLevel = old->scopeLevel;
1466 decl->mangleName = old->mangleName;
1467 decl->isDeleted = old->isDeleted;
1468 decl->uniqueId = old->uniqueId;
1469 decl->extension = old->extension;
1470
1471 this->node = decl;
1472 }
1473
1474 virtual void visit( StructDecl * old ) override final {
1475 if ( inCache( old ) ) return;
1476 auto decl = new ast::StructDecl(
1477 old->location,
1478 old->name,
1479 old->kind,
1480 GET_ACCEPT_V(attributes, Attribute),
1481 { old->linkage.val }
1482 );
1483 cache.emplace( old, decl );
1484 decl->parent = GET_ACCEPT_1(parent, AggregateDecl);
1485 decl->body = old->body;
1486 decl->params = GET_ACCEPT_V(parameters, TypeDecl);
1487 decl->members = GET_ACCEPT_V(members, Decl);
1488 decl->extension = old->extension;
1489 decl->uniqueId = old->uniqueId;
1490 decl->storage = { old->storageClasses.val };
1491
1492 this->node = decl;
1493 }
1494
1495 virtual void visit( UnionDecl * old ) override final {
1496 if ( inCache( old ) ) return;
1497 auto decl = new ast::UnionDecl(
1498 old->location,
1499 old->name,
1500 GET_ACCEPT_V(attributes, Attribute),
1501 { old->linkage.val }
1502 );
1503 cache.emplace( old, decl );
1504 decl->parent = GET_ACCEPT_1(parent, AggregateDecl);
1505 decl->body = old->body;
1506 decl->params = GET_ACCEPT_V(parameters, TypeDecl);
1507 decl->members = GET_ACCEPT_V(members, Decl);
1508 decl->extension = old->extension;
1509 decl->uniqueId = old->uniqueId;
1510 decl->storage = { old->storageClasses.val };
1511
1512 this->node = decl;
1513 }
1514
1515 virtual void visit( EnumDecl * old ) override final {
1516 if ( inCache( old ) ) return;
1517 auto decl = new ast::UnionDecl(
1518 old->location,
1519 old->name,
1520 GET_ACCEPT_V(attributes, Attribute),
1521 { old->linkage.val }
1522 );
1523 cache.emplace( old, decl );
1524 decl->parent = GET_ACCEPT_1(parent, AggregateDecl);
1525 decl->body = old->body;
1526 decl->params = GET_ACCEPT_V(parameters, TypeDecl);
1527 decl->members = GET_ACCEPT_V(members, Decl);
1528 decl->extension = old->extension;
1529 decl->uniqueId = old->uniqueId;
1530 decl->storage = { old->storageClasses.val };
1531
1532 this->node = decl;
1533 }
1534
1535 virtual void visit( TraitDecl * old ) override final {
1536 if ( inCache( old ) ) return;
1537 auto decl = new ast::UnionDecl(
1538 old->location,
1539 old->name,
1540 GET_ACCEPT_V(attributes, Attribute),
1541 { old->linkage.val }
1542 );
1543 cache.emplace( old, decl );
1544 decl->parent = GET_ACCEPT_1(parent, AggregateDecl);
1545 decl->body = old->body;
1546 decl->params = GET_ACCEPT_V(parameters, TypeDecl);
1547 decl->members = GET_ACCEPT_V(members, Decl);
1548 decl->extension = old->extension;
1549 decl->uniqueId = old->uniqueId;
1550 decl->storage = { old->storageClasses.val };
1551
1552 this->node = decl;
1553 }
1554
1555 virtual void visit( TypeDecl * old ) override final {
1556 if ( inCache( old ) ) return;
1557 auto decl = new ast::TypeDecl{
1558 old->location,
1559 old->name,
1560 { old->storageClasses.val },
1561 GET_ACCEPT_1(base, Type),
1562 (ast::TypeVar::Kind)(unsigned)old->kind,
1563 old->sized,
1564 GET_ACCEPT_1(init, Type)
1565 };
1566 cache.emplace( old, decl );
1567 decl->assertions = GET_ACCEPT_V(assertions, DeclWithType);
1568 decl->params = GET_ACCEPT_V(parameters, TypeDecl);
1569 decl->extension = old->extension;
1570 decl->uniqueId = old->uniqueId;
1571
1572 this->node = decl;
1573 }
1574
1575 virtual void visit( TypedefDecl * old ) override final {
1576 auto decl = new ast::TypedefDecl(
1577 old->location,
1578 old->name,
1579 { old->storageClasses.val },
1580 GET_ACCEPT_1(base, Type),
1581 { old->linkage.val }
1582 );
1583 decl->assertions = GET_ACCEPT_V(assertions, DeclWithType);
1584 decl->params = GET_ACCEPT_V(parameters, TypeDecl);
1585 decl->extension = old->extension;
1586 decl->uniqueId = old->uniqueId;
1587 decl->storage = { old->storageClasses.val };
1588
1589 this->node = decl;
1590 }
1591
1592 virtual void visit( AsmDecl * old ) override final {
1593 auto decl = new ast::AsmDecl{
1594 old->location,
1595 GET_ACCEPT_1(stmt, AsmStmt)
1596 };
1597 decl->extension = old->extension;
1598 decl->uniqueId = old->uniqueId;
1599 decl->storage = { old->storageClasses.val };
1600
1601 this->node = decl;
1602 }
1603
1604 virtual void visit( StaticAssertDecl * old ) override final {
1605 auto decl = new ast::StaticAssertDecl{
1606 old->location,
1607 GET_ACCEPT_1(condition, Expr),
1608 GET_ACCEPT_1(message, ConstantExpr)
1609 };
1610 decl->extension = old->extension;
1611 decl->uniqueId = old->uniqueId;
1612 decl->storage = { old->storageClasses.val };
1613
1614 this->node = decl;
1615 }
1616
1617 virtual void visit( CompoundStmt * old ) override final {
1618 if ( inCache( old ) ) return;
1619 auto stmt = new ast::CompoundStmt(
1620 old->location,
1621 to<std::list>::from( GET_ACCEPT_V(kids, Stmt) ),
1622 GET_LABELS_V(old->labels)
1623 );
1624
1625 this->node = stmt;
1626 cache.emplace( old, this->node );
1627 }
1628
1629 virtual void visit( ExprStmt * old ) override final {
1630 if ( inCache( old ) ) return;
1631 this->node = new ast::ExprStmt(
1632 old->location,
1633 GET_ACCEPT_1(expr, Expr),
1634 GET_LABELS_V(old->labels)
1635 );
1636 cache.emplace( old, this->node );
1637 }
1638
1639 virtual void visit( AsmStmt * old ) override final {
1640 if ( inCache( old ) ) return;
1641 this->node = new ast::AsmStmt(
1642 old->location,
1643 old->voltile,
1644 GET_ACCEPT_1(instruction, Expr),
1645 GET_ACCEPT_V(output, Expr),
1646 GET_ACCEPT_V(input, Expr),
1647 GET_ACCEPT_V(clobber, ConstantExpr),
1648 GET_LABELS_V(old->gotolabels),
1649 GET_LABELS_V(old->labels)
1650 );
1651 cache.emplace( old, this->node );
1652 }
1653
1654 virtual void visit( DirectiveStmt * old ) override final {
1655 if ( inCache( old ) ) return;
1656 this->node = new ast::DirectiveStmt(
1657 old->location,
1658 old->directive,
1659 GET_LABELS_V(old->labels)
1660 );
1661 cache.emplace( old, this->node );
1662 }
1663
1664 virtual void visit( IfStmt * old ) override final {
1665 if ( inCache( old ) ) return;
1666 this->node = new ast::IfStmt(
1667 old->location,
1668 GET_ACCEPT_1(condition, Expr),
1669 GET_ACCEPT_1(thenPart, Stmt),
1670 GET_ACCEPT_1(elsePart, Stmt),
1671 GET_ACCEPT_V(initialization, Stmt),
1672 GET_LABELS_V(old->labels)
1673 );
1674 cache.emplace( old, this->node );
1675 }
1676
1677 virtual void visit( SwitchStmt * old ) override final {
1678 if ( inCache( old ) ) return;
1679 this->node = new ast::SwitchStmt(
1680 old->location,
1681 GET_ACCEPT_1(condition, Expr),
1682 GET_ACCEPT_V(statements, Stmt),
1683 GET_LABELS_V(old->labels)
1684 );
1685 cache.emplace( old, this->node );
1686 }
1687
1688 virtual void visit( CaseStmt * old ) override final {
1689 if ( inCache( old ) ) return;
1690 this->node = new ast::CaseStmt(
1691 old->location,
1692 GET_ACCEPT_1(condition, Expr),
1693 GET_ACCEPT_V(stmts, Stmt),
1694 GET_LABELS_V(old->labels)
1695 );
1696 cache.emplace( old, this->node );
1697 }
1698
1699 virtual void visit( WhileStmt * old ) override final {
1700 if ( inCache( old ) ) return;
1701 this->node = new ast::WhileStmt(
1702 old->location,
1703 GET_ACCEPT_1(condition, Expr),
1704 GET_ACCEPT_1(body, Stmt),
1705 GET_ACCEPT_V(initialization, Stmt),
1706 old->isDoWhile,
1707 GET_LABELS_V(old->labels)
1708 );
1709 cache.emplace( old, this->node );
1710 }
1711
1712 virtual void visit( ForStmt * old ) override final {
1713 if ( inCache( old ) ) return;
1714 this->node = new ast::ForStmt(
1715 old->location,
1716 GET_ACCEPT_V(initialization, Stmt),
1717 GET_ACCEPT_1(condition, Expr),
1718 GET_ACCEPT_1(increment, Expr),
1719 GET_ACCEPT_1(body, Stmt),
1720 GET_LABELS_V(old->labels)
1721 );
1722 cache.emplace( old, this->node );
1723 }
1724
1725 virtual void visit( BranchStmt * old ) override final {
1726 if ( inCache( old ) ) return;
1727 if (old->computedTarget) {
1728 this->node = new ast::BranchStmt(
1729 old->location,
1730 GET_ACCEPT_1(computedTarget, Expr),
1731 GET_LABELS_V(old->labels)
1732 );
1733 } else {
1734 ast::BranchStmt::Kind kind;
1735 switch (old->type) {
1736 #define CASE(n) \
1737 case BranchStmt::n: \
1738 kind = ast::BranchStmt::n; \
1739 break
1740 CASE(Goto);
1741 CASE(Break);
1742 CASE(Continue);
1743 CASE(FallThrough);
1744 CASE(FallThroughDefault);
1745 #undef CASE
1746 default:
1747 assertf(false, "Invalid BranchStmt::Type %d\n", old->type);
1748 }
1749
1750 Label label = old->originalTarget;
1751 auto stmt = new ast::BranchStmt(
1752 old->location,
1753 kind,
1754 make_label(&label),
1755 GET_LABELS_V(old->labels)
1756 );
1757 stmt->target = make_label(&old->target);
1758 this->node = stmt;
1759 }
1760 cache.emplace( old, this->node );
1761 }
1762
1763 virtual void visit( ReturnStmt * old ) override final {
1764 if ( inCache( old ) ) return;
1765 this->node = new ast::ReturnStmt(
1766 old->location,
1767 GET_ACCEPT_1(expr, Expr),
1768 GET_LABELS_V(old->labels)
1769 );
1770 cache.emplace( old, this->node );
1771 }
1772
1773 virtual void visit( ThrowStmt * old ) override final {
1774 if ( inCache( old ) ) return;
1775 ast::ThrowStmt::Kind kind;
1776 switch (old->kind) {
1777 case ThrowStmt::Terminate:
1778 kind = ast::ThrowStmt::Terminate;
1779 break;
1780 case ThrowStmt::Resume:
1781 kind = ast::ThrowStmt::Resume;
1782 break;
1783 default:
1784 assertf(false, "Invalid ThrowStmt::Kind %d\n", old->kind);
1785 }
1786
1787 this->node = new ast::ThrowStmt(
1788 old->location,
1789 kind,
1790 GET_ACCEPT_1(expr, Expr),
1791 GET_ACCEPT_1(target, Expr),
1792 GET_LABELS_V(old->labels)
1793 );
1794 cache.emplace( old, this->node );
1795 }
1796
1797 virtual void visit( TryStmt * old ) override final {
1798 if ( inCache( old ) ) return;
1799 this->node = new ast::TryStmt(
1800 old->location,
1801 GET_ACCEPT_1(block, CompoundStmt),
1802 GET_ACCEPT_V(handlers, CatchStmt),
1803 GET_ACCEPT_1(finallyBlock, FinallyStmt),
1804 GET_LABELS_V(old->labels)
1805 );
1806 cache.emplace( old, this->node );
1807 }
1808
1809 virtual void visit( CatchStmt * old ) override final {
1810 if ( inCache( old ) ) return;
1811 ast::CatchStmt::Kind kind;
1812 switch (old->kind) {
1813 case CatchStmt::Terminate:
1814 kind = ast::CatchStmt::Terminate;
1815 break;
1816 case CatchStmt::Resume:
1817 kind = ast::CatchStmt::Resume;
1818 break;
1819 default:
1820 assertf(false, "Invalid CatchStmt::Kind %d\n", old->kind);
1821 }
1822
1823 this->node = new ast::CatchStmt(
1824 old->location,
1825 kind,
1826 GET_ACCEPT_1(decl, Decl),
1827 GET_ACCEPT_1(cond, Expr),
1828 GET_ACCEPT_1(body, Stmt),
1829 GET_LABELS_V(old->labels)
1830 );
1831 cache.emplace( old, this->node );
1832 }
1833
1834 virtual void visit( FinallyStmt * old ) override final {
1835 if ( inCache( old ) ) return;
1836 this->node = new ast::FinallyStmt(
1837 old->location,
1838 GET_ACCEPT_1(block, CompoundStmt),
1839 GET_LABELS_V(old->labels)
1840 );
1841 cache.emplace( old, this->node );
1842 }
1843
1844 virtual void visit( WaitForStmt * old ) override final {
1845 if ( inCache( old ) ) return;
1846 ast::WaitForStmt * stmt = new ast::WaitForStmt(
1847 old->location,
1848 GET_LABELS_V(old->labels)
1849 );
1850
1851 stmt->clauses.reserve( old->clauses.size() );
1852 for (size_t i = 0 ; i < old->clauses.size() ; ++i) {
1853 stmt->clauses.push_back({
1854 ast::WaitForStmt::Target{
1855 GET_ACCEPT_1(clauses[i].target.function, Expr),
1856 GET_ACCEPT_V(clauses[i].target.arguments, Expr)
1857 },
1858 GET_ACCEPT_1(clauses[i].statement, Stmt),
1859 GET_ACCEPT_1(clauses[i].condition, Expr)
1860 });
1861 }
1862 stmt->timeout = {
1863 GET_ACCEPT_1(timeout.time, Expr),
1864 GET_ACCEPT_1(timeout.statement, Stmt),
1865 GET_ACCEPT_1(timeout.condition, Expr),
1866 };
1867 stmt->orElse = {
1868 GET_ACCEPT_1(timeout.statement, Stmt),
1869 GET_ACCEPT_1(timeout.condition, Expr),
1870 };
1871
1872 this->node = stmt;
1873 cache.emplace( old, this->node );
1874 }
1875
1876 virtual void visit( WithStmt * old ) override final {
1877 if ( inCache( old ) ) return;
1878 this->node = new ast::WithStmt(
1879 old->location,
1880 GET_ACCEPT_V(exprs, Expr),
1881 GET_ACCEPT_1(stmt, Stmt),
1882 GET_LABELS_V(old->labels)
1883 );
1884 cache.emplace( old, this->node );
1885 }
1886
1887 virtual void visit( NullStmt * old ) override final {
1888 if ( inCache( old ) ) return;
1889 this->node = new ast::NullStmt(
1890 old->location,
1891 GET_LABELS_V(old->labels)
1892 );
1893 cache.emplace( old, this->node );
1894 }
1895
1896 virtual void visit( DeclStmt * old ) override final {
1897 if ( inCache( old ) ) return;
1898 this->node = new ast::DeclStmt(
1899 old->location,
1900 GET_ACCEPT_1(decl, Decl),
1901 GET_LABELS_V(old->labels)
1902 );
1903 cache.emplace( old, this->node );
1904 }
1905
1906 virtual void visit( ImplicitCtorDtorStmt * old ) override final {
1907 if ( inCache( old ) ) return;
1908 auto stmt = new ast::ImplicitCtorDtorStmt(
1909 old->location,
1910 nullptr,
1911 GET_LABELS_V(old->labels)
1912 );
1913 this->node = stmt;
1914 cache.emplace( old, this->node );
1915 stmt->callStmt = GET_ACCEPT_1(callStmt, Stmt);
1916 }
1917
1918 ast::TypeSubstitution * convertTypeSubstitution(const TypeSubstitution * old) {
1919
1920 if (!old) return nullptr;
1921
1922 ast::TypeSubstitution *rslt = new ast::TypeSubstitution();
1923
1924 for (decltype(old->begin()) old_i = old->begin(); old_i != old->end(); old_i++) {
1925 rslt->add( old_i->first,
1926 getAccept1<ast::Type>(old_i->second) );
1927 }
1928
1929 for (decltype(old->beginVar()) old_i = old->beginVar(); old_i != old->endVar(); old_i++) {
1930 rslt->addVar( old_i->first,
1931 getAccept1<ast::Expr>(old_i->second) );
1932 }
1933
1934 return rslt;
1935 }
1936
1937 void convertInferUnion(ast::Expr::InferUnion &newInferred,
1938 const std::map<UniqueId,ParamEntry> &oldInferParams,
1939 const std::vector<UniqueId> &oldResnSlots) {
1940
1941 assert( oldInferParams.empty() || oldResnSlots.empty() );
1942 assert( newInferred.mode == ast::Expr::InferUnion::Empty );
1943
1944 if ( !oldInferParams.empty() ) {
1945 ast::InferredParams &tgt = newInferred.inferParams();
1946 for (auto old : oldInferParams) {
1947 tgt[old.first] = ast::ParamEntry(
1948 old.second.decl,
1949 getAccept1<ast::Type>(old.second.actualType),
1950 getAccept1<ast::Type>(old.second.formalType),
1951 getAccept1<ast::Expr>(old.second.expr)
1952 );
1953 }
1954 } else if ( !oldResnSlots.empty() ) {
1955 ast::ResnSlots &tgt = newInferred.resnSlots();
1956 for (auto old : oldResnSlots) {
1957 tgt.push_back(old);
1958 }
1959 }
1960 }
1961
1962 ast::Expr * visitBaseExpr_SkipResultType(Expression * old, ast::Expr * nw) {
1963
1964 nw->env = convertTypeSubstitution(old->env);
1965
1966 nw->extension = old->extension;
1967 convertInferUnion(nw->inferred, old->inferParams, old->resnSlots);
1968
1969 return nw;
1970 }
1971
1972 ast::Expr * visitBaseExpr(Expression * old, ast::Expr * nw) {
1973
1974 nw->result = GET_ACCEPT_1(result, Type);
1975 return visitBaseExpr_SkipResultType(old, nw);;
1976 }
1977
1978 virtual void visit( ApplicationExpr * old ) override final {
1979 this->node = visitBaseExpr( old,
1980 new ast::ApplicationExpr(
1981 old->location,
1982 GET_ACCEPT_1(function, Expr),
1983 GET_ACCEPT_V(args, Expr)
1984 )
1985 );
1986 }
1987
1988 virtual void visit( UntypedExpr * old ) override final {
1989 this->node = visitBaseExpr( old,
1990 new ast::UntypedExpr(
1991 old->location,
1992 GET_ACCEPT_1(function, Expr),
1993 GET_ACCEPT_V(args, Expr)
1994 )
1995 );
1996 }
1997
1998 virtual void visit( NameExpr * old ) override final {
1999 this->node = visitBaseExpr( old,
2000 new ast::NameExpr(
2001 old->location,
2002 old->get_name()
2003 )
2004 );
2005 }
2006
2007 virtual void visit( CastExpr * old ) override final {
2008 this->node = visitBaseExpr( old,
2009 new ast::CastExpr(
2010 old->location,
2011 GET_ACCEPT_1(arg, Expr),
2012 old->isGenerated ? ast::GeneratedCast : ast::ExplicitCast
2013 )
2014 );
2015 }
2016
2017 virtual void visit( KeywordCastExpr * old) override final {
2018 ast::KeywordCastExpr::Target castTarget = ast::KeywordCastExpr::NUMBER_OF_TARGETS;
2019 switch (old->target) {
2020 case KeywordCastExpr::Coroutine:
2021 castTarget = ast::KeywordCastExpr::Coroutine;
2022 break;
2023 case KeywordCastExpr::Thread:
2024 castTarget = ast::KeywordCastExpr::Thread;
2025 break;
2026 case KeywordCastExpr::Monitor:
2027 castTarget = ast::KeywordCastExpr::Monitor;
2028 break;
2029 default:
2030 break;
2031 }
2032 assert ( castTarget < ast::KeywordCastExpr::NUMBER_OF_TARGETS );
2033 this->node = visitBaseExpr( old,
2034 new ast::KeywordCastExpr(
2035 old->location,
2036 GET_ACCEPT_1(arg, Expr),
2037 castTarget
2038 )
2039 );
2040 }
2041
2042 virtual void visit( VirtualCastExpr * old ) override final {
2043 this->node = visitBaseExpr_SkipResultType( old,
2044 new ast::VirtualCastExpr(
2045 old->location,
2046 GET_ACCEPT_1(arg, Expr),
2047 GET_ACCEPT_1(result, Type)
2048 )
2049 );
2050 }
2051
2052 virtual void visit( AddressExpr * old ) override final {
2053 this->node = visitBaseExpr( old,
2054 new ast::AddressExpr(
2055 old->location,
2056 GET_ACCEPT_1(arg, Expr)
2057 )
2058 );
2059 }
2060
2061 virtual void visit( LabelAddressExpr * old ) override final {
2062 this->node = visitBaseExpr( old,
2063 new ast::LabelAddressExpr(
2064 old->location,
2065 make_label(&old->arg)
2066 )
2067 );
2068 }
2069
2070 virtual void visit( UntypedMemberExpr * old ) override final {
2071 this->node = visitBaseExpr( old,
2072 new ast::UntypedMemberExpr(
2073 old->location,
2074 GET_ACCEPT_1(member, Expr),
2075 GET_ACCEPT_1(aggregate, Expr)
2076 )
2077 );
2078 }
2079
2080 virtual void visit( MemberExpr * old ) override final {
2081 this->node = visitBaseExpr( old,
2082 new ast::MemberExpr(
2083 old->location,
2084 inCache(old->member) ?
2085 dynamic_cast<ast::DeclWithType *>(this->node) :
2086 GET_ACCEPT_1(member, DeclWithType),
2087 GET_ACCEPT_1(aggregate, Expr)
2088 )
2089 );
2090 }
2091
2092 virtual void visit( VariableExpr * old ) override final {
2093 this->node = visitBaseExpr( old,
2094 new ast::VariableExpr(
2095 old->location,
2096 inCache(old->var) ?
2097 dynamic_cast<ast::DeclWithType *>(this->node) :
2098 GET_ACCEPT_1(var, DeclWithType)
2099 )
2100 );
2101 }
2102
2103 bool isIntlikeConstantType(const Type *t) {
2104 if ( const BasicType * basicType = dynamic_cast< const BasicType * >( t ) ) {
2105 if ( basicType->isInteger() ) {
2106 return true;
2107 }
2108 } else if ( dynamic_cast< const OneType * >( t ) ) {
2109 return true;
2110 } else if ( dynamic_cast< const ZeroType * >( t ) ) {
2111 return true;
2112 } else if ( dynamic_cast< const PointerType * >( t ) ) {
2113 // null pointer constants, with zero int-values
2114 return true;
2115 }
2116 return false;
2117 }
2118
2119 int isFloatlikeConstantType(const Type *t) {
2120 if ( const BasicType * bty = dynamic_cast< const BasicType * >( t ) ) {
2121 if ( ! bty->isInteger() ) {
2122 return true;
2123 }
2124 }
2125 return false;
2126 }
2127
2128 int isStringlikeConstantType(const Type *t) {
2129 if ( const ArrayType * aty = dynamic_cast< const ArrayType * >( t ) ) {
2130 if ( const BasicType * bty = dynamic_cast< const BasicType * >( aty->base ) ) {
2131 if ( bty->kind == BasicType::Kind::Char ) {
2132 return true;
2133 }
2134 }
2135 }
2136 return false;
2137 }
2138
2139 virtual void visit( ConstantExpr * old ) override final {
2140 ast::ConstantExpr *rslt = nullptr;
2141 if (isIntlikeConstantType(old->result)) {
2142 rslt = new ast::ConstantExpr(
2143 old->location,
2144 GET_ACCEPT_1(result, Type),
2145 old->constant.get_value(),
2146 (unsigned long long) old->intValue()
2147 );
2148 } else if (isFloatlikeConstantType(old->result)) {
2149 rslt = new ast::ConstantExpr(
2150 old->location,
2151 GET_ACCEPT_1(result, Type),
2152 old->constant.get_value(),
2153 (double) old->constant.get_dval()
2154 );
2155 } else if (isStringlikeConstantType(old->result)) {
2156 rslt = ast::ConstantExpr::from_string(
2157 old->location,
2158 old->constant.get_value()
2159 );
2160 }
2161 assert(rslt);
2162 this->node = visitBaseExpr( old, rslt );
2163 }
2164
2165 virtual void visit( SizeofExpr * old ) override final {
2166 assert (old->expr || old->type);
2167 assert (! (old->expr && old->type));
2168 ast::SizeofExpr *rslt;
2169 if (old->expr) {
2170 assert(!old->isType);
2171 rslt = new ast::SizeofExpr(
2172 old->location,
2173 GET_ACCEPT_1(expr, Expr)
2174 );
2175 }
2176 if (old->type) {
2177 assert(old->isType);
2178 rslt = new ast::SizeofExpr(
2179 old->location,
2180 GET_ACCEPT_1(type, Type)
2181 );
2182 }
2183 this->node = visitBaseExpr( old, rslt );
2184 }
2185
2186 virtual void visit( AlignofExpr * old ) override final {
2187 assert (old->expr || old->type);
2188 assert (! (old->expr && old->type));
2189 ast::AlignofExpr *rslt;
2190 if (old->expr) {
2191 assert(!old->isType);
2192 rslt = new ast::AlignofExpr(
2193 old->location,
2194 GET_ACCEPT_1(expr, Expr)
2195 );
2196 }
2197 if (old->type) {
2198 assert(old->isType);
2199 rslt = new ast::AlignofExpr(
2200 old->location,
2201 GET_ACCEPT_1(type, Type)
2202 );
2203 }
2204 this->node = visitBaseExpr( old, rslt );
2205 }
2206
2207 virtual void visit( UntypedOffsetofExpr * old ) override final {
2208 this->node = visitBaseExpr( old,
2209 new ast::UntypedOffsetofExpr(
2210 old->location,
2211 GET_ACCEPT_1(type, Type),
2212 old->member
2213 )
2214 );
2215 }
2216
2217 virtual void visit( OffsetofExpr * old ) override final {
2218 this->node = visitBaseExpr( old,
2219 new ast::OffsetofExpr(
2220 old->location,
2221 GET_ACCEPT_1(type, Type),
2222 inCache(old->member) ?
2223 dynamic_cast<ast::DeclWithType *>(this->node) :
2224 GET_ACCEPT_1(member, DeclWithType)
2225 )
2226 );
2227 }
2228
2229 virtual void visit( OffsetPackExpr * old ) override final {
2230 this->node = visitBaseExpr( old,
2231 new ast::OffsetPackExpr(
2232 old->location,
2233 GET_ACCEPT_1(type, StructInstType)
2234 )
2235 );
2236 }
2237
2238 virtual void visit( LogicalExpr * old ) override final {
2239 this->node = visitBaseExpr( old,
2240 new ast::LogicalExpr(
2241 old->location,
2242 GET_ACCEPT_1(arg1, Expr),
2243 GET_ACCEPT_1(arg2, Expr),
2244 old->get_isAnd() ?
2245 ast::LogicalFlag::AndExpr :
2246 ast::LogicalFlag::OrExpr
2247 )
2248 );
2249 }
2250
2251 virtual void visit( ConditionalExpr * old ) override final {
2252 this->node = visitBaseExpr( old,
2253 new ast::ConditionalExpr(
2254 old->location,
2255 GET_ACCEPT_1(arg1, Expr),
2256 GET_ACCEPT_1(arg2, Expr),
2257 GET_ACCEPT_1(arg3, Expr)
2258 )
2259 );
2260 }
2261
2262 virtual void visit( CommaExpr * old ) override final {
2263 this->node = visitBaseExpr( old,
2264 new ast::CommaExpr(
2265 old->location,
2266 GET_ACCEPT_1(arg1, Expr),
2267 GET_ACCEPT_1(arg2, Expr)
2268 )
2269 );
2270 }
2271
2272 virtual void visit( TypeExpr * old ) override final {
2273 this->node = visitBaseExpr( old,
2274 new ast::TypeExpr(
2275 old->location,
2276 GET_ACCEPT_1(type, Type)
2277 )
2278 );
2279 }
2280
2281 virtual void visit( AsmExpr * old ) override final {
2282 this->node = visitBaseExpr( old,
2283 new ast::AsmExpr(
2284 old->location,
2285 GET_ACCEPT_1(inout, Expr),
2286 GET_ACCEPT_1(constraint, Expr),
2287 GET_ACCEPT_1(operand, Expr)
2288 )
2289 );
2290 }
2291
2292 virtual void visit( ImplicitCopyCtorExpr * old ) override final {
2293 auto rslt = new ast::ImplicitCopyCtorExpr(
2294 old->location,
2295 GET_ACCEPT_1(callExpr, ApplicationExpr)
2296 );
2297
2298 rslt->tempDecls = GET_ACCEPT_V(tempDecls, ObjectDecl);
2299 rslt->returnDecls = GET_ACCEPT_V(returnDecls, ObjectDecl);
2300 rslt->dtors = GET_ACCEPT_V(dtors, Expr);
2301
2302 this->node = visitBaseExpr( old, rslt );
2303 }
2304
2305 virtual void visit( ConstructorExpr * old ) override final {
2306 this->node = visitBaseExpr( old,
2307 new ast::ConstructorExpr(
2308 old->location,
2309 GET_ACCEPT_1(callExpr, Expr)
2310 )
2311 );
2312 }
2313
2314 virtual void visit( CompoundLiteralExpr * old ) override final {
2315 this->node = visitBaseExpr_SkipResultType( old,
2316 new ast::CompoundLiteralExpr(
2317 old->location,
2318 GET_ACCEPT_1(result, Type),
2319 GET_ACCEPT_1(initializer, Init)
2320 )
2321 );
2322 }
2323
2324 virtual void visit( RangeExpr * old ) override final {
2325 this->node = visitBaseExpr( old,
2326 new ast::RangeExpr(
2327 old->location,
2328 GET_ACCEPT_1(low, Expr),
2329 GET_ACCEPT_1(high, Expr)
2330 )
2331 );
2332 }
2333
2334 virtual void visit( UntypedTupleExpr * old ) override final {
2335 this->node = visitBaseExpr( old,
2336 new ast::UntypedTupleExpr(
2337 old->location,
2338 GET_ACCEPT_V(exprs, Expr)
2339 )
2340 );
2341 }
2342
2343 virtual void visit( TupleExpr * old ) override final {
2344 this->node = visitBaseExpr( old,
2345 new ast::TupleExpr(
2346 old->location,
2347 GET_ACCEPT_V(exprs, Expr)
2348 )
2349 );
2350 }
2351
2352 virtual void visit( TupleIndexExpr * old ) override final {
2353 this->node = visitBaseExpr( old,
2354 new ast::TupleIndexExpr(
2355 old->location,
2356 GET_ACCEPT_1(tuple, Expr),
2357 old->index
2358 )
2359 );
2360 }
2361
2362 virtual void visit( TupleAssignExpr * old ) override final {
2363 this->node = visitBaseExpr_SkipResultType( old,
2364 new ast::TupleAssignExpr(
2365 old->location,
2366 GET_ACCEPT_1(result, Type),
2367 GET_ACCEPT_1(stmtExpr, StmtExpr)
2368 )
2369 );
2370 }
2371
2372 virtual void visit( StmtExpr * old ) override final {
2373 auto rslt = new ast::StmtExpr(
2374 old->location,
2375 GET_ACCEPT_1(statements, CompoundStmt)
2376 );
2377 rslt->returnDecls = GET_ACCEPT_V(returnDecls, ObjectDecl);
2378 rslt->dtors = GET_ACCEPT_V(dtors , Expr);
2379
2380 this->node = visitBaseExpr_SkipResultType( old, rslt );
2381 }
2382
2383 virtual void visit( UniqueExpr * old ) override final {
2384 auto rslt = new ast::UniqueExpr(
2385 old->location,
2386 GET_ACCEPT_1(expr, Expr)
2387 );
2388 rslt->object = GET_ACCEPT_1(object, ObjectDecl);
2389 rslt->var = GET_ACCEPT_1(var , VariableExpr);
2390
2391 this->node = visitBaseExpr( old, rslt );
2392 }
2393
2394 virtual void visit( UntypedInitExpr * old ) override final {
2395 std::vector<ast::InitAlternative> initAlts;
2396 for (auto ia : old->initAlts) {
2397 initAlts.push_back(ast::InitAlternative(
2398 getAccept1< ast::Type, Type * >( ia.type ),
2399 getAccept1< ast::Designation, Designation * >( ia.designation )
2400 ));
2401 }
2402 this->node = visitBaseExpr( old,
2403 new ast::UntypedInitExpr(
2404 old->location,
2405 GET_ACCEPT_1(expr, Expr),
2406 std::move(initAlts)
2407 )
2408 );
2409 }
2410
2411 virtual void visit( InitExpr * old ) override final {
2412 this->node = visitBaseExpr( old,
2413 new ast::InitExpr(
2414 old->location,
2415 GET_ACCEPT_1(expr, Expr),
2416 GET_ACCEPT_1(designation, Designation)
2417 )
2418 );
2419 }
2420
2421 virtual void visit( DeletedExpr * old ) override final {
2422 this->node = visitBaseExpr( old,
2423 new ast::DeletedExpr(
2424 old->location,
2425 GET_ACCEPT_1(expr, Expr),
2426 inCache(old->deleteStmt) ?
2427 this->node :
2428 GET_ACCEPT_1(deleteStmt, Node)
2429 )
2430 );
2431 }
2432
2433 virtual void visit( DefaultArgExpr * old ) override final {
2434 this->node = visitBaseExpr( old,
2435 new ast::DefaultArgExpr(
2436 old->location,
2437 GET_ACCEPT_1(expr, Expr)
2438 )
2439 );
2440 }
2441
2442 virtual void visit( GenericExpr * old ) override final {
2443 std::vector<ast::GenericExpr::Association> associations;
2444 for (auto association : old->associations) {
2445 associations.push_back(ast::GenericExpr::Association(
2446 getAccept1< ast::Type, Type * >( association.type ),
2447 getAccept1< ast::Expr, Expression * >( association.expr )
2448 ));
2449 }
2450 this->node = visitBaseExpr( old,
2451 new ast::GenericExpr(
2452 old->location,
2453 GET_ACCEPT_1(control, Expr),
2454 std::move(associations)
2455 )
2456 );
2457 }
2458
2459 virtual void visit( VoidType * old ) override final {
2460 this->node = new ast::VoidType{ cv( old ) };
2461 }
2462
2463 virtual void visit( BasicType * old ) override final {
2464 this->node = new ast::BasicType{ (ast::BasicType::Kind)(unsigned)old->kind, cv( old ) };
2465 }
2466
2467 virtual void visit( PointerType * old ) override final {
2468 this->node = new ast::PointerType{
2469 GET_ACCEPT_1( base, Type ),
2470 GET_ACCEPT_1( dimension, Expr ),
2471 (ast::LengthFlag)old->isVarLen,
2472 (ast::DimensionFlag)old->isStatic,
2473 cv( old )
2474 };
2475 }
2476
2477 virtual void visit( ArrayType * old ) override final {
2478 this->node = new ast::ArrayType{
2479 GET_ACCEPT_1( base, Type ),
2480 GET_ACCEPT_1( dimension, Expr ),
2481 (ast::LengthFlag)old->isVarLen,
2482 (ast::DimensionFlag)old->isStatic,
2483 cv( old )
2484 };
2485 }
2486
2487 virtual void visit( ReferenceType * old ) override final {
2488 this->node = new ast::ReferenceType{
2489 GET_ACCEPT_1( base, Type ),
2490 cv( old )
2491 };
2492 }
2493
2494 virtual void visit( QualifiedType * old ) override final {
2495 this->node = new ast::QualifiedType{
2496 GET_ACCEPT_1( parent, Type ),
2497 GET_ACCEPT_1( child, Type ),
2498 cv( old )
2499 };
2500 }
2501
2502 virtual void visit( FunctionType * old ) override final {
2503 auto ty = new ast::FunctionType {
2504 (ast::ArgumentFlag)old->isVarArgs,
2505 cv( old )
2506 };
2507 ty->returns = GET_ACCEPT_V( returnVals, DeclWithType );
2508 ty->params = GET_ACCEPT_V( parameters, DeclWithType );
2509 ty->forall = GET_ACCEPT_V( forall, TypeDecl );
2510 this->node = ty;
2511 }
2512
2513 void postvisit( ReferenceToType * old, ast::ReferenceToType * ty ) {
2514 ty->forall = GET_ACCEPT_V( forall, TypeDecl );
2515 ty->params = GET_ACCEPT_V( parameters, Expr );
2516 ty->hoistType = old->hoistType;
2517 }
2518
2519 virtual void visit( StructInstType * old ) override final {
2520 ast::StructInstType * ty;
2521 if ( old->baseStruct ) {
2522 ty = new ast::StructInstType{
2523 GET_ACCEPT_1( baseStruct, StructDecl ),
2524 cv( old ),
2525 GET_ACCEPT_V( attributes, Attribute )
2526 };
2527 } else {
2528 ty = new ast::StructInstType{
2529 old->name,
2530 cv( old ),
2531 GET_ACCEPT_V( attributes, Attribute )
2532 };
2533 }
2534 postvisit( old, ty );
2535 this->node = ty;
2536 }
2537
2538 virtual void visit( UnionInstType * old ) override final {
2539 ast::UnionInstType * ty;
2540 if ( old->baseUnion ) {
2541 ty = new ast::UnionInstType{
2542 GET_ACCEPT_1( baseUnion, UnionDecl ),
2543 cv( old ),
2544 GET_ACCEPT_V( attributes, Attribute )
2545 };
2546 } else {
2547 ty = new ast::UnionInstType{
2548 old->name,
2549 cv( old ),
2550 GET_ACCEPT_V( attributes, Attribute )
2551 };
2552 }
2553 postvisit( old, ty );
2554 this->node = ty;
2555 }
2556
2557 virtual void visit( EnumInstType * old ) override final {
2558 ast::EnumInstType * ty;
2559 if ( old->baseEnum ) {
2560 ty = new ast::EnumInstType{
2561 GET_ACCEPT_1( baseEnum, EnumDecl ),
2562 cv( old ),
2563 GET_ACCEPT_V( attributes, Attribute )
2564 };
2565 } else {
2566 ty = new ast::EnumInstType{
2567 old->name,
2568 cv( old ),
2569 GET_ACCEPT_V( attributes, Attribute )
2570 };
2571 }
2572 postvisit( old, ty );
2573 this->node = ty;
2574 }
2575
2576 virtual void visit( TraitInstType * old ) override final {
2577 ast::TraitInstType * ty;
2578 if ( old->baseTrait ) {
2579 ty = new ast::TraitInstType{
2580 GET_ACCEPT_1( baseTrait, TraitDecl ),
2581 cv( old ),
2582 GET_ACCEPT_V( attributes, Attribute )
2583 };
2584 } else {
2585 ty = new ast::TraitInstType{
2586 old->name,
2587 cv( old ),
2588 GET_ACCEPT_V( attributes, Attribute )
2589 };
2590 }
2591 postvisit( old, ty );
2592 this->node = ty;
2593 }
2594
2595 virtual void visit( TypeInstType * old ) override final {
2596 ast::TypeInstType * ty;
2597 if ( old->baseType ) {
2598 ty = new ast::TypeInstType{
2599 old->name,
2600 GET_ACCEPT_1( baseType, TypeDecl ),
2601 cv( old ),
2602 GET_ACCEPT_V( attributes, Attribute )
2603 };
2604 } else {
2605 ty = new ast::TypeInstType{
2606 old->name,
2607 old->isFtype ? ast::TypeVar::Ftype : ast::TypeVar::Dtype,
2608 cv( old ),
2609 GET_ACCEPT_V( attributes, Attribute )
2610 };
2611 }
2612 postvisit( old, ty );
2613 this->node = ty;
2614 }
2615
2616 virtual void visit( TupleType * old ) override final {
2617 this->node = new ast::TupleType{
2618 GET_ACCEPT_V( types, Type ),
2619 // members generated by TupleType c'tor
2620 cv( old )
2621 };
2622 }
2623
2624 virtual void visit( TypeofType * old ) override final {
2625 this->node = new ast::TypeofType{
2626 GET_ACCEPT_1( expr, Expr ),
2627 (ast::TypeofType::Kind)old->is_basetypeof,
2628 cv( old )
2629 };
2630 }
2631
2632 virtual void visit( AttrType * ) override final {
2633 assertf( false, "AttrType deprecated in new AST." );
2634 }
2635
2636 virtual void visit( VarArgsType * old ) override final {
2637 this->node = new ast::VarArgsType{ cv( old ) };
2638 }
2639
2640 virtual void visit( ZeroType * old ) override final {
2641 this->node = new ast::ZeroType{ cv( old ) };
2642 }
2643
2644 virtual void visit( OneType * old ) override final {
2645 this->node = new ast::OneType{ cv( old ) };
2646 }
2647
2648 virtual void visit( GlobalScopeType * ) override final {
2649 this->node = new ast::GlobalScopeType{};
2650 }
2651
2652 virtual void visit( Designation * old ) override final {
2653 this->node = new ast::Designation(
2654 old->location,
2655 GET_ACCEPT_V(designators, Expr)
2656 );
2657 }
2658
2659 virtual void visit( SingleInit * old ) override final {
2660 this->node = new ast::SingleInit(
2661 old->location,
2662 GET_ACCEPT_1(value, Expr),
2663 (old->get_maybeConstructed()) ? ast::MaybeConstruct : ast::DoConstruct
2664 );
2665 }
2666
2667 virtual void visit( ListInit * old ) override final {
2668 this->node = new ast::ListInit(
2669 old->location,
2670 GET_ACCEPT_V(initializers, Init),
2671 GET_ACCEPT_V(designations, Designation),
2672 (old->get_maybeConstructed()) ? ast::MaybeConstruct : ast::DoConstruct
2673 );
2674 }
2675
2676 virtual void visit( ConstructorInit * old ) override final {
2677 this->node = new ast::ConstructorInit(
2678 old->location,
2679 GET_ACCEPT_1(ctor, Stmt),
2680 GET_ACCEPT_1(dtor, Stmt),
2681 GET_ACCEPT_1(init, Init)
2682 );
2683 }
2684
2685 virtual void visit( Constant * ) override final {
2686 // Handled in visit( ConstantEpxr * ).
2687 // In the new tree, Constant fields are inlined into containing ConstantExpression.
2688 assert( 0 );
2689 }
2690
2691 virtual void visit( Attribute * old ) override final {
2692 this->node = new ast::Attribute(
2693 old->name,
2694 GET_ACCEPT_V( parameters, Expr )
2695 );
2696 }
2697
2698 virtual void visit( AttrExpr * ) override final {
2699 assertf( false, "AttrExpr deprecated in new AST." );
2700 }
2701};
2702
2703#undef GET_LABELS_V
2704#undef GET_ACCEPT_V
2705#undef GET_ACCEPT_1
2706
2707std::list< ast::ptr< ast::Decl > > convert( const std::list< Declaration * > && translationUnit ) {
2708 ConverterOldToNew c;
2709 std::list< ast::ptr< ast::Decl > > decls;
2710 for(auto d : translationUnit) {
2711 d->accept( c );
2712 decls.emplace_back( c.decl() );
2713 }
2714 deleteAll(translationUnit);
2715 return decls;
2716}
Note: See TracBrowser for help on using the repository browser.