source: src/AST/Convert.cpp@ 043a5b6

ADT arm-eh ast-experimental enum forall-pointer-decay jacob/cs343-translation jenkins-sandbox new-ast new-ast-unique-expr pthread-emulation qualifiedEnum stuck-waitfor-destruct
Last change on this file since 043a5b6 was 043a5b6, checked in by Thierry Delisle <tdelisle@…>, 7 years ago

Extended dereference operator hack to destroy clause

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