source: src/AST/Convert.cpp@ 9d6e7fa9

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 9d6e7fa9 was 0b57626, checked in by Andrew Beach <ajbeach@…>, 6 years ago

Silenced a warning and removed trailing whitespace.

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