Changeset f53acdf8 for src


Ignore:
Timestamp:
Jul 19, 2019, 2:16:01 PM (6 years ago)
Author:
Thierry Delisle <tdelisle@…>
Branches:
ADT, arm-eh, ast-experimental, enum, forall-pointer-decay, jacob/cs343-translation, master, new-ast, new-ast-unique-expr, pthread-emulation, qualifiedEnum
Children:
4eb43fa
Parents:
1f1c102 (diff), 8ac3b0e (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the (diff) links above to see all the changes relative to each parent.
Message:

Merge branch 'master' into new-ast

Location:
src
Files:
53 edited

Legend:

Unmodified
Added
Removed
  • src/AST/Convert.cpp

    r1f1c102 rf53acdf8  
    518518        }
    519519
    520         const ast::Stmt * visit( const ast::WithStmt * node ) override final {
     520        const ast::Decl * visit( const ast::WithStmt * node ) override final {
    521521                if ( inCache( node ) ) return nullptr;
    522522                auto stmt = new WithStmt(
     
    524524                        get<Statement>().accept1( node->stmt )
    525525                );
    526                 return stmtPostamble( stmt, node );
     526                declPostamble( stmt, node );
     527                return nullptr;
    527528        }
    528529
     
    10391040                                get<Expression>().accept1(node->expr),
    10401041                                inCache(node->deleteStmt) ?
    1041                                         this->node :
    1042                                         get<BaseSyntaxNode>().accept1(node->deleteStmt)
     1042                                        strict_dynamic_cast<Declaration*>(this->node) :
     1043                                        get<Declaration>().accept1(node->deleteStmt)
    10431044                        )
    10441045                );
     
    13551356        ast::Node * node = nullptr;
    13561357        /// cache of nodes that might be referenced by readonly<> for de-duplication
    1357         std::unordered_map< BaseSyntaxNode *, ast::Node * > cache = {};
     1358        std::unordered_map< const BaseSyntaxNode *, ast::Node * > cache = {};
    13581359
    13591360        // Local Utilities:
     
    14221423                to<std::vector>::from( make_labels( std::move( labels ) ) )
    14231424
    1424         static ast::CV::Qualifiers cv( Type * ty ) { return { ty->get_qualifiers().val }; }
     1425        static ast::CV::Qualifiers cv( const Type * ty ) { return { ty->tq.val }; }
    14251426
    14261427        /// returns true and sets `node` if in cache
    1427         bool inCache( BaseSyntaxNode * old ) {
     1428        bool inCache( const BaseSyntaxNode * old ) {
    14281429                auto it = cache.find( old );
    14291430                if ( it == cache.end() ) return false;
     
    14341435        // Now all the visit functions:
    14351436
    1436         virtual void visit( ObjectDecl * old ) override final {
     1437        virtual void visit( const ObjectDecl * old ) override final {
    14371438                auto&& type = GET_ACCEPT_1(type, Type);
    14381439                auto&& init = GET_ACCEPT_1(init, Init);
     
    14651466        }
    14661467
    1467         virtual void visit( FunctionDecl * old ) override final {
     1468        virtual void visit( const FunctionDecl * old ) override final {
    14681469                if ( inCache( old ) ) return;
    14691470                auto decl = new ast::FunctionDecl{
     
    14981499        }
    14991500
    1500         virtual void visit( StructDecl * old ) override final {
     1501        virtual void visit( const StructDecl * old ) override final {
    15011502                if ( inCache( old ) ) return;
    15021503                auto decl = new ast::StructDecl(
     
    15231524        }
    15241525
    1525         virtual void visit( UnionDecl * old ) override final {
     1526        virtual void visit( const UnionDecl * old ) override final {
    15261527                if ( inCache( old ) ) return;
    15271528                auto decl = new ast::UnionDecl(
     
    15431544        }
    15441545
    1545         virtual void visit( EnumDecl * old ) override final {
     1546        virtual void visit( const EnumDecl * old ) override final {
    15461547                if ( inCache( old ) ) return;
    15471548                auto decl = new ast::EnumDecl(
     
    15631564        }
    15641565
    1565         virtual void visit( TraitDecl * old ) override final {
     1566        virtual void visit( const TraitDecl * old ) override final {
    15661567                if ( inCache( old ) ) return;
    15671568                auto decl = new ast::TraitDecl(
     
    15831584        }
    15841585
    1585         virtual void visit( TypeDecl * old ) override final {
     1586        virtual void visit( const TypeDecl * old ) override final {
    15861587                if ( inCache( old ) ) return;
    15871588                auto decl = new ast::TypeDecl{
     
    16031604        }
    16041605
    1605         virtual void visit( TypedefDecl * old ) override final {
     1606        virtual void visit( const TypedefDecl * old ) override final {
    16061607                auto decl = new ast::TypedefDecl(
    16071608                        old->location,
     
    16201621        }
    16211622
    1622         virtual void visit( AsmDecl * old ) override final {
     1623        virtual void visit( const AsmDecl * old ) override final {
    16231624                auto decl = new ast::AsmDecl{
    16241625                        old->location,
     
    16321633        }
    16331634
    1634         virtual void visit( StaticAssertDecl * old ) override final {
     1635        virtual void visit( const StaticAssertDecl * old ) override final {
    16351636                auto decl = new ast::StaticAssertDecl{
    16361637                        old->location,
     
    16451646        }
    16461647
    1647         virtual void visit( CompoundStmt * old ) override final {
     1648        virtual void visit( const CompoundStmt * old ) override final {
    16481649                if ( inCache( old ) ) return;
    16491650                auto stmt = new ast::CompoundStmt(
     
    16571658        }
    16581659
    1659         virtual void visit( ExprStmt * old ) override final {
     1660        virtual void visit( const ExprStmt * old ) override final {
    16601661                if ( inCache( old ) ) return;
    16611662                this->node = new ast::ExprStmt(
     
    16671668        }
    16681669
    1669         virtual void visit( AsmStmt * old ) override final {
     1670        virtual void visit( const AsmStmt * old ) override final {
    16701671                if ( inCache( old ) ) return;
    16711672                this->node = new ast::AsmStmt(
     
    16821683        }
    16831684
    1684         virtual void visit( DirectiveStmt * old ) override final {
     1685        virtual void visit( const DirectiveStmt * old ) override final {
    16851686                if ( inCache( old ) ) return;
    16861687                this->node = new ast::DirectiveStmt(
     
    16921693        }
    16931694
    1694         virtual void visit( IfStmt * old ) override final {
     1695        virtual void visit( const IfStmt * old ) override final {
    16951696                if ( inCache( old ) ) return;
    16961697                this->node = new ast::IfStmt(
     
    17051706        }
    17061707
    1707         virtual void visit( SwitchStmt * old ) override final {
     1708        virtual void visit( const SwitchStmt * old ) override final {
    17081709                if ( inCache( old ) ) return;
    17091710                this->node = new ast::SwitchStmt(
     
    17161717        }
    17171718
    1718         virtual void visit( CaseStmt * old ) override final {
     1719        virtual void visit( const CaseStmt * old ) override final {
    17191720                if ( inCache( old ) ) return;
    17201721                this->node = new ast::CaseStmt(
     
    17271728        }
    17281729
    1729         virtual void visit( WhileStmt * old ) override final {
     1730        virtual void visit( const WhileStmt * old ) override final {
    17301731                if ( inCache( old ) ) return;
    17311732                this->node = new ast::WhileStmt(
     
    17401741        }
    17411742
    1742         virtual void visit( ForStmt * old ) override final {
     1743        virtual void visit( const ForStmt * old ) override final {
    17431744                if ( inCache( old ) ) return;
    17441745                this->node = new ast::ForStmt(
     
    17531754        }
    17541755
    1755         virtual void visit( BranchStmt * old ) override final {
     1756        virtual void visit( const BranchStmt * old ) override final {
    17561757                if ( inCache( old ) ) return;
    17571758                if (old->computedTarget) {
     
    17901791        }
    17911792
    1792         virtual void visit( ReturnStmt * old ) override final {
     1793        virtual void visit( const ReturnStmt * old ) override final {
    17931794                if ( inCache( old ) ) return;
    17941795                this->node = new ast::ReturnStmt(
     
    18001801        }
    18011802
    1802         virtual void visit( ThrowStmt * old ) override final {
     1803        virtual void visit( const ThrowStmt * old ) override final {
    18031804                if ( inCache( old ) ) return;
    18041805                ast::ExceptionKind kind;
     
    18241825        }
    18251826
    1826         virtual void visit( TryStmt * old ) override final {
     1827        virtual void visit( const TryStmt * old ) override final {
    18271828                if ( inCache( old ) ) return;
    18281829                this->node = new ast::TryStmt(
     
    18361837        }
    18371838
    1838         virtual void visit( CatchStmt * old ) override final {
     1839        virtual void visit( const CatchStmt * old ) override final {
    18391840                if ( inCache( old ) ) return;
    18401841                ast::ExceptionKind kind;
     
    18611862        }
    18621863
    1863         virtual void visit( FinallyStmt * old ) override final {
     1864        virtual void visit( const FinallyStmt * old ) override final {
    18641865                if ( inCache( old ) ) return;
    18651866                this->node = new ast::FinallyStmt(
     
    18711872        }
    18721873
    1873         virtual void visit( WaitForStmt * old ) override final {
     1874        virtual void visit( const WaitForStmt * old ) override final {
    18741875                if ( inCache( old ) ) return;
    18751876                ast::WaitForStmt * stmt = new ast::WaitForStmt(
     
    19031904        }
    19041905
    1905         virtual void visit( WithStmt * old ) override final {
     1906        virtual void visit( const WithStmt * old ) override final {
    19061907                if ( inCache( old ) ) return;
    19071908                this->node = new ast::WithStmt(
    19081909                        old->location,
    19091910                        GET_ACCEPT_V(exprs, Expr),
    1910                         GET_ACCEPT_1(stmt, Stmt),
    1911                         GET_LABELS_V(old->labels)
     1911                        GET_ACCEPT_1(stmt, Stmt)
    19121912                );
    19131913                cache.emplace( old, this->node );
    19141914        }
    19151915
    1916         virtual void visit( NullStmt * old ) override final {
     1916        virtual void visit( const NullStmt * old ) override final {
    19171917                if ( inCache( old ) ) return;
    19181918                this->node = new ast::NullStmt(
     
    19231923        }
    19241924
    1925         virtual void visit( DeclStmt * old ) override final {
     1925        virtual void visit( const DeclStmt * old ) override final {
    19261926                if ( inCache( old ) ) return;
    19271927                this->node = new ast::DeclStmt(
     
    19331933        }
    19341934
    1935         virtual void visit( ImplicitCtorDtorStmt * old ) override final {
     1935        virtual void visit( const ImplicitCtorDtorStmt * old ) override final {
    19361936                if ( inCache( old ) ) return;
    19371937                auto stmt = new ast::ImplicitCtorDtorStmt(
     
    19901990        }
    19911991
    1992         ast::Expr * visitBaseExpr_SkipResultType(Expression * old, ast::Expr * nw) {
     1992        ast::Expr * visitBaseExpr_SkipResultType( const Expression * old, ast::Expr * nw) {
    19931993
    19941994                nw->env    = convertTypeSubstitution(old->env);
     
    20002000        }
    20012001
    2002         ast::Expr * visitBaseExpr(Expression * old, ast::Expr * nw) {
     2002        ast::Expr * visitBaseExpr( const Expression * old, ast::Expr * nw) {
    20032003
    20042004                nw->result = GET_ACCEPT_1(result, Type);
     
    20062006        }
    20072007
    2008         virtual void visit( ApplicationExpr * old ) override final {
     2008        virtual void visit( const ApplicationExpr * old ) override final {
    20092009                this->node = visitBaseExpr( old,
    20102010                        new ast::ApplicationExpr(
     
    20162016        }
    20172017
    2018         virtual void visit( UntypedExpr * old ) override final {
     2018        virtual void visit( const UntypedExpr * old ) override final {
    20192019                this->node = visitBaseExpr( old,
    20202020                        new ast::UntypedExpr(
     
    20262026        }
    20272027
    2028         virtual void visit( NameExpr * old ) override final {
     2028        virtual void visit( const NameExpr * old ) override final {
    20292029                this->node = visitBaseExpr( old,
    20302030                        new ast::NameExpr(
     
    20352035        }
    20362036
    2037         virtual void visit( CastExpr * old ) override final {
     2037        virtual void visit( const CastExpr * old ) override final {
    20382038                this->node = visitBaseExpr( old,
    20392039                        new ast::CastExpr(
     
    20452045        }
    20462046
    2047         virtual void visit( KeywordCastExpr * old) override final {
     2047        virtual void visit( const KeywordCastExpr * old) override final {
    20482048                ast::KeywordCastExpr::Target castTarget = ast::KeywordCastExpr::NUMBER_OF_TARGETS;
    20492049                switch (old->target) {
     
    20702070        }
    20712071
    2072         virtual void visit( VirtualCastExpr * old ) override final {
     2072        virtual void visit( const VirtualCastExpr * old ) override final {
    20732073                this->node = visitBaseExpr_SkipResultType( old,
    20742074                        new ast::VirtualCastExpr(
     
    20802080        }
    20812081
    2082         virtual void visit( AddressExpr * old ) override final {
     2082        virtual void visit( const AddressExpr * old ) override final {
    20832083                this->node = visitBaseExpr( old,
    20842084                        new ast::AddressExpr(
     
    20892089        }
    20902090
    2091         virtual void visit( LabelAddressExpr * old ) override final {
     2091        virtual void visit( const LabelAddressExpr * old ) override final {
    20922092                this->node = visitBaseExpr( old,
    20932093                        new ast::LabelAddressExpr(
     
    20982098        }
    20992099
    2100         virtual void visit( UntypedMemberExpr * old ) override final {
     2100        virtual void visit( const UntypedMemberExpr * old ) override final {
    21012101                this->node = visitBaseExpr( old,
    21022102                        new ast::UntypedMemberExpr(
     
    21082108        }
    21092109
    2110         virtual void visit( MemberExpr * old ) override final {
     2110        virtual void visit( const MemberExpr * old ) override final {
    21112111                this->node = visitBaseExpr( old,
    21122112                        new ast::MemberExpr(
     
    21182118        }
    21192119
    2120         virtual void visit( VariableExpr * old ) override final {
     2120        virtual void visit( const VariableExpr * old ) override final {
    21212121                auto expr = new ast::VariableExpr(
    21222122                        old->location
     
    21292129        }
    21302130
    2131         virtual void visit( ConstantExpr * old ) override final {
     2131        virtual void visit( const ConstantExpr * old ) override final {
    21322132                ast::ConstantExpr *rslt = new ast::ConstantExpr(
    21332133                        old->location,
    21342134                        GET_ACCEPT_1(result, Type),
    2135                         old->constant.get_value(),
     2135                        old->constant.rep,
    21362136                        old->constant.ival
    21372137                );
    2138                 rslt->underlyer = getAccept1< ast::Type, Type* >( old->constant.get_type() );
     2138                rslt->underlyer = getAccept1< ast::Type, Type* >( old->constant.type );
    21392139                this->node = visitBaseExpr( old, rslt );
    21402140        }
    21412141
    2142         virtual void visit( SizeofExpr * old ) override final {
     2142        virtual void visit( const SizeofExpr * old ) override final {
    21432143                assert (old->expr || old->type);
    21442144                assert (! (old->expr && old->type));
     
    21612161        }
    21622162
    2163         virtual void visit( AlignofExpr * old ) override final {
     2163        virtual void visit( const AlignofExpr * old ) override final {
    21642164                assert (old->expr || old->type);
    21652165                assert (! (old->expr && old->type));
     
    21822182        }
    21832183
    2184         virtual void visit( UntypedOffsetofExpr * old ) override final {
     2184        virtual void visit( const UntypedOffsetofExpr * old ) override final {
    21852185                this->node = visitBaseExpr( old,
    21862186                        new ast::UntypedOffsetofExpr(
     
    21922192        }
    21932193
    2194         virtual void visit( OffsetofExpr * old ) override final {
     2194        virtual void visit( const OffsetofExpr * old ) override final {
    21952195                this->node = visitBaseExpr( old,
    21962196                        new ast::OffsetofExpr(
     
    22022202        }
    22032203
    2204         virtual void visit( OffsetPackExpr * old ) override final {
     2204        virtual void visit( const OffsetPackExpr * old ) override final {
    22052205                this->node = visitBaseExpr( old,
    22062206                        new ast::OffsetPackExpr(
     
    22112211        }
    22122212
    2213         virtual void visit( LogicalExpr * old ) override final {
     2213        virtual void visit( const LogicalExpr * old ) override final {
    22142214                this->node = visitBaseExpr( old,
    22152215                        new ast::LogicalExpr(
     
    22242224        }
    22252225
    2226         virtual void visit( ConditionalExpr * old ) override final {
     2226        virtual void visit( const ConditionalExpr * old ) override final {
    22272227                this->node = visitBaseExpr( old,
    22282228                        new ast::ConditionalExpr(
     
    22352235        }
    22362236
    2237         virtual void visit( CommaExpr * old ) override final {
     2237        virtual void visit( const CommaExpr * old ) override final {
    22382238                this->node = visitBaseExpr( old,
    22392239                        new ast::CommaExpr(
     
    22452245        }
    22462246
    2247         virtual void visit( TypeExpr * old ) override final {
     2247        virtual void visit( const TypeExpr * old ) override final {
    22482248                this->node = visitBaseExpr( old,
    22492249                        new ast::TypeExpr(
     
    22542254        }
    22552255
    2256         virtual void visit( AsmExpr * old ) override final {
     2256        virtual void visit( const AsmExpr * old ) override final {
    22572257                this->node = visitBaseExpr( old,
    22582258                        new ast::AsmExpr(
     
    22652265        }
    22662266
    2267         virtual void visit( ImplicitCopyCtorExpr * old ) override final {
     2267        virtual void visit( const ImplicitCopyCtorExpr * old ) override final {
    22682268                auto rslt = new ast::ImplicitCopyCtorExpr(
    22692269                        old->location,
     
    22742274        }
    22752275
    2276         virtual void visit( ConstructorExpr * old ) override final {
     2276        virtual void visit( const ConstructorExpr * old ) override final {
    22772277                this->node = visitBaseExpr( old,
    22782278                        new ast::ConstructorExpr(
     
    22832283        }
    22842284
    2285         virtual void visit( CompoundLiteralExpr * old ) override final {
     2285        virtual void visit( const CompoundLiteralExpr * old ) override final {
    22862286                this->node = visitBaseExpr_SkipResultType( old,
    22872287                        new ast::CompoundLiteralExpr(
     
    22932293        }
    22942294
    2295         virtual void visit( RangeExpr * old ) override final {
     2295        virtual void visit( const RangeExpr * old ) override final {
    22962296                this->node = visitBaseExpr( old,
    22972297                        new ast::RangeExpr(
     
    23032303        }
    23042304
    2305         virtual void visit( UntypedTupleExpr * old ) override final {
     2305        virtual void visit( const UntypedTupleExpr * old ) override final {
    23062306                this->node = visitBaseExpr( old,
    23072307                        new ast::UntypedTupleExpr(
     
    23122312        }
    23132313
    2314         virtual void visit( TupleExpr * old ) override final {
     2314        virtual void visit( const TupleExpr * old ) override final {
    23152315                this->node = visitBaseExpr( old,
    23162316                        new ast::TupleExpr(
     
    23212321        }
    23222322
    2323         virtual void visit( TupleIndexExpr * old ) override final {
     2323        virtual void visit( const TupleIndexExpr * old ) override final {
    23242324                this->node = visitBaseExpr( old,
    23252325                        new ast::TupleIndexExpr(
     
    23312331        }
    23322332
    2333         virtual void visit( TupleAssignExpr * old ) override final {
     2333        virtual void visit( const TupleAssignExpr * old ) override final {
    23342334                this->node = visitBaseExpr_SkipResultType( old,
    23352335                        new ast::TupleAssignExpr(
     
    23412341        }
    23422342
    2343         virtual void visit( StmtExpr * old ) override final {
     2343        virtual void visit( const StmtExpr * old ) override final {
    23442344                auto rslt = new ast::StmtExpr(
    23452345                        old->location,
     
    23522352        }
    23532353
    2354         virtual void visit( UniqueExpr * old ) override final {
     2354        virtual void visit( const UniqueExpr * old ) override final {
    23552355                auto rslt = new ast::UniqueExpr(
    23562356                        old->location,
     
    23642364        }
    23652365
    2366         virtual void visit( UntypedInitExpr * old ) override final {
     2366        virtual void visit( const UntypedInitExpr * old ) override final {
    23672367                std::deque<ast::InitAlternative> initAlts;
    23682368                for (auto ia : old->initAlts) {
     
    23812381        }
    23822382
    2383         virtual void visit( InitExpr * old ) override final {
     2383        virtual void visit( const InitExpr * old ) override final {
    23842384                this->node = visitBaseExpr( old,
    23852385                        new ast::InitExpr(
     
    23912391        }
    23922392
    2393         virtual void visit( DeletedExpr * old ) override final {
     2393        virtual void visit( const DeletedExpr * old ) override final {
    23942394                this->node = visitBaseExpr( old,
    23952395                        new ast::DeletedExpr(
     
    23972397                                GET_ACCEPT_1(expr, Expr),
    23982398                                inCache(old->deleteStmt) ?
    2399                                         this->node :
    2400                                         GET_ACCEPT_1(deleteStmt, Node)
    2401                         )
    2402                 );
    2403         }
    2404 
    2405         virtual void visit( DefaultArgExpr * old ) override final {
     2399                                        strict_dynamic_cast<ast::Decl*>(this->node) :
     2400                                        GET_ACCEPT_1(deleteStmt, Decl)
     2401                        )
     2402                );
     2403        }
     2404
     2405        virtual void visit( const DefaultArgExpr * old ) override final {
    24062406                this->node = visitBaseExpr( old,
    24072407                        new ast::DefaultArgExpr(
     
    24122412        }
    24132413
    2414         virtual void visit( GenericExpr * old ) override final {
     2414        virtual void visit( const GenericExpr * old ) override final {
    24152415                std::vector<ast::GenericExpr::Association> associations;
    24162416                for (auto association : old->associations) {
     
    24292429        }
    24302430
    2431         void visitType( Type * old, ast::Type * type ) {
     2431        void visitType( const Type * old, ast::Type * type ) {
    24322432                // Some types do this in their constructor so add a check.
    24332433                if ( !old->attributes.empty() && type->attributes.empty() ) {
     
    24372437        }
    24382438
    2439         virtual void visit( VoidType * old ) override final {
     2439        virtual void visit( const VoidType * old ) override final {
    24402440                visitType( old, new ast::VoidType{ cv( old ) } );
    24412441        }
    24422442
    2443         virtual void visit( BasicType * old ) override final {
     2443        virtual void visit( const BasicType * old ) override final {
    24442444                auto type = new ast::BasicType{ (ast::BasicType::Kind)(unsigned)old->kind, cv( old ) };
    24452445                // I believe this should always be a BasicType.
     
    24502450        }
    24512451
    2452         virtual void visit( PointerType * old ) override final {
     2452        virtual void visit( const PointerType * old ) override final {
    24532453                visitType( old, new ast::PointerType{
    24542454                        GET_ACCEPT_1( base, Type ),
     
    24602460        }
    24612461
    2462         virtual void visit( ArrayType * old ) override final {
     2462        virtual void visit( const ArrayType * old ) override final {
    24632463                visitType( old, new ast::ArrayType{
    24642464                        GET_ACCEPT_1( base, Type ),
     
    24702470        }
    24712471
    2472         virtual void visit( ReferenceType * old ) override final {
     2472        virtual void visit( const ReferenceType * old ) override final {
    24732473                visitType( old, new ast::ReferenceType{
    24742474                        GET_ACCEPT_1( base, Type ),
     
    24772477        }
    24782478
    2479         virtual void visit( QualifiedType * old ) override final {
     2479        virtual void visit( const QualifiedType * old ) override final {
    24802480                visitType( old, new ast::QualifiedType{
    24812481                        GET_ACCEPT_1( parent, Type ),
     
    24852485        }
    24862486
    2487         virtual void visit( FunctionType * old ) override final {
     2487        virtual void visit( const FunctionType * old ) override final {
    24882488                auto ty = new ast::FunctionType {
    24892489                        (ast::ArgumentFlag)old->isVarArgs,
     
    24962496        }
    24972497
    2498         void postvisit( ReferenceToType * old, ast::ReferenceToType * ty ) {
     2498        void postvisit( const ReferenceToType * old, ast::ReferenceToType * ty ) {
    24992499                ty->forall = GET_ACCEPT_V( forall, TypeDecl );
    25002500                ty->params = GET_ACCEPT_V( parameters, Expr );
     
    25032503        }
    25042504
    2505         virtual void visit( StructInstType * old ) override final {
     2505        virtual void visit( const StructInstType * old ) override final {
    25062506                ast::StructInstType * ty;
    25072507                if ( old->baseStruct ) {
     
    25212521        }
    25222522
    2523         virtual void visit( UnionInstType * old ) override final {
     2523        virtual void visit( const UnionInstType * old ) override final {
    25242524                ast::UnionInstType * ty;
    25252525                if ( old->baseUnion ) {
     
    25392539        }
    25402540
    2541         virtual void visit( EnumInstType * old ) override final {
     2541        virtual void visit( const EnumInstType * old ) override final {
    25422542                ast::EnumInstType * ty;
    25432543                if ( old->baseEnum ) {
     
    25572557        }
    25582558
    2559         virtual void visit( TraitInstType * old ) override final {
     2559        virtual void visit( const TraitInstType * old ) override final {
    25602560                ast::TraitInstType * ty;
    25612561                if ( old->baseTrait ) {
     
    25752575        }
    25762576
    2577         virtual void visit( TypeInstType * old ) override final {
     2577        virtual void visit( const TypeInstType * old ) override final {
    25782578                ast::TypeInstType * ty;
    25792579                if ( old->baseType ) {
     
    25952595        }
    25962596
    2597         virtual void visit( TupleType * old ) override final {
     2597        virtual void visit( const TupleType * old ) override final {
    25982598                visitType( old, new ast::TupleType{
    25992599                        GET_ACCEPT_V( types, Type ),
     
    26032603        }
    26042604
    2605         virtual void visit( TypeofType * old ) override final {
     2605        virtual void visit( const TypeofType * old ) override final {
    26062606                visitType( old, new ast::TypeofType{
    26072607                        GET_ACCEPT_1( expr, Expr ),
     
    26112611        }
    26122612
    2613         virtual void visit( AttrType * ) override final {
     2613        virtual void visit( const AttrType * ) override final {
    26142614                assertf( false, "AttrType deprecated in new AST." );
    26152615        }
    26162616
    2617         virtual void visit( VarArgsType * old ) override final {
     2617        virtual void visit( const VarArgsType * old ) override final {
    26182618                visitType( old, new ast::VarArgsType{ cv( old ) } );
    26192619        }
    26202620
    2621         virtual void visit( ZeroType * old ) override final {
     2621        virtual void visit( const ZeroType * old ) override final {
    26222622                visitType( old, new ast::ZeroType{ cv( old ) } );
    26232623        }
    26242624
    2625         virtual void visit( OneType * old ) override final {
     2625        virtual void visit( const OneType * old ) override final {
    26262626                visitType( old, new ast::OneType{ cv( old ) } );
    26272627        }
    26282628
    2629         virtual void visit( GlobalScopeType * old ) override final {
     2629        virtual void visit( const GlobalScopeType * old ) override final {
    26302630                visitType( old, new ast::GlobalScopeType{} );
    26312631        }
    26322632
    2633         virtual void visit( Designation * old ) override final {
     2633        virtual void visit( const Designation * old ) override final {
    26342634                this->node = new ast::Designation(
    26352635                        old->location,
     
    26382638        }
    26392639
    2640         virtual void visit( SingleInit * old ) override final {
     2640        virtual void visit( const SingleInit * old ) override final {
    26412641                this->node = new ast::SingleInit(
    26422642                        old->location,
     
    26462646        }
    26472647
    2648         virtual void visit( ListInit * old ) override final {
     2648        virtual void visit( const ListInit * old ) override final {
    26492649                this->node = new ast::ListInit(
    26502650                        old->location,
     
    26552655        }
    26562656
    2657         virtual void visit( ConstructorInit * old ) override final {
     2657        virtual void visit( const ConstructorInit * old ) override final {
    26582658                this->node = new ast::ConstructorInit(
    26592659                        old->location,
     
    26642664        }
    26652665
    2666         virtual void visit( Constant * ) override final {
     2666        virtual void visit( const Constant * ) override final {
    26672667                // Handled in visit( ConstantEpxr * ).
    26682668                // In the new tree, Constant fields are inlined into containing ConstantExpression.
     
    26702670        }
    26712671
    2672         virtual void visit( Attribute * old ) override final {
     2672        virtual void visit( const Attribute * old ) override final {
    26732673                this->node = new ast::Attribute(
    26742674                        old->name,
     
    26772677        }
    26782678
    2679         virtual void visit( AttrExpr * ) override final {
     2679        virtual void visit( const AttrExpr * ) override final {
    26802680                assertf( false, "AttrExpr deprecated in new AST." );
    26812681        }
  • src/AST/Decl.hpp

    r1f1c102 rf53acdf8  
    102102        ptr<Expr> bitfieldWidth;
    103103
    104         ObjectDecl( const CodeLocation & loc, const std::string & name, const Type * type, 
    105                 const Init * init = nullptr, Storage::Classes storage = {}, 
    106                 Linkage::Spec linkage = Linkage::C, const Expr * bitWd = nullptr, 
     104        ObjectDecl( const CodeLocation & loc, const std::string & name, const Type * type,
     105                const Init * init = nullptr, Storage::Classes storage = {},
     106                Linkage::Spec linkage = Linkage::C, const Expr * bitWd = nullptr,
    107107                std::vector< ptr<Attribute> > && attrs = {}, Function::Specs fs = {} )
    108108        : DeclWithType( loc, name, storage, linkage, std::move(attrs), fs ), type( type ),
     
    323323};
    324324
     325/// With statement `with (...) ...`
     326class WithStmt final : public Decl {
     327public:
     328        std::vector<ptr<Expr>> exprs;
     329        ptr<Stmt> stmt;
     330
     331        WithStmt( const CodeLocation & loc, std::vector<ptr<Expr>> && exprs, const Stmt * stmt )
     332        : Decl(loc, "", Storage::Auto, Linkage::Cforall), exprs(std::move(exprs)), stmt(stmt) {}
     333
     334        const Decl * accept( Visitor & v ) const override { return v.visit( this ); }
     335private:
     336        WithStmt * clone() const override { return new WithStmt{ *this }; }
     337        MUTATE_FRIEND
     338};
     339
    325340class AsmDecl : public Decl {
    326341public:
  • src/AST/Expr.hpp

    r1f1c102 rf53acdf8  
    4747
    4848        ParamEntry() : decl( 0 ), declptr( nullptr ), actualType( nullptr ), formalType( nullptr ), expr( nullptr ) {}
    49         ParamEntry( 
    50                 UniqueId id, const Decl * declptr, const Type * actual, const Type * formal, 
     49        ParamEntry(
     50                UniqueId id, const Decl * declptr, const Type * actual, const Type * formal,
    5151                const Expr * e )
    5252        : decl( id ), declptr( declptr ), actualType( actual ), formalType( formal ), expr( e ) {}
     
    112112                        case Empty: new(&data.resnSlots) ResnSlots{}; mode = Slots; // fallthrough
    113113                        case Slots: return data.resnSlots;
    114                         case Params: assert(!"Cannot return to resnSlots from Params");
     114                        case Params: assertf(false, "Cannot return to resnSlots from Params"); abort();
    115115                        }
    116                         return *((ResnSlots*)nullptr);
     116                        assertf(false, "unreachable");
    117117                }
    118118
     
    121121                                return data.resnSlots;
    122122                        }
    123                         assert(!"Mode was not already resnSlots");
    124                         return *((ResnSlots*)nullptr);
     123                        assertf(false, "Mode was not already resnSlots");
     124                        abort();
    125125                }
    126126
     
    131131                        case Params: return data.inferParams;
    132132                        }
    133                         assert(!"unreachable");
    134                         return *((InferredParams*)nullptr);
     133                        assertf(false, "unreachable");
    135134                }
    136135
     
    139138                                return data.inferParams;
    140139                        }
    141                         assert(!"Mode was not already Params");
    142                         return *((InferredParams*)nullptr);
     140                        assertf(false, "Mode was not already Params");
     141                        abort();
    143142                }
    144143
    145144                void set_inferParams( InferredParams && ps ) {
    146145                        switch(mode) {
    147                         case Slots: 
     146                        case Slots:
    148147                                data.resnSlots.~ResnSlots();
    149148                                // fallthrough
    150                         case Empty: 
     149                        case Empty:
    151150                                new(&data.inferParams) InferredParams{ std::move( ps ) };
    152151                                mode = Params;
     
    172171                                        data.inferParams[p.first] = std::move(p.second);
    173172                                }
    174                         } else assert(!"invalid mode");
     173                        } else assertf(false, "invalid mode");
    175174                }
    176175        };
     
    384383
    385384        ConstantExpr(
    386                 const CodeLocation & loc, const Type * ty, const std::string & r, 
     385                const CodeLocation & loc, const Type * ty, const std::string & r,
    387386                        std::optional<unsigned long long> i )
    388387        : Expr( loc, ty ), rep( r ), ival( i ) {}
     
    770769public:
    771770        ptr<Expr> expr;
    772         readonly<Node> deleteStmt;
    773 
    774         DeletedExpr( const CodeLocation & loc, const Expr * e, const Node * del )
     771        readonly<Decl> deleteStmt;
     772
     773        DeletedExpr( const CodeLocation & loc, const Expr * e, const Decl * del )
    775774        : Expr( loc, e->result ), expr( e ), deleteStmt( del ) { assert( expr->result ); }
    776775
  • src/AST/Pass.hpp

    r1f1c102 rf53acdf8  
    115115        const ast::Stmt *             visit( const ast::FinallyStmt          * ) override final;
    116116        const ast::Stmt *             visit( const ast::WaitForStmt          * ) override final;
    117         const ast::Stmt *             visit( const ast::WithStmt             * ) override final;
     117        const ast::Decl *             visit( const ast::WithStmt             * ) override final;
    118118        const ast::NullStmt *         visit( const ast::NullStmt             * ) override final;
    119119        const ast::Stmt *             visit( const ast::DeclStmt             * ) override final;
  • src/AST/Pass.impl.hpp

    r1f1c102 rf53acdf8  
    909909// WithStmt
    910910template< typename pass_t >
    911 const ast::Stmt * ast::Pass< pass_t >::visit( const ast::WithStmt * node ) {
     911const ast::Decl * ast::Pass< pass_t >::visit( const ast::WithStmt * node ) {
    912912        VISIT_START( node );
    913913
  • src/AST/Print.cpp

    r1f1c102 rf53acdf8  
    3737}
    3838
    39 class Printer : public Visitor {
     39class Printer final : public Visitor {
    4040public:
    4141        ostream & os;
     
    272272
    273273public:
    274         virtual const ast::DeclWithType * visit( const ast::ObjectDecl * node ) {
     274        virtual const ast::DeclWithType * visit( const ast::ObjectDecl * node ) override final {
    275275                if ( ! node->name.empty() ) os << node->name << ": ";
    276276
     
    314314        }
    315315
    316         virtual const ast::DeclWithType * visit( const ast::FunctionDecl * node ) {
     316        virtual const ast::DeclWithType * visit( const ast::FunctionDecl * node ) override final {
    317317                if ( !node->name.empty() ) os << node->name << ": ";
    318318
     
    342342        }
    343343
    344         virtual const ast::Decl * visit( const ast::StructDecl * node ) {
     344        virtual const ast::Decl * visit( const ast::StructDecl * node ) override final {
    345345                print(node);
    346346                return node;
    347347        }
    348348
    349         virtual const ast::Decl * visit( const ast::UnionDecl * node ) {
     349        virtual const ast::Decl * visit( const ast::UnionDecl * node ) override final {
    350350                print(node);
    351351                return node;
    352352        }
    353353
    354         virtual const ast::Decl * visit( const ast::EnumDecl * node ) {
     354        virtual const ast::Decl * visit( const ast::EnumDecl * node ) override final {
    355355                print(node);
    356356                return node;
    357357        }
    358358
    359         virtual const ast::Decl * visit( const ast::TraitDecl * node ) {
     359        virtual const ast::Decl * visit( const ast::TraitDecl * node ) override final {
    360360                print(node);
    361361                return node;
    362362        }
    363363
    364         virtual const ast::Decl * visit( const ast::TypeDecl * node ) {
     364        virtual const ast::Decl * visit( const ast::TypeDecl * node ) override final {
    365365                preprint( node );
    366366                if ( ! short_mode && node->init ) {
     
    374374        }
    375375
    376         virtual const ast::Decl * visit( const ast::TypedefDecl * node ) {
    377                 preprint( node );
    378                 return node;
    379         }
    380 
    381         virtual const ast::AsmDecl * visit( const ast::AsmDecl * node ) {
     376        virtual const ast::Decl * visit( const ast::TypedefDecl * node ) override final {
     377                preprint( node );
     378                return node;
     379        }
     380
     381        virtual const ast::AsmDecl * visit( const ast::AsmDecl * node ) override final {
    382382                safe_print( node->stmt );
    383383                return node;
    384384        }
    385385
    386         virtual const ast::StaticAssertDecl * visit( const ast::StaticAssertDecl * node ) {
     386        virtual const ast::StaticAssertDecl * visit( const ast::StaticAssertDecl * node ) override final {
    387387                os << "Static Assert with condition: ";
    388388                ++indent;
     
    396396        }
    397397
    398         virtual const ast::CompoundStmt * visit( const ast::CompoundStmt * node ) {
     398        virtual const ast::CompoundStmt * visit( const ast::CompoundStmt * node ) override final {
    399399                os << "Compound Statement:" << endl;
    400400                ++indent;
     
    404404        }
    405405
    406         virtual const ast::Stmt * visit( const ast::ExprStmt * node ) {
     406        virtual const ast::Stmt * visit( const ast::ExprStmt * node ) override final {
    407407                ++indent;
    408408                os << "Expression Statement:" << endl << indent;
     
    412412        }
    413413
    414         virtual const ast::Stmt * visit( const ast::AsmStmt * node ) {
     414        virtual const ast::Stmt * visit( const ast::AsmStmt * node ) override final {
    415415                os << "Assembler Statement:" << endl;
    416416                ++indent;
     
    433433        }
    434434
    435         virtual const ast::Stmt * visit( const ast::DirectiveStmt * node ) {
     435        virtual const ast::Stmt * visit( const ast::DirectiveStmt * node ) override final {
    436436                os << "GCC Directive: " << node->directive << endl;
    437437                return node;
    438438        }
    439439
    440         virtual const ast::Stmt * visit( const ast::IfStmt * node ) {
     440        virtual const ast::Stmt * visit( const ast::IfStmt * node ) override final {
    441441                os << "If on condition:" << endl;
    442442                ++indent;
     
    473473        }
    474474
    475         virtual const ast::Stmt * visit( const ast::WhileStmt * node ) {
     475        virtual const ast::Stmt * visit( const ast::WhileStmt * node ) override final {
    476476                if ( node->isDoWhile ) { os << "Do-"; }
    477477                os << "While on condition:" << endl;
     
    490490        }
    491491
    492         virtual const ast::Stmt * visit( const ast::ForStmt * node ) {
     492        virtual const ast::Stmt * visit( const ast::ForStmt * node ) override final {
    493493                os << "For Statement" << endl;
    494494
     
    532532        }
    533533
    534         virtual const ast::Stmt * visit( const ast::SwitchStmt * node ) {
     534        virtual const ast::Stmt * visit( const ast::SwitchStmt * node ) override final {
    535535                os << "Switch on condition: ";
    536536                safe_print( node->cond );
     
    546546        }
    547547
    548         virtual const ast::Stmt * visit( const ast::CaseStmt * node ) {
     548        virtual const ast::Stmt * visit( const ast::CaseStmt * node ) override final {
    549549                if ( node->isDefault() ) {
    550550                        os << indent << "Default ";
     
    565565        }
    566566
    567         virtual const ast::Stmt * visit( const ast::BranchStmt * node ) {
     567        virtual const ast::Stmt * visit( const ast::BranchStmt * node ) override final {
    568568                os << "Branch (" << node->kindName() << ")" << endl;
    569569                ++indent;
     
    586586        }
    587587
    588         virtual const ast::Stmt * visit( const ast::ReturnStmt * node ) {
     588        virtual const ast::Stmt * visit( const ast::ReturnStmt * node ) override final {
    589589                os << "Return Statement, returning";
    590590                if ( node->expr ) {
     
    601601        }
    602602
    603         virtual const ast::Stmt * visit( const ast::ThrowStmt * node ) {
     603        virtual const ast::Stmt * visit( const ast::ThrowStmt * node ) override final {
    604604                if ( node->target ) os << "Non-Local ";
    605605
     
    621621        }
    622622
    623         virtual const ast::Stmt * visit( const ast::TryStmt * node ) {
     623        virtual const ast::Stmt * visit( const ast::TryStmt * node ) override final {
    624624                ++indent;
    625625                os << "Try Statement" << endl << indent-1
     
    642642        }
    643643
    644         virtual const ast::Stmt * visit( const ast::CatchStmt * node ) {
     644        virtual const ast::Stmt * visit( const ast::CatchStmt * node ) override final {
    645645                os << "Catch ";
    646646                switch ( node->kind ) {
     
    667667        }
    668668
    669         virtual const ast::Stmt * visit( const ast::FinallyStmt * node ) {
     669        virtual const ast::Stmt * visit( const ast::FinallyStmt * node ) override final {
    670670                os << "Finally Statement" << endl;
    671671                os << indent << "... with block:" << endl;
     
    678678        }
    679679
    680         virtual const ast::Stmt * visit( const ast::WaitForStmt * node ) {
     680        virtual const ast::Stmt * visit( const ast::WaitForStmt * node ) override final {
    681681                os << "Waitfor Statement" << endl;
    682682                indent += 2;
     
    732732        }
    733733
    734         virtual const ast::Stmt * visit( const ast::WithStmt * node ) {
     734        virtual const ast::Decl * visit( const ast::WithStmt * node ) override final {
    735735                os << "With statement" << endl;
    736736                os << indent << "... with expressions:" << endl;
     
    744744        }
    745745
    746         virtual const ast::NullStmt * visit( const ast::NullStmt * node ) {
     746        virtual const ast::NullStmt * visit( const ast::NullStmt * node ) override final {
    747747                os << "Null Statement" << endl;
    748748                print( node->labels );
     
    751751        }
    752752
    753         virtual const ast::Stmt * visit( const ast::DeclStmt * node ) {
     753        virtual const ast::Stmt * visit( const ast::DeclStmt * node ) override final {
    754754                os << "Declaration of ";
    755755                safe_print( node->decl );
     
    758758        }
    759759
    760         virtual const ast::Stmt * visit( const ast::ImplicitCtorDtorStmt * node ) {
     760        virtual const ast::Stmt * visit( const ast::ImplicitCtorDtorStmt * node ) override final {
    761761                os << "Implicit Ctor Dtor Statement" << endl;
    762762                os << indent << "... with Ctor/Dtor: ";
     
    769769        }
    770770
    771         virtual const ast::Expr * visit( const ast::ApplicationExpr * node ) {
     771        virtual const ast::Expr * visit( const ast::ApplicationExpr * node ) override final {
    772772                ++indent;
    773773                os << "Application of" << endl << indent;
     
    784784        }
    785785
    786         virtual const ast::Expr * visit( const ast::UntypedExpr * node ) {
     786        virtual const ast::Expr * visit( const ast::UntypedExpr * node ) override final {
    787787                ++indent;
    788788                os << "Applying untyped:" << endl;
     
    797797        }
    798798
    799         virtual const ast::Expr * visit( const ast::NameExpr * node ) {
     799        virtual const ast::Expr * visit( const ast::NameExpr * node ) override final {
    800800                os << "Name: " << node->name;
    801801                postprint( node );
     
    804804        }
    805805
    806         virtual const ast::Expr * visit( const ast::AddressExpr * node ) {
     806        virtual const ast::Expr * visit( const ast::AddressExpr * node ) override final {
    807807                os << "Address of:" << endl;
    808808                ++indent;
     
    815815        }
    816816
    817         virtual const ast::Expr * visit( const ast::LabelAddressExpr * node ) {
     817        virtual const ast::Expr * visit( const ast::LabelAddressExpr * node ) override final {
    818818                os << "Address of label:" << node->arg;
    819819
     
    821821        }
    822822
    823         virtual const ast::Expr * visit( const ast::CastExpr * node ) {
     823        virtual const ast::Expr * visit( const ast::CastExpr * node ) override final {
    824824                ++indent;
    825825                os << (node->isGenerated ? "Generated" : "Explicit") << " cast of:" << endl << indent;
     
    841841        }
    842842
    843         virtual const ast::Expr * visit( const ast::KeywordCastExpr * node ) {
     843        virtual const ast::Expr * visit( const ast::KeywordCastExpr * node ) override final {
    844844                ++indent;
    845845                os << "Keyword Cast of:" << endl << indent;
     
    852852        }
    853853
    854         virtual const ast::Expr * visit( const ast::VirtualCastExpr * node ) {
     854        virtual const ast::Expr * visit( const ast::VirtualCastExpr * node ) override final {
    855855                ++indent;
    856856                os << "Virtual Cast of:" << endl << indent;
     
    869869        }
    870870
    871         virtual const ast::Expr * visit( const ast::UntypedMemberExpr * node ) {
     871        virtual const ast::Expr * visit( const ast::UntypedMemberExpr * node ) override final {
    872872                ++indent;
    873873                os << "Untyped Member Expression, with field: " << endl << indent;
     
    881881        }
    882882
    883         virtual const ast::Expr * visit( const ast::MemberExpr * node ) {
     883        virtual const ast::Expr * visit( const ast::MemberExpr * node ) override final {
    884884                ++indent;
    885885                os << "Member Expression, with field:" << endl << indent;
     
    893893        }
    894894
    895         virtual const ast::Expr * visit( const ast::VariableExpr * node ) {
     895        virtual const ast::Expr * visit( const ast::VariableExpr * node ) override final {
    896896                os << "Variable Expression: ";
    897897                short_print( node->var );
     
    901901        }
    902902
    903         virtual const ast::Expr * visit( const ast::ConstantExpr * node ) {
     903        virtual const ast::Expr * visit( const ast::ConstantExpr * node ) override final {
    904904                os << "Constant Expression (" << node->rep;
    905905                if ( node->result ) {
     
    913913        }
    914914
    915         virtual const ast::Expr * visit( const ast::SizeofExpr * node ) {
     915        virtual const ast::Expr * visit( const ast::SizeofExpr * node ) override final {
    916916                os << "Sizeof Expression on: ";
    917917                ++indent;
     
    924924        }
    925925
    926         virtual const ast::Expr * visit( const ast::AlignofExpr * node ) {
     926        virtual const ast::Expr * visit( const ast::AlignofExpr * node ) override final {
    927927                os << "Alignof Expression on: ";
    928928                ++indent;
     
    935935        }
    936936
    937         virtual const ast::Expr * visit( const ast::UntypedOffsetofExpr * node ) {
     937        virtual const ast::Expr * visit( const ast::UntypedOffsetofExpr * node ) override final {
    938938                os << "Untyped Offsetof Expression on member " << node->member << " of ";
    939939                ++indent;
     
    945945        }
    946946
    947         virtual const ast::Expr * visit( const ast::OffsetofExpr * node ) {
     947        virtual const ast::Expr * visit( const ast::OffsetofExpr * node ) override final {
    948948                os << "Offsetof Expression on member " << node->member->name << " of ";
    949949                ++indent;
     
    955955        }
    956956
    957         virtual const ast::Expr * visit( const ast::OffsetPackExpr * node ) {
     957        virtual const ast::Expr * visit( const ast::OffsetPackExpr * node ) override final {
    958958                os << "Offset Pack Expression on: ";
    959959                ++indent;
     
    965965        }
    966966
    967         virtual const ast::Expr * visit( const ast::LogicalExpr * node ) {
     967        virtual const ast::Expr * visit( const ast::LogicalExpr * node ) override final {
    968968                os << "Short-circuited operation (" << (node->isAnd ? "and" : "or") << ") on: ";
    969969                safe_print( node->arg1 );
     
    975975        }
    976976
    977         virtual const ast::Expr * visit( const ast::ConditionalExpr * node ) {
     977        virtual const ast::Expr * visit( const ast::ConditionalExpr * node ) override final {
    978978                ++indent;
    979979                os << "Conditional expression on:" << endl << indent;
     
    989989        }
    990990
    991         virtual const ast::Expr * visit( const ast::CommaExpr * node ) {
     991        virtual const ast::Expr * visit( const ast::CommaExpr * node ) override final {
    992992                ++indent;
    993993                os << "Comma Expression:" << endl << indent;
     
    10011001        }
    10021002
    1003         virtual const ast::Expr * visit( const ast::TypeExpr * node ) {
     1003        virtual const ast::Expr * visit( const ast::TypeExpr * node ) override final {
    10041004                safe_print( node->type );
    10051005                postprint( node );
     
    10081008        }
    10091009
    1010         virtual const ast::Expr * visit( const ast::AsmExpr * node ) {
     1010        virtual const ast::Expr * visit( const ast::AsmExpr * node ) override final {
    10111011                os << "Asm Expression:" << endl;
    10121012                ++indent;
     
    10191019        }
    10201020
    1021         virtual const ast::Expr * visit( const ast::ImplicitCopyCtorExpr * node ) {
     1021        virtual const ast::Expr * visit( const ast::ImplicitCopyCtorExpr * node ) override final {
    10221022                ++indent;
    10231023                os << "Implicit Copy Constructor Expression:" << endl << indent;
     
    10291029        }
    10301030
    1031         virtual const ast::Expr * visit( const ast::ConstructorExpr * node ) {
     1031        virtual const ast::Expr * visit( const ast::ConstructorExpr * node ) override final {
    10321032                os <<  "Constructor Expression:" << endl << indent+1;
    10331033                indent += 2;
     
    10391039        }
    10401040
    1041         virtual const ast::Expr * visit( const ast::CompoundLiteralExpr * node ) {
     1041        virtual const ast::Expr * visit( const ast::CompoundLiteralExpr * node ) override final {
    10421042                ++indent;
    10431043                os << "Compound Literal Expression: " << endl << indent;
     
    10511051        }
    10521052
    1053         virtual const ast::Expr * visit( const ast::RangeExpr * node ) {
     1053        virtual const ast::Expr * visit( const ast::RangeExpr * node ) override final {
    10541054                os << "Range Expression: ";
    10551055                safe_print( node->low );
     
    10611061        }
    10621062
    1063         virtual const ast::Expr * visit( const ast::UntypedTupleExpr * node ) {
     1063        virtual const ast::Expr * visit( const ast::UntypedTupleExpr * node ) override final {
    10641064                os << "Untyped Tuple:" << endl;
    10651065                ++indent;
     
    10711071        }
    10721072
    1073         virtual const ast::Expr * visit( const ast::TupleExpr * node ) {
     1073        virtual const ast::Expr * visit( const ast::TupleExpr * node ) override final {
    10741074                os << "Tuple:" << endl;
    10751075                ++indent;
     
    10811081        }
    10821082
    1083         virtual const ast::Expr * visit( const ast::TupleIndexExpr * node ) {
     1083        virtual const ast::Expr * visit( const ast::TupleIndexExpr * node ) override final {
    10841084                os << "Tuple Index Expression, with tuple:" << endl;
    10851085                ++indent;
     
    10931093        }
    10941094
    1095         virtual const ast::Expr * visit( const ast::TupleAssignExpr * node ) {
     1095        virtual const ast::Expr * visit( const ast::TupleAssignExpr * node ) override final {
    10961096                os << "Tuple Assignment Expression, with stmt expr:" << endl;
    10971097                ++indent;
     
    11041104        }
    11051105
    1106         virtual const ast::Expr * visit( const ast::StmtExpr * node ) {
     1106        virtual const ast::Expr * visit( const ast::StmtExpr * node ) override final {
    11071107                ++indent;
    11081108                os << "Statement Expression:" << endl << indent;
     
    11221122        }
    11231123
    1124         virtual const ast::Expr * visit( const ast::UniqueExpr * node ) {
     1124        virtual const ast::Expr * visit( const ast::UniqueExpr * node ) override final {
    11251125                ++indent;
    11261126                os << "Unique Expression with id: " << node->id << endl << indent;
     
    11361136        }
    11371137
    1138         virtual const ast::Expr * visit( const ast::UntypedInitExpr * node ) {
     1138        virtual const ast::Expr * visit( const ast::UntypedInitExpr * node ) override final {
    11391139                ++indent;
    11401140                os << "Untyped Init Expression" << endl << indent;
     
    11521152        }
    11531153
    1154         virtual const ast::Expr * visit( const ast::InitExpr * node ) {
     1154        virtual const ast::Expr * visit( const ast::InitExpr * node ) override final {
    11551155                ++indent;
    11561156                os << "Init Expression" << endl << indent;
     
    11631163        }
    11641164
    1165         virtual const ast::Expr * visit( const ast::DeletedExpr * node ) {
     1165        virtual const ast::Expr * visit( const ast::DeletedExpr * node ) override final {
    11661166                ++indent;
    11671167                os << "Deleted Expression" << endl << indent;
     
    11741174        }
    11751175
    1176         virtual const ast::Expr * visit( const ast::DefaultArgExpr * node ) {
     1176        virtual const ast::Expr * visit( const ast::DefaultArgExpr * node ) override final {
    11771177                ++indent;
    11781178                os << "Default Argument Expression" << endl << indent;
     
    11831183        }
    11841184
    1185         virtual const ast::Expr * visit( const ast::GenericExpr * node ) {
     1185        virtual const ast::Expr * visit( const ast::GenericExpr * node ) override final {
    11861186                ++indent;
    11871187                os << "C11 _Generic Expression" << endl << indent;
     
    12061206        }
    12071207
    1208         virtual const ast::Type * visit( const ast::VoidType * node ) {
     1208        virtual const ast::Type * visit( const ast::VoidType * node ) override final {
    12091209                preprint( node );
    12101210                os << "void";
     
    12121212        }
    12131213
    1214         virtual const ast::Type * visit( const ast::BasicType * node ) {
     1214        virtual const ast::Type * visit( const ast::BasicType * node ) override final {
    12151215                preprint( node );
    12161216                os << ast::BasicType::typeNames[ node->kind ];
     
    12181218        }
    12191219
    1220         virtual const ast::Type * visit( const ast::PointerType * node ) {
     1220        virtual const ast::Type * visit( const ast::PointerType * node ) override final {
    12211221                preprint( node );
    12221222                if ( ! node->isArray() ) {
     
    12411241        }
    12421242
    1243         virtual const ast::Type * visit( const ast::ArrayType * node ) {
     1243        virtual const ast::Type * visit( const ast::ArrayType * node ) override final {
    12441244                preprint( node );
    12451245                if ( node->isStatic ) {
     
    12651265        }
    12661266
    1267         virtual const ast::Type * visit( const ast::ReferenceType * node ) {
     1267        virtual const ast::Type * visit( const ast::ReferenceType * node ) override final {
    12681268                preprint( node );
    12691269                os << "reference to ";
     
    12731273        }
    12741274
    1275         virtual const ast::Type * visit( const ast::QualifiedType * node ) {
     1275        virtual const ast::Type * visit( const ast::QualifiedType * node ) override final {
    12761276                preprint( node );
    12771277                ++indent;
     
    12861286        }
    12871287
    1288         virtual const ast::Type * visit( const ast::FunctionType * node ) {
     1288        virtual const ast::Type * visit( const ast::FunctionType * node ) override final {
    12891289                preprint( node );
    12901290
     
    13151315        }
    13161316
    1317         virtual const ast::Type * visit( const ast::StructInstType * node ) {
     1317        virtual const ast::Type * visit( const ast::StructInstType * node ) override final {
    13181318                preprint( node );
    13191319                os << "instance of struct " << node->name;
     
    13261326        }
    13271327
    1328         virtual const ast::Type * visit( const ast::UnionInstType * node ) {
     1328        virtual const ast::Type * visit( const ast::UnionInstType * node ) override final {
    13291329                preprint( node );
    13301330                os << "instance of union " << node->name;
     
    13371337        }
    13381338
    1339         virtual const ast::Type * visit( const ast::EnumInstType * node ) {
     1339        virtual const ast::Type * visit( const ast::EnumInstType * node ) override final {
    13401340                preprint( node );
    13411341                os << "instance of enum " << node->name;
     
    13481348        }
    13491349
    1350         virtual const ast::Type * visit( const ast::TraitInstType * node ) {
     1350        virtual const ast::Type * visit( const ast::TraitInstType * node ) override final {
    13511351                preprint( node );
    13521352                os << "instance of trait " << node->name;
     
    13561356        }
    13571357
    1358         virtual const ast::Type * visit( const ast::TypeInstType * node ) {
     1358        virtual const ast::Type * visit( const ast::TypeInstType * node ) override final {
    13591359                preprint( node );
    13601360                os << "instance of type " << node->name
     
    13651365        }
    13661366
    1367         virtual const ast::Type * visit( const ast::TupleType * node ) {
     1367        virtual const ast::Type * visit( const ast::TupleType * node ) override final {
    13681368                preprint( node );
    13691369                os << "tuple of types" << endl;
     
    13751375        }
    13761376
    1377         virtual const ast::Type * visit( const ast::TypeofType * node ) {
     1377        virtual const ast::Type * visit( const ast::TypeofType * node ) override final {
    13781378                preprint( node );
    13791379                if ( node->kind == ast::TypeofType::Basetypeof ) { os << "base-"; }
     
    13841384        }
    13851385
    1386         virtual const ast::Type * visit( const ast::VarArgsType * node ) {
     1386        virtual const ast::Type * visit( const ast::VarArgsType * node ) override final {
    13871387                preprint( node );
    13881388                os << "builtin var args pack";
     
    13901390        }
    13911391
    1392         virtual const ast::Type * visit( const ast::ZeroType * node ) {
     1392        virtual const ast::Type * visit( const ast::ZeroType * node ) override final {
    13931393                preprint( node );
    13941394                os << "zero_t";
     
    13961396        }
    13971397
    1398         virtual const ast::Type * visit( const ast::OneType * node ) {
     1398        virtual const ast::Type * visit( const ast::OneType * node ) override final {
    13991399                preprint( node );
    14001400                os << "one_t";
     
    14021402        }
    14031403
    1404         virtual const ast::Type * visit( const ast::GlobalScopeType * node ) {
     1404        virtual const ast::Type * visit( const ast::GlobalScopeType * node ) override final {
    14051405                preprint( node );
    14061406                os << "Global Scope Type";
     
    14081408        }
    14091409
    1410         virtual const ast::Designation * visit( const ast::Designation * node ) {
     1410        virtual const ast::Designation * visit( const ast::Designation * node ) override final {
    14111411                if ( node->designators.empty() ) return node;
    14121412                os << "... designated by: " << endl;
     
    14211421        }
    14221422
    1423         virtual const ast::Init * visit( const ast::SingleInit * node ) {
     1423        virtual const ast::Init * visit( const ast::SingleInit * node ) override final {
    14241424                os << "Simple Initializer: ";
    14251425                safe_print( node->value );
     
    14271427        }
    14281428
    1429         virtual const ast::Init * visit( const ast::ListInit * node ) {
     1429        virtual const ast::Init * visit( const ast::ListInit * node ) override final {
    14301430                os << "Compound initializer: " << endl;
    14311431                ++indent;
     
    14451445        }
    14461446
    1447         virtual const ast::Init * visit( const ast::ConstructorInit * node ) {
     1447        virtual const ast::Init * visit( const ast::ConstructorInit * node ) override final {
    14481448                os << "Constructor initializer: " << endl;
    14491449                if ( node->ctor ) {
     
    14701470        }
    14711471
    1472         virtual const ast::Attribute * visit( const ast::Attribute * node ) {
     1472        virtual const ast::Attribute * visit( const ast::Attribute * node ) override final {
    14731473                if ( node->empty() ) return node;
    14741474                os << "Attribute with name: " << node->name;
     
    14811481        }
    14821482
    1483         virtual const ast::TypeSubstitution * visit( const ast::TypeSubstitution * node ) {
     1483        virtual const ast::TypeSubstitution * visit( const ast::TypeSubstitution * node ) override final {
    14841484                os << indent << "Types:" << endl;
    14851485                for ( const auto& i : *node ) {
  • src/AST/Stmt.hpp

    r1f1c102 rf53acdf8  
    380380};
    381381
    382 /// With statement `with (...) ...`
    383 class WithStmt final : public Stmt {
    384 public:
    385         std::vector<ptr<Expr>> exprs;
    386         ptr<Stmt> stmt;
    387 
    388         WithStmt( const CodeLocation & loc, std::vector<ptr<Expr>> && exprs, const Stmt * stmt,
    389                 std::vector<Label> && labels = {} )
    390         : Stmt(loc, std::move(labels)), exprs(std::move(exprs)), stmt(stmt) {}
    391 
    392         const Stmt * accept( Visitor & v ) const override { return v.visit( this ); }
    393 private:
    394         WithStmt * clone() const override { return new WithStmt{ *this }; }
    395         MUTATE_FRIEND
    396 };
    397 
    398382/// Any declaration in a (compound) statement.
    399383class DeclStmt final : public Stmt {
  • src/AST/SymbolTable.cpp

    r1f1c102 rf53acdf8  
    7373
    7474SymbolTable::SymbolTable()
    75 : idTable(), typeTable(), structTable(), enumTable(), unionTable(), traitTable(), 
     75: idTable(), typeTable(), structTable(), enumTable(), unionTable(), traitTable(),
    7676  prevScope(), scope( 0 ), repScope( 0 ) { ++*stats().count; }
    7777
     
    171171}
    172172
    173 void SymbolTable::addDeletedId( const DeclWithType * decl, const Node * deleter ) {
     173void SymbolTable::addDeletedId( const DeclWithType * decl, const Decl * deleter ) {
    174174        // default handling of conflicts is to raise an error
    175175        addId( decl, OnConflict::error(), nullptr, deleter );
     
    189189                        }
    190190                }
    191                 // does not need to be added to the table if both existing and added have a base that are 
     191                // does not need to be added to the table if both existing and added have a base that are
    192192                // the same
    193193                return true;
     
    209209        const std::string &id = decl->name;
    210210
    211         if ( ! typeTable ) { 
     211        if ( ! typeTable ) {
    212212                typeTable = TypeTable::new_ptr();
    213213        } else {
    214214                ++*stats().map_lookups;
    215215                auto existing = typeTable->find( id );
    216                 if ( existing != typeTable->end() 
    217                         && existing->second.scope == scope 
     216                if ( existing != typeTable->end()
     217                        && existing->second.scope == scope
    218218                        && addedTypeConflicts( existing->second.decl, decl ) ) return;
    219219        }
    220        
     220
    221221        lazyInitScope();
    222222        ++*stats().map_mutations;
     
    237237                ++*stats().map_lookups;
    238238                auto existing = structTable->find( id );
    239                 if ( existing != structTable->end() 
    240                         && existing->second.scope == scope 
     239                if ( existing != structTable->end()
     240                        && existing->second.scope == scope
    241241                        && addedDeclConflicts( existing->second.decl, decl ) ) return;
    242242        }
     
    256256                ++*stats().map_lookups;
    257257                auto existing = enumTable->find( id );
    258                 if ( existing != enumTable->end() 
    259                         && existing->second.scope == scope 
     258                if ( existing != enumTable->end()
     259                        && existing->second.scope == scope
    260260                        && addedDeclConflicts( existing->second.decl, decl ) ) return;
    261261        }
    262        
     262
    263263        lazyInitScope();
    264264        ++*stats().map_mutations;
     
    279279                ++*stats().map_lookups;
    280280                auto existing = unionTable->find( id );
    281                 if ( existing != unionTable->end() 
    282                         && existing->second.scope == scope 
     281                if ( existing != unionTable->end()
     282                        && existing->second.scope == scope
    283283                        && addedDeclConflicts( existing->second.decl, decl ) ) return;
    284284        }
     
    298298                ++*stats().map_lookups;
    299299                auto existing = traitTable->find( id );
    300                 if ( existing != traitTable->end() 
    301                         && existing->second.scope == scope 
     300                if ( existing != traitTable->end()
     301                        && existing->second.scope == scope
    302302                        && addedDeclConflicts( existing->second.decl, decl ) ) return;
    303303        }
     
    309309
    310310
    311 void SymbolTable::addWith( const std::vector< ptr<Expr> > & withExprs, const Node * withStmt ) {
     311void SymbolTable::addWith( const std::vector< ptr<Expr> > & withExprs, const Decl * withStmt ) {
    312312        for ( const Expr * expr : withExprs ) {
    313313                if ( ! expr->result ) continue;
    314314                const Type * resTy = expr->result->stripReferences();
    315315                auto aggrType = dynamic_cast< const ReferenceToType * >( resTy );
    316                 assertf( aggrType, "WithStmt expr has non-aggregate type: %s", 
     316                assertf( aggrType, "WithStmt expr has non-aggregate type: %s",
    317317                        toString( expr->result ).c_str() );
    318318                const AggregateDecl * aggr = aggrType->aggr();
    319                 assertf( aggr, "WithStmt has null aggregate from type: %s", 
     319                assertf( aggr, "WithStmt has null aggregate from type: %s",
    320320                        toString( expr->result ).c_str() );
    321                
     321
    322322                addMembers( aggr, expr, OnConflict::deleteWith( withStmt ) );
    323323        }
     
    373373        }
    374374
    375         /// gets the declaration for the function acting on a type specified by otype key, 
     375        /// gets the declaration for the function acting on a type specified by otype key,
    376376        /// nullptr if none such
    377         const FunctionDecl * getFunctionForOtype( 
     377        const FunctionDecl * getFunctionForOtype(
    378378                        const DeclWithType * decl, const std::string & otypeKey ) {
    379379                auto func = dynamic_cast< const FunctionDecl * >( decl );
     
    383383}
    384384
    385 bool SymbolTable::removeSpecialOverrides( 
     385bool SymbolTable::removeSpecialOverrides(
    386386                SymbolTable::IdData & data, SymbolTable::MangleTable::Ptr & mangleTable ) {
    387         // if a type contains user defined ctor/dtor/assign, then special rules trigger, which 
    388         // determine the set of ctor/dtor/assign that can be used  by the requester. In particular, 
    389         // if the user defines a default ctor, then the generated default ctor is unavailable, 
    390         // likewise for copy ctor and dtor. If the user defines any ctor/dtor, then no generated 
    391         // field ctors are available. If the user defines any ctor then the generated default ctor 
    392         // is unavailable (intrinsic default ctor must be overridden exactly). If the user defines 
    393         // anything that looks like a copy constructor, then the generated copy constructor is 
     387        // if a type contains user defined ctor/dtor/assign, then special rules trigger, which
     388        // determine the set of ctor/dtor/assign that can be used  by the requester. In particular,
     389        // if the user defines a default ctor, then the generated default ctor is unavailable,
     390        // likewise for copy ctor and dtor. If the user defines any ctor/dtor, then no generated
     391        // field ctors are available. If the user defines any ctor then the generated default ctor
     392        // is unavailable (intrinsic default ctor must be overridden exactly). If the user defines
     393        // anything that looks like a copy constructor, then the generated copy constructor is
    394394        // unavailable, and likewise for the assignment operator.
    395395
     
    450450                // if this is the first user-defined function, delete non-user-defined overloads
    451451                std::vector< MangleTable::value_type > deleted;
    452                
     452
    453453                for ( const auto& entry : *mangleTable ) {
    454454                        // skip decls that aren't functions or are for the wrong type
     
    489489                        if ( dataIsCopyFunc ) {
    490490                                // remove current function if exists a user-defined copy function
    491                                 // since the signatures for copy functions don't need to match exactly, using 
     491                                // since the signatures for copy functions don't need to match exactly, using
    492492                                // a delete statement is the wrong approach
    493493                                if ( InitTweak::isCopyFunction( decl ) ) return false;
     
    499499                }
    500500        }
    501        
     501
    502502        // nothing (more) to fix, return true
    503503        return true;
     
    525525
    526526bool SymbolTable::addedIdConflicts(
    527                 const SymbolTable::IdData & existing, const DeclWithType * added, 
    528                 SymbolTable::OnConflict handleConflicts, const Node * deleter ) {
    529         // if we're giving the same name mangling to things of different types then there is something 
     527                const SymbolTable::IdData & existing, const DeclWithType * added,
     528                SymbolTable::OnConflict handleConflicts, const Decl * deleter ) {
     529        // if we're giving the same name mangling to things of different types then there is something
    530530        // wrong
    531531        assert( (isObject( added ) && isObject( existing.id ) )
    532532                || ( isFunction( added ) && isFunction( existing.id ) ) );
    533        
     533
    534534        if ( existing.id->linkage.is_overrideable ) {
    535535                // new definition shadows the autogenerated one, even at the same scope
    536536                return false;
    537         } else if ( existing.id->linkage.is_mangled 
    538                         || ResolvExpr::typesCompatible( 
     537        } else if ( existing.id->linkage.is_mangled
     538                        || ResolvExpr::typesCompatible(
    539539                                added->get_type(), existing.id->get_type(), SymbolTable{} ) ) {
    540                
     540
    541541                // it is a conflict if one declaration is deleted and the other is not
    542542                if ( deleter && ! existing.deleter ) {
     
    555555                if ( isDefinition( added ) && isDefinition( existing.id ) ) {
    556556                        if ( handleConflicts.mode == OnConflict::Error ) {
    557                                 SemanticError( added, 
    558                                         isFunction( added ) ? 
    559                                                 "duplicate function definition for " : 
     557                                SemanticError( added,
     558                                        isFunction( added ) ?
     559                                                "duplicate function definition for " :
    560560                                                "duplicate object definition for " );
    561561                        }
     
    572572}
    573573
    574 void SymbolTable::addId( 
    575                 const DeclWithType * decl, SymbolTable::OnConflict handleConflicts, const Expr * baseExpr, 
    576                 const Node * deleter ) {
     574void SymbolTable::addId(
     575                const DeclWithType * decl, SymbolTable::OnConflict handleConflicts, const Expr * baseExpr,
     576                const Decl * deleter ) {
    577577        ++*stats().add_calls;
    578578        const std::string &name = decl->name;
     
    581581        std::string mangleName;
    582582        if ( decl->linkage.is_overrideable ) {
    583                 // mangle the name without including the appropriate suffix, so overridable routines 
     583                // mangle the name without including the appropriate suffix, so overridable routines
    584584                // are placed into the same "bucket" as their user defined versions.
    585585                mangleName = Mangle::mangle( decl, Mangle::Mode{ Mangle::NoOverrideable } );
     
    588588        }
    589589
    590         // this ensures that no two declarations with the same unmangled name at the same scope 
     590        // this ensures that no two declarations with the same unmangled name at the same scope
    591591        // both have C linkage
    592592        if ( decl->linkage.is_mangled ) {
     
    596596                }
    597597        } else {
    598                 // NOTE: only correct if name mangling is completely isomorphic to C 
     598                // NOTE: only correct if name mangling is completely isomorphic to C
    599599                // type-compatibility, which it may not be.
    600600                if ( hasIncompatibleCDecl( name, mangleName ) ) {
     
    628628                                                idTable = idTable->set(
    629629                                                        name,
    630                                                         mangleTable->set( 
    631                                                                 mangleName, 
     630                                                        mangleTable->set(
     631                                                                mangleName,
    632632                                                                IdData{ existing->second, handleConflicts.deleter } ) );
    633633                                        }
     
    647647}
    648648
    649 void SymbolTable::addMembers( 
     649void SymbolTable::addMembers(
    650650                const AggregateDecl * aggr, const Expr * expr, SymbolTable::OnConflict handleConflicts ) {
    651651        for ( const Decl * decl : aggr->members ) {
     
    655655                                const Type * t = dwt->get_type()->stripReferences();
    656656                                if ( auto rty = dynamic_cast<const ReferenceToType *>( t ) ) {
    657                                         if ( ! dynamic_cast<const StructInstType *>(rty) 
     657                                        if ( ! dynamic_cast<const StructInstType *>(rty)
    658658                                                && ! dynamic_cast<const UnionInstType *>(rty) ) continue;
    659659                                        ResolvExpr::Cost cost = ResolvExpr::Cost::zero;
    660660                                        const Expr * base = ResolvExpr::referenceToRvalueConversion( expr, cost );
    661                                         addMembers( 
     661                                        addMembers(
    662662                                                rty->aggr(), new MemberExpr{ base->location, dwt, base }, handleConflicts );
    663663                                }
     
    680680                if ( ! decl.second.id->linkage.is_mangled && decl.first == mangleName ) return true;
    681681        }
    682        
     682
    683683        return false;
    684684}
  • src/AST/SymbolTable.hpp

    r1f1c102 rf53acdf8  
    3737                readonly<DeclWithType> id = nullptr;  ///< Identifier of declaration
    3838                readonly<Expr> baseExpr = nullptr;    ///< Implied containing aggregate (from WithExpr)
    39                 readonly<Node> deleter = nullptr;     ///< Node deleting this declaration (if non-null)
     39                readonly<Decl> deleter = nullptr;     ///< Node deleting this declaration (if non-null)
    4040                unsigned long scope = 0;              ///< Scope of identifier
    4141
    4242                IdData() = default;
    43                 IdData( const DeclWithType * i, const Expr * base, const Node * del, unsigned long s )
     43                IdData( const DeclWithType * i, const Expr * base, const Decl * del, unsigned long s )
    4444                : id( i ), baseExpr( base ), deleter( del ), scope( s ) {}
    45                
     45
    4646                /// Modify an existing node with a new deleter
    47                 IdData( const IdData & o, const Node * del )
     47                IdData( const IdData & o, const Decl * del )
    4848                : id( o.id ), baseExpr( o.baseExpr ), deleter( del ), scope( o.scope ) {}
    4949
     
    5858        struct scoped {
    5959                readonly<D> decl;     ///< wrapped declaration
    60                 unsigned long scope;  ///< scope of this declaration 
     60                unsigned long scope;  ///< scope of this declaration
    6161
    6262                scoped(const D * d, unsigned long s) : decl(d), scope(s) {}
     
    8888        ~SymbolTable();
    8989
    90         // when using an indexer manually (e.g., within a mutator traversal), it is necessary to 
     90        // when using an indexer manually (e.g., within a mutator traversal), it is necessary to
    9191        // tell the indexer explicitly when scopes begin and end
    9292        void enterScope();
     
    118118        void addId( const DeclWithType * decl, const Expr * baseExpr = nullptr );
    119119        /// Adds a deleted identifier declaration to the symbol table
    120         void addDeletedId( const DeclWithType * decl, const Node * deleter );
     120        void addDeletedId( const DeclWithType * decl, const Decl * deleter );
    121121
    122122        /// Adds a type to the symbol table
     
    136136
    137137        /// adds all of the IDs from WithStmt exprs
    138         void addWith( const std::vector< ptr<Expr> > & withExprs, const Node * withStmt );
     138        void addWith( const std::vector< ptr<Expr> > & withExprs, const Decl * withStmt );
    139139
    140140        /// convenience function for adding a list of Ids to the indexer
     
    154154        const SymbolTable * atScope( unsigned long i ) const;
    155155
    156         /// Removes matching autogenerated constructors and destructors so that they will not be 
     156        /// Removes matching autogenerated constructors and destructors so that they will not be
    157157        /// selected. If returns false, passed decl should not be added.
    158158        bool removeSpecialOverrides( IdData & decl, MangleTable::Ptr & mangleTable );
     
    164164                        Delete  ///< Delete the earlier version with the delete statement
    165165                } mode;
    166                 const Node * deleter;  ///< Statement that deletes this expression
     166                const Decl * deleter;  ///< Statement that deletes this expression
    167167
    168168        private:
    169169                OnConflict() : mode(Error), deleter(nullptr) {}
    170                 OnConflict( const Node * d ) : mode(Delete), deleter(d) {}
     170                OnConflict( const Decl * d ) : mode(Delete), deleter(d) {}
    171171        public:
    172172                OnConflict( const OnConflict& ) = default;
    173173
    174174                static OnConflict error() { return {}; }
    175                 static OnConflict deleteWith( const Node * d ) { return { d }; }
     175                static OnConflict deleteWith( const Decl * d ) { return { d }; }
    176176        };
    177177
    178178        /// true if the existing identifier conflicts with the added identifier
    179179        bool addedIdConflicts(
    180                 const IdData & existing, const DeclWithType * added, OnConflict handleConflicts, 
    181                 const Node * deleter );
     180                const IdData & existing, const DeclWithType * added, OnConflict handleConflicts,
     181                const Decl * deleter );
    182182
    183183        /// common code for addId, addDeletedId, etc.
    184         void addId( 
    185                 const DeclWithType * decl, OnConflict handleConflicts, const Expr * baseExpr = nullptr, 
    186                 const Node * deleter = nullptr );
     184        void addId(
     185                const DeclWithType * decl, OnConflict handleConflicts, const Expr * baseExpr = nullptr,
     186                const Decl * deleter = nullptr );
    187187
    188188        /// adds all of the members of the Aggregate (addWith helper)
  • src/AST/Type.hpp

    r1f1c102 rf53acdf8  
    3535
    3636template< typename T > class Pass;
    37 class ForallSubstitutor;
     37
     38struct ForallSubstitutor;
    3839
    3940class Type : public Node {
     
    167168        static const char *typeNames[];
    168169
    169         BasicType( Kind k, CV::Qualifiers q = {}, std::vector<ptr<Attribute>> && as = {} ) 
     170        BasicType( Kind k, CV::Qualifiers q = {}, std::vector<ptr<Attribute>> && as = {} )
    170171        : Type(q, std::move(as)), kind(k) {}
    171172
     
    274275public:
    275276        using ForallList = std::vector<ptr<TypeDecl>>;
    276        
     277
    277278        ForallList forall;
    278279
     
    338339        bool hoistType = false;
    339340
    340         ReferenceToType( 
     341        ReferenceToType(
    341342                const std::string& n, CV::Qualifiers q = {}, std::vector<ptr<Attribute>> && as = {} )
    342343        : ParameterizedType(q, std::move(as)), params(), name(n) {}
     
    359360        readonly<StructDecl> base;
    360361
    361         StructInstType( 
     362        StructInstType(
    362363                const std::string& n, CV::Qualifiers q = {}, std::vector<ptr<Attribute>> && as = {} )
    363364        : ReferenceToType( n, q, std::move(as) ), base() {}
    364365
    365         StructInstType( 
     366        StructInstType(
    366367                const StructDecl * b, CV::Qualifiers q = {}, std::vector<ptr<Attribute>> && as = {} );
    367368
     
    381382        readonly<UnionDecl> base;
    382383
    383         UnionInstType( 
     384        UnionInstType(
    384385                const std::string& n, CV::Qualifiers q = {}, std::vector<ptr<Attribute>> && as = {} )
    385386        : ReferenceToType( n, q, std::move(as) ), base() {}
    386387
    387         UnionInstType( 
     388        UnionInstType(
    388389                const UnionDecl * b, CV::Qualifiers q = {}, std::vector<ptr<Attribute>> && as = {} );
    389390
     
    403404        readonly<EnumDecl> base;
    404405
    405         EnumInstType( 
     406        EnumInstType(
    406407                const std::string& n, CV::Qualifiers q = {}, std::vector<ptr<Attribute>> && as = {} )
    407408        : ReferenceToType( n, q, std::move(as) ), base() {}
    408409
    409         EnumInstType( 
     410        EnumInstType(
    410411                const EnumDecl * b, CV::Qualifiers q = {}, std::vector<ptr<Attribute>> && as = {} );
    411412
     
    425426        readonly<TraitDecl> base;
    426427
    427         TraitInstType( 
     428        TraitInstType(
    428429                const std::string& n, CV::Qualifiers q = {}, std::vector<ptr<Attribute>> && as = {} )
    429430        : ReferenceToType( n, q, std::move(as) ), base() {}
    430        
    431         TraitInstType( 
     431
     432        TraitInstType(
    432433                const TraitDecl * b, CV::Qualifiers q = {}, std::vector<ptr<Attribute>> && as = {} );
    433434
     
    449450        TypeVar::Kind kind;
    450451
    451         TypeInstType( 
     452        TypeInstType(
    452453                const std::string& n, const TypeDecl * b, CV::Qualifiers q = {},
    453454                std::vector<ptr<Attribute>> && as = {} )
    454455        : ReferenceToType( n, q, std::move(as) ), base( b ), kind( b->kind ) {}
    455        
    456         TypeInstType( 
     456
     457        TypeInstType(
    457458                const std::string& n, TypeVar::Kind k, CV::Qualifiers q = {},
    458459                std::vector<ptr<Attribute>> && as = {} )
  • src/AST/Visitor.hpp

    r1f1c102 rf53acdf8  
    4848    virtual const ast::Stmt *             visit( const ast::FinallyStmt          * ) = 0;
    4949    virtual const ast::Stmt *             visit( const ast::WaitForStmt          * ) = 0;
    50     virtual const ast::Stmt *             visit( const ast::WithStmt             * ) = 0;
     50    virtual const ast::Decl *             visit( const ast::WithStmt             * ) = 0;
    5151    virtual const ast::NullStmt *         visit( const ast::NullStmt             * ) = 0;
    5252    virtual const ast::Stmt *             visit( const ast::DeclStmt             * ) = 0;
  • src/Common/PassVisitor.h

    r1f1c102 rf53acdf8  
    6060
    6161        virtual void visit( ObjectDecl * objectDecl ) override final;
     62        virtual void visit( const ObjectDecl * objectDecl ) override final;
    6263        virtual void visit( FunctionDecl * functionDecl ) override final;
     64        virtual void visit( const FunctionDecl * functionDecl ) override final;
    6365        virtual void visit( StructDecl * aggregateDecl ) override final;
     66        virtual void visit( const StructDecl * aggregateDecl ) override final;
    6467        virtual void visit( UnionDecl * aggregateDecl ) override final;
     68        virtual void visit( const UnionDecl * aggregateDecl ) override final;
    6569        virtual void visit( EnumDecl * aggregateDecl ) override final;
     70        virtual void visit( const EnumDecl * aggregateDecl ) override final;
    6671        virtual void visit( TraitDecl * aggregateDecl ) override final;
     72        virtual void visit( const TraitDecl * aggregateDecl ) override final;
    6773        virtual void visit( TypeDecl * typeDecl ) override final;
     74        virtual void visit( const TypeDecl * typeDecl ) override final;
    6875        virtual void visit( TypedefDecl * typeDecl ) override final;
     76        virtual void visit( const TypedefDecl * typeDecl ) override final;
    6977        virtual void visit( AsmDecl * asmDecl ) override final;
     78        virtual void visit( const AsmDecl * asmDecl ) override final;
    7079        virtual void visit( StaticAssertDecl * assertDecl ) override final;
     80        virtual void visit( const StaticAssertDecl * assertDecl ) override final;
    7181
    7282        virtual void visit( CompoundStmt * compoundStmt ) override final;
     83        virtual void visit( const CompoundStmt * compoundStmt ) override final;
    7384        virtual void visit( ExprStmt * exprStmt ) override final;
     85        virtual void visit( const ExprStmt * exprStmt ) override final;
    7486        virtual void visit( AsmStmt * asmStmt ) override final;
     87        virtual void visit( const AsmStmt * asmStmt ) override final;
    7588        virtual void visit( DirectiveStmt * dirStmt ) override final;
     89        virtual void visit( const DirectiveStmt * dirStmt ) override final;
    7690        virtual void visit( IfStmt * ifStmt ) override final;
     91        virtual void visit( const IfStmt * ifStmt ) override final;
    7792        virtual void visit( WhileStmt * whileStmt ) override final;
     93        virtual void visit( const WhileStmt * whileStmt ) override final;
    7894        virtual void visit( ForStmt * forStmt ) override final;
     95        virtual void visit( const ForStmt * forStmt ) override final;
    7996        virtual void visit( SwitchStmt * switchStmt ) override final;
     97        virtual void visit( const SwitchStmt * switchStmt ) override final;
    8098        virtual void visit( CaseStmt * caseStmt ) override final;
     99        virtual void visit( const CaseStmt * caseStmt ) override final;
    81100        virtual void visit( BranchStmt * branchStmt ) override final;
     101        virtual void visit( const BranchStmt * branchStmt ) override final;
    82102        virtual void visit( ReturnStmt * returnStmt ) override final;
     103        virtual void visit( const ReturnStmt * returnStmt ) override final;
    83104        virtual void visit( ThrowStmt * throwStmt ) override final;
     105        virtual void visit( const ThrowStmt * throwStmt ) override final;
    84106        virtual void visit( TryStmt * tryStmt ) override final;
     107        virtual void visit( const TryStmt * tryStmt ) override final;
    85108        virtual void visit( CatchStmt * catchStmt ) override final;
     109        virtual void visit( const CatchStmt * catchStmt ) override final;
    86110        virtual void visit( FinallyStmt * finallyStmt ) override final;
     111        virtual void visit( const FinallyStmt * finallyStmt ) override final;
    87112        virtual void visit( WaitForStmt * waitforStmt ) override final;
     113        virtual void visit( const WaitForStmt * waitforStmt ) override final;
    88114        virtual void visit( WithStmt * withStmt ) override final;
     115        virtual void visit( const WithStmt * withStmt ) override final;
    89116        virtual void visit( NullStmt * nullStmt ) override final;
     117        virtual void visit( const NullStmt * nullStmt ) override final;
    90118        virtual void visit( DeclStmt * declStmt ) override final;
     119        virtual void visit( const DeclStmt * declStmt ) override final;
    91120        virtual void visit( ImplicitCtorDtorStmt * impCtorDtorStmt ) override final;
     121        virtual void visit( const ImplicitCtorDtorStmt * impCtorDtorStmt ) override final;
    92122
    93123        virtual void visit( ApplicationExpr * applicationExpr ) override final;
     124        virtual void visit( const ApplicationExpr * applicationExpr ) override final;
    94125        virtual void visit( UntypedExpr * untypedExpr ) override final;
     126        virtual void visit( const UntypedExpr * untypedExpr ) override final;
    95127        virtual void visit( NameExpr * nameExpr ) override final;
     128        virtual void visit( const NameExpr * nameExpr ) override final;
    96129        virtual void visit( CastExpr * castExpr ) override final;
     130        virtual void visit( const CastExpr * castExpr ) override final;
    97131        virtual void visit( KeywordCastExpr * castExpr ) override final;
     132        virtual void visit( const KeywordCastExpr * castExpr ) override final;
    98133        virtual void visit( VirtualCastExpr * castExpr ) override final;
     134        virtual void visit( const VirtualCastExpr * castExpr ) override final;
    99135        virtual void visit( AddressExpr * addressExpr ) override final;
     136        virtual void visit( const AddressExpr * addressExpr ) override final;
    100137        virtual void visit( LabelAddressExpr * labAddressExpr ) override final;
     138        virtual void visit( const LabelAddressExpr * labAddressExpr ) override final;
    101139        virtual void visit( UntypedMemberExpr * memberExpr ) override final;
     140        virtual void visit( const UntypedMemberExpr * memberExpr ) override final;
    102141        virtual void visit( MemberExpr * memberExpr ) override final;
     142        virtual void visit( const MemberExpr * memberExpr ) override final;
    103143        virtual void visit( VariableExpr * variableExpr ) override final;
     144        virtual void visit( const VariableExpr * variableExpr ) override final;
    104145        virtual void visit( ConstantExpr * constantExpr ) override final;
     146        virtual void visit( const ConstantExpr * constantExpr ) override final;
    105147        virtual void visit( SizeofExpr * sizeofExpr ) override final;
     148        virtual void visit( const SizeofExpr * sizeofExpr ) override final;
    106149        virtual void visit( AlignofExpr * alignofExpr ) override final;
     150        virtual void visit( const AlignofExpr * alignofExpr ) override final;
    107151        virtual void visit( UntypedOffsetofExpr * offsetofExpr ) override final;
     152        virtual void visit( const UntypedOffsetofExpr * offsetofExpr ) override final;
    108153        virtual void visit( OffsetofExpr * offsetofExpr ) override final;
     154        virtual void visit( const OffsetofExpr * offsetofExpr ) override final;
    109155        virtual void visit( OffsetPackExpr * offsetPackExpr ) override final;
     156        virtual void visit( const OffsetPackExpr * offsetPackExpr ) override final;
    110157        virtual void visit( AttrExpr * attrExpr ) override final;
     158        virtual void visit( const AttrExpr * attrExpr ) override final;
    111159        virtual void visit( LogicalExpr * logicalExpr ) override final;
     160        virtual void visit( const LogicalExpr * logicalExpr ) override final;
    112161        virtual void visit( ConditionalExpr * conditionalExpr ) override final;
     162        virtual void visit( const ConditionalExpr * conditionalExpr ) override final;
    113163        virtual void visit( CommaExpr * commaExpr ) override final;
     164        virtual void visit( const CommaExpr * commaExpr ) override final;
    114165        virtual void visit( TypeExpr * typeExpr ) override final;
     166        virtual void visit( const TypeExpr * typeExpr ) override final;
    115167        virtual void visit( AsmExpr * asmExpr ) override final;
     168        virtual void visit( const AsmExpr * asmExpr ) override final;
    116169        virtual void visit( ImplicitCopyCtorExpr * impCpCtorExpr ) override final;
     170        virtual void visit( const ImplicitCopyCtorExpr * impCpCtorExpr ) override final;
    117171        virtual void visit( ConstructorExpr *  ctorExpr ) override final;
     172        virtual void visit( const ConstructorExpr *  ctorExpr ) override final;
    118173        virtual void visit( CompoundLiteralExpr * compLitExpr ) override final;
     174        virtual void visit( const CompoundLiteralExpr * compLitExpr ) override final;
    119175        virtual void visit( RangeExpr * rangeExpr ) override final;
     176        virtual void visit( const RangeExpr * rangeExpr ) override final;
    120177        virtual void visit( UntypedTupleExpr * tupleExpr ) override final;
     178        virtual void visit( const UntypedTupleExpr * tupleExpr ) override final;
    121179        virtual void visit( TupleExpr * tupleExpr ) override final;
     180        virtual void visit( const TupleExpr * tupleExpr ) override final;
    122181        virtual void visit( TupleIndexExpr * tupleExpr ) override final;
     182        virtual void visit( const TupleIndexExpr * tupleExpr ) override final;
    123183        virtual void visit( TupleAssignExpr * assignExpr ) override final;
     184        virtual void visit( const TupleAssignExpr * assignExpr ) override final;
    124185        virtual void visit( StmtExpr *  stmtExpr ) override final;
     186        virtual void visit( const StmtExpr *  stmtExpr ) override final;
    125187        virtual void visit( UniqueExpr *  uniqueExpr ) override final;
     188        virtual void visit( const UniqueExpr *  uniqueExpr ) override final;
    126189        virtual void visit( UntypedInitExpr *  initExpr ) override final;
     190        virtual void visit( const UntypedInitExpr *  initExpr ) override final;
    127191        virtual void visit( InitExpr *  initExpr ) override final;
     192        virtual void visit( const InitExpr *  initExpr ) override final;
    128193        virtual void visit( DeletedExpr *  delExpr ) override final;
     194        virtual void visit( const DeletedExpr *  delExpr ) override final;
    129195        virtual void visit( DefaultArgExpr * argExpr ) override final;
     196        virtual void visit( const DefaultArgExpr * argExpr ) override final;
    130197        virtual void visit( GenericExpr * genExpr ) override final;
     198        virtual void visit( const GenericExpr * genExpr ) override final;
    131199
    132200        virtual void visit( VoidType * basicType ) override final;
     201        virtual void visit( const VoidType * basicType ) override final;
    133202        virtual void visit( BasicType * basicType ) override final;
     203        virtual void visit( const BasicType * basicType ) override final;
    134204        virtual void visit( PointerType * pointerType ) override final;
     205        virtual void visit( const PointerType * pointerType ) override final;
    135206        virtual void visit( ArrayType * arrayType ) override final;
     207        virtual void visit( const ArrayType * arrayType ) override final;
    136208        virtual void visit( ReferenceType * referenceType ) override final;
     209        virtual void visit( const ReferenceType * referenceType ) override final;
    137210        virtual void visit( QualifiedType * qualType ) override final;
     211        virtual void visit( const QualifiedType * qualType ) override final;
    138212        virtual void visit( FunctionType * functionType ) override final;
     213        virtual void visit( const FunctionType * functionType ) override final;
    139214        virtual void visit( StructInstType * aggregateUseType ) override final;
     215        virtual void visit( const StructInstType * aggregateUseType ) override final;
    140216        virtual void visit( UnionInstType * aggregateUseType ) override final;
     217        virtual void visit( const UnionInstType * aggregateUseType ) override final;
    141218        virtual void visit( EnumInstType * aggregateUseType ) override final;
     219        virtual void visit( const EnumInstType * aggregateUseType ) override final;
    142220        virtual void visit( TraitInstType * aggregateUseType ) override final;
     221        virtual void visit( const TraitInstType * aggregateUseType ) override final;
    143222        virtual void visit( TypeInstType * aggregateUseType ) override final;
     223        virtual void visit( const TypeInstType * aggregateUseType ) override final;
    144224        virtual void visit( TupleType * tupleType ) override final;
     225        virtual void visit( const TupleType * tupleType ) override final;
    145226        virtual void visit( TypeofType * typeofType ) override final;
     227        virtual void visit( const TypeofType * typeofType ) override final;
    146228        virtual void visit( AttrType * attrType ) override final;
     229        virtual void visit( const AttrType * attrType ) override final;
    147230        virtual void visit( VarArgsType * varArgsType ) override final;
     231        virtual void visit( const VarArgsType * varArgsType ) override final;
    148232        virtual void visit( ZeroType * zeroType ) override final;
     233        virtual void visit( const ZeroType * zeroType ) override final;
    149234        virtual void visit( OneType * oneType ) override final;
     235        virtual void visit( const OneType * oneType ) override final;
    150236        virtual void visit( GlobalScopeType * globalType ) override final;
     237        virtual void visit( const GlobalScopeType * globalType ) override final;
    151238
    152239        virtual void visit( Designation * designation ) override final;
     240        virtual void visit( const Designation * designation ) override final;
    153241        virtual void visit( SingleInit * singleInit ) override final;
     242        virtual void visit( const SingleInit * singleInit ) override final;
    154243        virtual void visit( ListInit * listInit ) override final;
     244        virtual void visit( const ListInit * listInit ) override final;
    155245        virtual void visit( ConstructorInit * ctorInit ) override final;
     246        virtual void visit( const ConstructorInit * ctorInit ) override final;
    156247
    157248        virtual void visit( Constant * constant ) override final;
     249        virtual void visit( const Constant * constant ) override final;
    158250
    159251        virtual void visit( Attribute * attribute ) override final;
     252        virtual void visit( const Attribute * attribute ) override final;
    160253
    161254        virtual DeclarationWithType * mutate( ObjectDecl * objectDecl ) override final;
     
    186279        virtual Statement * mutate( FinallyStmt * finallyStmt ) override final;
    187280        virtual Statement * mutate( WaitForStmt * waitforStmt ) override final;
    188         virtual Statement * mutate( WithStmt * withStmt ) override final;
     281        virtual Declaration * mutate( WithStmt * withStmt ) override final;
    189282        virtual NullStmt * mutate( NullStmt * nullStmt ) override final;
    190283        virtual Statement * mutate( DeclStmt * declStmt ) override final;
     
    265358
    266359        template<typename pass_t> friend void acceptAll( std::list< Declaration* > &decls, PassVisitor< pass_t >& visitor );
     360        template<typename pass_t> friend void acceptAll( const std::list< const Declaration * > &decls, PassVisitor< pass_t >& visitor );
    267361        template<typename pass_t> friend void mutateAll( std::list< Declaration* > &decls, PassVisitor< pass_t >& visitor );
    268362        template< typename TreeType, typename pass_t > friend void maybeAccept_impl( TreeType * tree, PassVisitor< pass_t > & visitor );
     363        template< typename TreeType, typename pass_t > friend void maybeAccept_impl( const TreeType * tree, PassVisitor< pass_t > & visitor );
    269364        template< typename TreeType, typename pass_t > friend void maybeMutate_impl( TreeType *& tree, PassVisitor< pass_t > & mutator );
    270365        template< typename Container, typename pass_t > friend void maybeAccept_impl( Container & container, PassVisitor< pass_t > & visitor );
     366        template< typename Container, typename pass_t > friend void maybeAccept_impl( const Container & container, PassVisitor< pass_t > & visitor );
    271367        template< typename Container, typename pass_t > friend void maybeMutate_impl( Container & container, PassVisitor< pass_t > & mutator );
    272368
    273369        template<typename node_type> void call_previsit ( node_type * node ) { previsit_impl ( pass, node, 0 ); }
     370        template<typename node_type> void call_previsit ( const node_type * node ) { previsit_impl ( pass, node, 0 ); }
    274371        template<typename node_type> void call_postvisit( node_type * node ) { postvisit_impl( pass, node, 0 ); }
     372        template<typename node_type> void call_postvisit( const node_type * node ) { postvisit_impl( pass, node, 0 ); }
    275373
    276374        template<typename node_type> void call_premutate ( node_type * node ) { premutate_impl( pass, node, 0 ); }
     
    286384        void visitStatementList ( std::list< Statement* > &statements );
    287385        void mutateStatementList( std::list< Statement* > &statements );
     386        void visitStatementList ( const std::list< Statement * > & statements );
    288387
    289388        template< typename func_t >
     
    291390        Statement * visitStatement ( Statement * stmt );
    292391        Statement * mutateStatement( Statement * stmt );
     392        void visitStatement ( const Statement * stmt );
    293393
    294394        template< typename func_t >
     
    296396        Expression * visitExpression ( Expression * expr );
    297397        Expression * mutateExpression( Expression * expr );
     398        void visitExpression ( const Expression * expr );
    298399
    299400
     
    309410        void indexerScopeEnter  ()                                    { indexer_impl_enterScope  ( pass, 0       ); }
    310411        void indexerScopeLeave  ()                                    { indexer_impl_leaveScope  ( pass, 0       ); }
    311         void indexerAddId       ( DeclarationWithType      * node  ) { indexer_impl_addId       ( pass, 0, node ); }
    312         void indexerAddType     ( NamedTypeDecl             * node  ) { indexer_impl_addType     ( pass, 0, node ); }
     412        void indexerAddId       ( const DeclarationWithType * node  ) { indexer_impl_addId       ( pass, 0, node ); }
     413        void indexerAddType     ( const NamedTypeDecl       * node  ) { indexer_impl_addType     ( pass, 0, node ); }
    313414        void indexerAddStruct   ( const std::string         & id    ) { indexer_impl_addStruct   ( pass, 0, id   ); }
    314         void indexerAddStruct   ( StructDecl                * node  ) { indexer_impl_addStruct   ( pass, 0, node ); }
    315         void indexerAddStructFwd( StructDecl                * node  ) { indexer_impl_addStructFwd( pass, 0, node ); }
    316         void indexerAddEnum     ( EnumDecl                  * node  ) { indexer_impl_addEnum     ( pass, 0, node ); }
     415        void indexerAddStruct   ( const StructDecl          * node  ) { indexer_impl_addStruct   ( pass, 0, node ); }
     416        void indexerAddStructFwd( const StructDecl          * node  ) { indexer_impl_addStructFwd( pass, 0, node ); }
     417        void indexerAddEnum     ( const EnumDecl            * node  ) { indexer_impl_addEnum     ( pass, 0, node ); }
    317418        void indexerAddUnion    ( const std::string         & id    ) { indexer_impl_addUnion    ( pass, 0, id   ); }
    318         void indexerAddUnion    ( UnionDecl                 * node  ) { indexer_impl_addUnion    ( pass, 0, node ); }
    319         void indexerAddUnionFwd ( UnionDecl                 * node  ) { indexer_impl_addUnionFwd ( pass, 0, node ); }
    320         void indexerAddTrait    ( TraitDecl                 * node  ) { indexer_impl_addTrait    ( pass, 0, node ); }
    321         void indexerAddWith     ( std::list< Expression * > & exprs, BaseSyntaxNode * withStmt ) { indexer_impl_addWith( pass, 0, exprs, withStmt ); }
     419        void indexerAddUnion    ( const UnionDecl           * node  ) { indexer_impl_addUnion    ( pass, 0, node ); }
     420        void indexerAddUnionFwd ( const UnionDecl           * node  ) { indexer_impl_addUnionFwd ( pass, 0, node ); }
     421        void indexerAddTrait    ( const TraitDecl           * node  ) { indexer_impl_addTrait    ( pass, 0, node ); }
     422        void indexerAddWith     ( const std::list< Expression * > & exprs, const Declaration * withStmt ) { indexer_impl_addWith( pass, 0, exprs, withStmt ); }
    322423
    323424
    324425        template< typename TreeType, typename VisitorType >
    325         friend inline void indexerScopedAccept( TreeType * tree, VisitorType &visitor );
     426        friend inline void indexerScopedAccept( TreeType * tree, VisitorType & visitor );
    326427
    327428        template< typename TreeType, typename VisitorType >
    328         friend inline void indexerScopedMutate( TreeType *& tree, VisitorType &visitor );
     429        friend inline void indexerScopedAccept( const TreeType * tree, VisitorType & visitor );
     430
     431        template< typename TreeType, typename VisitorType >
     432        friend inline void indexerScopedMutate( TreeType *& tree, VisitorType & visitor );
    329433};
    330434
  • src/Common/PassVisitor.impl.h

    r1f1c102 rf53acdf8  
    8080
    8181template< typename pass_type >
     82inline void acceptAll( const std::list< const Declaration * > & decls, PassVisitor< pass_type >& visitor ) {
     83        SemanticErrorException errors;
     84
     85        pass_visitor_stats.depth++;
     86        pass_visitor_stats.max->push(pass_visitor_stats.depth);
     87        pass_visitor_stats.avg->push(pass_visitor_stats.depth);
     88        for ( const Declaration * decl : decls ) {
     89                try {
     90                        // run visitor on declaration
     91                        maybeAccept_impl( decl, visitor );
     92                }
     93                catch( SemanticErrorException &e ) {
     94                        errors.append( e );
     95                }
     96        }
     97        pass_visitor_stats.depth--;
     98        if ( ! errors.isEmpty() ) {
     99                throw errors;
     100        }
     101}
     102
     103template< typename pass_type >
    82104inline void mutateAll( std::list< Declaration* > &decls, PassVisitor< pass_type >& mutator ) {
    83105        DeclList_t* beforeDecls = mutator.get_beforeDecls();
     
    117139}
    118140
     141template< typename TreeType, typename pass_type >
     142inline void maybeAccept_impl( const TreeType * tree, PassVisitor< pass_type > & visitor ) {
     143        if ( ! visitor.get_visit_children() ) return;
     144        if ( tree ) {
     145                tree->accept( visitor );
     146        }
     147}
     148
    119149template< typename Container, typename pass_type >
    120150inline void maybeAccept_impl( Container & container, PassVisitor< pass_type > & visitor ) {
     
    129159                        if ( *i ) {
    130160                                (*i)->accept( visitor );
     161                        }
     162                } catch( SemanticErrorException &e ) {
     163                        errors.append( e );
     164                }
     165        }
     166        pass_visitor_stats.depth--;
     167        if ( ! errors.isEmpty() ) {
     168                throw errors;
     169        }
     170}
     171
     172template< typename Container, typename pass_type >
     173inline void maybeAccept_impl( const Container & container, PassVisitor< pass_type > & visitor ) {
     174        if ( ! visitor.get_visit_children() ) return;
     175        SemanticErrorException errors;
     176
     177        pass_visitor_stats.depth++;
     178        pass_visitor_stats.max->push(pass_visitor_stats.depth);
     179        pass_visitor_stats.avg->push(pass_visitor_stats.depth);
     180        for ( const auto & i : container ) {
     181                try {
     182                        if ( i ) {
     183                                i->accept( visitor );
    131184                        }
    132185                } catch( SemanticErrorException &e ) {
     
    227280
    228281template< typename pass_type >
     282void PassVisitor< pass_type >::visitStatementList( const std::list< Statement * > & statements ) {
     283        if ( ! get_visit_children() ) return;
     284        SemanticErrorException errors;
     285
     286        pass_visitor_stats.depth++;
     287        pass_visitor_stats.max->push(pass_visitor_stats.depth);
     288        pass_visitor_stats.avg->push(pass_visitor_stats.depth);
     289        for ( const Statement * i : statements ) {
     290                try {
     291                        maybeAccept_impl( i, *this );
     292                } catch ( SemanticErrorException &e ) {
     293                        errors.append( e );
     294                }
     295        }
     296        pass_visitor_stats.depth--;
     297        if ( !errors.isEmpty() ) { throw errors; }
     298}
     299
     300template< typename pass_type >
    229301void PassVisitor< pass_type >::mutateStatementList( std::list< Statement * > & statements ) {
    230302        handleStatementList( statements, [this]( Statement *& stmt) {
     
    275347
    276348template< typename pass_type >
     349void PassVisitor< pass_type >::visitStatement( const Statement * stmt ) {
     350        if ( ! get_visit_children() ) return;
     351
     352        // don't want statements from outer CompoundStmts to be added to this CompoundStmt
     353        ValueGuardPtr< typename std::remove_pointer<decltype(get_env_ptr())>::type >  oldEnv( get_env_ptr() );
     354
     355        maybeAccept_impl( stmt, *this );
     356}
     357
     358template< typename pass_type >
    277359Statement * PassVisitor< pass_type >::mutateStatement( Statement * stmt ) {
    278360        return handleStatement( stmt, [this]( Statement * stmt ) {
     
    306388
    307389template< typename pass_type >
     390void PassVisitor< pass_type >::visitExpression( const Expression * expr ) {
     391        if ( ! get_visit_children() ) return;
     392        if( !expr ) return;
     393
     394        auto env_ptr = get_env_ptr();
     395        if ( env_ptr && expr->get_env() ) {
     396                *env_ptr = expr->get_env();
     397        }
     398
     399        maybeAccept_impl( expr, *this );
     400}
     401
     402template< typename pass_type >
    308403Expression * PassVisitor< pass_type >::mutateExpression( Expression * expr ) {
    309404        return handleExpression(expr, [this]( Expression * expr ) {
     
    315410template< typename TreeType, typename VisitorType >
    316411inline void indexerScopedAccept( TreeType * tree, VisitorType & visitor ) {
     412        if ( ! visitor.get_visit_children() ) return;
     413        auto guard = makeFuncGuard(
     414                [&visitor]() { visitor.indexerScopeEnter(); },
     415                [&visitor]() { visitor.indexerScopeLeave(); }
     416        );
     417        maybeAccept_impl( tree, visitor );
     418}
     419
     420template< typename TreeType, typename VisitorType >
     421inline void indexerScopedAccept( const TreeType * tree, VisitorType & visitor ) {
    317422        if ( ! visitor.get_visit_children() ) return;
    318423        auto guard = makeFuncGuard(
     
    372477
    373478        indexerAddId( node );
     479
     480        VISIT_END( node );
     481}
     482
     483template< typename pass_type >
     484void PassVisitor< pass_type >::visit( const ObjectDecl * node ) {
     485        VISIT_START( node );
     486
     487        maybeAccept_impl( node->type         , *this );
     488        maybeAccept_impl( node->init         , *this );
     489        maybeAccept_impl( node->bitfieldWidth, *this );
     490        maybeAccept_impl( node->attributes   , *this );
    374491
    375492        VISIT_END( node );
     
    428545
    429546template< typename pass_type >
     547void PassVisitor< pass_type >::visit( const FunctionDecl * node ) {
     548        VISIT_START( node );
     549
     550        indexerAddId( node );
     551
     552        maybeAccept_impl( node->withExprs, *this );
     553        {
     554                // with clause introduces a level of scope (for the with expression members).
     555                // with clause exprs are added to the indexer before parameters so that parameters
     556                // shadow with exprs and not the other way around.
     557                auto guard = makeFuncGuard( [this]() { indexerScopeEnter(); }, [this]() { indexerScopeLeave(); } );
     558                indexerAddWith( node->withExprs, node );
     559                {
     560                        auto guard = makeFuncGuard( [this]() { indexerScopeEnter(); }, [this]() { indexerScopeLeave(); } );
     561                        // implicit add __func__ identifier as specified in the C manual 6.4.2.2
     562                        static ObjectDecl func(
     563                                "__func__", noStorageClasses, LinkageSpec::C, nullptr,
     564                                new ArrayType( Type::Qualifiers(), new BasicType( Type::Qualifiers( Type::Const ), BasicType::Char ), nullptr, true, false ),
     565                                nullptr
     566                        );
     567                        indexerAddId( &func );
     568                        maybeAccept_impl( node->type, *this );
     569                        // function body needs to have the same scope as parameters - CompoundStmt will not enter
     570                        // a new scope if inFunction is true
     571                        ValueGuard< bool > oldInFunction( inFunction );
     572                        inFunction = true;
     573                        maybeAccept_impl( node->statements, *this );
     574                        maybeAccept_impl( node->attributes, *this );
     575                }
     576        }
     577
     578        VISIT_END( node );
     579}
     580
     581template< typename pass_type >
    430582DeclarationWithType * PassVisitor< pass_type >::mutate( FunctionDecl * node ) {
    431583        MUTATE_START( node );
     
    484636
    485637template< typename pass_type >
    486 Declaration * PassVisitor< pass_type >::mutate( StructDecl * node ) {
    487         MUTATE_START( node );
     638void PassVisitor< pass_type >::visit( const StructDecl * node ) {
     639        VISIT_START( node );
    488640
    489641        // make up a forward declaration and add it before processing the members
     
    493645        {
    494646                auto guard = makeFuncGuard( [this]() { indexerScopeEnter(); }, [this]() { indexerScopeLeave(); } );
     647                maybeAccept_impl( node->parameters, *this );
     648                maybeAccept_impl( node->members   , *this );
     649        }
     650
     651        // this addition replaces the forward declaration
     652        indexerAddStruct( node );
     653
     654        VISIT_END( node );
     655}
     656
     657template< typename pass_type >
     658Declaration * PassVisitor< pass_type >::mutate( StructDecl * node ) {
     659        MUTATE_START( node );
     660
     661        // make up a forward declaration and add it before processing the members
     662        // needs to be on the heap because addStruct saves the pointer
     663        indexerAddStructFwd( node );
     664
     665        {
     666                auto guard = makeFuncGuard( [this]() { indexerScopeEnter(); }, [this]() { indexerScopeLeave(); } );
    495667                maybeMutate_impl( node->parameters, *this );
    496668                maybeMutate_impl( node->members   , *this );
     
    522694        VISIT_END( node );
    523695}
     696template< typename pass_type >
     697void PassVisitor< pass_type >::visit( const UnionDecl * node ) {
     698        VISIT_START( node );
     699
     700        // make up a forward declaration and add it before processing the members
     701        indexerAddUnionFwd( node );
     702
     703        {
     704                auto guard = makeFuncGuard( [this]() { indexerScopeEnter(); }, [this]() { indexerScopeLeave(); } );
     705                maybeAccept_impl( node->parameters, *this );
     706                maybeAccept_impl( node->members   , *this );
     707        }
     708
     709        indexerAddUnion( node );
     710
     711        VISIT_END( node );
     712}
    524713
    525714template< typename pass_type >
     
    557746
    558747template< typename pass_type >
     748void PassVisitor< pass_type >::visit( const EnumDecl * node ) {
     749        VISIT_START( node );
     750
     751        indexerAddEnum( node );
     752
     753        // unlike structs, traits, and unions, enums inject their members into the global scope
     754        maybeAccept_impl( node->parameters, *this );
     755        maybeAccept_impl( node->members   , *this );
     756
     757        VISIT_END( node );
     758}
     759
     760template< typename pass_type >
    559761Declaration * PassVisitor< pass_type >::mutate( EnumDecl * node ) {
    560762        MUTATE_START( node );
     
    573775template< typename pass_type >
    574776void PassVisitor< pass_type >::visit( TraitDecl * node ) {
     777        VISIT_START( node );
     778
     779        {
     780                auto guard = makeFuncGuard( [this]() { indexerScopeEnter(); }, [this]() { indexerScopeLeave(); } );
     781                maybeAccept_impl( node->parameters, *this );
     782                maybeAccept_impl( node->members   , *this );
     783        }
     784
     785        indexerAddTrait( node );
     786
     787        VISIT_END( node );
     788}
     789
     790template< typename pass_type >
     791void PassVisitor< pass_type >::visit( const TraitDecl * node ) {
    575792        VISIT_START( node );
    576793
     
    625842}
    626843
    627 template< typename pass_type >
    628 Declaration * PassVisitor< pass_type >::mutate( TypeDecl * node ) {
    629         MUTATE_START( node );
     844
     845template< typename pass_type >
     846void PassVisitor< pass_type >::visit( const TypeDecl * node ) {
     847        VISIT_START( node );
    630848
    631849        {
    632850                auto guard = makeFuncGuard( [this]() { indexerScopeEnter(); }, [this]() { indexerScopeLeave(); } );
    633                 maybeMutate_impl( node->parameters, *this );
    634                 maybeMutate_impl( node->base      , *this );
     851                maybeAccept_impl( node->parameters, *this );
     852                maybeAccept_impl( node->base      , *this );
    635853        }
    636854
     
    640858        indexerAddType( node );
    641859
     860        maybeAccept_impl( node->assertions, *this );
     861
     862        indexerScopedAccept( node->init, *this );
     863
     864        VISIT_END( node );
     865}
     866
     867template< typename pass_type >
     868Declaration * PassVisitor< pass_type >::mutate( TypeDecl * node ) {
     869        MUTATE_START( node );
     870
     871        {
     872                auto guard = makeFuncGuard( [this]() { indexerScopeEnter(); }, [this]() { indexerScopeLeave(); } );
     873                maybeMutate_impl( node->parameters, *this );
     874                maybeMutate_impl( node->base      , *this );
     875        }
     876
     877        // see A NOTE ON THE ORDER OF TRAVERSAL, above
     878        // note that assertions come after the type is added to the symtab, since they are not part of the type proper
     879        // and may depend on the type itself
     880        indexerAddType( node );
     881
    642882        maybeMutate_impl( node->assertions, *this );
    643883
     
    667907
    668908template< typename pass_type >
     909void PassVisitor< pass_type >::visit( const TypedefDecl * node ) {
     910        VISIT_START( node );
     911
     912        {
     913                auto guard = makeFuncGuard( [this]() { indexerScopeEnter(); }, [this]() { indexerScopeLeave(); } );
     914                maybeAccept_impl( node->parameters, *this );
     915                maybeAccept_impl( node->base      , *this );
     916        }
     917
     918        indexerAddType( node );
     919
     920        maybeAccept_impl( node->assertions, *this );
     921
     922        VISIT_END( node );
     923}
     924
     925template< typename pass_type >
    669926Declaration * PassVisitor< pass_type >::mutate( TypedefDecl * node ) {
    670927        MUTATE_START( node );
     
    695952
    696953template< typename pass_type >
     954void PassVisitor< pass_type >::visit( const AsmDecl * node ) {
     955        VISIT_START( node );
     956
     957        maybeAccept_impl( node->stmt, *this );
     958
     959        VISIT_END( node );
     960}
     961
     962template< typename pass_type >
    697963AsmDecl * PassVisitor< pass_type >::mutate( AsmDecl * node ) {
    698964        MUTATE_START( node );
     
    710976
    711977        node->condition = visitExpression( node->condition );
     978        maybeAccept_impl( node->message, *this );
     979
     980        VISIT_END( node );
     981}
     982
     983template< typename pass_type >
     984void PassVisitor< pass_type >::visit( const StaticAssertDecl * node ) {
     985        VISIT_START( node );
     986
     987        visitExpression( node->condition );
    712988        maybeAccept_impl( node->message, *this );
    713989
     
    7421018
    7431019template< typename pass_type >
     1020void PassVisitor< pass_type >::visit( const CompoundStmt * node ) {
     1021        VISIT_START( node );
     1022        {
     1023                // do not enter a new scope if inFunction is true - needs to check old state before the assignment
     1024                ValueGuard< bool > oldInFunction( inFunction );
     1025                auto guard1 = makeFuncGuard( [this, &oldInFunction]() { if ( ! oldInFunction.old ) indexerScopeEnter(); }, [this, &oldInFunction]() { if ( ! oldInFunction.old ) indexerScopeLeave(); } );
     1026                auto guard2 = makeFuncGuard( [this]() { call_beginScope();   }, [this]() { call_endScope();     } );
     1027                inFunction = false;
     1028                visitStatementList( node->kids );
     1029        }
     1030        VISIT_END( node );
     1031}
     1032
     1033template< typename pass_type >
    7441034CompoundStmt * PassVisitor< pass_type >::mutate( CompoundStmt * node ) {
    7451035        MUTATE_START( node );
     
    7671057
    7681058template< typename pass_type >
     1059void PassVisitor< pass_type >::visit( const ExprStmt * node ) {
     1060        VISIT_START( node );
     1061
     1062        visitExpression( node->expr );
     1063
     1064        VISIT_END( node );
     1065}
     1066
     1067template< typename pass_type >
    7691068Statement * PassVisitor< pass_type >::mutate( ExprStmt * node ) {
    7701069        MUTATE_START( node );
     
    7901089
    7911090template< typename pass_type >
     1091void PassVisitor< pass_type >::visit( const AsmStmt * node ) {
     1092        VISIT_START( node )
     1093
     1094        maybeAccept_impl( node->instruction, *this );
     1095        maybeAccept_impl( node->output, *this );
     1096        maybeAccept_impl( node->input, *this );
     1097        maybeAccept_impl( node->clobber, *this );
     1098
     1099        VISIT_END( node );
     1100}
     1101
     1102template< typename pass_type >
    7921103Statement * PassVisitor< pass_type >::mutate( AsmStmt * node ) {
    7931104        MUTATE_START( node );
     
    8111122
    8121123template< typename pass_type >
     1124void PassVisitor< pass_type >::visit( const DirectiveStmt * node ) {
     1125        VISIT_START( node )
     1126
     1127        VISIT_END( node );
     1128}
     1129
     1130template< typename pass_type >
    8131131Statement * PassVisitor< pass_type >::mutate( DirectiveStmt * node ) {
    8141132        MUTATE_START( node );
     
    8251143                // if statements introduce a level of scope (for the initialization)
    8261144                auto guard = makeFuncGuard( [this]() { indexerScopeEnter(); }, [this]() { indexerScopeLeave(); } );
    827                 maybeAccept_impl( node->get_initialization(), *this );
     1145                maybeAccept_impl( node->initialization, *this );
    8281146                visitExpression ( node->condition );
    8291147                node->thenPart = visitStatement( node->thenPart );
     
    8341152
    8351153template< typename pass_type >
    836 Statement * PassVisitor< pass_type >::mutate( IfStmt * node ) {
    837         MUTATE_START( node );
     1154void PassVisitor< pass_type >::visit( const IfStmt * node ) {
     1155        VISIT_START( node );
    8381156        {
    8391157                // if statements introduce a level of scope (for the initialization)
    8401158                auto guard = makeFuncGuard( [this]() { indexerScopeEnter(); }, [this]() { indexerScopeLeave(); } );
    841                 maybeMutate_impl( node->get_initialization(), *this );
     1159                maybeAccept_impl( node->initialization, *this );
     1160                visitExpression ( node->condition );
     1161                visitStatement  ( node->thenPart );
     1162                visitStatement  ( node->elsePart );
     1163        }
     1164        VISIT_END( node );
     1165}
     1166
     1167template< typename pass_type >
     1168Statement * PassVisitor< pass_type >::mutate( IfStmt * node ) {
     1169        MUTATE_START( node );
     1170        {
     1171                // if statements introduce a level of scope (for the initialization)
     1172                auto guard = makeFuncGuard( [this]() { indexerScopeEnter(); }, [this]() { indexerScopeLeave(); } );
     1173                maybeMutate_impl( node->initialization, *this );
    8421174                node->condition = mutateExpression( node->condition );
    8431175                node->thenPart  = mutateStatement ( node->thenPart  );
     
    8591191                visitExpression ( node->condition );
    8601192                node->body = visitStatement( node->body );
     1193        }
     1194
     1195        VISIT_END( node );
     1196}
     1197
     1198template< typename pass_type >
     1199void PassVisitor< pass_type >::visit( const WhileStmt * node ) {
     1200        VISIT_START( node );
     1201
     1202        {
     1203                // while statements introduce a level of scope (for the initialization)
     1204                auto guard = makeFuncGuard( [this]() { indexerScopeEnter(); }, [this]() { indexerScopeLeave(); } );
     1205                maybeAccept_impl( node->initialization, *this );
     1206                visitExpression ( node->condition );
     1207                visitStatement  ( node->body );
    8611208        }
    8621209
     
    8971244
    8981245template< typename pass_type >
     1246void PassVisitor< pass_type >::visit( const ForStmt * node ) {
     1247        VISIT_START( node );
     1248        {
     1249                // for statements introduce a level of scope (for the initialization)
     1250                auto guard = makeFuncGuard( [this]() { indexerScopeEnter(); }, [this]() { indexerScopeLeave(); } );
     1251                maybeAccept_impl( node->initialization, *this );
     1252                visitExpression( node->condition );
     1253                visitExpression( node->increment );
     1254                visitStatement ( node->body );
     1255        }
     1256        VISIT_END( node );
     1257}
     1258
     1259template< typename pass_type >
    8991260Statement * PassVisitor< pass_type >::mutate( ForStmt * node ) {
    9001261        MUTATE_START( node );
     
    9231284
    9241285template< typename pass_type >
     1286void PassVisitor< pass_type >::visit( const SwitchStmt * node ) {
     1287        VISIT_START( node );
     1288
     1289        visitExpression   ( node->condition  );
     1290        visitStatementList( node->statements );
     1291
     1292        VISIT_END( node );
     1293}
     1294
     1295template< typename pass_type >
    9251296Statement * PassVisitor< pass_type >::mutate( SwitchStmt * node ) {
    9261297        MUTATE_START( node );
     
    9451316
    9461317template< typename pass_type >
     1318void PassVisitor< pass_type >::visit( const CaseStmt * node ) {
     1319        VISIT_START( node );
     1320
     1321        visitExpression   ( node->condition );
     1322        visitStatementList( node->stmts     );
     1323
     1324        VISIT_END( node );
     1325}
     1326
     1327template< typename pass_type >
    9471328Statement * PassVisitor< pass_type >::mutate( CaseStmt * node ) {
    9481329        MUTATE_START( node );
     
    9631344
    9641345template< typename pass_type >
     1346void PassVisitor< pass_type >::visit( const BranchStmt * node ) {
     1347        VISIT_START( node );
     1348        VISIT_END( node );
     1349}
     1350
     1351template< typename pass_type >
    9651352Statement * PassVisitor< pass_type >::mutate( BranchStmt * node ) {
    9661353        MUTATE_START( node );
     
    9801367
    9811368template< typename pass_type >
     1369void PassVisitor< pass_type >::visit( const ReturnStmt * node ) {
     1370        VISIT_START( node );
     1371
     1372        visitExpression( node->expr );
     1373
     1374        VISIT_END( node );
     1375}
     1376
     1377template< typename pass_type >
    9821378Statement * PassVisitor< pass_type >::mutate( ReturnStmt * node ) {
    9831379        MUTATE_START( node );
     
    9901386//--------------------------------------------------------------------------
    9911387// ThrowStmt
    992 
    9931388template< typename pass_type >
    9941389void PassVisitor< pass_type >::visit( ThrowStmt * node ) {
     
    10021397
    10031398template< typename pass_type >
     1399void PassVisitor< pass_type >::visit( const ThrowStmt * node ) {
     1400        VISIT_START( node );
     1401
     1402        maybeAccept_impl( node->expr, *this );
     1403        maybeAccept_impl( node->target, *this );
     1404
     1405        VISIT_END( node );
     1406}
     1407
     1408template< typename pass_type >
    10041409Statement * PassVisitor< pass_type >::mutate( ThrowStmt * node ) {
    10051410        MUTATE_START( node );
     
    10151420template< typename pass_type >
    10161421void PassVisitor< pass_type >::visit( TryStmt * node ) {
     1422        VISIT_START( node );
     1423
     1424        maybeAccept_impl( node->block       , *this );
     1425        maybeAccept_impl( node->handlers    , *this );
     1426        maybeAccept_impl( node->finallyBlock, *this );
     1427
     1428        VISIT_END( node );
     1429}
     1430
     1431template< typename pass_type >
     1432void PassVisitor< pass_type >::visit( const TryStmt * node ) {
    10171433        VISIT_START( node );
    10181434
     
    10511467
    10521468template< typename pass_type >
     1469void PassVisitor< pass_type >::visit( const CatchStmt * node ) {
     1470        VISIT_START( node );
     1471        {
     1472                // catch statements introduce a level of scope (for the caught exception)
     1473                auto guard = makeFuncGuard( [this]() { indexerScopeEnter(); }, [this]() { indexerScopeLeave(); } );
     1474                maybeAccept_impl( node->decl, *this );
     1475                visitExpression ( node->cond );
     1476                visitStatement  ( node->body );
     1477        }
     1478        VISIT_END( node );
     1479}
     1480
     1481template< typename pass_type >
    10531482Statement * PassVisitor< pass_type >::mutate( CatchStmt * node ) {
    10541483        MUTATE_START( node );
     
    10751504
    10761505template< typename pass_type >
     1506void PassVisitor< pass_type >::visit( const FinallyStmt * node ) {
     1507        VISIT_START( node );
     1508
     1509        maybeAccept_impl( node->block, *this );
     1510
     1511        VISIT_END( node );
     1512}
     1513
     1514template< typename pass_type >
    10771515Statement * PassVisitor< pass_type >::mutate( FinallyStmt * node ) {
    10781516        MUTATE_START( node );
     
    11071545
    11081546template< typename pass_type >
     1547void PassVisitor< pass_type >::visit( const WaitForStmt * node ) {
     1548        VISIT_START( node );
     1549
     1550        for( auto & clause : node->clauses ) {
     1551                maybeAccept_impl( clause.target.function, *this );
     1552                maybeAccept_impl( clause.target.arguments, *this );
     1553
     1554                maybeAccept_impl( clause.statement, *this );
     1555                maybeAccept_impl( clause.condition, *this );
     1556        }
     1557
     1558        maybeAccept_impl( node->timeout.time, *this );
     1559        maybeAccept_impl( node->timeout.statement, *this );
     1560        maybeAccept_impl( node->timeout.condition, *this );
     1561        maybeAccept_impl( node->orelse.statement, *this );
     1562        maybeAccept_impl( node->orelse.condition, *this );
     1563
     1564        VISIT_END( node );
     1565}
     1566
     1567template< typename pass_type >
    11091568Statement * PassVisitor< pass_type >::mutate( WaitForStmt * node ) {
    11101569        MUTATE_START( node );
     
    11301589
    11311590//--------------------------------------------------------------------------
    1132 // NullStmt
     1591// WithStmt
    11331592template< typename pass_type >
    11341593void PassVisitor< pass_type >::visit( WithStmt * node ) {
     
    11451604
    11461605template< typename pass_type >
    1147 Statement * PassVisitor< pass_type >::mutate( WithStmt * node ) {
     1606void PassVisitor< pass_type >::visit( const WithStmt * node ) {
     1607        VISIT_START( node );
     1608        maybeAccept_impl( node->exprs, *this );
     1609        {
     1610                // catch statements introduce a level of scope (for the caught exception)
     1611                auto guard = makeFuncGuard( [this]() { indexerScopeEnter(); }, [this]() { indexerScopeLeave(); } );
     1612                indexerAddWith( node->exprs, node );
     1613                maybeAccept_impl( node->stmt, *this );
     1614        }
     1615        VISIT_END( node );
     1616}
     1617
     1618template< typename pass_type >
     1619Declaration * PassVisitor< pass_type >::mutate( WithStmt * node ) {
    11481620        MUTATE_START( node );
    11491621        maybeMutate_impl( node->exprs, *this );
     
    11541626                maybeMutate_impl( node->stmt, *this );
    11551627        }
     1628        MUTATE_END( Declaration, node );
     1629}
     1630
     1631//--------------------------------------------------------------------------
     1632// NullStmt
     1633template< typename pass_type >
     1634void PassVisitor< pass_type >::visit( NullStmt * node ) {
     1635        VISIT_START( node );
     1636        VISIT_END( node );
     1637}
     1638
     1639template< typename pass_type >
     1640void PassVisitor< pass_type >::visit( const NullStmt * node ) {
     1641        VISIT_START( node );
     1642        VISIT_END( node );
     1643}
     1644
     1645template< typename pass_type >
     1646NullStmt * PassVisitor< pass_type >::mutate( NullStmt * node ) {
     1647        MUTATE_START( node );
     1648        MUTATE_END( NullStmt, node );
     1649}
     1650
     1651//--------------------------------------------------------------------------
     1652// DeclStmt
     1653template< typename pass_type >
     1654void PassVisitor< pass_type >::visit( DeclStmt * node ) {
     1655        VISIT_START( node );
     1656
     1657        maybeAccept_impl( node->decl, *this );
     1658
     1659        VISIT_END( node );
     1660}
     1661
     1662template< typename pass_type >
     1663void PassVisitor< pass_type >::visit( const DeclStmt * node ) {
     1664        VISIT_START( node );
     1665
     1666        maybeAccept_impl( node->decl, *this );
     1667
     1668        VISIT_END( node );
     1669}
     1670
     1671template< typename pass_type >
     1672Statement * PassVisitor< pass_type >::mutate( DeclStmt * node ) {
     1673        MUTATE_START( node );
     1674
     1675        maybeMutate_impl( node->decl, *this );
     1676
    11561677        MUTATE_END( Statement, node );
    11571678}
    11581679
    11591680//--------------------------------------------------------------------------
    1160 // NullStmt
    1161 template< typename pass_type >
    1162 void PassVisitor< pass_type >::visit( NullStmt * node ) {
    1163         VISIT_START( node );
    1164         VISIT_END( node );
    1165 }
    1166 
    1167 template< typename pass_type >
    1168 NullStmt * PassVisitor< pass_type >::mutate( NullStmt * node ) {
    1169         MUTATE_START( node );
    1170         MUTATE_END( NullStmt, node );
    1171 }
    1172 
    1173 //--------------------------------------------------------------------------
    1174 // DeclStmt
    1175 template< typename pass_type >
    1176 void PassVisitor< pass_type >::visit( DeclStmt * node ) {
    1177         VISIT_START( node );
    1178 
    1179         maybeAccept_impl( node->decl, *this );
    1180 
    1181         VISIT_END( node );
    1182 }
    1183 
    1184 template< typename pass_type >
    1185 Statement * PassVisitor< pass_type >::mutate( DeclStmt * node ) {
    1186         MUTATE_START( node );
    1187 
    1188         maybeMutate_impl( node->decl, *this );
     1681// ImplicitCtorDtorStmt
     1682template< typename pass_type >
     1683void PassVisitor< pass_type >::visit( ImplicitCtorDtorStmt * node ) {
     1684        VISIT_START( node );
     1685
     1686        maybeAccept_impl( node->callStmt, *this );
     1687
     1688        VISIT_END( node );
     1689}
     1690
     1691template< typename pass_type >
     1692void PassVisitor< pass_type >::visit( const ImplicitCtorDtorStmt * node ) {
     1693        VISIT_START( node );
     1694
     1695        maybeAccept_impl( node->callStmt, *this );
     1696
     1697        VISIT_END( node );
     1698}
     1699
     1700template< typename pass_type >
     1701Statement * PassVisitor< pass_type >::mutate( ImplicitCtorDtorStmt * node ) {
     1702        MUTATE_START( node );
     1703
     1704        maybeMutate_impl( node->callStmt, *this );
    11891705
    11901706        MUTATE_END( Statement, node );
     
    11921708
    11931709//--------------------------------------------------------------------------
    1194 // ImplicitCtorDtorStmt
    1195 template< typename pass_type >
    1196 void PassVisitor< pass_type >::visit( ImplicitCtorDtorStmt * node ) {
    1197         VISIT_START( node );
    1198 
    1199         maybeAccept_impl( node->callStmt, *this );
    1200 
    1201         VISIT_END( node );
    1202 }
    1203 
    1204 template< typename pass_type >
    1205 Statement * PassVisitor< pass_type >::mutate( ImplicitCtorDtorStmt * node ) {
    1206         MUTATE_START( node );
    1207 
    1208         maybeMutate_impl( node->callStmt, *this );
    1209 
    1210         MUTATE_END( Statement, node );
    1211 }
    1212 
    1213 //--------------------------------------------------------------------------
    12141710// ApplicationExpr
    12151711template< typename pass_type >
     
    12181714
    12191715        indexerScopedAccept( node->result  , *this );
    1220         maybeAccept_impl        ( node->function, *this );
    1221         maybeAccept_impl        ( node->args    , *this );
     1716        maybeAccept_impl   ( node->function, *this );
     1717        maybeAccept_impl   ( node->args    , *this );
     1718
     1719        VISIT_END( node );
     1720}
     1721
     1722template< typename pass_type >
     1723void PassVisitor< pass_type >::visit( const ApplicationExpr * node ) {
     1724        VISIT_START( node );
     1725
     1726        indexerScopedAccept( node->result  , *this );
     1727        maybeAccept_impl   ( node->function, *this );
     1728        maybeAccept_impl   ( node->args    , *this );
    12221729
    12231730        VISIT_END( node );
     
    12531760
    12541761template< typename pass_type >
     1762void PassVisitor< pass_type >::visit( const UntypedExpr * node ) {
     1763        VISIT_START( node );
     1764
     1765        indexerScopedAccept( node->result, *this );
     1766
     1767        for ( auto expr : node->args ) {
     1768                visitExpression( expr );
     1769        }
     1770
     1771        VISIT_END( node );
     1772}
     1773
     1774template< typename pass_type >
    12551775Expression * PassVisitor< pass_type >::mutate( UntypedExpr * node ) {
    12561776        MUTATE_START( node );
     
    12781798
    12791799template< typename pass_type >
     1800void PassVisitor< pass_type >::visit( const NameExpr * node ) {
     1801        VISIT_START( node );
     1802
     1803        indexerScopedAccept( node->result, *this );
     1804
     1805        VISIT_END( node );
     1806}
     1807
     1808template< typename pass_type >
    12801809Expression * PassVisitor< pass_type >::mutate( NameExpr * node ) {
    12811810        MUTATE_START( node );
     
    12941823
    12951824        indexerScopedAccept( node->result, *this );
    1296         maybeAccept_impl        ( node->arg   , *this );
     1825        maybeAccept_impl   ( node->arg   , *this );
     1826
     1827        VISIT_END( node );
     1828}
     1829
     1830template< typename pass_type >
     1831void PassVisitor< pass_type >::visit( const CastExpr * node ) {
     1832        VISIT_START( node );
     1833
     1834        indexerScopedAccept( node->result, *this );
     1835        maybeAccept_impl   ( node->arg   , *this );
    12971836
    12981837        VISIT_END( node );
     
    13231862
    13241863template< typename pass_type >
     1864void PassVisitor< pass_type >::visit( const KeywordCastExpr * node ) {
     1865        VISIT_START( node );
     1866
     1867        indexerScopedAccept( node->result, *this );
     1868        maybeAccept_impl   ( node->arg   , *this );
     1869
     1870        VISIT_END( node );
     1871}
     1872
     1873template< typename pass_type >
    13251874Expression * PassVisitor< pass_type >::mutate( KeywordCastExpr * node ) {
    13261875        MUTATE_START( node );
     
    13401889
    13411890        indexerScopedAccept( node->result, *this );
    1342         maybeAccept_impl( node->arg, *this );
     1891        maybeAccept_impl   ( node->arg, *this );
     1892
     1893        VISIT_END( node );
     1894}
     1895
     1896template< typename pass_type >
     1897void PassVisitor< pass_type >::visit( const VirtualCastExpr * node ) {
     1898        VISIT_START( node );
     1899
     1900        indexerScopedAccept( node->result, *this );
     1901        maybeAccept_impl   ( node->arg, *this );
    13431902
    13441903        VISIT_END( node );
     
    13691928
    13701929template< typename pass_type >
     1930void PassVisitor< pass_type >::visit( const AddressExpr * node ) {
     1931        VISIT_START( node );
     1932
     1933        indexerScopedAccept( node->result, *this );
     1934        maybeAccept_impl   ( node->arg   , *this );
     1935
     1936        VISIT_END( node );
     1937}
     1938
     1939template< typename pass_type >
    13711940Expression * PassVisitor< pass_type >::mutate( AddressExpr * node ) {
    13721941        MUTATE_START( node );
     
    13911960
    13921961template< typename pass_type >
     1962void PassVisitor< pass_type >::visit( const LabelAddressExpr * node ) {
     1963        VISIT_START( node );
     1964
     1965        indexerScopedAccept( node->result, *this );
     1966
     1967        VISIT_END( node );
     1968}
     1969
     1970template< typename pass_type >
    13931971Expression * PassVisitor< pass_type >::mutate( LabelAddressExpr * node ) {
    13941972        MUTATE_START( node );
     
    14041982template< typename pass_type >
    14051983void PassVisitor< pass_type >::visit( UntypedMemberExpr * node ) {
     1984        VISIT_START( node );
     1985
     1986        indexerScopedAccept( node->result   , *this );
     1987        maybeAccept_impl   ( node->aggregate, *this );
     1988        maybeAccept_impl   ( node->member   , *this );
     1989
     1990        VISIT_END( node );
     1991}
     1992
     1993template< typename pass_type >
     1994void PassVisitor< pass_type >::visit( const UntypedMemberExpr * node ) {
    14061995        VISIT_START( node );
    14071996
     
    14382027
    14392028template< typename pass_type >
     2029void PassVisitor< pass_type >::visit( const MemberExpr * node ) {
     2030        VISIT_START( node );
     2031
     2032        indexerScopedAccept( node->result   , *this );
     2033        maybeAccept_impl   ( node->aggregate, *this );
     2034
     2035        VISIT_END( node );
     2036}
     2037
     2038template< typename pass_type >
    14402039Expression * PassVisitor< pass_type >::mutate( MemberExpr * node ) {
    14412040        MUTATE_START( node );
     
    14602059
    14612060template< typename pass_type >
     2061void PassVisitor< pass_type >::visit( const VariableExpr * node ) {
     2062        VISIT_START( node );
     2063
     2064        indexerScopedAccept( node->result, *this );
     2065
     2066        VISIT_END( node );
     2067}
     2068
     2069template< typename pass_type >
    14622070Expression * PassVisitor< pass_type >::mutate( VariableExpr * node ) {
    14632071        MUTATE_START( node );
     
    14732081template< typename pass_type >
    14742082void PassVisitor< pass_type >::visit( ConstantExpr * node ) {
     2083        VISIT_START( node );
     2084
     2085        indexerScopedAccept( node->result   , *this );
     2086        maybeAccept_impl   ( &node->constant, *this );
     2087
     2088        VISIT_END( node );
     2089}
     2090
     2091template< typename pass_type >
     2092void PassVisitor< pass_type >::visit( const ConstantExpr * node ) {
    14752093        VISIT_START( node );
    14762094
     
    14982116template< typename pass_type >
    14992117void PassVisitor< pass_type >::visit( SizeofExpr * node ) {
     2118        VISIT_START( node );
     2119
     2120        indexerScopedAccept( node->result, *this );
     2121        if ( node->get_isType() ) {
     2122                maybeAccept_impl( node->type, *this );
     2123        } else {
     2124                maybeAccept_impl( node->expr, *this );
     2125        }
     2126
     2127        VISIT_END( node );
     2128}
     2129
     2130template< typename pass_type >
     2131void PassVisitor< pass_type >::visit( const SizeofExpr * node ) {
    15002132        VISIT_START( node );
    15012133
     
    15422174
    15432175template< typename pass_type >
     2176void PassVisitor< pass_type >::visit( const AlignofExpr * node ) {
     2177        VISIT_START( node );
     2178
     2179        indexerScopedAccept( node->result, *this );
     2180        if ( node->get_isType() ) {
     2181                maybeAccept_impl( node->type, *this );
     2182        } else {
     2183                maybeAccept_impl( node->expr, *this );
     2184        }
     2185
     2186        VISIT_END( node );
     2187}
     2188
     2189template< typename pass_type >
    15442190Expression * PassVisitor< pass_type >::mutate( AlignofExpr * node ) {
    15452191        MUTATE_START( node );
     
    15692215
    15702216template< typename pass_type >
     2217void PassVisitor< pass_type >::visit( const UntypedOffsetofExpr * node ) {
     2218        VISIT_START( node );
     2219
     2220        indexerScopedAccept( node->result, *this );
     2221        maybeAccept_impl   ( node->type  , *this );
     2222
     2223        VISIT_END( node );
     2224}
     2225
     2226template< typename pass_type >
    15712227Expression * PassVisitor< pass_type >::mutate( UntypedOffsetofExpr * node ) {
    15722228        MUTATE_START( node );
     
    15922248
    15932249template< typename pass_type >
     2250void PassVisitor< pass_type >::visit( const OffsetofExpr * node ) {
     2251        VISIT_START( node );
     2252
     2253        indexerScopedAccept( node->result, *this );
     2254        maybeAccept_impl   ( node->type  , *this );
     2255
     2256        VISIT_END( node );
     2257}
     2258
     2259template< typename pass_type >
    15942260Expression * PassVisitor< pass_type >::mutate( OffsetofExpr * node ) {
    15952261        MUTATE_START( node );
     
    16152281
    16162282template< typename pass_type >
     2283void PassVisitor< pass_type >::visit( const OffsetPackExpr * node ) {
     2284        VISIT_START( node );
     2285
     2286        indexerScopedAccept( node->result, *this );
     2287        maybeAccept_impl   ( node->type  , *this );
     2288
     2289        VISIT_END( node );
     2290}
     2291
     2292template< typename pass_type >
    16172293Expression * PassVisitor< pass_type >::mutate( OffsetPackExpr * node ) {
    16182294        MUTATE_START( node );
     
    16292305template< typename pass_type >
    16302306void PassVisitor< pass_type >::visit( AttrExpr * node ) {
     2307        VISIT_START( node );
     2308
     2309        indexerScopedAccept( node->result, *this );
     2310        if ( node->get_isType() ) {
     2311                maybeAccept_impl( node->type, *this );
     2312        } else {
     2313                maybeAccept_impl( node->expr, *this );
     2314        }
     2315
     2316        VISIT_END( node );
     2317}
     2318
     2319template< typename pass_type >
     2320void PassVisitor< pass_type >::visit( const AttrExpr * node ) {
    16312321        VISIT_START( node );
    16322322
     
    16702360
    16712361template< typename pass_type >
     2362void PassVisitor< pass_type >::visit( const LogicalExpr * node ) {
     2363        VISIT_START( node );
     2364
     2365        indexerScopedAccept( node->result, *this );
     2366        maybeAccept_impl   ( node->arg1  , *this );
     2367        maybeAccept_impl   ( node->arg2  , *this );
     2368
     2369        VISIT_END( node );
     2370}
     2371
     2372template< typename pass_type >
    16722373Expression * PassVisitor< pass_type >::mutate( LogicalExpr * node ) {
    16732374        MUTATE_START( node );
     
    16912392        maybeAccept_impl        ( node->arg2  , *this );
    16922393        maybeAccept_impl        ( node->arg3  , *this );
     2394
     2395        VISIT_END( node );
     2396}
     2397
     2398template< typename pass_type >
     2399void PassVisitor< pass_type >::visit( const ConditionalExpr * node ) {
     2400        VISIT_START( node );
     2401
     2402        indexerScopedAccept( node->result, *this );
     2403        maybeAccept_impl   ( node->arg1  , *this );
     2404        maybeAccept_impl   ( node->arg2  , *this );
     2405        maybeAccept_impl   ( node->arg3  , *this );
    16932406
    16942407        VISIT_END( node );
     
    17222435
    17232436template< typename pass_type >
     2437void PassVisitor< pass_type >::visit( const CommaExpr * node ) {
     2438        VISIT_START( node );
     2439
     2440        indexerScopedAccept( node->result, *this );
     2441        maybeAccept_impl   ( node->arg1  , *this );
     2442        maybeAccept_impl   ( node->arg2  , *this );
     2443
     2444        VISIT_END( node );
     2445}
     2446
     2447template< typename pass_type >
    17242448Expression * PassVisitor< pass_type >::mutate( CommaExpr * node ) {
    17252449        MUTATE_START( node );
     
    17462470
    17472471template< typename pass_type >
     2472void PassVisitor< pass_type >::visit( const TypeExpr * node ) {
     2473        VISIT_START( node );
     2474
     2475        indexerScopedAccept( node->result, *this );
     2476        maybeAccept_impl   ( node->type, *this );
     2477
     2478        VISIT_END( node );
     2479}
     2480
     2481template< typename pass_type >
    17482482Expression * PassVisitor< pass_type >::mutate( TypeExpr * node ) {
    17492483        MUTATE_START( node );
     
    17602494template< typename pass_type >
    17612495void PassVisitor< pass_type >::visit( AsmExpr * node ) {
     2496        VISIT_START( node );
     2497
     2498        indexerScopedAccept( node->result    , *this );
     2499        maybeAccept_impl   ( node->inout     , *this );
     2500        maybeAccept_impl   ( node->constraint, *this );
     2501        maybeAccept_impl   ( node->operand   , *this );
     2502
     2503        VISIT_END( node );
     2504}
     2505
     2506template< typename pass_type >
     2507void PassVisitor< pass_type >::visit( const AsmExpr * node ) {
    17622508        VISIT_START( node );
    17632509
     
    17962542
    17972543template< typename pass_type >
     2544void PassVisitor< pass_type >::visit( const ImplicitCopyCtorExpr * node ) {
     2545        VISIT_START( node );
     2546
     2547        indexerScopedAccept( node->result    , *this );
     2548        maybeAccept_impl   ( node->callExpr  , *this );
     2549
     2550        VISIT_END( node );
     2551}
     2552
     2553template< typename pass_type >
    17982554Expression * PassVisitor< pass_type >::mutate( ImplicitCopyCtorExpr * node ) {
    17992555        MUTATE_START( node );
     
    18192575
    18202576template< typename pass_type >
     2577void PassVisitor< pass_type >::visit( const ConstructorExpr * node ) {
     2578        VISIT_START( node );
     2579
     2580        indexerScopedAccept( node->result  , *this );
     2581        maybeAccept_impl   ( node->callExpr, *this );
     2582
     2583        VISIT_END( node );
     2584}
     2585
     2586template< typename pass_type >
    18212587Expression * PassVisitor< pass_type >::mutate( ConstructorExpr * node ) {
    18222588        MUTATE_START( node );
     
    18422608
    18432609template< typename pass_type >
     2610void PassVisitor< pass_type >::visit( const CompoundLiteralExpr * node ) {
     2611        VISIT_START( node );
     2612
     2613        indexerScopedAccept( node->result     , *this );
     2614        maybeAccept_impl   ( node->initializer, *this );
     2615
     2616        VISIT_END( node );
     2617}
     2618
     2619template< typename pass_type >
    18442620Expression * PassVisitor< pass_type >::mutate( CompoundLiteralExpr * node ) {
    18452621        MUTATE_START( node );
     
    18562632template< typename pass_type >
    18572633void PassVisitor< pass_type >::visit( RangeExpr * node ) {
     2634        VISIT_START( node );
     2635
     2636        indexerScopedAccept( node->result, *this );
     2637        maybeAccept_impl   ( node->low   , *this );
     2638        maybeAccept_impl   ( node->high  , *this );
     2639
     2640        VISIT_END( node );
     2641}
     2642
     2643template< typename pass_type >
     2644void PassVisitor< pass_type >::visit( const RangeExpr * node ) {
    18582645        VISIT_START( node );
    18592646
     
    18902677
    18912678template< typename pass_type >
     2679void PassVisitor< pass_type >::visit( const UntypedTupleExpr * node ) {
     2680        VISIT_START( node );
     2681
     2682        indexerScopedAccept( node->result, *this );
     2683        maybeAccept_impl   ( node->exprs , *this );
     2684
     2685        VISIT_END( node );
     2686}
     2687
     2688template< typename pass_type >
    18922689Expression * PassVisitor< pass_type >::mutate( UntypedTupleExpr * node ) {
    18932690        MUTATE_START( node );
     
    19132710
    19142711template< typename pass_type >
     2712void PassVisitor< pass_type >::visit( const TupleExpr * node ) {
     2713        VISIT_START( node );
     2714
     2715        indexerScopedAccept( node->result, *this );
     2716        maybeAccept_impl   ( node->exprs , *this );
     2717
     2718        VISIT_END( node );
     2719}
     2720
     2721template< typename pass_type >
    19152722Expression * PassVisitor< pass_type >::mutate( TupleExpr * node ) {
    19162723        MUTATE_START( node );
     
    19362743
    19372744template< typename pass_type >
     2745void PassVisitor< pass_type >::visit( const TupleIndexExpr * node ) {
     2746        VISIT_START( node );
     2747
     2748        indexerScopedAccept( node->result, *this );
     2749        maybeAccept_impl   ( node->tuple , *this );
     2750
     2751        VISIT_END( node );
     2752}
     2753
     2754template< typename pass_type >
    19382755Expression * PassVisitor< pass_type >::mutate( TupleIndexExpr * node ) {
    19392756        MUTATE_START( node );
     
    19542771        indexerScopedAccept( node->result  , *this );
    19552772        maybeAccept_impl   ( node->stmtExpr, *this );
     2773
     2774        VISIT_END( node );
     2775}
     2776
     2777template< typename pass_type >
     2778void PassVisitor< pass_type >::visit( const TupleAssignExpr * node ) {
     2779        VISIT_START( node );
     2780
     2781        indexerScopedAccept( node->result  , *this );
     2782        maybeAccept_impl( node->stmtExpr, *this );
    19562783
    19572784        VISIT_END( node );
     
    19892816
    19902817template< typename pass_type >
    1991 Expression * PassVisitor< pass_type >::mutate( StmtExpr * node ) {
    1992         MUTATE_START( node );
     2818void PassVisitor< pass_type >::visit( const StmtExpr * node ) {
     2819        VISIT_START( node );
    19932820
    19942821        // don't want statements from outer CompoundStmts to be added to this StmtExpr
     
    19972824        ValueGuardPtr< std::list< Statement* > > oldAfterStmts ( get_afterStmts () );
    19982825
     2826        indexerScopedAccept( node->result     , *this );
     2827        maybeAccept_impl   ( node->statements , *this );
     2828        maybeAccept_impl   ( node->returnDecls, *this );
     2829        maybeAccept_impl   ( node->dtors      , *this );
     2830
     2831        VISIT_END( node );
     2832}
     2833
     2834template< typename pass_type >
     2835Expression * PassVisitor< pass_type >::mutate( StmtExpr * node ) {
     2836        MUTATE_START( node );
     2837
     2838        // don't want statements from outer CompoundStmts to be added to this StmtExpr
     2839        ValueGuardPtr< typename std::remove_pointer<decltype(get_env_ptr())>::type >  oldEnv( get_env_ptr() );
     2840        ValueGuardPtr< std::list< Statement* > > oldBeforeStmts( get_beforeStmts() );
     2841        ValueGuardPtr< std::list< Statement* > > oldAfterStmts ( get_afterStmts () );
     2842
    19992843        indexerScopedMutate( node->result     , *this );
    20002844        maybeMutate_impl   ( node->statements , *this );
     
    20182862
    20192863template< typename pass_type >
     2864void PassVisitor< pass_type >::visit( const UniqueExpr * node ) {
     2865        VISIT_START( node );
     2866
     2867        indexerScopedAccept( node->result, *this );
     2868        maybeAccept_impl   ( node->expr  , *this );
     2869
     2870        VISIT_END( node );
     2871}
     2872
     2873template< typename pass_type >
    20202874Expression * PassVisitor< pass_type >::mutate( UniqueExpr * node ) {
    20212875        MUTATE_START( node );
     
    20322886template< typename pass_type >
    20332887void PassVisitor< pass_type >::visit( UntypedInitExpr * node ) {
     2888        VISIT_START( node );
     2889
     2890        indexerScopedAccept( node->result, *this );
     2891        maybeAccept_impl   ( node->expr  , *this );
     2892        // not currently visiting initAlts, but this doesn't matter since this node is only used in the resolver.
     2893
     2894        VISIT_END( node );
     2895}
     2896
     2897template< typename pass_type >
     2898void PassVisitor< pass_type >::visit( const UntypedInitExpr * node ) {
    20342899        VISIT_START( node );
    20352900
     
    20672932
    20682933template< typename pass_type >
     2934void PassVisitor< pass_type >::visit( const InitExpr * node ) {
     2935        VISIT_START( node );
     2936
     2937        indexerScopedAccept( node->result, *this );
     2938        maybeAccept_impl   ( node->expr  , *this );
     2939        maybeAccept_impl   ( node->designation, *this );
     2940
     2941        VISIT_END( node );
     2942}
     2943
     2944template< typename pass_type >
    20692945Expression * PassVisitor< pass_type >::mutate( InitExpr * node ) {
    20702946        MUTATE_START( node );
     
    20852961
    20862962        indexerScopedAccept( node->result, *this );
    2087         maybeAccept_impl( node->expr, *this );
     2963        maybeAccept_impl   ( node->expr, *this );
     2964        // don't visit deleteStmt, because it is a pointer to somewhere else in the tree.
     2965
     2966        VISIT_END( node );
     2967}
     2968
     2969template< typename pass_type >
     2970void PassVisitor< pass_type >::visit( const DeletedExpr * node ) {
     2971        VISIT_START( node );
     2972
     2973        indexerScopedAccept( node->result, *this );
     2974        maybeAccept_impl   ( node->expr, *this );
    20882975        // don't visit deleteStmt, because it is a pointer to somewhere else in the tree.
    20892976
     
    21092996
    21102997        indexerScopedAccept( node->result, *this );
    2111         maybeAccept_impl( node->expr, *this );
     2998        maybeAccept_impl   ( node->expr, *this );
     2999
     3000        VISIT_END( node );
     3001}
     3002
     3003template< typename pass_type >
     3004void PassVisitor< pass_type >::visit( const DefaultArgExpr * node ) {
     3005        VISIT_START( node );
     3006
     3007        indexerScopedAccept( node->result, *this );
     3008        maybeAccept_impl   ( node->expr, *this );
    21123009
    21133010        VISIT_END( node );
     
    21343031        maybeAccept_impl( node->control, *this );
    21353032        for ( GenericExpr::Association & assoc : node->associations ) {
     3033                indexerScopedAccept( assoc.type, *this );
     3034                maybeAccept_impl( assoc.expr, *this );
     3035        }
     3036
     3037        VISIT_END( node );
     3038}
     3039
     3040template< typename pass_type >
     3041void PassVisitor< pass_type >::visit( const GenericExpr * node ) {
     3042        VISIT_START( node );
     3043
     3044        indexerScopedAccept( node->result, *this );
     3045        maybeAccept_impl( node->control, *this );
     3046        for ( const GenericExpr::Association & assoc : node->associations ) {
    21363047                indexerScopedAccept( assoc.type, *this );
    21373048                maybeAccept_impl( assoc.expr, *this );
     
    21683079
    21693080template< typename pass_type >
     3081void PassVisitor< pass_type >::visit( const VoidType * node ) {
     3082        VISIT_START( node );
     3083
     3084        maybeAccept_impl( node->forall, *this );
     3085
     3086        VISIT_END( node );
     3087}
     3088
     3089template< typename pass_type >
    21703090Type * PassVisitor< pass_type >::mutate( VoidType * node ) {
    21713091        MUTATE_START( node );
     
    21803100template< typename pass_type >
    21813101void PassVisitor< pass_type >::visit( BasicType * node ) {
     3102        VISIT_START( node );
     3103
     3104        maybeAccept_impl( node->forall, *this );
     3105
     3106        VISIT_END( node );
     3107}
     3108
     3109template< typename pass_type >
     3110void PassVisitor< pass_type >::visit( const BasicType * node ) {
    21823111        VISIT_START( node );
    21833112
     
    22103139
    22113140template< typename pass_type >
     3141void PassVisitor< pass_type >::visit( const PointerType * node ) {
     3142        VISIT_START( node );
     3143
     3144        maybeAccept_impl( node->forall, *this );
     3145        // xxx - should PointerType visit/mutate dimension?
     3146        maybeAccept_impl( node->base, *this );
     3147
     3148        VISIT_END( node );
     3149}
     3150
     3151template< typename pass_type >
    22123152Type * PassVisitor< pass_type >::mutate( PointerType * node ) {
    22133153        MUTATE_START( node );
     
    22343174
    22353175template< typename pass_type >
     3176void PassVisitor< pass_type >::visit( const ArrayType * node ) {
     3177        VISIT_START( node );
     3178
     3179        maybeAccept_impl( node->forall, *this );
     3180        maybeAccept_impl( node->dimension, *this );
     3181        maybeAccept_impl( node->base, *this );
     3182
     3183        VISIT_END( node );
     3184}
     3185
     3186template< typename pass_type >
    22363187Type * PassVisitor< pass_type >::mutate( ArrayType * node ) {
    22373188        MUTATE_START( node );
     
    22573208
    22583209template< typename pass_type >
     3210void PassVisitor< pass_type >::visit( const ReferenceType * node ) {
     3211        VISIT_START( node );
     3212
     3213        maybeAccept_impl( node->forall, *this );
     3214        maybeAccept_impl( node->base, *this );
     3215
     3216        VISIT_END( node );
     3217}
     3218
     3219template< typename pass_type >
    22593220Type * PassVisitor< pass_type >::mutate( ReferenceType * node ) {
    22603221        MUTATE_START( node );
     
    22803241
    22813242template< typename pass_type >
     3243void PassVisitor< pass_type >::visit( const QualifiedType * node ) {
     3244        VISIT_START( node );
     3245
     3246        maybeAccept_impl( node->forall, *this );
     3247        maybeAccept_impl( node->parent, *this );
     3248        maybeAccept_impl( node->child, *this );
     3249
     3250        VISIT_END( node );
     3251}
     3252
     3253template< typename pass_type >
    22823254Type * PassVisitor< pass_type >::mutate( QualifiedType * node ) {
    22833255        MUTATE_START( node );
     
    23043276
    23053277template< typename pass_type >
     3278void PassVisitor< pass_type >::visit( const FunctionType * node ) {
     3279        VISIT_START( node );
     3280
     3281        maybeAccept_impl( node->forall, *this );
     3282        maybeAccept_impl( node->returnVals, *this );
     3283        maybeAccept_impl( node->parameters, *this );
     3284
     3285        VISIT_END( node );
     3286}
     3287
     3288template< typename pass_type >
    23063289Type * PassVisitor< pass_type >::mutate( FunctionType * node ) {
    23073290        MUTATE_START( node );
     
    23323315
    23333316template< typename pass_type >
     3317void PassVisitor< pass_type >::visit( const StructInstType * node ) {
     3318        VISIT_START( node );
     3319
     3320        indexerAddStruct( node->name );
     3321
     3322        {
     3323                auto guard = makeFuncGuard( [this]() { indexerScopeEnter(); }, [this]() { indexerScopeLeave(); } );
     3324                maybeAccept_impl( node->forall    , *this );
     3325                maybeAccept_impl( node->parameters, *this );
     3326        }
     3327
     3328        VISIT_END( node );
     3329}
     3330
     3331template< typename pass_type >
    23343332Type * PassVisitor< pass_type >::mutate( StructInstType * node ) {
    23353333        MUTATE_START( node );
     
    23643362
    23653363template< typename pass_type >
     3364void PassVisitor< pass_type >::visit( const UnionInstType * node ) {
     3365        VISIT_START( node );
     3366
     3367        indexerAddStruct( node->name );
     3368
     3369        {
     3370                auto guard = makeFuncGuard( [this]() { indexerScopeEnter(); }, [this]() { indexerScopeLeave(); } );
     3371                maybeAccept_impl( node->forall    , *this );
     3372                maybeAccept_impl( node->parameters, *this );
     3373        }
     3374
     3375        VISIT_END( node );
     3376}
     3377
     3378template< typename pass_type >
    23663379Type * PassVisitor< pass_type >::mutate( UnionInstType * node ) {
    23673380        MUTATE_START( node );
     
    23913404
    23923405template< typename pass_type >
     3406void PassVisitor< pass_type >::visit( const EnumInstType * node ) {
     3407        VISIT_START( node );
     3408
     3409        maybeAccept_impl( node->forall, *this );
     3410        maybeAccept_impl( node->parameters, *this );
     3411
     3412        VISIT_END( node );
     3413}
     3414
     3415template< typename pass_type >
    23933416Type * PassVisitor< pass_type >::mutate( EnumInstType * node ) {
    23943417        MUTATE_START( node );
     
    24133436
    24143437template< typename pass_type >
     3438void PassVisitor< pass_type >::visit( const TraitInstType * node ) {
     3439        VISIT_START( node );
     3440
     3441        maybeAccept_impl( node->forall    , *this );
     3442        maybeAccept_impl( node->parameters, *this );
     3443
     3444        VISIT_END( node );
     3445}
     3446
     3447template< typename pass_type >
    24153448Type * PassVisitor< pass_type >::mutate( TraitInstType * node ) {
    24163449        MUTATE_START( node );
     
    24263459template< typename pass_type >
    24273460void PassVisitor< pass_type >::visit( TypeInstType * node ) {
     3461        VISIT_START( node );
     3462
     3463        maybeAccept_impl( node->forall    , *this );
     3464        maybeAccept_impl( node->parameters, *this );
     3465
     3466        VISIT_END( node );
     3467}
     3468
     3469template< typename pass_type >
     3470void PassVisitor< pass_type >::visit( const TypeInstType * node ) {
    24283471        VISIT_START( node );
    24293472
     
    24583501
    24593502template< typename pass_type >
     3503void PassVisitor< pass_type >::visit( const TupleType * node ) {
     3504        VISIT_START( node );
     3505
     3506        maybeAccept_impl( node->forall, *this );
     3507        maybeAccept_impl( node->types, *this );
     3508        maybeAccept_impl( node->members, *this );
     3509
     3510        VISIT_END( node );
     3511}
     3512
     3513template< typename pass_type >
    24603514Type * PassVisitor< pass_type >::mutate( TupleType * node ) {
    24613515        MUTATE_START( node );
     
    24723526template< typename pass_type >
    24733527void PassVisitor< pass_type >::visit( TypeofType * node ) {
     3528        VISIT_START( node );
     3529
     3530        assert( node->expr );
     3531        maybeAccept_impl( node->expr, *this );
     3532
     3533        VISIT_END( node );
     3534}
     3535
     3536template< typename pass_type >
     3537void PassVisitor< pass_type >::visit( const TypeofType * node ) {
    24743538        VISIT_START( node );
    24753539
     
    25083572
    25093573template< typename pass_type >
     3574void PassVisitor< pass_type >::visit( const AttrType * node ) {
     3575        VISIT_START( node );
     3576
     3577        if ( node->isType ) {
     3578                assert( node->type );
     3579                maybeAccept_impl( node->type, *this );
     3580        } else {
     3581                assert( node->expr );
     3582                maybeAccept_impl( node->expr, *this );
     3583        } // if
     3584
     3585        VISIT_END( node );
     3586}
     3587
     3588template< typename pass_type >
    25103589Type * PassVisitor< pass_type >::mutate( AttrType * node ) {
    25113590        MUTATE_START( node );
     
    25343613
    25353614template< typename pass_type >
     3615void PassVisitor< pass_type >::visit( const VarArgsType * node ) {
     3616        VISIT_START( node );
     3617
     3618        maybeAccept_impl( node->forall, *this );
     3619
     3620        VISIT_END( node );
     3621}
     3622
     3623template< typename pass_type >
    25363624Type * PassVisitor< pass_type >::mutate( VarArgsType * node ) {
    25373625        MUTATE_START( node );
     
    25543642
    25553643template< typename pass_type >
     3644void PassVisitor< pass_type >::visit( const ZeroType * node ) {
     3645        VISIT_START( node );
     3646
     3647        maybeAccept_impl( node->forall, *this );
     3648
     3649        VISIT_END( node );
     3650}
     3651
     3652template< typename pass_type >
    25563653Type * PassVisitor< pass_type >::mutate( ZeroType * node ) {
    25573654        MUTATE_START( node );
     
    25743671
    25753672template< typename pass_type >
     3673void PassVisitor< pass_type >::visit( const OneType * node ) {
     3674        VISIT_START( node );
     3675
     3676        maybeAccept_impl( node->forall, *this );
     3677
     3678        VISIT_END( node );
     3679}
     3680
     3681template< typename pass_type >
    25763682Type * PassVisitor< pass_type >::mutate( OneType * node ) {
    25773683        MUTATE_START( node );
     
    25943700
    25953701template< typename pass_type >
     3702void PassVisitor< pass_type >::visit( const GlobalScopeType * node ) {
     3703        VISIT_START( node );
     3704
     3705        maybeAccept_impl( node->forall, *this );
     3706
     3707        VISIT_END( node );
     3708}
     3709
     3710template< typename pass_type >
    25963711Type * PassVisitor< pass_type >::mutate( GlobalScopeType * node ) {
    25973712        MUTATE_START( node );
     
    26143729
    26153730template< typename pass_type >
     3731void PassVisitor< pass_type >::visit( const Designation * node ) {
     3732        VISIT_START( node );
     3733
     3734        maybeAccept_impl( node->designators, *this );
     3735
     3736        VISIT_END( node );
     3737}
     3738
     3739template< typename pass_type >
    26163740Designation * PassVisitor< pass_type >::mutate( Designation * node ) {
    26173741        MUTATE_START( node );
     
    26343758
    26353759template< typename pass_type >
     3760void PassVisitor< pass_type >::visit( const SingleInit * node ) {
     3761        VISIT_START( node );
     3762
     3763        visitExpression( node->value );
     3764
     3765        VISIT_END( node );
     3766}
     3767
     3768template< typename pass_type >
    26363769Initializer * PassVisitor< pass_type >::mutate( SingleInit * node ) {
    26373770        MUTATE_START( node );
     
    26463779template< typename pass_type >
    26473780void PassVisitor< pass_type >::visit( ListInit * node ) {
     3781        VISIT_START( node );
     3782
     3783        maybeAccept_impl( node->designations, *this );
     3784        maybeAccept_impl( node->initializers, *this );
     3785
     3786        VISIT_END( node );
     3787}
     3788
     3789template< typename pass_type >
     3790void PassVisitor< pass_type >::visit( const ListInit * node ) {
    26483791        VISIT_START( node );
    26493792
     
    26783821
    26793822template< typename pass_type >
     3823void PassVisitor< pass_type >::visit( const ConstructorInit * node ) {
     3824        VISIT_START( node );
     3825
     3826        maybeAccept_impl( node->ctor, *this );
     3827        maybeAccept_impl( node->dtor, *this );
     3828        maybeAccept_impl( node->init, *this );
     3829
     3830        VISIT_END( node );
     3831}
     3832
     3833template< typename pass_type >
    26803834Initializer * PassVisitor< pass_type >::mutate( ConstructorInit * node ) {
    26813835        MUTATE_START( node );
     
    26983852
    26993853template< typename pass_type >
     3854void PassVisitor< pass_type >::visit( const Constant * node ) {
     3855        VISIT_START( node );
     3856
     3857        VISIT_END( node );
     3858}
     3859
     3860template< typename pass_type >
    27003861Constant * PassVisitor< pass_type >::mutate( Constant * node  )  {
    27013862        MUTATE_START( node );
     
    27083869template< typename pass_type >
    27093870void PassVisitor< pass_type >::visit( Attribute * node ) {
     3871        VISIT_START( node );
     3872
     3873        maybeAccept_impl( node->parameters, *this );
     3874
     3875        VISIT_END( node );
     3876}
     3877
     3878template< typename pass_type >
     3879void PassVisitor< pass_type >::visit( const Attribute * node ) {
    27103880        VISIT_START( node );
    27113881
  • src/Common/PassVisitor.proto.h

    r1f1c102 rf53acdf8  
    118118static inline void postvisit_impl( __attribute__((unused)) pass_type& pass, __attribute__((unused)) node_type * node, __attribute__((unused)) long unused ) {}
    119119
     120template<typename pass_type, typename node_type>
     121static inline auto previsit_impl( pass_type& pass, const node_type * node, __attribute__((unused)) int unused ) -> decltype( pass.previsit( node ), void() ) {
     122        pass.previsit( node );
     123}
     124
     125template<typename pass_type, typename node_type>
     126static inline void previsit_impl( __attribute__((unused)) pass_type& pass, __attribute__((unused)) const node_type * node, __attribute__((unused)) long unused ) {}
     127
     128
     129template<typename pass_type, typename node_type>
     130static inline auto postvisit_impl( pass_type& pass, const node_type * node, __attribute__((unused)) int unused ) -> decltype( pass.postvisit( node ), void() ) {
     131        pass.postvisit( node );
     132}
     133
     134template<typename pass_type, typename node_type>
     135static inline void postvisit_impl( __attribute__((unused)) pass_type& pass, __attribute__((unused)) const node_type * node, __attribute__((unused)) long unused ) {}
     136
    120137//---------------------------------------------------------
    121138// Mutate
     
    200217        pass.indexer.func( arg );                                                                                                \
    201218}                                                                                                                              \
    202                                                                                                                                \
    203 template<typename pass_type>                                                                                                   \
    204 static inline void indexer_impl_##func ( pass_type &, long, type ) { }                                                          \
     219template<typename pass_type>                                                                                                   \
     220static inline void indexer_impl_##func ( pass_type &, long, type ) { }
    205221
    206222#define INDEXER_FUNC2( func, type1, type2 )                                                                                             \
     
    209225        pass.indexer.func( arg1, arg2 );                                                                                                \
    210226}                                                                                                                              \
    211                                                                                                                                \
    212227template<typename pass_type>                                                                                                   \
    213228static inline void indexer_impl_##func ( pass_type &, long, type1, type2 ) { }
    214229
    215230
    216 INDEXER_FUNC1( addId     , DeclarationWithType *       );
    217 INDEXER_FUNC1( addType   , NamedTypeDecl *             );
    218 INDEXER_FUNC1( addStruct , StructDecl *                );
    219 INDEXER_FUNC1( addEnum   , EnumDecl *                  );
    220 INDEXER_FUNC1( addUnion  , UnionDecl *                 );
    221 INDEXER_FUNC1( addTrait  , TraitDecl *                 );
    222 INDEXER_FUNC2( addWith   , std::list< Expression * > &, BaseSyntaxNode * );
     231INDEXER_FUNC1( addId     , const DeclarationWithType *       );
     232INDEXER_FUNC1( addType   , const NamedTypeDecl *             );
     233INDEXER_FUNC1( addStruct , const StructDecl *                );
     234INDEXER_FUNC1( addEnum   , const EnumDecl *                  );
     235INDEXER_FUNC1( addUnion  , const UnionDecl *                 );
     236INDEXER_FUNC1( addTrait  , const TraitDecl *                 );
     237INDEXER_FUNC2( addWith   , const std::list< Expression * > &, const Declaration * );
    223238
    224239#undef INDEXER_FUNC1
     
    226241
    227242template<typename pass_type>
    228 static inline auto indexer_impl_addStructFwd( pass_type & pass, int, StructDecl * decl ) -> decltype( pass.indexer.addStruct( decl ), void() ) {
     243static inline auto indexer_impl_addStructFwd( pass_type & pass, int, const StructDecl * decl ) -> decltype( pass.indexer.addStruct( decl ), void() ) {
    229244        StructDecl * fwd = new StructDecl( decl->name );
    230245        cloneAll( decl->parameters, fwd->parameters );
     
    233248
    234249template<typename pass_type>
    235 static inline auto indexer_impl_addStructFwd( pass_type &, long, StructDecl * ) {}
    236 
    237 template<typename pass_type>
    238 static inline auto indexer_impl_addUnionFwd( pass_type & pass, int, UnionDecl * decl ) -> decltype( pass.indexer.addUnion( decl ), void() ) {
     250static inline auto indexer_impl_addStructFwd( pass_type &, long, const StructDecl * ) {}
     251
     252template<typename pass_type>
     253static inline auto indexer_impl_addUnionFwd( pass_type & pass, int, const UnionDecl * decl ) -> decltype( pass.indexer.addUnion( decl ), void() ) {
    239254        UnionDecl * fwd = new UnionDecl( decl->name );
    240255        cloneAll( decl->parameters, fwd->parameters );
     
    243258
    244259template<typename pass_type>
    245 static inline auto indexer_impl_addUnionFwd( pass_type &, long, UnionDecl * ) {}
     260static inline auto indexer_impl_addUnionFwd( pass_type &, long, const UnionDecl * ) {}
    246261
    247262template<typename pass_type>
  • src/InitTweak/InitTweak.cc

    r1f1c102 rf53acdf8  
    318318        virtual ~ExpanderImpl() = default;
    319319        virtual std::vector< ast::ptr< ast::Expr > > next( IndexList & indices ) = 0;
    320         virtual ast::ptr< ast::Stmt > buildListInit( 
     320        virtual ast::ptr< ast::Stmt > buildListInit(
    321321                ast::UntypedExpr * callExpr, IndexList & indices ) = 0;
    322322};
     
    324324namespace {
    325325        template< typename Out >
    326         void buildCallExpr( 
    327                 ast::UntypedExpr * callExpr, const ast::Expr * index, const ast::Expr * dimension, 
     326        void buildCallExpr(
     327                ast::UntypedExpr * callExpr, const ast::Expr * index, const ast::Expr * dimension,
    328328                const ast::Init * init, Out & out
    329329        ) {
    330330                const CodeLocation & loc = init->location;
    331331
    332                 auto cond = new ast::UntypedExpr{ 
     332                auto cond = new ast::UntypedExpr{
    333333                        loc, new ast::NameExpr{ loc, "?<?" }, { index, dimension } };
    334                
     334
    335335                std::vector< ast::ptr< ast::Expr > > args = makeInitList( init );
    336336                splice( callExpr->args, args );
     
    338338                out.emplace_back( new ast::IfStmt{ loc, cond, new ast::ExprStmt{ loc, callExpr } } );
    339339
    340                 out.emplace_back( new ast::ExprStmt{ 
     340                out.emplace_back( new ast::ExprStmt{
    341341                        loc, new ast::UntypedExpr{ loc, new ast::NameExpr{ loc, "++?" }, { index } } } );
    342342        }
     
    344344        template< typename Out >
    345345        void build(
    346                 ast::UntypedExpr * callExpr, const InitExpander_new::IndexList & indices, 
     346                ast::UntypedExpr * callExpr, const InitExpander_new::IndexList & indices,
    347347                const ast::Init * init, Out & out
    348348        ) {
     
    371371
    372372                        static UniqueName targetLabel( "L__autogen__" );
    373                         ast::Label switchLabel{ 
     373                        ast::Label switchLabel{
    374374                                loc, targetLabel.newName(), { new ast::Attribute{ "unused" } } };
    375                        
     375
    376376                        std::vector< ast::ptr< ast::Stmt > > branches;
    377377                        for ( const ast::Init * init : *listInit ) {
     
    381381                                std::vector< ast::ptr< ast::Stmt > > stmts;
    382382                                build( callExpr, indices, init, stmts );
    383                                 stmts.emplace_back( 
     383                                stmts.emplace_back(
    384384                                        new ast::BranchStmt{ loc, ast::BranchStmt::Break, switchLabel } );
    385385                                branches.emplace_back( new ast::CaseStmt{ loc, condition, std::move( stmts ) } );
     
    398398                        return makeInitList( init );
    399399                }
    400                
    401                 ast::ptr< ast::Stmt > buildListInit( 
    402                         ast::UntypedExpr * callExpr, InitExpander_new::IndexList & indices 
     400
     401                ast::ptr< ast::Stmt > buildListInit(
     402                        ast::UntypedExpr * callExpr, InitExpander_new::IndexList & indices
    403403                ) override {
    404                         // If array came with an initializer list, initialize each element. We may have more 
    405                         // initializers than elements of the array; need to check at each index that we have 
    406                         // not exceeded size. We may have fewer initializers than elements in the array; need 
    407                         // to default-construct remaining elements. To accomplish this, generate switch 
     404                        // If array came with an initializer list, initialize each element. We may have more
     405                        // initializers than elements of the array; need to check at each index that we have
     406                        // not exceeded size. We may have fewer initializers than elements in the array; need
     407                        // to default-construct remaining elements. To accomplish this, generate switch
    408408                        // statement consuming all of expander's elements
    409409
     
    427427                ExprImpl_new( const ast::Expr * a ) : arg( a ) {}
    428428
    429                 std::vector< ast::ptr< ast::Expr > > next( 
    430                         InitExpander_new::IndexList & indices 
     429                std::vector< ast::ptr< ast::Expr > > next(
     430                        InitExpander_new::IndexList & indices
    431431                ) override {
    432432                        if ( ! arg ) return {};
     
    437437                                // go through indices and layer on subscript exprs ?[?]
    438438                                ++it;
    439                                 expr = new ast::UntypedExpr{ 
     439                                expr = new ast::UntypedExpr{
    440440                                        loc, new ast::NameExpr{ loc, "?[?]" }, { expr, *it } };
    441441                        }
    442442                        return { expr };
    443443                }
    444                
    445                 ast::ptr< ast::Stmt > buildListInit( 
    446                         ast::UntypedExpr *, InitExpander_new::IndexList & 
    447                 ) override { 
     444
     445                ast::ptr< ast::Stmt > buildListInit(
     446                        ast::UntypedExpr *, InitExpander_new::IndexList &
     447                ) override {
    448448                        return {};
    449449                }
     
    464464}
    465465
    466 /// builds statement which has the same semantics as a C-style list initializer (for array 
     466/// builds statement which has the same semantics as a C-style list initializer (for array
    467467/// initializers) using callExpr as the base expression to perform initialization
    468468ast::ptr< ast::Stmt > InitExpander_new::buildListInit( ast::UntypedExpr * callExpr ) {
     
    668668
    669669                const ast::DeclWithType * func = getCalledFunction( appExpr->func );
    670                 assertf( func, 
     670                assertf( func,
    671671                        "getCalledFunction returned nullptr: %s", toString( appExpr->func ).c_str() );
    672                
    673                 // check for Intrinsic only -- don't want to remove all overridable ctor/dtor because 
    674                 // autogenerated ctor/dtor will call all member dtors, and some members may have a 
     672
     673                // check for Intrinsic only -- don't want to remove all overridable ctor/dtor because
     674                // autogenerated ctor/dtor will call all member dtors, and some members may have a
    675675                // user-defined dtor
    676676                return func->linkage == ast::Linkage::Intrinsic ? appExpr : nullptr;
     
    707707                return allofCtorDtor( stmt, []( const ast::Expr * callExpr ){
    708708                        if ( const ast::ApplicationExpr * appExpr = isIntrinsicCallExpr( callExpr ) ) {
    709                                 const ast::FunctionType * funcType = 
     709                                const ast::FunctionType * funcType =
    710710                                        GenPoly::getFunctionType( appExpr->func->result );
    711711                                assert( funcType );
     
    997997        bool isCtorDtorAssign( const std::string & str ) { return isCtorDtor( str ) || isAssignment( str ); }
    998998
    999         FunctionDecl * isCopyFunction( Declaration * decl, const std::string & fname ) {
    1000                 FunctionDecl * function = dynamic_cast< FunctionDecl * >( decl );
     999        const FunctionDecl * isCopyFunction( const Declaration * decl, const std::string & fname ) {
     1000                const FunctionDecl * function = dynamic_cast< const FunctionDecl * >( decl );
    10011001                if ( ! function ) return nullptr;
    10021002                if ( function->name != fname ) return nullptr;
     
    10221022                if ( ! t1 ) return false;
    10231023                const ast::Type * t2 = ftype->params.back()->get_type();
    1024                
     1024
    10251025                return ResolvExpr::typesCompatibleIgnoreQualifiers( t1, t2, ast::SymbolTable{} );
    10261026        }
    10271027
    1028         FunctionDecl * isAssignment( Declaration * decl ) {
     1028        const FunctionDecl * isAssignment( const Declaration * decl ) {
    10291029                return isCopyFunction( decl, "?=?" );
    10301030        }
    1031         FunctionDecl * isDestructor( Declaration * decl ) {
    1032                 if ( isDestructor( decl->get_name() ) ) {
    1033                         return dynamic_cast< FunctionDecl * >( decl );
     1031        const FunctionDecl * isDestructor( const Declaration * decl ) {
     1032                if ( isDestructor( decl->name ) ) {
     1033                        return dynamic_cast< const FunctionDecl * >( decl );
    10341034                }
    10351035                return nullptr;
    10361036        }
    1037         FunctionDecl * isDefaultConstructor( Declaration * decl ) {
     1037        const FunctionDecl * isDefaultConstructor( const Declaration * decl ) {
    10381038                if ( isConstructor( decl->name ) ) {
    1039                         if ( FunctionDecl * func = dynamic_cast< FunctionDecl * >( decl ) ) {
     1039                        if ( const FunctionDecl * func = dynamic_cast< const FunctionDecl * >( decl ) ) {
    10401040                                if ( func->type->parameters.size() == 1 ) {
    10411041                                        return func;
     
    10451045                return nullptr;
    10461046        }
    1047         FunctionDecl * isCopyConstructor( Declaration * decl ) {
     1047        const FunctionDecl * isCopyConstructor( const Declaration * decl ) {
    10481048                return isCopyFunction( decl, "?{}" );
    10491049        }
  • src/InitTweak/InitTweak.h

    r1f1c102 rf53acdf8  
    2626// helper functions for initialization
    2727namespace InitTweak {
    28         FunctionDecl * isAssignment( Declaration * decl );
    29         FunctionDecl * isDestructor( Declaration * decl );
    30         FunctionDecl * isDefaultConstructor( Declaration * decl );
    31         FunctionDecl * isCopyConstructor( Declaration * decl );
    32         FunctionDecl * isCopyFunction( Declaration * decl, const std::string & fname );
     28        const FunctionDecl * isAssignment( const Declaration * decl );
     29        const FunctionDecl * isDestructor( const Declaration * decl );
     30        const FunctionDecl * isDefaultConstructor( const Declaration * decl );
     31        const FunctionDecl * isCopyConstructor( const Declaration * decl );
     32        const FunctionDecl * isCopyFunction( const Declaration * decl, const std::string & fname );
    3333        bool isCopyFunction( const ast::FunctionDecl * decl );
    3434
     
    153153                InitExpander_new & operator++ ();
    154154
    155                 /// builds statement which has the same semantics as a C-style list initializer (for array 
    156                 /// initializers) using callExpr as the base expression to perform initialization. 
     155                /// builds statement which has the same semantics as a C-style list initializer (for array
     156                /// initializers) using callExpr as the base expression to perform initialization.
    157157                /// Mutates callExpr
    158158                ast::ptr< ast::Stmt > buildListInit( ast::UntypedExpr * callExpr );
  • src/Parser/LinkageSpec.h

    r1f1c102 rf53acdf8  
    99// Author           : Rodolfo G. Esteves
    1010// Created On       : Sat May 16 13:24:28 2015
    11 // Last Modified By : Andrew Beach
    12 // Last Modified On : Thr Spt 13 15:59:00 2018
    13 // Update Count     : 17
     11// Last Modified By : Peter A. Buhr
     12// Last Modified On : Wed Jul 10 16:02:34 2019
     13// Update Count     : 18
    1414//
    1515
     
    3535                constexpr Spec( unsigned int val ) : val( val ) {}
    3636                constexpr Spec( Spec const & other ) : val( other.val ) {}
     37                constexpr Spec & operator=( const Spec & ) = default;
    3738                // Operators may go here.
    3839                // Supports == and !=
  • src/Parser/ParseNode.h

    r1f1c102 rf53acdf8  
    437437WaitForStmt * build_waitfor_timeout( ExpressionNode * timeout, StatementNode * stmt, ExpressionNode * when );
    438438WaitForStmt * build_waitfor_timeout( ExpressionNode * timeout, StatementNode * stmt, ExpressionNode * when, StatementNode * else_stmt, ExpressionNode * else_when );
    439 WithStmt * build_with( ExpressionNode * exprs, StatementNode * stmt );
     439Statement * build_with( ExpressionNode * exprs, StatementNode * stmt );
    440440
    441441//##############################################################################
  • src/Parser/StatementNode.cc

    r1f1c102 rf53acdf8  
    317317} // build_waitfor_timeout
    318318
    319 WithStmt * build_with( ExpressionNode * exprs, StatementNode * stmt ) {
     319Statement * build_with( ExpressionNode * exprs, StatementNode * stmt ) {
    320320        std::list< Expression * > e;
    321321        buildMoveList( exprs, e );
    322322        Statement * s = maybeMoveBuild<Statement>( stmt );
    323         return new WithStmt( e, s );
     323        return new DeclStmt( new WithStmt( e, s ) );
    324324} // build_with
    325325
  • src/Parser/parser.yy

    r1f1c102 rf53acdf8  
    1010// Created On       : Sat Sep  1 20:22:55 2001
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Tue May 28 17:06:37 2019
    13 // Update Count     : 4354
     12// Last Modified On : Sun Jul 14 07:54:30 2019
     13// Update Count     : 4355
    1414//
    1515
     
    678678
    679679argument_expression_list:
    680         argument_expression
     680        // empty
     681                { $$ = nullptr; }
     682        | argument_expression
    681683        | argument_expression_list ',' argument_expression
    682684                { $$ = (ExpressionNode *)( $1->set_last( $3 )); }
     
    684686
    685687argument_expression:
    686         // empty
    687                 { $$ = nullptr; }
    688         | '@'                                                                                           // CFA, default parameter
     688        '@'                                                                                                     // CFA, default parameter
    689689                { SemanticError( yylloc, "Default parameter for argument is currently unimplemented." ); $$ = nullptr; }
    690690                // { $$ = new ExpressionNode( build_constantInteger( *new string( "2" ) ) ); }
  • src/ResolvExpr/AdjustExprType.cc

    r1f1c102 rf53acdf8  
    4747                void premutate( OneType * ) { visit_children = false; }
    4848
    49                 Type * postmutate( ArrayType *arrayType );
    50                 Type * postmutate( FunctionType *functionType );
    51                 Type * postmutate( TypeInstType *aggregateUseType );
     49                Type * postmutate( ArrayType * arrayType );
     50                Type * postmutate( FunctionType * functionType );
     51                Type * postmutate( TypeInstType * aggregateUseType );
    5252
    5353                private:
     
    6161
    6262        Type * AdjustExprType_old::postmutate( ArrayType * arrayType ) {
    63                 PointerType *pointerType = new PointerType{ arrayType->get_qualifiers(), arrayType->base };
     63                PointerType * pointerType = new PointerType{ arrayType->get_qualifiers(), arrayType->base };
    6464                arrayType->base = nullptr;
    6565                delete arrayType;
     
    7272
    7373        Type * AdjustExprType_old::postmutate( TypeInstType * typeInst ) {
    74                 if ( const EqvClass* eqvClass = env.lookup( typeInst->get_name() ) ) {
     74                if ( const EqvClass * eqvClass = env.lookup( typeInst->get_name() ) ) {
    7575                        if ( eqvClass->data.kind == TypeDecl::Ftype ) {
    7676                                return new PointerType{ Type::Qualifiers(), typeInst };
    7777                        }
    78                 } else if ( NamedTypeDecl *ntDecl = indexer.lookupType( typeInst->get_name() ) ) {
    79                         if ( TypeDecl *tyDecl = dynamic_cast< TypeDecl* >( ntDecl ) ) {
     78                } else if ( const NamedTypeDecl * ntDecl = indexer.lookupType( typeInst->get_name() ) ) {
     79                        if ( const TypeDecl * tyDecl = dynamic_cast< const TypeDecl * >( ntDecl ) ) {
    8080                                if ( tyDecl->get_kind() == TypeDecl::Ftype ) {
    8181                                        return new PointerType{ Type::Qualifiers(), typeInst };
     
    8989void adjustExprType( Type *&type, const TypeEnvironment &env, const SymTab::Indexer &indexer ) {
    9090        PassVisitor<AdjustExprType_old> adjuster( env, indexer );
    91         Type *newType = type->acceptMutator( adjuster );
     91        Type * newType = type->acceptMutator( adjuster );
    9292        type = newType;
    9393}
     
    149149} // anonymous namespace
    150150
    151 const ast::Type * adjustExprType( 
    152         const ast::Type * type, const ast::TypeEnvironment & env, const ast::SymbolTable & symtab 
     151const ast::Type * adjustExprType(
     152        const ast::Type * type, const ast::TypeEnvironment & env, const ast::SymbolTable & symtab
    153153) {
    154154        ast::Pass<AdjustExprType_new> adjuster{ env, symtab };
  • src/ResolvExpr/AlternativeFinder.cc

    r1f1c102 rf53acdf8  
    336336                }
    337337
    338                 if ( StructInstType *structInst = dynamic_cast< StructInstType* >( aggrExpr->result ) ) {
     338                if ( StructInstType * structInst = dynamic_cast< StructInstType* >( aggrExpr->result ) ) {
    339339                        addAggMembers( structInst, aggrExpr.get(), alt, alt.cost+Cost::safe, "" );
    340                 } else if ( UnionInstType *unionInst = dynamic_cast< UnionInstType* >( aggrExpr->result ) ) {
     340                } else if ( UnionInstType * unionInst = dynamic_cast< UnionInstType* >( aggrExpr->result ) ) {
    341341                        addAggMembers( unionInst, aggrExpr.get(), alt, alt.cost+Cost::safe, "" );
    342342                } // if
     
    344344
    345345        template< typename StructOrUnionType >
    346         void AlternativeFinder::Finder::addAggMembers( StructOrUnionType *aggInst, Expression *expr, const Alternative& alt, const Cost &newCost, const std::string & name ) {
     346        void AlternativeFinder::Finder::addAggMembers( StructOrUnionType * aggInst, Expression * expr, const Alternative& alt, const Cost &newCost, const std::string & name ) {
    347347                std::list< Declaration* > members;
    348348                aggInst->lookup( name, members );
    349349
    350350                for ( Declaration * decl : members ) {
    351                         if ( DeclarationWithType *dwt = dynamic_cast< DeclarationWithType* >( decl ) ) {
     351                        if ( DeclarationWithType * dwt = dynamic_cast< DeclarationWithType* >( decl ) ) {
    352352                                // addAnonAlternatives uses vector::push_back, which invalidates references to existing elements, so
    353353                                // can't construct in place and use vector::back
     
    362362        }
    363363
    364         void AlternativeFinder::Finder::addTupleMembers( TupleType *tupleType, Expression *expr,                        const Alternative &alt, const Cost &newCost, Expression *member ) {
     364        void AlternativeFinder::Finder::addTupleMembers( TupleType * tupleType, Expression * expr, const Alternative &alt, const Cost &newCost, Expression * member ) {
    365365                if ( ConstantExpr * constantExpr = dynamic_cast< ConstantExpr * >( member ) ) {
    366366                        // get the value of the constant expression as an int, must be between 0 and the length of the tuple type to have meaning
     
    368368                        std::string tmp;
    369369                        if ( val >= 0 && (unsigned long long)val < tupleType->size() ) {
    370                                 alternatives.push_back( Alternative{ 
     370                                alternatives.push_back( Alternative{
    371371                                        alt, new TupleIndexExpr( expr->clone(), val ), newCost } );
    372372                        } // if
     
    374374        }
    375375
    376         void AlternativeFinder::Finder::postvisit( ApplicationExpr *applicationExpr ) {
     376        void AlternativeFinder::Finder::postvisit( ApplicationExpr * applicationExpr ) {
    377377                alternatives.push_back( Alternative{ applicationExpr->clone(), env } );
    378378        }
     
    475475                }
    476476
    477                 // specialization cost of return types can't be accounted for directly, it disables 
     477                // specialization cost of return types can't be accounted for directly, it disables
    478478                // otherwise-identical calls, like this example based on auto-newline in the I/O lib:
    479479                //
     
    12261226                                // count one safe conversion for each value that is thrown away
    12271227                                thisCost.incSafe( discardedValues );
    1228                                 Alternative newAlt{ 
    1229                                         restructureCast( alt.expr->clone(), toType, castExpr->isGenerated ), 
     1228                                Alternative newAlt{
     1229                                        restructureCast( alt.expr->clone(), toType, castExpr->isGenerated ),
    12301230                                        alt.env, openVars, needAssertions, alt.cost, alt.cost + thisCost };
    12311231                                inferParameters( newAlt, back_inserter( candidates ) );
     
    13281328                if ( sizeofExpr->get_isType() ) {
    13291329                        Type * newType = sizeofExpr->get_type()->clone();
    1330                         alternatives.push_back( Alternative{ 
     1330                        alternatives.push_back( Alternative{
    13311331                                new SizeofExpr{ resolveTypeof( newType, indexer ) }, env } );
    13321332                } else {
     
    13431343                        Alternative &choice = winners.front();
    13441344                        referenceToRvalueConversion( choice.expr, choice.cost );
    1345                         alternatives.push_back( Alternative{ 
     1345                        alternatives.push_back( Alternative{
    13461346                                choice, new SizeofExpr( choice.expr->clone() ), Cost::zero } );
    13471347                } // if
     
    13511351                if ( alignofExpr->get_isType() ) {
    13521352                        Type * newType = alignofExpr->get_type()->clone();
    1353                         alternatives.push_back( Alternative{ 
     1353                        alternatives.push_back( Alternative{
    13541354                                new AlignofExpr{ resolveTypeof( newType, indexer ) }, env } );
    13551355                } else {
     
    13661366                        Alternative &choice = winners.front();
    13671367                        referenceToRvalueConversion( choice.expr, choice.cost );
    1368                         alternatives.push_back( Alternative{ 
     1368                        alternatives.push_back( Alternative{
    13691369                                choice, new AlignofExpr{ choice.expr->clone() }, Cost::zero } );
    13701370                } // if
     
    13771377                for ( std::list< Declaration* >::const_iterator i = members.begin(); i != members.end(); ++i ) {
    13781378                        if ( DeclarationWithType *dwt = dynamic_cast< DeclarationWithType* >( *i ) ) {
    1379                                 alternatives.push_back( Alternative{ 
     1379                                alternatives.push_back( Alternative{
    13801380                                        new OffsetofExpr{ aggInst->clone(), dwt }, env } );
    13811381                                renameTypes( alternatives.back().expr );
     
    14051405
    14061406        namespace {
    1407                 void resolveAttr( SymTab::Indexer::IdData data, FunctionType *function, Type *argType, const TypeEnvironment &env, AlternativeFinder & finder ) {
     1407                void resolveAttr( SymTab::Indexer::IdData data, const FunctionType * function, Type * argType, const TypeEnvironment &env, AlternativeFinder & finder ) {
    14081408                        // assume no polymorphism
    14091409                        // assume no implicit conversions
    1410                         assert( function->get_parameters().size() == 1 );
     1410                        assert( function->parameters.size() == 1 );
    14111411                        PRINT(
    14121412                                std::cerr << "resolvAttr: funcDecl is ";
     
    14181418                        const SymTab::Indexer & indexer = finder.get_indexer();
    14191419                        AltList & alternatives = finder.get_alternatives();
    1420                         if ( typesCompatibleIgnoreQualifiers( argType, function->get_parameters().front()->get_type(), indexer, env ) ) {
     1420                        if ( typesCompatibleIgnoreQualifiers( argType, function->parameters.front()->get_type(), indexer, env ) ) {
    14211421                                Cost cost = Cost::zero;
    14221422                                Expression * newExpr = data.combine( cost );
    1423                                 alternatives.push_back( Alternative{ 
    1424                                         new AttrExpr{ newExpr, argType->clone() }, env, OpenVarSet{}, 
     1423                                alternatives.push_back( Alternative{
     1424                                        new AttrExpr{ newExpr, argType->clone() }, env, OpenVarSet{},
    14251425                                        AssertionList{}, Cost::zero, cost } );
    14261426                                for ( DeclarationWithType * retVal : function->returnVals ) {
     
    14311431        }
    14321432
    1433         void AlternativeFinder::Finder::postvisit( AttrExpr *attrExpr ) {
     1433        void AlternativeFinder::Finder::postvisit( AttrExpr * attrExpr ) {
    14341434                // assume no 'pointer-to-attribute'
    1435                 NameExpr *nameExpr = dynamic_cast< NameExpr* >( attrExpr->get_attr() );
     1435                NameExpr * nameExpr = dynamic_cast< NameExpr* >( attrExpr->get_attr() );
    14361436                assert( nameExpr );
    14371437                std::list< SymTab::Indexer::IdData > attrList;
     
    14391439                if ( attrExpr->get_isType() || attrExpr->get_expr() ) {
    14401440                        for ( auto & data : attrList ) {
    1441                                 DeclarationWithType * id = data.id;
     1441                                const DeclarationWithType * id = data.id;
    14421442                                // check if the type is function
    1443                                 if ( FunctionType *function = dynamic_cast< FunctionType* >( id->get_type() ) ) {
     1443                                if ( const FunctionType * function = dynamic_cast< const FunctionType * >( id->get_type() ) ) {
    14441444                                        // assume exactly one parameter
    1445                                         if ( function->get_parameters().size() == 1 ) {
     1445                                        if ( function->parameters.size() == 1 ) {
    14461446                                                if ( attrExpr->get_isType() ) {
    14471447                                                        resolveAttr( data, function, attrExpr->get_type(), env, altFinder);
     
    14621462                                Cost cost = Cost::zero;
    14631463                                Expression * newExpr = data.combine( cost );
    1464                                 alternatives.push_back( Alternative{ 
     1464                                alternatives.push_back( Alternative{
    14651465                                        newExpr, env, OpenVarSet{}, AssertionList{}, Cost::zero, cost } );
    14661466                                renameTypes( alternatives.back().expr );
     
    14691469        }
    14701470
    1471         void AlternativeFinder::Finder::postvisit( LogicalExpr *logicalExpr ) {
     1471        void AlternativeFinder::Finder::postvisit( LogicalExpr * logicalExpr ) {
    14721472                AlternativeFinder firstFinder( indexer, env );
    14731473                firstFinder.findWithAdjustment( logicalExpr->get_arg1() );
     
    14861486                                cloneAll( second.need, need );
    14871487
    1488                                 LogicalExpr *newExpr = new LogicalExpr{ 
     1488                                LogicalExpr *newExpr = new LogicalExpr{
    14891489                                        first.expr->clone(), second.expr->clone(), logicalExpr->get_isAnd() };
    1490                                 alternatives.push_back( Alternative{ 
    1491                                         newExpr, std::move(compositeEnv), std::move(openVars), 
     1490                                alternatives.push_back( Alternative{
     1491                                        newExpr, std::move(compositeEnv), std::move(openVars),
    14921492                                        AssertionList( need.begin(), need.end() ), first.cost + second.cost } );
    14931493                        }
     
    15221522                                        cloneAll( third.need, need );
    15231523                                        AssertionSet have;
    1524                                        
     1524
    15251525                                        // unify true and false types, then infer parameters to produce new alternatives
    15261526                                        Type* commonType = nullptr;
    1527                                         if ( unify( second.expr->result, third.expr->result, compositeEnv, 
     1527                                        if ( unify( second.expr->result, third.expr->result, compositeEnv,
    15281528                                                        need, have, openVars, indexer, commonType ) ) {
    1529                                                 ConditionalExpr *newExpr = new ConditionalExpr{ 
     1529                                                ConditionalExpr *newExpr = new ConditionalExpr{
    15301530                                                        first.expr->clone(), second.expr->clone(), third.expr->clone() };
    15311531                                                newExpr->result = commonType ? commonType : second.expr->result->clone();
    15321532                                                // convert both options to the conditional result type
    15331533                                                Cost cost = first.cost + second.cost + third.cost;
    1534                                                 cost += computeExpressionConversionCost( 
     1534                                                cost += computeExpressionConversionCost(
    15351535                                                        newExpr->arg2, newExpr->result, indexer, compositeEnv );
    1536                                                 cost += computeExpressionConversionCost( 
     1536                                                cost += computeExpressionConversionCost(
    15371537                                                        newExpr->arg3, newExpr->result, indexer, compositeEnv );
    15381538                                                // output alternative
    1539                                                 Alternative newAlt{ 
    1540                                                         newExpr, std::move(compositeEnv), std::move(openVars), 
     1539                                                Alternative newAlt{
     1540                                                        newExpr, std::move(compositeEnv), std::move(openVars),
    15411541                                                        AssertionList( need.begin(), need.end() ), cost };
    15421542                                                inferParameters( newAlt, back_inserter( alternatives ) );
     
    15531553                secondFinder.findWithAdjustment( commaExpr->get_arg2() );
    15541554                for ( const Alternative & alt : secondFinder.alternatives ) {
    1555                         alternatives.push_back( Alternative{ 
     1555                        alternatives.push_back( Alternative{
    15561556                                alt, new CommaExpr{ newFirstArg->clone(), alt.expr->clone() }, alt.cost } );
    15571557                } // for
     
    15791579
    15801580                                Type* commonType = nullptr;
    1581                                 if ( unify( first.expr->result, second.expr->result, compositeEnv, need, have, 
     1581                                if ( unify( first.expr->result, second.expr->result, compositeEnv, need, have,
    15821582                                                openVars, indexer, commonType ) ) {
    1583                                         RangeExpr * newExpr = 
     1583                                        RangeExpr * newExpr =
    15841584                                                new RangeExpr{ first.expr->clone(), second.expr->clone() };
    15851585                                        newExpr->result = commonType ? commonType : first.expr->result->clone();
    1586                                         Alternative newAlt{ 
    1587                                                 newExpr, std::move(compositeEnv), std::move(openVars), 
     1586                                        Alternative newAlt{
     1587                                                newExpr, std::move(compositeEnv), std::move(openVars),
    15881588                                                AssertionList( need.begin(), need.end() ), first.cost + second.cost };
    15891589                                        inferParameters( newAlt, back_inserter( alternatives ) );
     
    16121612                                cloneAll( alt.need, need );
    16131613                        }
    1614                        
    1615                         alternatives.push_back( Alternative{ 
    1616                                 new TupleExpr{ exprs }, std::move(compositeEnv), std::move(openVars), 
     1614
     1615                        alternatives.push_back( Alternative{
     1616                                new TupleExpr{ exprs }, std::move(compositeEnv), std::move(openVars),
    16171617                                AssertionList( need.begin(), need.end() ), sumCost( alts ) } );
    16181618                } // for
     
    16331633                finder.findWithoutPrune( ctorExpr->get_callExpr() );
    16341634                for ( Alternative & alt : finder.alternatives ) {
    1635                         alternatives.push_back( Alternative{ 
     1635                        alternatives.push_back( Alternative{
    16361636                                alt, new ConstructorExpr( alt.expr->clone() ), alt.cost } );
    16371637                }
     
    16851685                                cloneAll( alt.need, need );
    16861686                                AssertionSet have;
    1687                                 OpenVarSet openVars( alt.openVars ); 
    1688                                 // xxx - find things in env that don't have a "representative type" and claim 
     1687                                OpenVarSet openVars( alt.openVars );
     1688                                // xxx - find things in env that don't have a "representative type" and claim
    16891689                                // those are open vars?
    16901690                                PRINT(
    16911691                                        std::cerr << "  @ " << toType << " " << initAlt.designation << std::endl;
    16921692                                )
    1693                                 // It's possible that a cast can throw away some values in a multiply-valued 
    1694                                 // expression. (An example is a cast-to-void, which casts from one value to 
    1695                                 // zero.)  Figure out the prefix of the subexpression results that are cast 
    1696                                 // directly.  The candidate is invalid if it has fewer results than there are 
     1693                                // It's possible that a cast can throw away some values in a multiply-valued
     1694                                // expression. (An example is a cast-to-void, which casts from one value to
     1695                                // zero.)  Figure out the prefix of the subexpression results that are cast
     1696                                // directly.  The candidate is invalid if it has fewer results than there are
    16971697                                // types to cast to.
    16981698                                int discardedValues = alt.expr->result->size() - toType->size();
    16991699                                if ( discardedValues < 0 ) continue;
    1700                                 // xxx - may need to go into tuple types and extract relevant types and use 
    1701                                 // unifyList. Note that currently, this does not allow casting a tuple to an 
     1700                                // xxx - may need to go into tuple types and extract relevant types and use
     1701                                // unifyList. Note that currently, this does not allow casting a tuple to an
    17021702                                // atomic type (e.g. (int)([1, 2, 3]))
    1703                                
     1703
    17041704                                // unification run for side-effects
    17051705                                unify( toType, alt.expr->result, newEnv, need, have, openVars, indexer );
     
    17101710                                        // count one safe conversion for each value that is thrown away
    17111711                                        thisCost.incSafe( discardedValues );
    1712                                         Alternative newAlt{ 
    1713                                                 new InitExpr{ 
    1714                                                         restructureCast( alt.expr->clone(), toType, true ), initAlt.designation->clone() }, 
    1715                                                 std::move(newEnv), std::move(openVars), 
     1712                                        Alternative newAlt{
     1713                                                new InitExpr{
     1714                                                        restructureCast( alt.expr->clone(), toType, true ), initAlt.designation->clone() },
     1715                                                std::move(newEnv), std::move(openVars),
    17161716                                                AssertionList( need.begin(), need.end() ), alt.cost, thisCost };
    17171717                                        inferParameters( newAlt, back_inserter( candidates ) );
  • src/ResolvExpr/CastCost.cc

    r1f1c102 rf53acdf8  
    3737        struct CastCost_old : public ConversionCost {
    3838          public:
    39                 CastCost_old( Type *dest, const SymTab::Indexer &indexer, const TypeEnvironment &env, CostFunction costFunc );
     39                CastCost_old( const Type * dest, const SymTab::Indexer &indexer, const TypeEnvironment &env, CostFunction costFunc );
    4040
    4141                using ConversionCost::previsit;
    4242                using ConversionCost::postvisit;
    43                 void postvisit( BasicType * basicType );
    44                 void postvisit( PointerType * pointerType );
     43                void postvisit( const BasicType * basicType );
     44                void postvisit( const PointerType * pointerType );
    4545        };
    4646
    47         Cost castCost( Type *src, Type *dest, const SymTab::Indexer &indexer, const TypeEnvironment &env ) {
    48                 if ( TypeInstType *destAsTypeInst = dynamic_cast< TypeInstType* >( dest ) ) {
    49                         if ( const EqvClass* eqvClass = env.lookup( destAsTypeInst->get_name() ) ) {
     47        Cost castCost( const Type * src, const Type * dest, const SymTab::Indexer &indexer, const TypeEnvironment &env ) {
     48                if ( const TypeInstType * destAsTypeInst = dynamic_cast< const TypeInstType * >( dest ) ) {
     49                        if ( const EqvClass * eqvClass = env.lookup( destAsTypeInst->name ) ) {
    5050                                if ( eqvClass->type ) {
    5151                                        return castCost( src, eqvClass->type, indexer, env );
     
    5353                                        return Cost::infinity;
    5454                                }
    55                         } else if ( NamedTypeDecl *namedType = indexer.lookupType( destAsTypeInst->get_name() ) ) {
     55                        } else if ( const NamedTypeDecl * namedType = indexer.lookupType( destAsTypeInst->name ) ) {
    5656                                // all typedefs should be gone by this point
    57                                 TypeDecl *type = strict_dynamic_cast< TypeDecl* >( namedType );
     57                                const TypeDecl * type = strict_dynamic_cast< const TypeDecl * >( namedType );
    5858                                if ( type->base ) {
    5959                                        return castCost( src, type->base, indexer, env ) + Cost::safe;
     
    7474                        PRINT( std::cerr << "compatible!" << std::endl; )
    7575                        return Cost::zero;
    76                 } else if ( dynamic_cast< VoidType* >( dest ) ) {
     76                } else if ( dynamic_cast< const VoidType * >( dest ) ) {
    7777                        return Cost::safe;
    78                 } else if ( ReferenceType * refType = dynamic_cast< ReferenceType * > ( dest ) ) {
     78                } else if ( const ReferenceType * refType = dynamic_cast< const ReferenceType * > ( dest ) ) {
    7979                        PRINT( std::cerr << "conversionCost: dest is reference" << std::endl; )
    80                         return convertToReferenceCost( src, refType, indexer, env, [](Type * t1, Type * t2, const SymTab::Indexer & indexer, const TypeEnvironment & env ) {
     80                        return convertToReferenceCost( src, refType, indexer, env, [](const Type * t1, const Type * t2, const SymTab::Indexer & indexer, const TypeEnvironment & env ) {
    8181                                return ptrsCastable( t1, t2, env, indexer );
    8282                        });
    8383                } else {
    84                         PassVisitor<CastCost_old> converter( 
    85                                 dest, indexer, env, 
    86                                 (Cost (*)( Type *, Type *, const SymTab::Indexer &, const TypeEnvironment & ))
     84                        PassVisitor<CastCost_old> converter(
     85                                dest, indexer, env,
     86                                (Cost (*)( const Type *, const Type *, const SymTab::Indexer &, const TypeEnvironment & ))
    8787                                        castCost );
    8888                        src->accept( converter );
     
    9696        }
    9797
    98         CastCost_old::CastCost_old( Type *dest, const SymTab::Indexer &indexer, const TypeEnvironment &env, CostFunction costFunc )
     98        CastCost_old::CastCost_old( const Type * dest, const SymTab::Indexer &indexer, const TypeEnvironment &env, CostFunction costFunc )
    9999                : ConversionCost( dest, indexer, env, costFunc ) {
    100100        }
    101101
    102         void CastCost_old::postvisit( BasicType *basicType ) {
    103                 PointerType *destAsPointer = dynamic_cast< PointerType* >( dest );
     102        void CastCost_old::postvisit( const BasicType * basicType ) {
     103                const PointerType * destAsPointer = dynamic_cast< const PointerType * >( dest );
    104104                if ( destAsPointer && basicType->isInteger() ) {
    105                         // necessary for, e.g. unsigned long => void*
     105                        // necessary for, e.g. unsigned long => void *
    106106                        cost = Cost::unsafe;
    107107                } else {
     
    110110        }
    111111
    112         void CastCost_old::postvisit( PointerType *pointerType ) {
    113                 if ( PointerType *destAsPtr = dynamic_cast< PointerType* >( dest ) ) {
    114                         if ( pointerType->get_qualifiers() <= destAsPtr->get_qualifiers() && typesCompatibleIgnoreQualifiers( pointerType->base, destAsPtr->base, indexer, env ) ) {
     112        void CastCost_old::postvisit( const PointerType * pointerType ) {
     113                if ( const PointerType * destAsPtr = dynamic_cast< const PointerType * >( dest ) ) {
     114                        if ( pointerType->tq <= destAsPtr->tq && typesCompatibleIgnoreQualifiers( pointerType->base, destAsPtr->base, indexer, env ) ) {
    115115                                cost = Cost::safe;
    116116                        } else {
     
    125125                                } // if
    126126                        } // if
    127                 } else if ( BasicType *destAsBasic = dynamic_cast< BasicType* >( dest ) ) {
     127                } else if ( const BasicType * destAsBasic = dynamic_cast< const BasicType * >( dest ) ) {
    128128                        if ( destAsBasic->isInteger() ) {
    129                                 // necessary for, e.g. void* => unsigned long
     129                                // necessary for, e.g. void * => unsigned long
    130130                                cost = Cost::unsafe;
    131131                        } // if
     
    138138                using ConversionCost_new::postvisit;
    139139
    140                 CastCost_new( 
    141                         const ast::Type * dst, const ast::SymbolTable & symtab, 
     140                CastCost_new(
     141                        const ast::Type * dst, const ast::SymbolTable & symtab,
    142142                        const ast::TypeEnvironment & env, CostCalculation costFunc )
    143143                : ConversionCost_new( dst, symtab, env, costFunc ) {}
     
    182182} // anonymous namespace
    183183
    184 Cost castCost( 
    185         const ast::Type * src, const ast::Type * dst, const ast::SymbolTable & symtab, 
    186         const ast::TypeEnvironment & env 
     184Cost castCost(
     185        const ast::Type * src, const ast::Type * dst, const ast::SymbolTable & symtab,
     186        const ast::TypeEnvironment & env
    187187) {
    188188        if ( auto typeInst = dynamic_cast< const ast::TypeInstType * >( dst ) ) {
     
    220220                PRINT( std::cerr << "conversionCost: dest is reference" << std::endl; )
    221221                #warning cast on ptrsCastable artifact of having two functions, remove when port done
    222                 return convertToReferenceCost( 
    223                         src, refType, symtab, env, 
    224                         ( int (*)( 
    225                                 const ast::Type *, const ast::Type *, const ast::SymbolTable &, 
     222                return convertToReferenceCost(
     223                        src, refType, symtab, env,
     224                        ( int (*)(
     225                                const ast::Type *, const ast::Type *, const ast::SymbolTable &,
    226226                                const ast::TypeEnvironment & )
    227227                        ) ptrsCastable );
     
    229229                #warning cast on castCost artifact of having two functions, remove when port done
    230230                ast::Pass< CastCost_new > converter{
    231                         dst, symtab, env, 
    232                         ( Cost (*)( 
    233                                 const ast::Type *, const ast::Type *, const ast::SymbolTable &, 
     231                        dst, symtab, env,
     232                        ( Cost (*)(
     233                                const ast::Type *, const ast::Type *, const ast::SymbolTable &,
    234234                                const ast::TypeEnvironment & )
    235235                        ) castCost };
  • src/ResolvExpr/CommonType.cc

    r1f1c102 rf53acdf8  
    3838namespace ResolvExpr {
    3939        struct CommonType_old : public WithShortCircuiting {
    40                 CommonType_old( Type *type2, bool widenFirst, bool widenSecond, const SymTab::Indexer &indexer, TypeEnvironment &env, const OpenVarSet &openVars );
    41                 Type *get_result() const { return result; }
     40                CommonType_old( Type * type2, bool widenFirst, bool widenSecond, const SymTab::Indexer &indexer, TypeEnvironment &env, const OpenVarSet &openVars );
     41                Type * get_result() const { return result; }
    4242
    4343                void previsit( BaseSyntaxNode * ) { visit_children = false; }
     
    6060
    6161          private:
    62                 template< typename Pointer > void getCommonWithVoidPointer( Pointer* voidPointer, Pointer* otherPointer );
    63                 template< typename RefType > void handleRefType( RefType *inst, Type *other );
    64 
    65                 Type *result;
    66                 Type *type2;                            // inherited
     62                template< typename Pointer > void getCommonWithVoidPointer( Pointer * voidPointer, Pointer * otherPointer );
     63                template< typename RefType > void handleRefType( RefType * inst, Type * other );
     64
     65                Type * result;
     66                Type * type2;                           // inherited
    6767                bool widenFirst, widenSecond;
    6868                const SymTab::Indexer &indexer;
     
    8080                                std::cerr << "unify success: " << widenFirst << " " << widenSecond << std::endl;
    8181                        )
    82                         if ( (widenFirst || t2->get_qualifiers() <= t1->get_qualifiers()) && (widenSecond || t1->get_qualifiers() <= t2->get_qualifiers()) ) {
     82                        if ( (widenFirst || t2->tq <= t1->tq) && (widenSecond || t1->tq <= t2->tq) ) {
    8383                                PRINT(
    8484                                        std::cerr << "widen okay" << std::endl;
    8585                                )
    86                                 common->get_qualifiers() |= t1->get_qualifiers();
    87                                 common->get_qualifiers() |= t2->get_qualifiers();
     86                                common->tq |= t1->tq;
     87                                common->tq |= t2->tq;
    8888                                return common;
    8989                        }
     
    9595        }
    9696
    97         Type *commonType( Type *type1, Type *type2, bool widenFirst, bool widenSecond, const SymTab::Indexer &indexer, TypeEnvironment &env, const OpenVarSet &openVars ) {
     97        Type * commonType( Type * type1, Type * type2, bool widenFirst, bool widenSecond, const SymTab::Indexer &indexer, TypeEnvironment &env, const OpenVarSet &openVars ) {
    9898                PassVisitor<CommonType_old> visitor( type2, widenFirst, widenSecond, indexer, env, openVars );
    9999
     
    127127                                                std::cerr << "formal is reference; result should be reference" << std::endl;
    128128                                        )
    129                                         result = new ReferenceType( ref1->get_qualifiers(), result );
     129                                        result = new ReferenceType( ref1->tq, result );
    130130                                }
    131131                                PRINT(
     
    138138
    139139                type1->accept( visitor );
    140                 Type *result = visitor.pass.get_result();
     140                Type * result = visitor.pass.get_result();
    141141                if ( ! result ) {
    142142                        // this appears to be handling for opaque type declarations
    143143                        if ( widenSecond ) {
    144                                 if ( TypeInstType *inst = dynamic_cast< TypeInstType* >( type2 ) ) {
    145                                         if ( NamedTypeDecl *nt = indexer.lookupType( inst->get_name() ) ) {
    146                                                 TypeDecl *type = strict_dynamic_cast< TypeDecl* >( nt );
     144                                if ( const TypeInstType * inst = dynamic_cast< const TypeInstType * >( type2 ) ) {
     145                                        if ( const NamedTypeDecl * nt = indexer.lookupType( inst->get_name() ) ) {
     146                                                const TypeDecl * type = strict_dynamic_cast< const TypeDecl * >( nt );
    147147                                                if ( type->get_base() ) {
    148                                                         Type::Qualifiers tq1 = type1->get_qualifiers(), tq2 = type2->get_qualifiers();
     148                                                        Type::Qualifiers tq1 = type1->tq, tq2 = type2->tq;
    149149                                                        AssertionSet have, need;
    150150                                                        OpenVarSet newOpen( openVars );
    151                                                         type1->get_qualifiers() = Type::Qualifiers();
    152                                                         type->get_base()->get_qualifiers() = tq1;
     151                                                        type1->tq = Type::Qualifiers();
     152                                                        type->get_base()->tq = tq1;
    153153                                                        if ( unifyExact( type1, type->get_base(), env, have, need, newOpen, indexer ) ) {
    154154                                                                result = type1->clone();
    155                                                                 result->get_qualifiers() = tq1 | tq2;
     155                                                                result->tq = tq1 | tq2;
    156156                                                        } // if
    157                                                         type1->get_qualifiers() = tq1;
    158                                                         type->get_base()->get_qualifiers() = Type::Qualifiers();
     157                                                        type1->tq = tq1;
     158                                                        type->get_base()->tq = Type::Qualifiers();
    159159                                                } // if
    160160                                        } // if
     
    190190                                 */
    191191                                  {
    192                 /*     B*/                BT Bool,                BT Char,          BT SignedChar,        BT UnsignedChar,      BT ShortSignedInt,    BT ShortUnsignedInt,
     192                /*     B */                BT Bool,                BT Char,          BT SignedChar,        BT UnsignedChar,      BT ShortSignedInt,    BT ShortUnsignedInt,
    193193                                             BT SignedInt,         BT UnsignedInt,       BT LongSignedInt,     BT LongUnsignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
    194194                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
     
    198198                                  },
    199199                                  {
    200                 /*     C*/                BT Char,                BT Char,          BT SignedChar,        BT UnsignedChar,      BT ShortSignedInt,    BT ShortUnsignedInt,
     200                /*     C */                BT Char,                BT Char,          BT SignedChar,        BT UnsignedChar,      BT ShortSignedInt,    BT ShortUnsignedInt,
    201201                                             BT SignedInt,         BT UnsignedInt,       BT LongSignedInt,     BT LongUnsignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
    202202                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
     
    206206                                  },
    207207                                  {
    208                 /*    SC*/          BT SignedChar,          BT SignedChar,          BT SignedChar,        BT UnsignedChar,      BT ShortSignedInt,    BT ShortUnsignedInt,
     208                /*    SC */          BT SignedChar,          BT SignedChar,          BT SignedChar,        BT UnsignedChar,      BT ShortSignedInt,    BT ShortUnsignedInt,
    209209                                             BT SignedInt,         BT UnsignedInt,       BT LongSignedInt,     BT LongUnsignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
    210210                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
     
    214214                                  },
    215215                                  {
    216                 /*    UC*/        BT UnsignedChar,        BT UnsignedChar,        BT UnsignedChar,        BT UnsignedChar,      BT ShortSignedInt,    BT ShortUnsignedInt,
     216                /*    UC */        BT UnsignedChar,        BT UnsignedChar,        BT UnsignedChar,        BT UnsignedChar,      BT ShortSignedInt,    BT ShortUnsignedInt,
    217217                                             BT SignedInt,         BT UnsignedInt,       BT LongSignedInt,     BT LongUnsignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
    218218                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
     
    222222                                  },
    223223                                  {
    224                 /*    SI*/      BT ShortSignedInt,      BT ShortSignedInt,      BT ShortSignedInt,      BT ShortSignedInt,      BT ShortSignedInt,    BT ShortUnsignedInt,
     224                /*    SI */      BT ShortSignedInt,      BT ShortSignedInt,      BT ShortSignedInt,      BT ShortSignedInt,      BT ShortSignedInt,    BT ShortUnsignedInt,
    225225                                             BT SignedInt,         BT UnsignedInt,       BT LongSignedInt,     BT LongUnsignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
    226226                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
     
    230230                                  },
    231231                                  {
    232                 /*   SUI*/    BT ShortUnsignedInt,    BT ShortUnsignedInt,    BT ShortUnsignedInt,    BT ShortUnsignedInt,    BT ShortUnsignedInt,    BT ShortUnsignedInt,
     232                /*   SUI */    BT ShortUnsignedInt,    BT ShortUnsignedInt,    BT ShortUnsignedInt,    BT ShortUnsignedInt,    BT ShortUnsignedInt,    BT ShortUnsignedInt,
    233233                                             BT SignedInt,         BT UnsignedInt,       BT LongSignedInt,     BT LongUnsignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
    234234                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
     
    238238                                  },
    239239                                  {
    240                 /*     I*/           BT SignedInt,           BT SignedInt,           BT SignedInt,           BT SignedInt,           BT SignedInt,           BT SignedInt,
     240                /*     I */           BT SignedInt,           BT SignedInt,           BT SignedInt,           BT SignedInt,           BT SignedInt,           BT SignedInt,
    241241                                             BT SignedInt,         BT UnsignedInt,       BT LongSignedInt,     BT LongUnsignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
    242242                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
     
    246246                                  },
    247247                                  {
    248                 /*    UI*/         BT UnsignedInt,         BT UnsignedInt,         BT UnsignedInt,         BT UnsignedInt,         BT UnsignedInt,         BT UnsignedInt,
     248                /*    UI */         BT UnsignedInt,         BT UnsignedInt,         BT UnsignedInt,         BT UnsignedInt,         BT UnsignedInt,         BT UnsignedInt,
    249249                                           BT UnsignedInt,         BT UnsignedInt,       BT LongSignedInt,     BT LongUnsignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
    250250                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
     
    254254                                  },
    255255                                  {
    256                 /*    LI*/       BT LongSignedInt,       BT LongSignedInt,       BT LongSignedInt,       BT LongSignedInt,       BT LongSignedInt,       BT LongSignedInt,
     256                /*    LI */       BT LongSignedInt,       BT LongSignedInt,       BT LongSignedInt,       BT LongSignedInt,       BT LongSignedInt,       BT LongSignedInt,
    257257                                         BT LongSignedInt,       BT LongSignedInt,       BT LongSignedInt,     BT LongUnsignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
    258258                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
     
    262262                                  },
    263263                                  {
    264                 /*   LUI*/     BT LongUnsignedInt,     BT LongUnsignedInt,     BT LongUnsignedInt,     BT LongUnsignedInt,     BT LongUnsignedInt,     BT LongUnsignedInt,
     264                /*   LUI */     BT LongUnsignedInt,     BT LongUnsignedInt,     BT LongUnsignedInt,     BT LongUnsignedInt,     BT LongUnsignedInt,     BT LongUnsignedInt,
    265265                                       BT LongUnsignedInt,     BT LongUnsignedInt,     BT LongUnsignedInt,     BT LongUnsignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
    266266                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
     
    270270                                  },
    271271                                  {
    272                 /*   LLI*/   BT LongLongSignedInt,   BT LongLongSignedInt,   BT LongLongSignedInt,   BT LongLongSignedInt,   BT LongLongSignedInt,   BT LongLongSignedInt,
     272                /*   LLI */   BT LongLongSignedInt,   BT LongLongSignedInt,   BT LongLongSignedInt,   BT LongLongSignedInt,   BT LongLongSignedInt,   BT LongLongSignedInt,
    273273                                     BT LongLongSignedInt,   BT LongLongSignedInt,   BT LongLongSignedInt,   BT LongLongSignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
    274274                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
     
    278278                                  },
    279279                                  {
    280                 /*  LLUI*/ BT LongLongUnsignedInt, BT LongLongUnsignedInt, BT LongLongUnsignedInt, BT LongLongUnsignedInt, BT LongLongUnsignedInt, BT LongLongUnsignedInt,
     280                /*  LLUI */ BT LongLongUnsignedInt, BT LongLongUnsignedInt, BT LongLongUnsignedInt, BT LongLongUnsignedInt, BT LongLongUnsignedInt, BT LongLongUnsignedInt,
    281281                                   BT LongLongUnsignedInt, BT LongLongUnsignedInt, BT LongLongUnsignedInt, BT LongLongUnsignedInt, BT LongLongUnsignedInt, BT LongLongUnsignedInt,
    282282                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
     
    286286                                  },
    287287                                  {
    288                 /*    IB*/        BT SignedInt128,        BT SignedInt128,        BT SignedInt128,        BT SignedInt128,        BT SignedInt128,        BT SignedInt128,
     288                /*    IB */        BT SignedInt128,        BT SignedInt128,        BT SignedInt128,        BT SignedInt128,        BT SignedInt128,        BT SignedInt128,
    289289                                          BT SignedInt128,        BT SignedInt128,        BT SignedInt128,        BT SignedInt128,        BT SignedInt128,        BT SignedInt128,
    290290                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
     
    294294                                  },
    295295                                  {
    296                 /*   UIB*/      BT UnsignedInt128,      BT UnsignedInt128,      BT UnsignedInt128,      BT UnsignedInt128,      BT UnsignedInt128,      BT UnsignedInt128,
     296                /*   UIB */      BT UnsignedInt128,      BT UnsignedInt128,      BT UnsignedInt128,      BT UnsignedInt128,      BT UnsignedInt128,      BT UnsignedInt128,
    297297                                        BT UnsignedInt128,      BT UnsignedInt128,      BT UnsignedInt128,      BT UnsignedInt128,      BT UnsignedInt128,      BT UnsignedInt128,
    298298                                        BT UnsignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
     
    302302                                  },
    303303                                  {
    304                 /*   _FH*/            BT uFloat16,            BT uFloat16,            BT uFloat16,            BT uFloat16,            BT uFloat16,            BT uFloat16,
     304                /*   _FH */            BT uFloat16,            BT uFloat16,            BT uFloat16,            BT uFloat16,            BT uFloat16,            BT uFloat16,
    305305                                              BT uFloat16,            BT uFloat16,            BT uFloat16,            BT uFloat16,            BT uFloat16,            BT uFloat16,
    306306                                              BT uFloat16,            BT uFloat16,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
     
    310310                                  },
    311311                                  {
    312                 /*   _FH*/     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,
     312                /*   _FH */     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,
    313313                                       BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,
    314314                                       BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat32Complex,     BT uFloat32Complex,
     
    318318                                  },
    319319                                  {
    320                 /*    _F*/            BT uFloat32,            BT uFloat32,            BT uFloat32,            BT uFloat32,            BT uFloat32,            BT uFloat32,
     320                /*    _F */            BT uFloat32,            BT uFloat32,            BT uFloat32,            BT uFloat32,            BT uFloat32,            BT uFloat32,
    321321                                              BT uFloat32,            BT uFloat32,            BT uFloat32,            BT uFloat32,            BT uFloat32,            BT uFloat32,
    322322                                              BT uFloat32,            BT uFloat32,            BT uFloat32,     BT uFloat32Complex,            BT uFloat32,     BT uFloat32Complex,
     
    326326                                  },
    327327                                  {
    328                 /*   _FC*/     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,
     328                /*   _FC */     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,
    329329                                       BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,
    330330                                       BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,
     
    334334                                  },
    335335                                  {
    336                 /*     F*/               BT Float,               BT Float,               BT Float,               BT Float,               BT Float,               BT Float,
     336                /*     F */               BT Float,               BT Float,               BT Float,               BT Float,               BT Float,               BT Float,
    337337                                                 BT Float,               BT Float,               BT Float,               BT Float,               BT Float,               BT Float,
    338338                                                 BT Float,               BT Float,               BT Float,        BT FloatComplex,               BT Float,        BT FloatComplex,
     
    342342                                  },
    343343                                  {
    344                 /*    FC*/        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,
     344                /*    FC */        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,
    345345                                          BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,
    346346                                          BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,
     
    350350                                  },
    351351                                  {
    352                 /*   _FX*/           BT uFloat32x,           BT uFloat32x,           BT uFloat32x,           BT uFloat32x,           BT uFloat32x,           BT uFloat32x,
     352                /*   _FX */           BT uFloat32x,           BT uFloat32x,           BT uFloat32x,           BT uFloat32x,           BT uFloat32x,           BT uFloat32x,
    353353                                             BT uFloat32x,           BT uFloat32x,           BT uFloat32x,           BT uFloat32x,           BT uFloat32x,           BT uFloat32x,
    354354                                             BT uFloat32x,           BT uFloat32x,           BT uFloat32x,    BT uFloat32xComplex,           BT uFloat32x,    BT uFloat32xComplex,
     
    358358                                  },
    359359                                  {
    360                 /*  _FXC*/    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,
     360                /*  _FXC */    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,
    361361                                      BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,
    362362                                      BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,
     
    366366                                  },
    367367                                  {
    368                 /*    FD*/            BT uFloat64,            BT uFloat64,            BT uFloat64,            BT uFloat64,            BT uFloat64,            BT uFloat64,
     368                /*    FD */            BT uFloat64,            BT uFloat64,            BT uFloat64,            BT uFloat64,            BT uFloat64,            BT uFloat64,
    369369                                              BT uFloat64,            BT uFloat64,            BT uFloat64,            BT uFloat64,            BT uFloat64,            BT uFloat64,
    370370                                              BT uFloat64,            BT uFloat64,            BT uFloat64,     BT uFloat64Complex,            BT uFloat64,     BT uFloat64Complex,
     
    374374                                  },
    375375                                  {
    376                 /*  _FDC*/     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,
     376                /*  _FDC */     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,
    377377                                       BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,
    378378                                       BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,
     
    382382                                  },
    383383                                  {
    384                 /*     D*/              BT Double,              BT Double,              BT Double,              BT Double,              BT Double,              BT Double,
     384                /*     D */              BT Double,              BT Double,              BT Double,              BT Double,              BT Double,              BT Double,
    385385                                                BT Double,              BT Double,              BT Double,              BT Double,              BT Double,              BT Double,
    386386                                                BT Double,              BT Double,              BT Double,       BT DoubleComplex,              BT Double,       BT DoubleComplex,
     
    390390                                  },
    391391                                  {
    392                 /*    DC*/       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,
     392                /*    DC */       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,
    393393                                         BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,
    394394                                         BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,
     
    398398                                  },
    399399                                  {
    400                 /*  F80X*/           BT uFloat64x,           BT uFloat64x,           BT uFloat64x,           BT uFloat64x,           BT uFloat64x,           BT uFloat64x,
     400                /*  F80X */           BT uFloat64x,           BT uFloat64x,           BT uFloat64x,           BT uFloat64x,           BT uFloat64x,           BT uFloat64x,
    401401                                             BT uFloat64x,           BT uFloat64x,           BT uFloat64x,           BT uFloat64x,           BT uFloat64x,           BT uFloat64x,
    402402                                             BT uFloat64x,           BT uFloat64x,           BT uFloat64x,    BT uFloat64xComplex,           BT uFloat64x,    BT uFloat64xComplex,
     
    406406                                  },
    407407                                  {
    408                 /* _FDXC*/    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,
     408                /* _FDXC */    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,
    409409                                      BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,
    410410                                      BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,
     
    422422                                  },
    423423                                  {
    424                 /*   _FB*/           BT uFloat128,           BT uFloat128,           BT uFloat128,           BT uFloat128,           BT uFloat128,           BT uFloat128,
     424                /*   _FB */           BT uFloat128,           BT uFloat128,           BT uFloat128,           BT uFloat128,           BT uFloat128,           BT uFloat128,
    425425                                             BT uFloat128,           BT uFloat128,           BT uFloat128,           BT uFloat128,           BT uFloat128,           BT uFloat128,
    426426                                             BT uFloat128,           BT uFloat128,           BT uFloat128,    BT uFloat128Complex,           BT uFloat128,    BT uFloat128Complex,
     
    430430                                  },
    431431                                  {
    432                 /* _FLDC*/    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,
     432                /* _FLDC */    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,
    433433                                      BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,
    434434                                      BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,
     
    438438                                  },
    439439                                  {
    440                 /*    FB*/          BT uuFloat128,          BT uuFloat128,          BT uuFloat128,          BT uuFloat128,          BT uuFloat128,          BT uuFloat128,
     440                /*    FB */          BT uuFloat128,          BT uuFloat128,          BT uuFloat128,          BT uuFloat128,          BT uuFloat128,          BT uuFloat128,
    441441                                            BT uuFloat128,          BT uuFloat128,          BT uuFloat128,          BT uuFloat128,          BT uuFloat128,          BT uuFloat128,
    442442                                            BT uuFloat128,          BT uuFloat128,          BT uuFloat128,    BT uFloat128Complex,          BT uuFloat128,    BT uFloat128Complex,
     
    446446                                  },
    447447                                  {
    448                 /*    LD*/          BT LongDouble,          BT LongDouble,          BT LongDouble,          BT LongDouble,          BT LongDouble,          BT LongDouble,
     448                /*    LD */          BT LongDouble,          BT LongDouble,          BT LongDouble,          BT LongDouble,          BT LongDouble,          BT LongDouble,
    449449                                            BT LongDouble,          BT LongDouble,          BT LongDouble,          BT LongDouble,          BT LongDouble,          BT LongDouble,
    450450                                            BT LongDouble,          BT LongDouble,          BT LongDouble,   BT LongDoubleComplex,          BT LongDouble,   BT LongDoubleComplex,
     
    454454                                  },
    455455                                  {
    456                 /*   LDC*/   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,
     456                /*   LDC */   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,
    457457                                     BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,
    458458                                     BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,
     
    462462                                  },
    463463                                  {
    464                 /*  _FBX*/          BT uFloat128x,          BT uFloat128x,          BT uFloat128x,          BT uFloat128x,          BT uFloat128x,          BT uFloat128x,
     464                /*  _FBX */          BT uFloat128x,          BT uFloat128x,          BT uFloat128x,          BT uFloat128x,          BT uFloat128x,          BT uFloat128x,
    465465                                            BT uFloat128x,          BT uFloat128x,          BT uFloat128x,          BT uFloat128x,          BT uFloat128x,          BT uFloat128x,
    466466                                            BT uFloat128x,          BT uFloat128x,          BT uFloat128x,   BT uFloat128xComplex,          BT uFloat128x,   BT uFloat128xComplex,
     
    470470                                  },
    471471                                  {
    472                 /*_FLDXC*/   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,
     472                /* _FLDXC */   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,
    473473                                     BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,
    474474                                     BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,
     
    481481        // GENERATED END
    482482        static_assert(
    483                 sizeof(commonTypes)/sizeof(commonTypes[0][0]) == BasicType::NUMBER_OF_BASIC_TYPES*BasicType::NUMBER_OF_BASIC_TYPES,
     483                sizeof(commonTypes)/sizeof(commonTypes[0][0]) == BasicType::NUMBER_OF_BASIC_TYPES * BasicType::NUMBER_OF_BASIC_TYPES,
    484484                "Each basic type kind should have a corresponding row in the combined type matrix"
    485485        );
    486486
    487         CommonType_old::CommonType_old( Type *type2, bool widenFirst, bool widenSecond, const SymTab::Indexer &indexer, TypeEnvironment &env, const OpenVarSet &openVars )
     487        CommonType_old::CommonType_old( Type * type2, bool widenFirst, bool widenSecond, const SymTab::Indexer &indexer, TypeEnvironment &env, const OpenVarSet &openVars )
    488488                : result( 0 ), type2( type2 ), widenFirst( widenFirst ), widenSecond( widenSecond ), indexer( indexer ), env( env ), openVars( openVars ) {
    489489        }
     
    491491        void CommonType_old::postvisit( VoidType * ) {}
    492492
    493         void CommonType_old::postvisit( BasicType *basicType ) {
    494                 if ( BasicType *otherBasic = dynamic_cast< BasicType* >( type2 ) ) {
     493        void CommonType_old::postvisit( BasicType * basicType ) {
     494                if ( BasicType * otherBasic = dynamic_cast< BasicType * >( type2 ) ) {
    495495                        BasicType::Kind newType = commonTypes[ basicType->get_kind() ][ otherBasic->get_kind() ];
    496                         if ( ( ( newType == basicType->get_kind() && basicType->get_qualifiers() >= otherBasic->get_qualifiers() ) || widenFirst ) && ( ( newType == otherBasic->get_kind() && basicType->get_qualifiers() <= otherBasic->get_qualifiers() ) || widenSecond ) ) {
    497                                 result = new BasicType( basicType->get_qualifiers() | otherBasic->get_qualifiers(), newType );
     496                        if ( ( ( newType == basicType->get_kind() && basicType->tq >= otherBasic->tq ) || widenFirst ) && ( ( newType == otherBasic->get_kind() && basicType->tq <= otherBasic->tq ) || widenSecond ) ) {
     497                                result = new BasicType( basicType->tq | otherBasic->tq, newType );
    498498                        } // if
    499                 } else if ( dynamic_cast< EnumInstType * > ( type2 ) || dynamic_cast< ZeroType* >( type2 ) || dynamic_cast< OneType* >( type2 ) ) {
     499                } else if ( dynamic_cast< EnumInstType * > ( type2 ) || dynamic_cast< ZeroType * >( type2 ) || dynamic_cast< OneType * >( type2 ) ) {
    500500                        // use signed int in lieu of the enum/zero/one type
    501501                        BasicType::Kind newType = commonTypes[ basicType->get_kind() ][ BasicType::SignedInt ];
    502                         if ( ( ( newType == basicType->get_kind() && basicType->get_qualifiers() >= type2->get_qualifiers() ) || widenFirst ) && ( ( newType != basicType->get_kind() && basicType->get_qualifiers() <= type2->get_qualifiers() ) || widenSecond ) ) {
    503                                 result = new BasicType( basicType->get_qualifiers() | type2->get_qualifiers(), newType );
     502                        if ( ( ( newType == basicType->get_kind() && basicType->tq >= type2->tq ) || widenFirst ) && ( ( newType != basicType->get_kind() && basicType->tq <= type2->tq ) || widenSecond ) ) {
     503                                result = new BasicType( basicType->tq | type2->tq, newType );
    504504                        } // if
    505505                } // if
     
    507507
    508508        template< typename Pointer >
    509         void CommonType_old::getCommonWithVoidPointer( Pointer* voidPointer, Pointer* otherPointer ) {
    510                 if ( TypeInstType* var = dynamic_cast< TypeInstType* >( otherPointer->get_base() ) ) {
     509        void CommonType_old::getCommonWithVoidPointer( Pointer * voidPointer, Pointer * otherPointer ) {
     510                if ( TypeInstType * var = dynamic_cast< TypeInstType * >( otherPointer->get_base() ) ) {
    511511                        OpenVarSet::const_iterator entry = openVars.find( var->get_name() );
    512512                        if ( entry != openVars.end() ) {
     
    517517                }
    518518                result = voidPointer->clone();
    519                 result->get_qualifiers() |= otherPointer->get_qualifiers();
    520         }
    521 
    522         void CommonType_old::postvisit( PointerType *pointerType ) {
    523                 if ( PointerType *otherPointer = dynamic_cast< PointerType* >( type2 ) ) {
     519                result->tq |= otherPointer->tq;
     520        }
     521
     522        void CommonType_old::postvisit( PointerType * pointerType ) {
     523                if ( PointerType * otherPointer = dynamic_cast< PointerType * >( type2 ) ) {
    524524                        // std::cerr << "commonType: two pointers: " << pointerType << " / " << otherPointer << std::endl;
    525                         if ( widenFirst && dynamic_cast< VoidType* >( otherPointer->get_base() ) && ! isFtype(pointerType->get_base()) ) {
     525                        if ( widenFirst && dynamic_cast< VoidType * >( otherPointer->get_base() ) && ! isFtype(pointerType->get_base()) ) {
    526526                                getCommonWithVoidPointer( otherPointer, pointerType );
    527                         } else if ( widenSecond && dynamic_cast< VoidType* >( pointerType->get_base() ) && ! isFtype(otherPointer->get_base()) ) {
     527                        } else if ( widenSecond && dynamic_cast< VoidType * >( pointerType->get_base() ) && ! isFtype(otherPointer->get_base()) ) {
    528528                                getCommonWithVoidPointer( pointerType, otherPointer );
    529                         } else if ( ( pointerType->get_base()->get_qualifiers() >= otherPointer->get_base()->get_qualifiers() || widenFirst )
    530                                            && ( pointerType->get_base()->get_qualifiers() <= otherPointer->get_base()->get_qualifiers() || widenSecond ) ) {
     529                        } else if ( ( pointerType->get_base()->tq >= otherPointer->get_base()->tq || widenFirst )
     530                                           && ( pointerType->get_base()->tq <= otherPointer->get_base()->tq || widenSecond ) ) {
    531531                                // std::cerr << "middle case" << std::endl;
    532                                 Type::Qualifiers tq1 = pointerType->get_base()->get_qualifiers(), tq2 = otherPointer->get_base()->get_qualifiers();
    533                                 pointerType->get_base()->get_qualifiers() = Type::Qualifiers();
    534                                 otherPointer->get_base()->get_qualifiers() = Type::Qualifiers();
     532                                Type::Qualifiers tq1 = pointerType->get_base()->tq, tq2 = otherPointer->get_base()->tq;
     533                                pointerType->get_base()->tq = Type::Qualifiers();
     534                                otherPointer->get_base()->tq = Type::Qualifiers();
    535535                                AssertionSet have, need;
    536536                                OpenVarSet newOpen( openVars );
     
    542542                                                result = otherPointer->clone();
    543543                                        } // if
    544                                         strict_dynamic_cast<PointerType*>(result)->base->get_qualifiers() = tq1 | tq2;
     544                                        strict_dynamic_cast<PointerType *>(result)->base->tq = tq1 | tq2;
    545545                                } else {
    546546                                        /// std::cerr << "place for ptr-to-type" << std::endl;
    547547                                } // if
    548                                 pointerType->get_base()->get_qualifiers() = tq1;
    549                                 otherPointer->get_base()->get_qualifiers() = tq2;
     548                                pointerType->get_base()->tq = tq1;
     549                                otherPointer->get_base()->tq = tq2;
    550550                        } // if
    551                 } else if ( widenSecond && dynamic_cast< ZeroType* >( type2 ) ) {
     551                } else if ( widenSecond && dynamic_cast< ZeroType * >( type2 ) ) {
    552552                        result = pointerType->clone();
    553                         result->get_qualifiers() |= type2->get_qualifiers();
     553                        result->tq |= type2->tq;
    554554                } // if
    555555        }
     
    557557        void CommonType_old::postvisit( ArrayType * ) {}
    558558
    559         void CommonType_old::postvisit( ReferenceType *refType ) {
    560                 if ( ReferenceType *otherRef = dynamic_cast< ReferenceType* >( type2 ) ) {
     559        void CommonType_old::postvisit( ReferenceType * refType ) {
     560                if ( ReferenceType * otherRef = dynamic_cast< ReferenceType * >( type2 ) ) {
    561561                        // std::cerr << "commonType: both references: " << refType << " / " << otherRef << std::endl;
    562                         // std::cerr << ( refType->get_base()->get_qualifiers() >= otherRef->get_base()->get_qualifiers() || widenFirst ) << (refType->get_base()->get_qualifiers() <= otherRef->get_base()->get_qualifiers() || widenSecond) << std::endl;
    563                         if ( widenFirst && dynamic_cast< VoidType* >( otherRef->get_base() ) && ! isFtype(refType->get_base()) ) {
     562                        // std::cerr << ( refType->get_base()->tq >= otherRef->get_base()->tq || widenFirst ) << (refType->get_base()->tq <= otherRef->get_base()->tq || widenSecond) << std::endl;
     563                        if ( widenFirst && dynamic_cast< VoidType * >( otherRef->get_base() ) && ! isFtype(refType->get_base()) ) {
    564564                                getCommonWithVoidPointer( otherRef, refType );
    565                         } else if ( widenSecond && dynamic_cast< VoidType* >( refType->get_base() ) && ! isFtype(otherRef->get_base()) ) {
     565                        } else if ( widenSecond && dynamic_cast< VoidType * >( refType->get_base() ) && ! isFtype(otherRef->get_base()) ) {
    566566                                getCommonWithVoidPointer( refType, otherRef );
    567                         } else if ( ( refType->get_base()->get_qualifiers() >= otherRef->get_base()->get_qualifiers() || widenFirst )
    568                                            && ( refType->get_base()->get_qualifiers() <= otherRef->get_base()->get_qualifiers() || widenSecond ) ) {
     567                        } else if ( ( refType->get_base()->tq >= otherRef->get_base()->tq || widenFirst )
     568                                           && ( refType->get_base()->tq <= otherRef->get_base()->tq || widenSecond ) ) {
    569569                                // std::cerr << "middle case" << std::endl;
    570                                 Type::Qualifiers tq1 = refType->get_base()->get_qualifiers(), tq2 = otherRef->get_base()->get_qualifiers();
    571                                 refType->get_base()->get_qualifiers() = Type::Qualifiers();
    572                                 otherRef->get_base()->get_qualifiers() = Type::Qualifiers();
     570                                Type::Qualifiers tq1 = refType->get_base()->tq, tq2 = otherRef->get_base()->tq;
     571                                refType->get_base()->tq = Type::Qualifiers();
     572                                otherRef->get_base()->tq = Type::Qualifiers();
    573573                                AssertionSet have, need;
    574574                                OpenVarSet newOpen( openVars );
     
    579579                                                result = otherRef->clone();
    580580                                        } // if
    581                                         strict_dynamic_cast<ReferenceType*>(result)->base->get_qualifiers() = tq1 | tq2;
     581                                        strict_dynamic_cast<ReferenceType *>(result)->base->tq = tq1 | tq2;
    582582                                } else {
    583583                                        /// std::cerr << "place for ptr-to-type" << std::endl;
    584584                                } // if
    585                                 refType->get_base()->get_qualifiers() = tq1;
    586                                 otherRef->get_base()->get_qualifiers() = tq2;
     585                                refType->get_base()->tq = tq1;
     586                                otherRef->get_base()->tq = tq2;
    587587                        } // if
    588                 } else if ( widenSecond && dynamic_cast< ZeroType* >( type2 ) ) {
     588                } else if ( widenSecond && dynamic_cast< ZeroType * >( type2 ) ) {
    589589                        result = refType->clone();
    590                         result->get_qualifiers() |= type2->get_qualifiers();
     590                        result->tq |= type2->tq;
    591591                } // if
    592592        }
     
    596596        void CommonType_old::postvisit( UnionInstType * ) {}
    597597
    598         void CommonType_old::postvisit( EnumInstType *enumInstType ) {
    599                 if ( dynamic_cast< BasicType * >( type2 ) || dynamic_cast< ZeroType* >( type2 ) || dynamic_cast< OneType* >( type2 ) ) {
     598        void CommonType_old::postvisit( EnumInstType * enumInstType ) {
     599                if ( dynamic_cast< BasicType * >( type2 ) || dynamic_cast< ZeroType * >( type2 ) || dynamic_cast< OneType * >( type2 ) ) {
    600600                        // reuse BasicType, EnumInstType code by swapping type2 with enumInstType
    601601                        result = commonType( type2, enumInstType, widenSecond, widenFirst, indexer, env, openVars );
     
    606606        }
    607607
    608         void CommonType_old::postvisit( TypeInstType *inst ) {
     608        void CommonType_old::postvisit( TypeInstType * inst ) {
    609609                if ( widenFirst ) {
    610                         NamedTypeDecl *nt = indexer.lookupType( inst->get_name() );
     610                        const NamedTypeDecl * nt = indexer.lookupType( inst->get_name() );
    611611                        if ( nt ) {
    612                                 TypeDecl *type = strict_dynamic_cast< TypeDecl* >( nt );
     612                                const TypeDecl * type = strict_dynamic_cast< const TypeDecl * >( nt );
    613613                                if ( type->get_base() ) {
    614                                         Type::Qualifiers tq1 = inst->get_qualifiers(), tq2 = type2->get_qualifiers();
     614                                        Type::Qualifiers tq1 = inst->tq, tq2 = type2->tq;
    615615                                        AssertionSet have, need;
    616616                                        OpenVarSet newOpen( openVars );
    617                                         type2->get_qualifiers() = Type::Qualifiers();
    618                                         type->get_base()->get_qualifiers() = tq1;
     617                                        type2->tq = Type::Qualifiers();
     618                                        type->get_base()->tq = tq1;
    619619                                        if ( unifyExact( type->get_base(), type2, env, have, need, newOpen, indexer ) ) {
    620620                                                result = type2->clone();
    621                                                 result->get_qualifiers() = tq1 | tq2;
     621                                                result->tq = tq1 | tq2;
    622622                                        } // if
    623                                         type2->get_qualifiers() = tq2;
    624                                         type->get_base()->get_qualifiers() = Type::Qualifiers();
     623                                        type2->tq = tq2;
     624                                        type->get_base()->tq = Type::Qualifiers();
    625625                                } // if
    626626                        } // if
     
    631631        void CommonType_old::postvisit( VarArgsType * ) {}
    632632
    633         void CommonType_old::postvisit( ZeroType *zeroType ) {
     633        void CommonType_old::postvisit( ZeroType * zeroType ) {
    634634                if ( widenFirst ) {
    635                         if ( dynamic_cast< BasicType* >( type2 ) || dynamic_cast< PointerType* >( type2 ) || dynamic_cast< EnumInstType* >( type2 ) ) {
    636                                 if ( widenSecond || zeroType->get_qualifiers() <= type2->get_qualifiers() ) {
     635                        if ( dynamic_cast< BasicType * >( type2 ) || dynamic_cast< PointerType * >( type2 ) || dynamic_cast< EnumInstType * >( type2 ) ) {
     636                                if ( widenSecond || zeroType->tq <= type2->tq ) {
    637637                                        result = type2->clone();
    638                                         result->get_qualifiers() |= zeroType->get_qualifiers();
    639                                 }
    640                         } else if ( widenSecond && dynamic_cast< OneType* >( type2 ) ) {
    641                                 result = new BasicType( zeroType->get_qualifiers(), BasicType::SignedInt );
    642                                 result->get_qualifiers() |= type2->get_qualifiers();
    643                         }
    644                 }
    645         }
    646 
    647         void CommonType_old::postvisit( OneType *oneType ) {
     638                                        result->tq |= zeroType->tq;
     639                                }
     640                        } else if ( widenSecond && dynamic_cast< OneType * >( type2 ) ) {
     641                                result = new BasicType( zeroType->tq, BasicType::SignedInt );
     642                                result->tq |= type2->tq;
     643                        }
     644                }
     645        }
     646
     647        void CommonType_old::postvisit( OneType * oneType ) {
    648648                if ( widenFirst ) {
    649                         if ( dynamic_cast< BasicType* >( type2 ) || dynamic_cast< EnumInstType* >( type2 ) ) {
    650                                 if ( widenSecond || oneType->get_qualifiers() <= type2->get_qualifiers() ) {
     649                        if ( dynamic_cast< BasicType * >( type2 ) || dynamic_cast< EnumInstType * >( type2 ) ) {
     650                                if ( widenSecond || oneType->tq <= type2->tq ) {
    651651                                        result = type2->clone();
    652                                         result->get_qualifiers() |= oneType->get_qualifiers();
    653                                 }
    654                         } else if ( widenSecond && dynamic_cast< ZeroType* >( type2 ) ) {
    655                                 result = new BasicType( oneType->get_qualifiers(), BasicType::SignedInt );
    656                                 result->get_qualifiers() |= type2->get_qualifiers();
     652                                        result->tq |= oneType->tq;
     653                                }
     654                        } else if ( widenSecond && dynamic_cast< ZeroType * >( type2 ) ) {
     655                                result = new BasicType( oneType->tq, BasicType::SignedInt );
     656                                result->tq |= type2->tq;
    657657                        }
    658658                }
     
    668668                ast::ptr< ast::Type > result;
    669669
    670                 CommonType_new( 
    671                         const ast::Type * t2, WidenMode w, const ast::SymbolTable & st, 
     670                CommonType_new(
     671                        const ast::Type * t2, WidenMode w, const ast::SymbolTable & st,
    672672                        ast::TypeEnvironment & env, const ast::OpenVarSet & o )
    673673                : type2( t2 ), widen( w ), symtab( st ), tenv( env ), open( o ), result() {}
     
    681681                                #warning remove casts when `commonTypes` moved to new AST
    682682                                ast::BasicType::Kind kind = (ast::BasicType::Kind)(int)commonTypes[ (BasicType::Kind)(int)basic->kind ][ (BasicType::Kind)(int)basic2->kind ];
    683                                 if ( 
    684                                         ( ( kind == basic->kind && basic->qualifiers >= basic2->qualifiers ) 
    685                                                 || widen.first ) 
    686                                         && ( ( kind == basic2->kind && basic->qualifiers <= basic2->qualifiers ) 
    687                                                 || widen.second ) 
     683                                if (
     684                                        ( ( kind == basic->kind && basic->qualifiers >= basic2->qualifiers )
     685                                                || widen.first )
     686                                        && ( ( kind == basic2->kind && basic->qualifiers <= basic2->qualifiers )
     687                                                || widen.second )
    688688                                ) {
    689689                                        result = new ast::BasicType{ kind, basic->qualifiers | basic2->qualifiers };
    690690                                }
    691                         } else if ( 
    692                                 dynamic_cast< const ast::EnumInstType * >( type2 ) 
     691                        } else if (
     692                                dynamic_cast< const ast::EnumInstType * >( type2 )
    693693                                || dynamic_cast< const ast::ZeroType * >( type2 )
    694694                                || dynamic_cast< const ast::OneType * >( type2 )
     
    696696                                #warning remove casts when `commonTypes` moved to new AST
    697697                                ast::BasicType::Kind kind = (ast::BasicType::Kind)(int)commonTypes[ (BasicType::Kind)(int)basic->kind ][ (BasicType::Kind)(int)ast::BasicType::SignedInt ];
    698                                 if ( 
    699                                         ( ( kind == basic->kind && basic->qualifiers >= type2->qualifiers ) 
    700                                                 || widen.first ) 
    701                                         && ( ( kind != basic->kind && basic->qualifiers <= type2->qualifiers ) 
    702                                                 || widen.second ) 
     698                                if (
     699                                        ( ( kind == basic->kind && basic->qualifiers >= type2->qualifiers )
     700                                                || widen.first )
     701                                        && ( ( kind != basic->kind && basic->qualifiers <= type2->qualifiers )
     702                                                || widen.second )
    703703                                ) {
    704704                                        result = new ast::BasicType{ kind, basic->qualifiers | type2->qualifiers };
     
    715715                                if ( entry != open.end() ) {
    716716                                        ast::AssertionSet need, have;
    717                                         if ( ! tenv.bindVar( 
    718                                                 var, voidPtr->base, entry->second, need, have, open, widen, symtab ) 
     717                                        if ( ! tenv.bindVar(
     718                                                var, voidPtr->base, entry->second, need, have, open, widen, symtab )
    719719                                        ) return;
    720720                                }
     
    727727                void postvisit( const ast::PointerType * pointer ) {
    728728                        if ( auto pointer2 = dynamic_cast< const ast::PointerType * >( type2 ) ) {
    729                                 if ( 
    730                                         widen.first 
    731                                         && pointer2->base.as< ast::VoidType >() 
    732                                         && ! ast::isFtype( pointer->base ) 
     729                                if (
     730                                        widen.first
     731                                        && pointer2->base.as< ast::VoidType >()
     732                                        && ! ast::isFtype( pointer->base )
    733733                                ) {
    734734                                        getCommonWithVoidPointer( pointer2, pointer );
    735                                 } else if ( 
    736                                         widen.second 
    737                                         && pointer->base.as< ast::VoidType >() 
    738                                         && ! ast::isFtype( pointer2->base ) 
     735                                } else if (
     736                                        widen.second
     737                                        && pointer->base.as< ast::VoidType >()
     738                                        && ! ast::isFtype( pointer2->base )
    739739                                ) {
    740740                                        getCommonWithVoidPointer( pointer, pointer2 );
     
    746746                                        ast::CV::Qualifiers q2 = pointer2->base->qualifiers;
    747747
    748                                         // force t{1,2} to be cloned if their qualifiers must be stripped, so that 
     748                                        // force t{1,2} to be cloned if their qualifiers must be stripped, so that
    749749                                        // pointer{,2}->base are unchanged
    750750                                        ast::ptr< ast::Type > t1{ pointer->base }, t2{ pointer2->base };
    751751                                        reset_qualifiers( t1 );
    752752                                        reset_qualifiers( t2 );
    753                                        
     753
    754754                                        ast::AssertionSet have, need;
    755755                                        ast::OpenVarSet newOpen{ open };
     
    758758                                                if ( q1.val != q2.val ) {
    759759                                                        // reset result->base->qualifiers to be union of two base qualifiers
    760                                                         strict_dynamic_cast< ast::PointerType * >( 
    761                                                                 result.get_and_mutate() 
     760                                                        strict_dynamic_cast< ast::PointerType * >(
     761                                                                result.get_and_mutate()
    762762                                                        )->base.get_and_mutate()->qualifiers = q1 | q2;
    763763                                                }
     
    775775                        if ( auto ref2 = dynamic_cast< const ast::ReferenceType * >( type2 ) ) {
    776776                                if (
    777                                         widen.first && ref2->base.as< ast::VoidType >() && ! ast::isFtype( ref->base ) 
     777                                        widen.first && ref2->base.as< ast::VoidType >() && ! ast::isFtype( ref->base )
    778778                                ) {
    779779                                        getCommonWithVoidPointer( ref2, ref );
    780                                 } else if ( 
    781                                         widen.second && ref->base.as< ast::VoidType>() && ! ast::isFtype( ref2->base ) 
     780                                } else if (
     781                                        widen.second && ref->base.as< ast::VoidType>() && ! ast::isFtype( ref2->base )
    782782                                ) {
    783783                                        getCommonWithVoidPointer( ref, ref2 );
     
    788788                                        ast::CV::Qualifiers q1 = ref->base->qualifiers, q2 = ref2->base->qualifiers;
    789789
    790                                         // force t{1,2} to be cloned if their qualifiers must be stripped, so that 
     790                                        // force t{1,2} to be cloned if their qualifiers must be stripped, so that
    791791                                        // ref{,2}->base are unchanged
    792792                                        ast::ptr< ast::Type > t1{ ref->base }, t2{ ref2->base };
     
    800800                                                if ( q1.val != q2.val ) {
    801801                                                        // reset result->base->qualifiers to be union of two base qualifiers
    802                                                         strict_dynamic_cast< ast::ReferenceType * >( 
    803                                                                 result.get_and_mutate() 
     802                                                        strict_dynamic_cast< ast::ReferenceType * >(
     803                                                                result.get_and_mutate()
    804804                                                        )->base.get_and_mutate()->qualifiers = q1 | q2;
    805805                                                }
     
    819819
    820820                void postvisit( const ast::EnumInstType * enumInst ) {
    821                         if ( 
    822                                 dynamic_cast< const ast::BasicType * >( type2 ) 
     821                        if (
     822                                dynamic_cast< const ast::BasicType * >( type2 )
    823823                                || dynamic_cast< const ast::ZeroType * >( type2 )
    824824                                || dynamic_cast< const ast::OneType * >( type2 )
     
    834834                        if ( ! widen.first ) return;
    835835                        if ( const ast::NamedTypeDecl * nt = symtab.lookupType( inst->name ) ) {
    836                                 if ( const ast::Type * base = 
    837                                                 strict_dynamic_cast< const ast::TypeDecl * >( nt )->base 
     836                                if ( const ast::Type * base =
     837                                                strict_dynamic_cast< const ast::TypeDecl * >( nt )->base
    838838                                ) {
    839839                                        ast::CV::Qualifiers q1 = inst->qualifiers, q2 = type2->qualifiers;
     
    860860                void postvisit( const ast::ZeroType * zero ) {
    861861                        if ( ! widen.first ) return;
    862                         if ( 
     862                        if (
    863863                                dynamic_cast< const ast::BasicType * >( type2 )
    864864                                || dynamic_cast< const ast::PointerType * >( type2 )
     
    870870                                }
    871871                        } else if ( widen.second && dynamic_cast< const ast::OneType * >( type2 ) ) {
    872                                 result = new ast::BasicType{ 
     872                                result = new ast::BasicType{
    873873                                        ast::BasicType::SignedInt, zero->qualifiers | type2->qualifiers };
    874874                        }
     
    877877                void postvisit( const ast::OneType * one ) {
    878878                        if ( ! widen.first ) return;
    879                         if ( 
     879                        if (
    880880                                dynamic_cast< const ast::BasicType * >( type2 )
    881881                                || dynamic_cast< const ast::EnumInstType * >( type2 )
     
    886886                                }
    887887                        } else if ( widen.second && dynamic_cast< const ast::ZeroType * >( type2 ) ) {
    888                                 result = new ast::BasicType{ 
     888                                result = new ast::BasicType{
    889889                                        ast::BasicType::SignedInt, one->qualifiers | type2->qualifiers };
    890890                        }
     
    894894
    895895        namespace {
    896                 ast::ptr< ast::Type > handleReference( 
    897                         const ast::ptr< ast::Type > & t1, const ast::ptr< ast::Type > & t2, WidenMode widen, 
    898                         const ast::SymbolTable & symtab, ast::TypeEnvironment & env, 
    899                         const ast::OpenVarSet & open 
     896                ast::ptr< ast::Type > handleReference(
     897                        const ast::ptr< ast::Type > & t1, const ast::ptr< ast::Type > & t2, WidenMode widen,
     898                        const ast::SymbolTable & symtab, ast::TypeEnvironment & env,
     899                        const ast::OpenVarSet & open
    900900                ) {
    901901                        ast::ptr<ast::Type> common;
     
    926926
    927927        ast::ptr< ast::Type > commonType(
    928                         const ast::ptr< ast::Type > & type1, const ast::ptr< ast::Type > & type2, 
    929                         WidenMode widen, const ast::SymbolTable & symtab, ast::TypeEnvironment & env, 
    930                         const ast::OpenVarSet & open 
     928                        const ast::ptr< ast::Type > & type1, const ast::ptr< ast::Type > & type2,
     929                        WidenMode widen, const ast::SymbolTable & symtab, ast::TypeEnvironment & env,
     930                        const ast::OpenVarSet & open
    931931        ) {
    932932                unsigned depth1 = type1->referenceDepth();
     
    940940                        const ast::ReferenceType * ref1 = type1.as< ast::ReferenceType >();
    941941                        const ast::ReferenceType * ref2 = type2.as< ast::ReferenceType >();
    942                        
     942
    943943                        if ( depth1 > depth2 ) {
    944944                                assert( ref1 );
     
    978978                                                ast::OpenVarSet newOpen{ open };
    979979
    980                                                 // force t{1,2} to be cloned if its qualifiers must be stripped, so that 
    981                                                 // type1 and type->base are left unchanged; calling convention forces 
     980                                                // force t{1,2} to be cloned if its qualifiers must be stripped, so that
     981                                                // type1 and type->base are left unchanged; calling convention forces
    982982                                                // {type1,type->base}->strong_ref >= 1
    983983                                                ast::ptr<ast::Type> t1{ type1 }, t2{ type->base };
    984984                                                reset_qualifiers( t1 );
    985985                                                reset_qualifiers( t2, q1 );
    986                                                
     986
    987987                                                if ( unifyExact( t1, t2, env, have, need, newOpen, noWiden(), symtab ) ) {
    988988                                                        result = t1;
  • src/ResolvExpr/ConversionCost.cc

    r1f1c102 rf53acdf8  
    4646#endif
    4747
    48         Cost conversionCost( Type *src, Type *dest, const SymTab::Indexer &indexer, const TypeEnvironment &env ) {
    49                 if ( TypeInstType *destAsTypeInst = dynamic_cast< TypeInstType* >( dest ) ) {
     48        Cost conversionCost( const Type * src, const Type * dest, const SymTab::Indexer &indexer, const TypeEnvironment &env ) {
     49                if ( const TypeInstType * destAsTypeInst = dynamic_cast< const TypeInstType * >( dest ) ) {
    5050                        PRINT( std::cerr << "type inst " << destAsTypeInst->name; )
    51                         if ( const EqvClass* eqvClass = env.lookup( destAsTypeInst->name ) ) {
     51                        if ( const EqvClass * eqvClass = env.lookup( destAsTypeInst->name ) ) {
    5252                                if ( eqvClass->type ) {
    5353                                        return conversionCost( src, eqvClass->type, indexer, env );
     
    5555                                        return Cost::infinity;
    5656                                }
    57                         } else if ( NamedTypeDecl *namedType = indexer.lookupType( destAsTypeInst->name ) ) {
     57                        } else if ( const NamedTypeDecl * namedType = indexer.lookupType( destAsTypeInst->name ) ) {
    5858                                PRINT( std::cerr << " found" << std::endl; )
    59                                 TypeDecl *type = dynamic_cast< TypeDecl* >( namedType );
     59                                const TypeDecl * type = dynamic_cast< const TypeDecl * >( namedType );
    6060                                // all typedefs should be gone by this point
    6161                                assert( type );
     
    7777                        PRINT( std::cerr << "compatible!" << std::endl; )
    7878                        return Cost::zero;
    79                 } else if ( dynamic_cast< VoidType* >( dest ) ) {
     79                } else if ( dynamic_cast< const VoidType * >( dest ) ) {
    8080                        return Cost::safe;
    81                 } else if ( ReferenceType * refType = dynamic_cast< ReferenceType * > ( dest ) ) {
     81                } else if ( const ReferenceType * refType = dynamic_cast< const ReferenceType * > ( dest ) ) {
    8282                        PRINT( std::cerr << "conversionCost: dest is reference" << std::endl; )
    83                         return convertToReferenceCost( src, refType, indexer, env, [](Type * t1, Type * t2, const SymTab::Indexer &, const TypeEnvironment & env ){
     83                        return convertToReferenceCost( src, refType, indexer, env, [](const Type * const t1, const Type * t2, const SymTab::Indexer &, const TypeEnvironment & env ){
    8484                                return ptrsAssignable( t1, t2, env );
    8585                        });
    8686                } else {
    87                         PassVisitor<ConversionCost> converter( 
    88                                 dest, indexer, env, 
    89                                 (Cost (*)(Type*, Type*, const SymTab::Indexer&, const TypeEnvironment&))
     87                        PassVisitor<ConversionCost> converter(
     88                                dest, indexer, env,
     89                                (Cost (*)(const Type *, const Type *, const SymTab::Indexer&, const TypeEnvironment&))
    9090                                        conversionCost );
    9191                        src->accept( converter );
     
    9898        }
    9999
    100         Cost convertToReferenceCost( Type * src, Type * dest, int diff, const SymTab::Indexer & indexer, const TypeEnvironment & env, PtrsFunction func ) {
     100        Cost convertToReferenceCost( const Type * src, const Type * dest, int diff, const SymTab::Indexer & indexer, const TypeEnvironment & env, PtrsFunction func ) {
    101101                PRINT( std::cerr << "convert to reference cost... diff " << diff << " " << src << " / " << dest << std::endl; )
    102102                if ( diff > 0 ) {
    103103                        // TODO: document this
    104                         Cost cost = convertToReferenceCost( strict_dynamic_cast< ReferenceType * >( src )->base, dest, diff-1, indexer, env, func );
     104                        Cost cost = convertToReferenceCost( strict_dynamic_cast< const ReferenceType * >( src )->base, dest, diff-1, indexer, env, func );
    105105                        cost.incReference();
    106106                        return cost;
    107107                } else if ( diff < -1 ) {
    108108                        // TODO: document this
    109                         Cost cost = convertToReferenceCost( src, strict_dynamic_cast< ReferenceType * >( dest )->base, diff+1, indexer, env, func );
     109                        Cost cost = convertToReferenceCost( src, strict_dynamic_cast< const ReferenceType * >( dest )->base, diff+1, indexer, env, func );
    110110                        cost.incReference();
    111111                        return cost;
    112112                } else if ( diff == 0 ) {
    113                         ReferenceType * srcAsRef = dynamic_cast< ReferenceType * >( src );
    114                         ReferenceType * destAsRef = dynamic_cast< ReferenceType * >( dest );
     113                        const ReferenceType * srcAsRef = dynamic_cast< const ReferenceType * >( src );
     114                        const ReferenceType * destAsRef = dynamic_cast< const ReferenceType * >( dest );
    115115                        if ( srcAsRef && destAsRef ) { // pointer-like conversions between references
    116116                                PRINT( std::cerr << "converting between references" << std::endl; )
    117                                 Type::Qualifiers tq1 = srcAsRef->base->get_qualifiers();
    118                                 Type::Qualifiers tq2 = destAsRef->base->get_qualifiers();
     117                                Type::Qualifiers tq1 = srcAsRef->base->tq;
     118                                Type::Qualifiers tq2 = destAsRef->base->tq;
    119119                                if ( tq1 <= tq2 && typesCompatibleIgnoreQualifiers( srcAsRef->base, destAsRef->base, indexer, env ) ) {
    120120                                        PRINT( std::cerr << " :: compatible and good qualifiers" << std::endl; )
     
    137137                        } else {
    138138                                PRINT( std::cerr << "reference to rvalue conversion" << std::endl; )
    139                                 PassVisitor<ConversionCost> converter( 
    140                                         dest, indexer, env, 
    141                                         (Cost (*)(Type*, Type*, const SymTab::Indexer&, const TypeEnvironment&))
     139                                PassVisitor<ConversionCost> converter(
     140                                        dest, indexer, env,
     141                                        (Cost (*)(const Type *, const Type *, const SymTab::Indexer&, const TypeEnvironment&))
    142142                                                conversionCost );
    143143                                src->accept( converter );
     
    145145                        } // if
    146146                } else {
    147                         ReferenceType * destAsRef = dynamic_cast< ReferenceType * >( dest );
     147                        const ReferenceType * destAsRef = dynamic_cast< const ReferenceType * >( dest );
    148148                        assert( diff == -1 && destAsRef );
    149149                        PRINT( std::cerr << "dest is: " << dest << " / src is: " << src << std::endl; )
     
    156156                                        )
    157157                                        // lvalue-to-reference conversion:  cv lvalue T => cv T &
    158                                         if ( src->get_qualifiers() == destAsRef->base->get_qualifiers() ) {
     158                                        if ( src->tq == destAsRef->base->tq ) {
    159159                                                return Cost::reference; // cost needs to be non-zero to add cast
    160                                         } if ( src->get_qualifiers() < destAsRef->base->get_qualifiers() ) {
     160                                        } if ( src->tq < destAsRef->base->tq ) {
    161161                                                return Cost::safe; // cost needs to be higher than previous cast to differentiate adding qualifiers vs. keeping same
    162162                                        } else {
     
    178178        }
    179179
    180         Cost convertToReferenceCost( Type * src, ReferenceType * dest, const SymTab::Indexer & indexer, const TypeEnvironment & env, PtrsFunction func ) {
     180        Cost convertToReferenceCost( const Type * src, const ReferenceType * dest, const SymTab::Indexer & indexer, const TypeEnvironment & env, PtrsFunction func ) {
    181181                int sdepth = src->referenceDepth(), ddepth = dest->referenceDepth();
    182182                Cost cost = convertToReferenceCost( src, dest, sdepth-ddepth, indexer, env, func );
     
    185185        }
    186186
    187         ConversionCost::ConversionCost( Type *dest, const SymTab::Indexer &indexer, const TypeEnvironment &env, CostFunction costFunc )
     187        ConversionCost::ConversionCost( const Type * dest, const SymTab::Indexer &indexer, const TypeEnvironment &env, CostFunction costFunc )
    188188                : dest( dest ), indexer( indexer ), cost( Cost::infinity ), env( env ), costFunc( costFunc ) {
    189189        }
     
    193193        /* EXTENDED INTEGRAL RANK HIERARCHY (root to leaves)
    194194                                 _Bool
    195         char                signed char         unsigned char       
    196                   signed short int         unsigned short int       
    197                   signed int               unsigned int             
    198                   signed long int          unsigned long int       
    199                   signed long long int     unsigned long long int   
    200                   __int128                 unsigned __int128       
    201                   _Float16                 _Float16 _Complex       
    202                   _Float32                 _Float32 _Complex       
    203                   float                    float _Complex           
    204                   _Float32x                _Float32x _Complex       
    205                   _Float64                 _Float64 _Complex       
    206                   double                   double _Complex         
    207                   _Float64x                _Float64x _Complex       
     195        char                signed char         unsigned char
     196                  signed short int         unsigned short int
     197                  signed int               unsigned int
     198                  signed long int          unsigned long int
     199                  signed long long int     unsigned long long int
     200                  __int128                 unsigned __int128
     201                  _Float16                 _Float16 _Complex
     202                  _Float32                 _Float32 _Complex
     203                  float                    float _Complex
     204                  _Float32x                _Float32x _Complex
     205                  _Float64                 _Float64 _Complex
     206                  double                   double _Complex
     207                  _Float64x                _Float64x _Complex
    208208                             __float80
    209                   _Float128                _Float128 _Complex       
     209                  _Float128                _Float128 _Complex
    210210                            __float128
    211                   long double              long double _Complex     
    212                   _Float128x               _Float128x _Complex     
     211                  long double              long double _Complex
     212                  _Float128x               _Float128x _Complex
    213213        */
    214214        // GENERATED END
     
    218218        static const int costMatrix[BasicType::NUMBER_OF_BASIC_TYPES][BasicType::NUMBER_OF_BASIC_TYPES] = { // path length from root to node
    219219                /*             B    C   SC   UC   SI  SUI    I   UI   LI  LUI  LLI LLUI   IB  UIB  _FH  _FH   _F  _FC    F   FC  _FX _FXC   FD _FDC    D   DC F80X_FDXC  F80  _FB_FLDC   FB   LD  LDC _FBX_FLDXC */
    220                 /*     B*/ {   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  11,  12,  12,  13,  13,  14,  14,  15,  15,  16,  17,  16,  18,  17, },
    221                 /*     C*/ {  -1,   0,   1,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  11,  12,  12,  13,  13,  14,  14,  15,  16,  15,  17,  16, },
    222                 /*    SC*/ {  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  11,  12,  12,  13,  13,  14,  14,  15,  16,  15,  17,  16, },
    223                 /*    UC*/ {  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  11,  12,  12,  13,  13,  14,  14,  15,  16,  15,  17,  16, },
    224                 /*    SI*/ {  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  11,  12,  12,  13,  13,  14,  15,  14,  16,  15, },
    225                 /*   SUI*/ {  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  11,  12,  12,  13,  13,  14,  15,  14,  16,  15, },
    226                 /*     I*/ {  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  11,  12,  12,  13,  14,  13,  15,  14, },
    227                 /*    UI*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  11,  12,  12,  13,  14,  13,  15,  14, },
    228                 /*    LI*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  11,  12,  13,  12,  14,  13, },
    229                 /*   LUI*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  11,  12,  13,  12,  14,  13, },
    230                 /*   LLI*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  12,  11,  13,  12, },
    231                 /*  LLUI*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  12,  11,  13,  12, },
    232                 /*    IB*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  11,  10,  12,  11, },
    233                 /*   UIB*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  11,  10,  12,  11, },
    234                 /*   _FH*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,  10,   9,  11,  10, },
    235                 /*   _FH*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   1,  -1,   2,  -1,   3,  -1,   4,  -1,   5,  -1,   6,  -1,  -1,   7,  -1,  -1,   8,  -1,   9, },
    236                 /*    _F*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   9,   8,  10,   9, },
    237                 /*   _FC*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   1,  -1,   2,  -1,   3,  -1,   4,  -1,   5,  -1,  -1,   6,  -1,  -1,   7,  -1,   8, },
    238                 /*     F*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   8,   7,   9,   8, },
    239                 /*    FC*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   1,  -1,   2,  -1,   3,  -1,   4,  -1,  -1,   5,  -1,  -1,   6,  -1,   7, },
    240                 /*   _FX*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   7,   6,   8,   7, },
    241                 /*  _FXC*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   1,  -1,   2,  -1,   3,  -1,  -1,   4,  -1,  -1,   5,  -1,   6, },
    242                 /*    FD*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   6,   5,   7,   6, },
    243                 /*  _FDC*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   1,  -1,   2,  -1,  -1,   3,  -1,  -1,   4,  -1,   5, },
    244                 /*     D*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   5,   4,   6,   5, },
    245                 /*    DC*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   1,  -1,  -1,   2,  -1,  -1,   3,  -1,   4, },
    246                 /*  F80X*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   4,   3,   5,   4, },
    247                 /* _FDXC*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,  -1,   1,  -1,  -1,   2,  -1,   3, },
     220                /*     B */ {   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  11,  12,  12,  13,  13,  14,  14,  15,  15,  16,  17,  16,  18,  17, },
     221                /*     C */ {  -1,   0,   1,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  11,  12,  12,  13,  13,  14,  14,  15,  16,  15,  17,  16, },
     222                /*    SC */ {  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  11,  12,  12,  13,  13,  14,  14,  15,  16,  15,  17,  16, },
     223                /*    UC */ {  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  11,  12,  12,  13,  13,  14,  14,  15,  16,  15,  17,  16, },
     224                /*    SI */ {  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  11,  12,  12,  13,  13,  14,  15,  14,  16,  15, },
     225                /*   SUI */ {  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  11,  12,  12,  13,  13,  14,  15,  14,  16,  15, },
     226                /*     I */ {  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  11,  12,  12,  13,  14,  13,  15,  14, },
     227                /*    UI */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  11,  12,  12,  13,  14,  13,  15,  14, },
     228                /*    LI */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  11,  12,  13,  12,  14,  13, },
     229                /*   LUI */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  11,  12,  13,  12,  14,  13, },
     230                /*   LLI */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  12,  11,  13,  12, },
     231                /*  LLUI */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  10,  11,  12,  11,  13,  12, },
     232                /*    IB */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  11,  10,  12,  11, },
     233                /*   UIB */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,   9,  10,  11,  10,  12,  11, },
     234                /*   _FH */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   8,   9,  10,   9,  11,  10, },
     235                /*   _FH */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   1,  -1,   2,  -1,   3,  -1,   4,  -1,   5,  -1,   6,  -1,  -1,   7,  -1,  -1,   8,  -1,   9, },
     236                /*    _F */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   7,   8,   9,   8,  10,   9, },
     237                /*   _FC */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   1,  -1,   2,  -1,   3,  -1,   4,  -1,   5,  -1,  -1,   6,  -1,  -1,   7,  -1,   8, },
     238                /*     F */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   6,   7,   8,   7,   9,   8, },
     239                /*    FC */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   1,  -1,   2,  -1,   3,  -1,   4,  -1,  -1,   5,  -1,  -1,   6,  -1,   7, },
     240                /*   _FX */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   5,   6,   7,   6,   8,   7, },
     241                /*  _FXC */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   1,  -1,   2,  -1,   3,  -1,  -1,   4,  -1,  -1,   5,  -1,   6, },
     242                /*    FD */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   4,   5,   6,   5,   7,   6, },
     243                /*  _FDC */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   1,  -1,   2,  -1,  -1,   3,  -1,  -1,   4,  -1,   5, },
     244                /*     D */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3,   4,   5,   4,   6,   5, },
     245                /*    DC */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   1,  -1,  -1,   2,  -1,  -1,   3,  -1,   4, },
     246                /*  F80X */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   4,   3,   5,   4, },
     247                /* _FDXC */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,  -1,   1,  -1,  -1,   2,  -1,   3, },
    248248                /*   F80*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   1,   0,   1,   2,   2,   3,   3,   4,   4, },
    249                 /*   _FB*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3, },
    250                 /* _FLDC*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,  -1,   1,  -1,   2, },
    251                 /*    FB*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   1,   0,   1,   2,   2,   3, },
    252                 /*    LD*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2, },
    253                 /*   LDC*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   1, },
    254                 /*  _FBX*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1, },
    255                 /*_FLDXC*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0, },
     249                /*   _FB */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2,   2,   3,   3, },
     250                /* _FLDC */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,  -1,   1,  -1,   2, },
     251                /*    FB */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   1,   0,   1,   2,   2,   3, },
     252                /*    LD */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   1,   2, },
     253                /*   LDC */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   1, },
     254                /*  _FBX */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1, },
     255                /* _FLDXC */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0, },
    256256        }; // costMatrix
    257257        static const int maxIntCost = 15;
    258258        // GENERATED END
    259259        static_assert(
    260                 sizeof(costMatrix)/sizeof(costMatrix[0][0]) == BasicType::NUMBER_OF_BASIC_TYPES*BasicType::NUMBER_OF_BASIC_TYPES,
     260                sizeof(costMatrix)/sizeof(costMatrix[0][0]) == BasicType::NUMBER_OF_BASIC_TYPES * BasicType::NUMBER_OF_BASIC_TYPES,
    261261                "Missing row in the cost matrix"
    262262        );
     
    266266        static const int signMatrix[BasicType::NUMBER_OF_BASIC_TYPES][BasicType::NUMBER_OF_BASIC_TYPES] = { // number of sign changes in safe conversion
    267267                /*             B    C   SC   UC   SI  SUI    I   UI   LI  LUI  LLI LLUI   IB  UIB  _FH  _FH   _F  _FC    F   FC  _FX _FXC   FD _FDC    D   DC F80X_FDXC  F80  _FB_FLDC   FB   LD  LDC _FBX_FLDXC */
    268                 /*     B*/ {   0,   0,   0,   1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    269                 /*     C*/ {  -1,   0,   0,   1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    270                 /*    SC*/ {  -1,  -1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    271                 /*    UC*/ {  -1,  -1,  -1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    272                 /*    SI*/ {  -1,  -1,  -1,  -1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    273                 /*   SUI*/ {  -1,  -1,  -1,  -1,  -1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    274                 /*     I*/ {  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    275                 /*    UI*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    276                 /*    LI*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    277                 /*   LUI*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    278                 /*   LLI*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    279                 /*  LLUI*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    280                 /*    IB*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    281                 /*   UIB*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    282                 /*   _FH*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    283                 /*   _FH*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   0,  -1,   0,  -1,   0,  -1,   0,  -1,   0,  -1,   0,  -1,  -1,   0,  -1,  -1,   0,  -1,   0, },
    284                 /*    _F*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    285                 /*   _FC*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   0,  -1,   0,  -1,   0,  -1,   0,  -1,   0,  -1,  -1,   0,  -1,  -1,   0,  -1,   0, },
    286                 /*     F*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    287                 /*    FC*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   0,  -1,   0,  -1,   0,  -1,   0,  -1,  -1,   0,  -1,  -1,   0,  -1,   0, },
    288                 /*   _FX*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    289                 /*  _FXC*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   0,  -1,   0,  -1,   0,  -1,  -1,   0,  -1,  -1,   0,  -1,   0, },
    290                 /*    FD*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    291                 /*  _FDC*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   0,  -1,   0,  -1,  -1,   0,  -1,  -1,   0,  -1,   0, },
    292                 /*     D*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    293                 /*    DC*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   0,  -1,  -1,   0,  -1,  -1,   0,  -1,   0, },
    294                 /*  F80X*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    295                 /* _FDXC*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,  -1,   0,  -1,  -1,   0,  -1,   0, },
     268                /*     B */ {   0,   0,   0,   1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     269                /*     C */ {  -1,   0,   0,   1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     270                /*    SC */ {  -1,  -1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     271                /*    UC */ {  -1,  -1,  -1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     272                /*    SI */ {  -1,  -1,  -1,  -1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     273                /*   SUI */ {  -1,  -1,  -1,  -1,  -1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     274                /*     I */ {  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   0,   1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     275                /*    UI */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     276                /*    LI */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     277                /*   LUI */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     278                /*   LLI */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     279                /*  LLUI */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     280                /*    IB */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     281                /*   UIB */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     282                /*   _FH */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     283                /*   _FH */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   0,  -1,   0,  -1,   0,  -1,   0,  -1,   0,  -1,   0,  -1,  -1,   0,  -1,  -1,   0,  -1,   0, },
     284                /*    _F */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     285                /*   _FC */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   0,  -1,   0,  -1,   0,  -1,   0,  -1,   0,  -1,  -1,   0,  -1,  -1,   0,  -1,   0, },
     286                /*     F */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     287                /*    FC */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   0,  -1,   0,  -1,   0,  -1,   0,  -1,  -1,   0,  -1,  -1,   0,  -1,   0, },
     288                /*   _FX */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     289                /*  _FXC */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   0,  -1,   0,  -1,   0,  -1,  -1,   0,  -1,  -1,   0,  -1,   0, },
     290                /*    FD */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     291                /*  _FDC */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   0,  -1,   0,  -1,  -1,   0,  -1,  -1,   0,  -1,   0, },
     292                /*     D */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     293                /*    DC */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   0,  -1,  -1,   0,  -1,  -1,   0,  -1,   0, },
     294                /*  F80X */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
     295                /* _FDXC */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,  -1,   0,  -1,  -1,   0,  -1,   0, },
    296296                /*   F80*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0,   0,   0,   0, },
    297                 /*   _FB*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0,   0, },
    298                 /* _FLDC*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,  -1,   0,  -1,   0, },
    299                 /*    FB*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0, },
    300                 /*    LD*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0, },
    301                 /*   LDC*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   0, },
    302                 /*  _FBX*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0, },
    303                 /*_FLDXC*/ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0, },
     297                /*   _FB */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0,   0, },
     298                /* _FLDC */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,  -1,   0,  -1,   0, },
     299                /*    FB */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0,   0,   0, },
     300                /*    LD */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0,   0,   0, },
     301                /*   LDC */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,  -1,   0, },
     302                /*  _FBX */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0,   0, },
     303                /* _FLDXC */ {  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,  -1,   0, },
    304304        }; // signMatrix
    305305        // GENERATED END
    306306        static_assert(
    307                 sizeof(signMatrix)/sizeof(signMatrix[0][0]) == BasicType::NUMBER_OF_BASIC_TYPES*BasicType::NUMBER_OF_BASIC_TYPES,
     307                sizeof(signMatrix)/sizeof(signMatrix[0][0]) == BasicType::NUMBER_OF_BASIC_TYPES * BasicType::NUMBER_OF_BASIC_TYPES,
    308308                "Missing row in the sign matrix"
    309309        );
    310310
    311         void ConversionCost::postvisit( VoidType * ) {
     311        void ConversionCost::postvisit( const VoidType * ) {
    312312                cost = Cost::infinity;
    313313        }
    314314
    315         void ConversionCost::postvisit(BasicType *basicType) {
    316                 if ( BasicType *destAsBasic = dynamic_cast< BasicType* >( dest ) ) {
    317                         int tableResult = costMatrix[ basicType->get_kind() ][ destAsBasic->get_kind() ];
     315        void ConversionCost::postvisit(const BasicType * basicType) {
     316                if ( const BasicType * destAsBasic = dynamic_cast< const BasicType * >( dest ) ) {
     317                        int tableResult = costMatrix[ basicType->kind ][ destAsBasic->kind ];
    318318                        if ( tableResult == -1 ) {
    319319                                cost = Cost::unsafe;
     
    321321                                cost = Cost::zero;
    322322                                cost.incSafe( tableResult );
    323                                 cost.incSign( signMatrix[ basicType->get_kind() ][ destAsBasic->get_kind() ] );
    324                         } // if
    325                 } else if ( dynamic_cast< EnumInstType *>( dest ) ) {
     323                                cost.incSign( signMatrix[ basicType->kind ][ destAsBasic->kind ] );
     324                        } // if
     325                } else if ( dynamic_cast< const EnumInstType * >( dest ) ) {
    326326                        // xxx - not positive this is correct, but appears to allow casting int => enum
    327327                        cost = Cost::unsafe;
     
    330330        }
    331331
    332         void ConversionCost::postvisit( PointerType * pointerType ) {
    333                 if ( PointerType *destAsPtr = dynamic_cast< PointerType* >( dest ) ) {
     332        void ConversionCost::postvisit( const PointerType * pointerType ) {
     333                if ( const PointerType * destAsPtr = dynamic_cast< const PointerType * >( dest ) ) {
    334334                        PRINT( std::cerr << pointerType << " ===> " << destAsPtr << std::endl; )
    335                         Type::Qualifiers tq1 = pointerType->base->get_qualifiers();
    336                         Type::Qualifiers tq2 = destAsPtr->base->get_qualifiers();
     335                        Type::Qualifiers tq1 = pointerType->base->tq;
     336                        Type::Qualifiers tq2 = destAsPtr->base->tq;
    337337                        if ( tq1 <= tq2 && typesCompatibleIgnoreQualifiers( pointerType->base, destAsPtr->base, indexer, env ) ) {
    338338                                PRINT( std::cerr << " :: compatible and good qualifiers" << std::endl; )
     
    363363        }
    364364
    365         void ConversionCost::postvisit( ArrayType * ) {}
    366 
    367         void ConversionCost::postvisit( ReferenceType * refType ) {
     365        void ConversionCost::postvisit( const ArrayType * ) {}
     366
     367        void ConversionCost::postvisit( const ReferenceType * refType ) {
    368368                // Note: dest can never be a reference, since it would have been caught in an earlier check
    369                 assert( ! dynamic_cast< ReferenceType * >( dest ) );
     369                assert( ! dynamic_cast< const ReferenceType * >( dest ) );
    370370                // convert reference to rvalue: cv T1 & => T2
    371371                // recursively compute conversion cost from T1 to T2.
    372372                // cv can be safely dropped because of 'implicit dereference' behavior.
    373373                cost = costFunc( refType->base, dest, indexer, env );
    374                 if ( refType->base->get_qualifiers() == dest->get_qualifiers() ) {
     374                if ( refType->base->tq == dest->tq ) {
    375375                        cost.incReference();  // prefer exact qualifiers
    376                 } else if ( refType->base->get_qualifiers() < dest->get_qualifiers() ) {
     376                } else if ( refType->base->tq < dest->tq ) {
    377377                        cost.incSafe(); // then gaining qualifiers
    378378                } else {
     
    382382        }
    383383
    384         void ConversionCost::postvisit( FunctionType * ) {}
    385 
    386         void ConversionCost::postvisit( StructInstType * inst ) {
    387                 if ( StructInstType *destAsInst = dynamic_cast< StructInstType* >( dest ) ) {
     384        void ConversionCost::postvisit( const FunctionType * ) {}
     385
     386        void ConversionCost::postvisit( const StructInstType * inst ) {
     387                if ( const StructInstType * destAsInst = dynamic_cast< const StructInstType * >( dest ) ) {
    388388                        if ( inst->name == destAsInst->name ) {
    389389                                cost = Cost::zero;
     
    392392        }
    393393
    394         void ConversionCost::postvisit( UnionInstType * inst ) {
    395                 if ( UnionInstType *destAsInst = dynamic_cast< UnionInstType* >( dest ) ) {
     394        void ConversionCost::postvisit( const UnionInstType * inst ) {
     395                if ( const UnionInstType * destAsInst = dynamic_cast< const UnionInstType * >( dest ) ) {
    396396                        if ( inst->name == destAsInst->name ) {
    397397                                cost = Cost::zero;
     
    400400        }
    401401
    402         void ConversionCost::postvisit( EnumInstType * ) {
     402        void ConversionCost::postvisit( const EnumInstType * ) {
    403403                static Type::Qualifiers q;
    404404                static BasicType integer( q, BasicType::SignedInt );
     
    409409        }
    410410
    411         void ConversionCost::postvisit( TraitInstType * ) {}
    412 
    413         void ConversionCost::postvisit( TypeInstType *inst ) {
    414                 if ( const EqvClass *eqvClass = env.lookup( inst->name ) ) {
     411        void ConversionCost::postvisit( const TraitInstType * ) {}
     412
     413        void ConversionCost::postvisit( const TypeInstType * inst ) {
     414                if ( const EqvClass * eqvClass = env.lookup( inst->name ) ) {
    415415                        cost = costFunc( eqvClass->type, dest, indexer, env );
    416                 } else if ( TypeInstType *destAsInst = dynamic_cast< TypeInstType* >( dest ) ) {
     416                } else if ( const TypeInstType * destAsInst = dynamic_cast< const TypeInstType * >( dest ) ) {
    417417                        if ( inst->name == destAsInst->name ) {
    418418                                cost = Cost::zero;
    419419                        }
    420                 } else if ( NamedTypeDecl *namedType = indexer.lookupType( inst->name ) ) {
    421                         TypeDecl *type = dynamic_cast< TypeDecl* >( namedType );
     420                } else if ( const NamedTypeDecl * namedType = indexer.lookupType( inst->name ) ) {
     421                        const TypeDecl * type = dynamic_cast< const TypeDecl * >( namedType );
    422422                        // all typedefs should be gone by this point
    423423                        assert( type );
     
    428428        }
    429429
    430         void ConversionCost::postvisit( TupleType * tupleType ) {
     430        void ConversionCost::postvisit( const TupleType * tupleType ) {
    431431                Cost c = Cost::zero;
    432                 if ( TupleType * destAsTuple = dynamic_cast< TupleType * >( dest ) ) {
     432                if ( const TupleType * destAsTuple = dynamic_cast< const TupleType * >( dest ) ) {
    433433                        std::list< Type * >::const_iterator srcIt = tupleType->types.begin();
    434434                        std::list< Type * >::const_iterator destIt = destAsTuple->types.begin();
    435435                        while ( srcIt != tupleType->types.end() && destIt != destAsTuple->types.end() ) {
    436                                 Cost newCost = costFunc( *srcIt++, *destIt++, indexer, env );
     436                                Cost newCost = costFunc( * srcIt++, * destIt++, indexer, env );
    437437                                if ( newCost == Cost::infinity ) {
    438438                                        return;
     
    448448        }
    449449
    450         void ConversionCost::postvisit( VarArgsType * ) {
    451                 if ( dynamic_cast< VarArgsType* >( dest ) ) {
    452                         cost = Cost::zero;
    453                 }
    454         }
    455 
    456         void ConversionCost::postvisit( ZeroType * ) {
    457                 if ( dynamic_cast< ZeroType * >( dest ) ) {
    458                         cost = Cost::zero;
    459                 } else if ( BasicType *destAsBasic = dynamic_cast< BasicType* >( dest ) ) {
    460                         // copied from visit(BasicType*) for signed int, but +1 for safe conversions
    461                         int tableResult = costMatrix[ BasicType::SignedInt ][ destAsBasic->get_kind() ];
     450        void ConversionCost::postvisit( const VarArgsType * ) {
     451                if ( dynamic_cast< const VarArgsType * >( dest ) ) {
     452                        cost = Cost::zero;
     453                }
     454        }
     455
     456        void ConversionCost::postvisit( const ZeroType * ) {
     457                if ( dynamic_cast< const ZeroType * >( dest ) ) {
     458                        cost = Cost::zero;
     459                } else if ( const BasicType * destAsBasic = dynamic_cast< const BasicType * >( dest ) ) {
     460                        // copied from visit(BasicType *) for signed int, but +1 for safe conversions
     461                        int tableResult = costMatrix[ BasicType::SignedInt ][ destAsBasic->kind ];
    462462                        if ( tableResult == -1 ) {
    463463                                cost = Cost::unsafe;
     
    465465                                cost = Cost::zero;
    466466                                cost.incSafe( tableResult + 1 );
    467                                 cost.incSign( signMatrix[ BasicType::SignedInt ][ destAsBasic->get_kind() ] );
    468                         } // if
    469                 } else if ( dynamic_cast< PointerType* >( dest ) ) {
     467                                cost.incSign( signMatrix[ BasicType::SignedInt ][ destAsBasic->kind ] );
     468                        } // if
     469                } else if ( dynamic_cast< const PointerType * >( dest ) ) {
    470470                        cost = Cost::zero;
    471471                        cost.incSafe( maxIntCost + 2 ); // +1 for zero_t -> int, +1 for disambiguation
     
    473473        }
    474474
    475         void ConversionCost::postvisit( OneType * ) {
    476                 if ( dynamic_cast< OneType * >( dest ) ) {
    477                         cost = Cost::zero;
    478                 } else if ( BasicType *destAsBasic = dynamic_cast< BasicType* >( dest ) ) {
    479                         // copied from visit(BasicType*) for signed int, but +1 for safe conversions
    480                         int tableResult = costMatrix[ BasicType::SignedInt ][ destAsBasic->get_kind() ];
     475        void ConversionCost::postvisit( const OneType * ) {
     476                if ( dynamic_cast< const OneType * >( dest ) ) {
     477                        cost = Cost::zero;
     478                } else if ( const BasicType * destAsBasic = dynamic_cast< const BasicType * >( dest ) ) {
     479                        // copied from visit(BasicType *) for signed int, but +1 for safe conversions
     480                        int tableResult = costMatrix[ BasicType::SignedInt ][ destAsBasic->kind ];
    481481                        if ( tableResult == -1 ) {
    482482                                cost = Cost::unsafe;
     
    484484                                cost = Cost::zero;
    485485                                cost.incSafe( tableResult + 1 );
    486                                 cost.incSign( signMatrix[ BasicType::SignedInt ][ destAsBasic->get_kind() ] );
     486                                cost.incSign( signMatrix[ BasicType::SignedInt ][ destAsBasic->kind ] );
    487487                        } // if
    488488                } // if
     
    729729                auto dstEnd = dstAsTuple->types.end();
    730730                while ( srcIt != srcEnd && dstIt != dstEnd ) {
    731                         Cost newCost = costCalc( *srcIt++, *dstIt++, symtab, env );
     731                        Cost newCost = costCalc( * srcIt++, * dstIt++, symtab, env );
    732732                        if ( newCost == Cost::infinity ) {
    733733                                return;
  • src/ResolvExpr/ConversionCost.h

    r1f1c102 rf53acdf8  
    3333        class TypeEnvironment;
    3434
    35         typedef std::function<Cost(Type *, Type *, const SymTab::Indexer &, const TypeEnvironment &)> CostFunction;
     35        typedef std::function<Cost(const Type *, const Type *, const SymTab::Indexer &, const TypeEnvironment &)> CostFunction;
    3636        struct ConversionCost : public WithShortCircuiting {
    3737          public:
    38                 ConversionCost( Type *dest, const SymTab::Indexer &indexer, const TypeEnvironment &env, CostFunction );
     38                ConversionCost( const Type * dest, const SymTab::Indexer &indexer, const TypeEnvironment &env, CostFunction );
    3939
    4040                Cost get_cost() const { return cost; }
    4141
    42                 void previsit( BaseSyntaxNode * ) { visit_children = false; }
     42                void previsit( const BaseSyntaxNode * ) { visit_children = false; }
    4343
    44                 void postvisit( VoidType * voidType );
    45                 void postvisit( BasicType * basicType );
    46                 void postvisit( PointerType * pointerType );
    47                 void postvisit( ArrayType * arrayType );
    48                 void postvisit( ReferenceType * refType );
    49                 void postvisit( FunctionType * functionType );
    50                 void postvisit( StructInstType * aggregateUseType );
    51                 void postvisit( UnionInstType * aggregateUseType );
    52                 void postvisit( EnumInstType * aggregateUseType );
    53                 void postvisit( TraitInstType * aggregateUseType );
    54                 void postvisit( TypeInstType * aggregateUseType );
    55                 void postvisit( TupleType * tupleType );
    56                 void postvisit( VarArgsType * varArgsType );
    57                 void postvisit( ZeroType * zeroType );
    58                 void postvisit( OneType * oneType );
     44                void postvisit( const VoidType * voidType );
     45                void postvisit( const BasicType * basicType );
     46                void postvisit( const PointerType * pointerType );
     47                void postvisit( const ArrayType * arrayType );
     48                void postvisit( const ReferenceType * refType );
     49                void postvisit( const FunctionType * functionType );
     50                void postvisit( const StructInstType * aggregateUseType );
     51                void postvisit( const UnionInstType * aggregateUseType );
     52                void postvisit( const EnumInstType * aggregateUseType );
     53                void postvisit( const TraitInstType * aggregateUseType );
     54                void postvisit( const TypeInstType * aggregateUseType );
     55                void postvisit( const TupleType * tupleType );
     56                void postvisit( const VarArgsType * varArgsType );
     57                void postvisit( const ZeroType * zeroType );
     58                void postvisit( const OneType * oneType );
    5959          protected:
    60                 Type *dest;
     60                const Type * dest;
    6161                const SymTab::Indexer &indexer;
    6262                Cost cost;
     
    6565        };
    6666
    67         typedef std::function<int(Type *, Type *, const SymTab::Indexer &, const TypeEnvironment &)> PtrsFunction;
    68         Cost convertToReferenceCost( Type * src, ReferenceType * dest, const SymTab::Indexer & indexer, const TypeEnvironment & env, PtrsFunction func );
     67        typedef std::function<int(const Type *, const Type *, const SymTab::Indexer &, const TypeEnvironment &)> PtrsFunction;
     68        Cost convertToReferenceCost( const Type * src, const ReferenceType * dest, const SymTab::Indexer & indexer, const TypeEnvironment & env, PtrsFunction func );
    6969
    7070// Some function pointer types, differ in return type.
  • src/ResolvExpr/PtrsAssignable.cc

    r1f1c102 rf53acdf8  
    2727namespace ResolvExpr {
    2828        struct PtrsAssignable : public WithShortCircuiting {
    29                 PtrsAssignable( Type *dest, const TypeEnvironment &env );
     29                PtrsAssignable( const Type * dest, const TypeEnvironment &env );
    3030
    3131                int get_result() const { return result; }
    3232
    33                 void previsit( Type * ) { visit_children = false; }
    34 
    35                 void postvisit( VoidType * voidType );
    36                 void postvisit( BasicType * basicType );
    37                 void postvisit( PointerType * pointerType );
    38                 void postvisit( ArrayType * arrayType );
    39                 void postvisit( FunctionType * functionType );
    40                 void postvisit( StructInstType * inst );
    41                 void postvisit( UnionInstType * inst );
    42                 void postvisit( EnumInstType * inst );
    43                 void postvisit( TraitInstType * inst );
    44                 void postvisit( TypeInstType * inst );
    45                 void postvisit( TupleType * tupleType );
    46                 void postvisit( VarArgsType * varArgsType );
    47                 void postvisit( ZeroType * zeroType );
    48                 void postvisit( OneType * oneType );
     33                void previsit( const Type * ) { visit_children = false; }
     34
     35                void postvisit( const VoidType * voidType );
     36                void postvisit( const BasicType * basicType );
     37                void postvisit( const PointerType * pointerType );
     38                void postvisit( const ArrayType * arrayType );
     39                void postvisit( const FunctionType * functionType );
     40                void postvisit( const StructInstType * inst );
     41                void postvisit( const UnionInstType * inst );
     42                void postvisit( const EnumInstType * inst );
     43                void postvisit( const TraitInstType * inst );
     44                void postvisit( const TypeInstType * inst );
     45                void postvisit( const TupleType * tupleType );
     46                void postvisit( const VarArgsType * varArgsType );
     47                void postvisit( const ZeroType * zeroType );
     48                void postvisit( const OneType * oneType );
    4949          private:
    50                 Type *dest;
     50                const Type * dest;
    5151                int result;
    5252                const TypeEnvironment &env;
    5353        };
    5454
    55         int ptrsAssignable( Type *src, Type *dest, const TypeEnvironment &env ) {
     55        int ptrsAssignable( const Type *src, const Type * dest, const TypeEnvironment &env ) {
    5656                // std::cerr << "assignable: " << src << " | " << dest << std::endl;
    57                 if ( TypeInstType *destAsTypeInst = dynamic_cast< TypeInstType* >( dest ) ) {
    58                         if ( const EqvClass *eqvClass = env.lookup( destAsTypeInst->get_name() ) ) {
     57                if ( const TypeInstType * destAsTypeInst = dynamic_cast< const TypeInstType* >( dest ) ) {
     58                        if ( const EqvClass * eqvClass = env.lookup( destAsTypeInst->get_name() ) ) {
    5959                                return ptrsAssignable( src, eqvClass->type, env );
    6060                        } // if
    6161                } // if
    62                 if ( dynamic_cast< VoidType* >( dest ) ) {
     62                if ( dynamic_cast< const VoidType* >( dest ) ) {
    6363                        // void * = T * for any T is unsafe
    6464                        // xxx - this should be safe, but that currently breaks the build
     
    7171        }
    7272
    73         PtrsAssignable::PtrsAssignable( Type *dest, const TypeEnvironment &env ) : dest( dest ), result( 0 ), env( env ) {}
    74 
    75         void PtrsAssignable::postvisit( VoidType * ) {
     73        PtrsAssignable::PtrsAssignable( const Type * dest, const TypeEnvironment &env ) : dest( dest ), result( 0 ), env( env ) {}
     74
     75        void PtrsAssignable::postvisit( const VoidType * ) {
    7676                // T * = void * is disallowed - this is a change from C, where any
    7777                // void * can be assigned or passed to a non-void pointer without a cast.
    7878        }
    7979
    80         void PtrsAssignable::postvisit( __attribute__((unused)) BasicType *basicType ) {}
    81         void PtrsAssignable::postvisit( __attribute__((unused)) PointerType *pointerType ) {}
    82         void PtrsAssignable::postvisit( __attribute__((unused)) ArrayType *arrayType ) {}
    83         void PtrsAssignable::postvisit( __attribute__((unused)) FunctionType *functionType ) {}
    84 
    85         void PtrsAssignable::postvisit(  __attribute__((unused)) StructInstType *inst ) {}
    86         void PtrsAssignable::postvisit(  __attribute__((unused)) UnionInstType *inst ) {}
    87 
    88         void PtrsAssignable::postvisit( EnumInstType * ) {
    89                 if ( dynamic_cast< BasicType* >( dest ) ) {
     80        void PtrsAssignable::postvisit( const BasicType * ) {}
     81        void PtrsAssignable::postvisit( const PointerType * ) {}
     82        void PtrsAssignable::postvisit( const ArrayType * ) {}
     83        void PtrsAssignable::postvisit( const FunctionType * ) {}
     84
     85        void PtrsAssignable::postvisit( const StructInstType * ) {}
     86        void PtrsAssignable::postvisit( const UnionInstType * ) {}
     87
     88        void PtrsAssignable::postvisit( const EnumInstType * ) {
     89                if ( dynamic_cast< const BasicType* >( dest ) ) {
    9090                        // int * = E *, etc. is safe. This isn't technically correct, as each
    9191                        // enum has one basic type that it is compatible with, an that type can
     
    9797        }
    9898
    99         void PtrsAssignable::postvisit(  __attribute__((unused)) TraitInstType *inst ) {}
    100         void PtrsAssignable::postvisit( TypeInstType *inst ) {
    101                 if ( const EqvClass *eqvClass = env.lookup( inst->get_name() ) ) {
     99        void PtrsAssignable::postvisit(  const TraitInstType * ) {}
     100        void PtrsAssignable::postvisit( const TypeInstType * inst ) {
     101                if ( const EqvClass * eqvClass = env.lookup( inst->name ) ) {
    102102                        if ( eqvClass->type ) {
    103103                                // T * = S * for any S depends on the type bound to T
     
    107107        }
    108108
    109         void PtrsAssignable::postvisit(  __attribute__((unused)) TupleType *tupleType ) {}
    110         void PtrsAssignable::postvisit(  __attribute__((unused)) VarArgsType *varArgsType ) {}
    111         void PtrsAssignable::postvisit(  __attribute__((unused)) ZeroType *zeroType ) {}
    112         void PtrsAssignable::postvisit(  __attribute__((unused)) OneType *oneType ) {}
     109        void PtrsAssignable::postvisit( const TupleType * ) {}
     110        void PtrsAssignable::postvisit( const VarArgsType * ) {}
     111        void PtrsAssignable::postvisit( const ZeroType * ) {}
     112        void PtrsAssignable::postvisit( const OneType * ) {}
    113113
    114114// TODO: Get rid of the `_new` suffix when the old version is removed.
  • src/ResolvExpr/PtrsCastable.cc

    r1f1c102 rf53acdf8  
    2929        struct PtrsCastable_old : public WithShortCircuiting  {
    3030          public:
    31                 PtrsCastable_old( Type *dest, const TypeEnvironment &env, const SymTab::Indexer &indexer );
     31                PtrsCastable_old( const Type * dest, const TypeEnvironment &env, const SymTab::Indexer &indexer );
    3232
    3333                int get_result() const { return result; }
    3434
    35                 void previsit( Type * ) { visit_children = false; }
    36 
    37                 void postvisit( VoidType * voidType );
    38                 void postvisit( BasicType * basicType );
    39                 void postvisit( PointerType * pointerType );
    40                 void postvisit( ArrayType * arrayType );
    41                 void postvisit( FunctionType * functionType );
    42                 void postvisit( StructInstType * inst );
    43                 void postvisit( UnionInstType * inst );
    44                 void postvisit( EnumInstType * inst );
    45                 void postvisit( TraitInstType * inst );
    46                 void postvisit( TypeInstType * inst );
    47                 void postvisit( TupleType * tupleType );
    48                 void postvisit( VarArgsType * varArgsType );
    49                 void postvisit( ZeroType * zeroType );
    50                 void postvisit( OneType * oneType );
     35                void previsit( const Type * ) { visit_children = false; }
     36
     37                void postvisit( const VoidType * voidType );
     38                void postvisit( const BasicType * basicType );
     39                void postvisit( const PointerType * pointerType );
     40                void postvisit( const ArrayType * arrayType );
     41                void postvisit( const FunctionType * functionType );
     42                void postvisit( const StructInstType * inst );
     43                void postvisit( const UnionInstType * inst );
     44                void postvisit( const EnumInstType * inst );
     45                void postvisit( const TraitInstType * inst );
     46                void postvisit( const TypeInstType * inst );
     47                void postvisit( const TupleType * tupleType );
     48                void postvisit( const VarArgsType * varArgsType );
     49                void postvisit( const ZeroType * zeroType );
     50                void postvisit( const OneType * oneType );
    5151          private:
    52                 Type *dest;
     52                const Type * dest;
    5353                int result;
    5454                const TypeEnvironment &env;
     
    5757
    5858        namespace {
    59                 int objectCast( Type *src, const TypeEnvironment &env, const SymTab::Indexer &indexer ) {
    60                         if ( dynamic_cast< FunctionType* >( src ) ) {
     59                int objectCast( const Type * src, const TypeEnvironment &env, const SymTab::Indexer &indexer ) {
     60                        if ( dynamic_cast< const FunctionType* >( src ) ) {
    6161                                return -1;
    62                         } else if ( TypeInstType *typeInst = dynamic_cast< TypeInstType* >( src ) ) {
    63                                 if ( NamedTypeDecl *ntDecl = indexer.lookupType( typeInst->get_name() ) ) {
    64                                         if ( TypeDecl *tyDecl = dynamic_cast< TypeDecl* >( ntDecl ) ) {
    65                                                 if ( tyDecl->get_kind() == TypeDecl::Ftype ) {
     62                        } else if ( const TypeInstType * typeInst = dynamic_cast< const TypeInstType* >( src ) ) {
     63                                if ( const NamedTypeDecl * ntDecl = indexer.lookupType( typeInst->name ) ) {
     64                                        if ( const TypeDecl * tyDecl = dynamic_cast< const TypeDecl* >( ntDecl ) ) {
     65                                                if ( tyDecl->kind == TypeDecl::Ftype ) {
    6666                                                        return -1;
    6767                                                } // if
    6868                                        } //if
    69                                 } else if ( const EqvClass *eqvClass = env.lookup( typeInst->get_name() ) ) {
     69                                } else if ( const EqvClass * eqvClass = env.lookup( typeInst->get_name() ) ) {
    7070                                        if ( eqvClass->data.kind == TypeDecl::Ftype ) {
    7171                                                return -1;
     
    7575                        return 1;
    7676                }
    77                 int functionCast( Type *src, const TypeEnvironment &env, const SymTab::Indexer &indexer ) {
     77                int functionCast( const Type * src, const TypeEnvironment &env, const SymTab::Indexer &indexer ) {
    7878                        return -1 * objectCast( src, env, indexer );  // reverse the sense of objectCast
    7979                }
    8080        }
    8181
    82         int ptrsCastable( Type *src, Type *dest, const TypeEnvironment &env, const SymTab::Indexer &indexer ) {
    83                 if ( TypeInstType *destAsTypeInst = dynamic_cast< TypeInstType* >( dest ) ) {
    84                         if ( const EqvClass *eqvClass = env.lookup( destAsTypeInst->get_name() ) ) {
     82        int ptrsCastable( const Type * src, const Type * dest, const TypeEnvironment &env, const SymTab::Indexer &indexer ) {
     83                if ( const TypeInstType * destAsTypeInst = dynamic_cast< const TypeInstType* >( dest ) ) {
     84                        if ( const EqvClass * eqvClass = env.lookup( destAsTypeInst->get_name() ) ) {
    8585                                // xxx - should this be ptrsCastable?
    8686                                return ptrsAssignable( src, eqvClass->type, env );
    8787                        } // if
    8888                } // if
    89                 if ( dynamic_cast< VoidType* >( dest ) ) {
     89                if ( dynamic_cast< const VoidType* >( dest ) ) {
    9090                        return objectCast( src, env, indexer );
    9191                } else {
     
    9696        }
    9797
    98         PtrsCastable_old::PtrsCastable_old( Type *dest, const TypeEnvironment &env, const SymTab::Indexer &indexer )
     98        PtrsCastable_old::PtrsCastable_old( const Type * dest, const TypeEnvironment &env, const SymTab::Indexer &indexer )
    9999                : dest( dest ), result( 0 ), env( env ), indexer( indexer )     {
    100100        }
    101101
    102         void PtrsCastable_old::postvisit( VoidType * ) {
    103                 result = objectCast( dest, env, indexer );
    104         }
    105 
    106         void PtrsCastable_old::postvisit( BasicType * ) {
    107                 result = objectCast( dest, env, indexer );
    108         }
    109 
    110         void PtrsCastable_old::postvisit( PointerType * ) {
    111                 result = objectCast( dest, env, indexer );
    112         }
    113 
    114         void PtrsCastable_old::postvisit( ArrayType * ) {
    115                 result = objectCast( dest, env, indexer );
    116         }
    117 
    118         void PtrsCastable_old::postvisit( FunctionType * ) {
     102        void PtrsCastable_old::postvisit( const VoidType * ) {
     103                result = objectCast( dest, env, indexer );
     104        }
     105
     106        void PtrsCastable_old::postvisit( const BasicType * ) {
     107                result = objectCast( dest, env, indexer );
     108        }
     109
     110        void PtrsCastable_old::postvisit( const PointerType * ) {
     111                result = objectCast( dest, env, indexer );
     112        }
     113
     114        void PtrsCastable_old::postvisit( const ArrayType * ) {
     115                result = objectCast( dest, env, indexer );
     116        }
     117
     118        void PtrsCastable_old::postvisit( const FunctionType * ) {
    119119                // result = -1;
    120120                result = functionCast( dest, env, indexer );
    121121        }
    122122
    123         void PtrsCastable_old::postvisit( StructInstType * ) {
    124                 result = objectCast( dest, env, indexer );
    125         }
    126 
    127         void PtrsCastable_old::postvisit( UnionInstType * ) {
    128                 result = objectCast( dest, env, indexer );
    129         }
    130 
    131         void PtrsCastable_old::postvisit( EnumInstType * ) {
    132                 if ( dynamic_cast< EnumInstType* >( dest ) ) {
     123        void PtrsCastable_old::postvisit( const StructInstType * ) {
     124                result = objectCast( dest, env, indexer );
     125        }
     126
     127        void PtrsCastable_old::postvisit( const UnionInstType * ) {
     128                result = objectCast( dest, env, indexer );
     129        }
     130
     131        void PtrsCastable_old::postvisit( const EnumInstType * ) {
     132                if ( dynamic_cast< const EnumInstType * >( dest ) ) {
    133133                        result = 1;
    134                 } else if ( BasicType *bt = dynamic_cast< BasicType* >( dest ) ) {
    135                         if ( bt->get_kind() == BasicType::SignedInt ) {
     134                } else if ( const BasicType * bt = dynamic_cast< const BasicType * >( dest ) ) {
     135                        if ( bt->kind == BasicType::SignedInt ) {
    136136                                result = 0;
    137137                        } else {
     
    143143        }
    144144
    145         void PtrsCastable_old::postvisit( TraitInstType * ) {}
    146 
    147         void PtrsCastable_old::postvisit(TypeInstType *inst ) {
     145        void PtrsCastable_old::postvisit( const TraitInstType * ) {}
     146
     147        void PtrsCastable_old::postvisit( const TypeInstType *inst ) {
    148148                //result = objectCast( inst, env, indexer ) > 0 && objectCast( dest, env, indexer ) > 0 ? 1 : -1;
    149149                result = objectCast( inst, env, indexer ) == objectCast( dest, env, indexer ) ? 1 : -1;
    150150        }
    151151
    152         void PtrsCastable_old::postvisit( TupleType * ) {
    153                 result = objectCast( dest, env, indexer );
    154         }
    155 
    156         void PtrsCastable_old::postvisit( VarArgsType * ) {
    157                 result = objectCast( dest, env, indexer );
    158         }
    159 
    160         void PtrsCastable_old::postvisit( ZeroType * ) {
    161                 result = objectCast( dest, env, indexer );
    162         }
    163 
    164         void PtrsCastable_old::postvisit( OneType * ) {
     152        void PtrsCastable_old::postvisit( const TupleType * ) {
     153                result = objectCast( dest, env, indexer );
     154        }
     155
     156        void PtrsCastable_old::postvisit( const VarArgsType * ) {
     157                result = objectCast( dest, env, indexer );
     158        }
     159
     160        void PtrsCastable_old::postvisit( const ZeroType * ) {
     161                result = objectCast( dest, env, indexer );
     162        }
     163
     164        void PtrsCastable_old::postvisit( const OneType * ) {
    165165                result = objectCast( dest, env, indexer );
    166166        }
     
    168168namespace {
    169169        // can this type be cast to an object (1 for yes, -1 for no)
    170         int objectCast( 
    171                 const ast::Type * src, const ast::TypeEnvironment & env, const ast::SymbolTable & symtab 
     170        int objectCast(
     171                const ast::Type * src, const ast::TypeEnvironment & env, const ast::SymbolTable & symtab
    172172        ) {
    173173                if ( dynamic_cast< const ast::FunctionType * >( src ) ) {
     
    191191
    192192        // can this type be cast to a function (inverse of objectCast)
    193         int functionCast( 
    194                 const ast::Type * src, const ast::TypeEnvironment & env, const ast::SymbolTable & symtab 
     193        int functionCast(
     194                const ast::Type * src, const ast::TypeEnvironment & env, const ast::SymbolTable & symtab
    195195        ) {
    196196                return -1 * objectCast( src, env, symtab );
     
    204204                int result;
    205205
    206                 PtrsCastable_new( 
     206                PtrsCastable_new(
    207207                        const ast::Type * d, const ast::TypeEnvironment & e, const ast::SymbolTable & syms )
    208208                : dst( d ), env( e ), symtab( syms ), result( 0 ) {}
     
    278278} // anonymous namespace
    279279
    280 int ptrsCastable( 
    281         const ast::Type * src, const ast::Type * dst, const ast::SymbolTable & symtab, 
    282         const ast::TypeEnvironment & env 
     280int ptrsCastable(
     281        const ast::Type * src, const ast::Type * dst, const ast::SymbolTable & symtab,
     282        const ast::TypeEnvironment & env
    283283) {
    284284        if ( auto inst = dynamic_cast< const ast::TypeInstType * >( dst ) ) {
  • src/ResolvExpr/ResolveAssertions.cc

    r1f1c102 rf53acdf8  
    99// Author           : Aaron B. Moss
    1010// Created On       : Fri Oct 05 13:46:00 2018
    11 // Last Modified By : Aaron B. Moss
    12 // Last Modified On : Fri Oct 05 13:46:00 2018
    13 // Update Count     : 1
     11// Last Modified By : Peter A. Buhr
     12// Last Modified On : Wed Jul 10 16:10:37 2019
     13// Update Count     : 2
    1414//
    1515
     
    197197                        }
    198198                        if ( i == b.size() /* && i < a.size() */ ) return 1;
    199                        
     199
    200200                        int c = a[i].compare( b[i] );
    201201                        if ( c != 0 ) return c;
     
    220220
    221221                /// Initial resolution state for an alternative
    222                 ResnState( Alternative& a, SymTab::Indexer& indexer )
     222                ResnState( Alternative & a, SymTab::Indexer & indexer )
    223223                : alt(a), need(), newNeed(), deferred(), inferred(), costs{ Cost::zero }, indexer(indexer) {
    224224                        need.swap( a.need );
     
    226226
    227227                /// Updated resolution state with new need-list
    228                 ResnState( ResnState&& o, IterateFlag )
     228                ResnState( ResnState && o, IterateFlag )
    229229                : alt(std::move(o.alt)), need(o.newNeed.begin(), o.newNeed.end()), newNeed(), deferred(),
    230230                  inferred(std::move(o.inferred)), costs(o.costs), indexer(o.indexer) {
     
    234234
    235235        /// Binds a single assertion, updating resolution state
    236         void bindAssertion( const DeclarationWithType* decl, AssertionSetValue info, Alternative& alt,
    237                         AssnCandidate& match, InferCache& inferred ) {
    238 
    239                 DeclarationWithType* candidate = match.cdata.id;
    240                 assertf( candidate->get_uniqueId(), "Assertion candidate does not have a unique ID: %s", toString( candidate ).c_str() );
    241 
    242                 Expression* varExpr = match.cdata.combine( alt.cvtCost );
     236        void bindAssertion( const DeclarationWithType * decl, AssertionSetValue info, Alternative & alt,
     237                        AssnCandidate & match, InferCache & inferred ) {
     238
     239                const DeclarationWithType * candidate = match.cdata.id;
     240                assertf( candidate->uniqueId, "Assertion candidate does not have a unique ID: %s", toString( candidate ).c_str() );
     241
     242                Expression * varExpr = match.cdata.combine( alt.cvtCost );
    243243                delete varExpr->result;
    244244                varExpr->result = match.adjType->clone();
     
    247247                // place newly-inferred assertion in proper place in cache
    248248                inferred[ info.resnSlot ][ decl->get_uniqueId() ] = ParamEntry{
    249                                 candidate->get_uniqueId(), candidate->clone(), match.adjType->clone(), decl->get_type()->clone(),
     249                                candidate->uniqueId, candidate->clone(), match.adjType->clone(), decl->get_type()->clone(),
    250250                                varExpr };
    251251        }
    252252
    253253        /// Adds a captured assertion to the symbol table
    254         void addToIndexer( AssertionSet &assertSet, SymTab::Indexer &indexer ) {
     254        void addToIndexer( AssertionSet & assertSet, SymTab::Indexer & indexer ) {
    255255                for ( auto&  i : assertSet ) {
    256256                        if ( i.second.isUsed ) {
     
    264264
    265265        /// Resolve a single assertion, in context
    266         bool resolveAssertion( AssertionItem& assn, ResnState& resn ) {
     266        bool resolveAssertion( AssertionItem & assn, ResnState & resn ) {
    267267                // skip unused assertions
    268268                if ( ! assn.info.isUsed ) return true;
     
    274274                // find the candidates that unify with the desired type
    275275                CandidateList matches;
    276                 for ( const auto& cdata : candidates ) {
    277                         DeclarationWithType* candidate = cdata.id;
     276                for ( const auto & cdata : candidates ) {
     277                        const DeclarationWithType * candidate = cdata.id;
    278278
    279279                        // build independent unification context for candidate
     
    281281                        TypeEnvironment newEnv{ resn.alt.env };
    282282                        OpenVarSet newOpenVars{ resn.alt.openVars };
    283                         Type* adjType = candidate->get_type()->clone();
     283                        Type * adjType = candidate->get_type()->clone();
    284284                        adjustExprType( adjType, newEnv, resn.indexer );
    285285                        renameTyVars( adjType );
     
    368368                std::string resKey = SymTab::Mangler::mangleType( resType );
    369369                delete resType;
    370                 return std::move( resKey );
    371         }
    372        
    373         /// Replace resnSlots with inferParams and add alternative to output list, if meets pruning 
     370                return resKey;
     371        }
     372
     373        /// Replace resnSlots with inferParams and add alternative to output list, if meets pruning
    374374        /// threshold.
    375375        void finalizeAssertions( ResnState& resn, PruneMap & pruneThresholds, AltList& out ) {
     
    406406                ResnList resns{ ResnState{ alt, root_indexer } };
    407407                ResnList new_resns{};
    408                
     408
    409409                // Pruning thresholds by result type of the output alternatives.
    410410                // Alternatives *should* be generated in sorted order, so no need to retroactively prune
  • src/ResolvExpr/Resolver.cc

    r1f1c102 rf53acdf8  
    562562                // TODO: Replace *exception type with &exception type.
    563563                if ( throwStmt->get_expr() ) {
    564                         StructDecl * exception_decl =
    565                                 indexer.lookupStruct( "__cfaabi_ehm__base_exception_t" );
     564                        const StructDecl * exception_decl = indexer.lookupStruct( "__cfaabi_ehm__base_exception_t" );
    566565                        assert( exception_decl );
    567                         Type * exceptType = new PointerType( noQualifiers, new StructInstType( noQualifiers, exception_decl ) );
     566                        Type * exceptType = new PointerType( noQualifiers, new StructInstType( noQualifiers, const_cast<StructDecl *>(exception_decl) ) );
    568567                        findSingleExpression( throwStmt->expr, exceptType, indexer );
    569568                }
     
    972971                /// Calls the CandidateFinder and finds the single best candidate
    973972                CandidateRef findUnfinishedKindExpression(
    974                         const ast::Expr * untyped, const ast::SymbolTable & symtab, const std::string & kind, 
     973                        const ast::Expr * untyped, const ast::SymbolTable & symtab, const std::string & kind,
    975974                        std::function<bool(const Candidate &)> pred = anyCandidate, ResolvMode mode = {}
    976975                ) {
     
    994993                        // produce invalid error if no candidates
    995994                        if ( candidates.empty() ) {
    996                                 SemanticError( untyped, 
    997                                         toString( "No reasonable alternatives for ", kind, (kind != "" ? " " : ""), 
     995                                SemanticError( untyped,
     996                                        toString( "No reasonable alternatives for ", kind, (kind != "" ? " " : ""),
    998997                                        "expression: ") );
    999998                        }
     
    10311030                        if ( winners.size() != 1 ) {
    10321031                                std::ostringstream stream;
    1033                                 stream << "Cannot choose between " << winners.size() << " alternatives for " 
     1032                                stream << "Cannot choose between " << winners.size() << " alternatives for "
    10341033                                        << kind << (kind != "" ? " " : "") << "expression\n";
    10351034                                ast::print( stream, untyped );
     
    10541053                struct StripCasts_new final {
    10551054                        const ast::Expr * postmutate( const ast::CastExpr * castExpr ) {
    1056                                 if ( 
    1057                                         castExpr->isGenerated 
    1058                                         && typesCompatible( castExpr->arg->result, castExpr->result ) 
     1055                                if (
     1056                                        castExpr->isGenerated
     1057                                        && typesCompatible( castExpr->arg->result, castExpr->result )
    10591058                                ) {
    10601059                                        // generated cast is the same type as its argument, remove it after keeping env
    1061                                         return ast::mutate_field( 
     1060                                        return ast::mutate_field(
    10621061                                                castExpr->arg.get(), &ast::Expr::env, castExpr->env );
    10631062                                }
     
    10881087
    10891088                /// Establish post-resolver invariants for expressions
    1090                 void finishExpr( 
    1091                         ast::ptr< ast::Expr > & expr, const ast::TypeEnvironment & env, 
     1089                void finishExpr(
     1090                        ast::ptr< ast::Expr > & expr, const ast::TypeEnvironment & env,
    10921091                        const ast::TypeSubstitution * oldenv = nullptr
    10931092                ) {
    10941093                        // set up new type substitution for expression
    1095                         ast::ptr< ast::TypeSubstitution > newenv = 
     1094                        ast::ptr< ast::TypeSubstitution > newenv =
    10961095                                 oldenv ? oldenv : new ast::TypeSubstitution{};
    10971096                        env.writeToSubstitution( *newenv.get_and_mutate() );
     
    11021101        } // anonymous namespace
    11031102
    1104                
     1103
    11051104        ast::ptr< ast::Expr > resolveInVoidContext(
    11061105                const ast::Expr * expr, const ast::SymbolTable & symtab, ast::TypeEnvironment & env
    11071106        ) {
    11081107                assertf( expr, "expected a non-null expression" );
    1109                
     1108
    11101109                // set up and resolve expression cast to void
    11111110                ast::ptr< ast::CastExpr > untyped = new ast::CastExpr{ expr };
    1112                 CandidateRef choice = findUnfinishedKindExpression( 
     1111                CandidateRef choice = findUnfinishedKindExpression(
    11131112                        untyped, symtab, "", anyCandidate, ResolvMode::withAdjustment() );
    1114                
     1113
    11151114                // a cast expression has either 0 or 1 interpretations (by language rules);
    11161115                // if 0, an exception has already been thrown, and this code will not run
     
    11221121
    11231122        namespace {
    1124                 /// Resolve `untyped` to the expression whose candidate is the best match for a `void` 
     1123                /// Resolve `untyped` to the expression whose candidate is the best match for a `void`
    11251124                /// context.
    1126                 ast::ptr< ast::Expr > findVoidExpression( 
     1125                ast::ptr< ast::Expr > findVoidExpression(
    11271126                        const ast::Expr * untyped, const ast::SymbolTable & symtab
    11281127                ) {
     
    11341133                }
    11351134
    1136                 /// resolve `untyped` to the expression whose candidate satisfies `pred` with the 
     1135                /// resolve `untyped` to the expression whose candidate satisfies `pred` with the
    11371136                /// lowest cost, returning the resolved version
    11381137                ast::ptr< ast::Expr > findKindExpression(
    1139                         const ast::Expr * untyped, const ast::SymbolTable & symtab, 
    1140                         std::function<bool(const Candidate &)> pred = anyCandidate, 
     1138                        const ast::Expr * untyped, const ast::SymbolTable & symtab,
     1139                        std::function<bool(const Candidate &)> pred = anyCandidate,
    11411140                        const std::string & kind = "", ResolvMode mode = {}
    11421141                ) {
    11431142                        if ( ! untyped ) return {};
    1144                         CandidateRef choice = 
     1143                        CandidateRef choice =
    11451144                                findUnfinishedKindExpression( untyped, symtab, kind, pred, mode );
    11461145                        finishExpr( choice->expr, choice->env, untyped->env );
     
    11491148
    11501149                /// Resolve `untyped` to the single expression whose candidate is the best match
    1151                 ast::ptr< ast::Expr > findSingleExpression( 
    1152                         const ast::Expr * untyped, const ast::SymbolTable & symtab 
     1150                ast::ptr< ast::Expr > findSingleExpression(
     1151                        const ast::Expr * untyped, const ast::SymbolTable & symtab
    11531152                ) {
    11541153                        return findKindExpression( untyped, symtab );
     
    11701169                bool hasIntegralType( const Candidate & i ) {
    11711170                        const ast::Type * type = i.expr->result;
    1172                        
     1171
    11731172                        if ( auto bt = dynamic_cast< const ast::BasicType * >( type ) ) {
    11741173                                return bt->isInteger();
    1175                         } else if ( 
    1176                                 dynamic_cast< const ast::EnumInstType * >( type ) 
     1174                        } else if (
     1175                                dynamic_cast< const ast::EnumInstType * >( type )
    11771176                                || dynamic_cast< const ast::ZeroType * >( type )
    11781177                                || dynamic_cast< const ast::OneType * >( type )
     
    11831182
    11841183                /// Resolve `untyped` as an integral expression, returning the resolved version
    1185                 ast::ptr< ast::Expr > findIntegralExpression( 
    1186                         const ast::Expr * untyped, const ast::SymbolTable & symtab 
     1184                ast::ptr< ast::Expr > findIntegralExpression(
     1185                        const ast::Expr * untyped, const ast::SymbolTable & symtab
    11871186                ) {
    11881187                        return findKindExpression( untyped, symtab, hasIntegralType, "condition" );
     
    11921191                bool isCharType( const ast::Type * t ) {
    11931192                        if ( auto bt = dynamic_cast< const ast::BasicType * >( t ) ) {
    1194                                 return bt->kind == ast::BasicType::Char 
    1195                                         || bt->kind == ast::BasicType::SignedChar 
     1193                                return bt->kind == ast::BasicType::Char
     1194                                        || bt->kind == ast::BasicType::SignedChar
    11961195                                        || bt->kind == ast::BasicType::UnsignedChar;
    11971196                        }
     
    12531252        }
    12541253
    1255         ast::ptr< ast::Init > resolveCtorInit( 
    1256                 const ast::ConstructorInit * ctorInit, const ast::SymbolTable & symtab 
     1254        ast::ptr< ast::Init > resolveCtorInit(
     1255                const ast::ConstructorInit * ctorInit, const ast::SymbolTable & symtab
    12571256        ) {
    12581257                assert( ctorInit );
     
    12611260        }
    12621261
    1263         ast::ptr< ast::Expr > resolveStmtExpr( 
    1264                 const ast::StmtExpr * stmtExpr, const ast::SymbolTable & symtab 
     1262        ast::ptr< ast::Expr > resolveStmtExpr(
     1263                const ast::StmtExpr * stmtExpr, const ast::SymbolTable & symtab
    12651264        ) {
    12661265                assert( stmtExpr );
     
    13031302
    13041303        void Resolver_new::previsit( const ast::ObjectDecl * objectDecl ) {
    1305                 // To handle initialization of routine pointers [e.g. int (*fp)(int) = foo()], 
    1306                 // class-variable `initContext` is changed multiple times because the LHS is analyzed 
    1307                 // twice. The second analysis changes `initContext` because a function type can contain 
    1308                 // object declarations in the return and parameter types. Therefore each value of 
    1309                 // `initContext` is retained so the type on the first analysis is preserved and used for 
     1304                // To handle initialization of routine pointers [e.g. int (*fp)(int) = foo()],
     1305                // class-variable `initContext` is changed multiple times because the LHS is analyzed
     1306                // twice. The second analysis changes `initContext` because a function type can contain
     1307                // object declarations in the return and parameter types. Therefore each value of
     1308                // `initContext` is retained so the type on the first analysis is preserved and used for
    13101309                // selecting the RHS.
    13111310                GuardValue( currentObject );
    13121311                currentObject = ast::CurrentObject{ objectDecl->location, objectDecl->get_type() };
    13131312                if ( inEnumDecl && dynamic_cast< const ast::EnumInstType * >( objectDecl->get_type() ) ) {
    1314                         // enumerator initializers should not use the enum type to initialize, since the 
     1313                        // enumerator initializers should not use the enum type to initialize, since the
    13151314                        // enum type is still incomplete at this point. Use `int` instead.
    1316                         currentObject = ast::CurrentObject{ 
     1315                        currentObject = ast::CurrentObject{
    13171316                                objectDecl->location, new ast::BasicType{ ast::BasicType::SignedInt } };
    13181317                }
     
    13251324        }
    13261325
    1327         const ast::StaticAssertDecl * Resolver_new::previsit( 
    1328                 const ast::StaticAssertDecl * assertDecl 
     1326        const ast::StaticAssertDecl * Resolver_new::previsit(
     1327                const ast::StaticAssertDecl * assertDecl
    13291328        ) {
    1330                 return ast::mutate_field( 
    1331                         assertDecl, &ast::StaticAssertDecl::cond, 
     1329                return ast::mutate_field(
     1330                        assertDecl, &ast::StaticAssertDecl::cond,
    13321331                        findIntegralExpression( assertDecl->cond, symtab ) );
    13331332        }
     
    13381337                        #warning should use new equivalent to Validate::SizeType rather than sizeType here
    13391338                        ast::ptr< ast::Type > sizeType = new ast::BasicType{ ast::BasicType::LongUnsignedInt };
    1340                         ast::mutate_field( 
    1341                                 type, &PtrType::dimension, 
     1339                        ast::mutate_field(
     1340                                type, &PtrType::dimension,
    13421341                                findSingleExpression( type->dimension, sizeType, symtab ) );
    13431342                }
     
    13561355                visit_children = false;
    13571356                assertf( exprStmt->expr, "ExprStmt has null expression in resolver" );
    1358                
    1359                 return ast::mutate_field( 
     1357
     1358                return ast::mutate_field(
    13601359                        exprStmt, &ast::ExprStmt::expr, findVoidExpression( exprStmt->expr, symtab ) );
    13611360        }
     
    13641363                visit_children = false;
    13651364
    1366                 asmExpr = ast::mutate_field( 
     1365                asmExpr = ast::mutate_field(
    13671366                        asmExpr, &ast::AsmExpr::operand, findVoidExpression( asmExpr->operand, symtab ) );
    1368                
     1367
    13691368                if ( asmExpr->inout ) {
    13701369                        asmExpr = ast::mutate_field(
    13711370                                asmExpr, &ast::AsmExpr::inout, findVoidExpression( asmExpr->inout, symtab ) );
    13721371                }
    1373                
     1372
    13741373                return asmExpr;
    13751374        }
     
    13881387
    13891388        const ast::WhileStmt * Resolver_new::previsit( const ast::WhileStmt * whileStmt ) {
    1390                 return ast::mutate_field( 
     1389                return ast::mutate_field(
    13911390                        whileStmt, &ast::WhileStmt::cond, findIntegralExpression( whileStmt->cond, symtab ) );
    13921391        }
     
    14091408                GuardValue( currentObject );
    14101409                switchStmt = ast::mutate_field(
    1411                         switchStmt, &ast::SwitchStmt::cond, 
     1410                        switchStmt, &ast::SwitchStmt::cond,
    14121411                        findIntegralExpression( switchStmt->cond, symtab ) );
    14131412                currentObject = ast::CurrentObject{ switchStmt->location, switchStmt->cond->result };
     
    14201419                        assertf( initAlts.size() == 1, "SwitchStmt did not correctly resolve an integral "
    14211420                                "expression." );
    1422                        
    1423                         ast::ptr< ast::Expr > untyped = 
     1421
     1422                        ast::ptr< ast::Expr > untyped =
    14241423                                new ast::CastExpr{ caseStmt->location, caseStmt->cond, initAlts.front().type };
    14251424                        ast::ptr< ast::Expr > newExpr = findSingleExpression( untyped, symtab );
    1426                        
    1427                         // case condition cannot have a cast in C, so it must be removed here, regardless of 
     1425
     1426                        // case condition cannot have a cast in C, so it must be removed here, regardless of
    14281427                        // whether it would perform a conversion.
    14291428                        if ( const ast::CastExpr * castExpr = newExpr.as< ast::CastExpr >() ) {
    14301429                                swap_and_save_env( newExpr, castExpr->arg );
    14311430                        }
    1432                        
     1431
    14331432                        caseStmt = ast::mutate_field( caseStmt, &ast::CaseStmt::cond, newExpr );
    14341433                }
     
    14431442                        ast::ptr< ast::Type > target = new ast::PointerType{ new ast::VoidType{} };
    14441443                        branchStmt = ast::mutate_field(
    1445                                 branchStmt, &ast::BranchStmt::computedTarget, 
     1444                                branchStmt, &ast::BranchStmt::computedTarget,
    14461445                                findSingleExpression( branchStmt->computedTarget, target, symtab ) );
    14471446                }
     
    14531452                if ( returnStmt->expr ) {
    14541453                        returnStmt = ast::mutate_field(
    1455                                 returnStmt, &ast::ReturnStmt::expr, 
     1454                                returnStmt, &ast::ReturnStmt::expr,
    14561455                                findSingleExpression( returnStmt->expr, functionReturn, symtab ) );
    14571456                }
     
    14621461                visit_children = false;
    14631462                if ( throwStmt->expr ) {
    1464                         const ast::StructDecl * exceptionDecl = 
     1463                        const ast::StructDecl * exceptionDecl =
    14651464                                symtab.lookupStruct( "__cfaabi_ehm__base_exception_t" );
    14661465                        assert( exceptionDecl );
    1467                         ast::ptr< ast::Type > exceptType = 
     1466                        ast::ptr< ast::Type > exceptType =
    14681467                                new ast::PointerType{ new ast::StructInstType{ exceptionDecl } };
    14691468                        throwStmt = ast::mutate_field(
    1470                                 throwStmt, &ast::ThrowStmt::expr, 
     1469                                throwStmt, &ast::ThrowStmt::expr,
    14711470                                findSingleExpression( throwStmt->expr, exceptType, symtab ) );
    14721471                }
     
    14771476                if ( catchStmt->cond ) {
    14781477                        ast::ptr< ast::Type > boolType = new ast::BasicType{ ast::BasicType::Bool };
    1479                         catchStmt = ast::mutate_field( 
    1480                                 catchStmt, &ast::CatchStmt::cond, 
     1478                        catchStmt = ast::mutate_field(
     1479                                catchStmt, &ast::CatchStmt::cond,
    14811480                                findSingleExpression( catchStmt->cond, boolType, symtab ) );
    14821481                }
     
    15061505
    15071506                        if ( clause.target.args.empty() ) {
    1508                                 SemanticError( stmt->location, 
     1507                                SemanticError( stmt->location,
    15091508                                        "Waitfor clause must have at least one mutex parameter");
    15101509                        }
    15111510
    15121511                        // Find all alternatives for all arguments in canonical form
    1513                         std::vector< CandidateFinder > argFinders = 
     1512                        std::vector< CandidateFinder > argFinders =
    15141513                                funcFinder.findSubExprs( clause.target.args );
    1515                        
     1514
    15161515                        // List all combinations of arguments
    15171516                        std::vector< CandidateList > possibilities;
     
    15191518
    15201519                        // For every possible function:
    1521                         // * try matching the arguments to the parameters, not the other way around because 
     1520                        // * try matching the arguments to the parameters, not the other way around because
    15221521                        //   more arguments than parameters
    15231522                        CandidateList funcCandidates;
     
    15261525                        for ( CandidateRef & func : funcFinder.candidates ) {
    15271526                                try {
    1528                                         auto pointerType = dynamic_cast< const ast::PointerType * >( 
     1527                                        auto pointerType = dynamic_cast< const ast::PointerType * >(
    15291528                                                func->expr->result->stripReferences() );
    15301529                                        if ( ! pointerType ) {
    1531                                                 SemanticError( stmt->location, func->expr->result.get(), 
     1530                                                SemanticError( stmt->location, func->expr->result.get(),
    15321531                                                        "candidate not viable: not a pointer type\n" );
    15331532                                        }
     
    15351534                                        auto funcType = pointerType->base.as< ast::FunctionType >();
    15361535                                        if ( ! funcType ) {
    1537                                                 SemanticError( stmt->location, func->expr->result.get(), 
     1536                                                SemanticError( stmt->location, func->expr->result.get(),
    15381537                                                        "candidate not viable: not a function type\n" );
    15391538                                        }
     
    15441543
    15451544                                                if( ! nextMutex( param, paramEnd ) ) {
    1546                                                         SemanticError( stmt->location, funcType, 
     1545                                                        SemanticError( stmt->location, funcType,
    15471546                                                                "candidate function not viable: no mutex parameters\n");
    15481547                                                }
     
    15601559                                                        ast::AssertionSet need, have;
    15611560                                                        ast::TypeEnvironment resultEnv{ func->env };
    1562                                                         // Add all type variables as open so that those not used in the 
     1561                                                        // Add all type variables as open so that those not used in the
    15631562                                                        // parameter list are still considered open
    15641563                                                        resultEnv.add( funcType->forall );
     
    15801579                                                        unsigned n_mutex_param = 0;
    15811580
    1582                                                         // For every argument of its set, check if it matches one of the 
     1581                                                        // For every argument of its set, check if it matches one of the
    15831582                                                        // parameters. The order is important
    15841583                                                        for ( auto & arg : argsList ) {
     
    15871586                                                                        // We ran out of parameters but still have arguments.
    15881587                                                                        // This function doesn't match
    1589                                                                         SemanticError( stmt->location, funcType, 
     1588                                                                        SemanticError( stmt->location, funcType,
    15901589                                                                                toString("candidate function not viable: too many mutex "
    15911590                                                                                "arguments, expected ", n_mutex_param, "\n" ) );
     
    15941593                                                                ++n_mutex_param;
    15951594
    1596                                                                 // Check if the argument matches the parameter type in the current 
     1595                                                                // Check if the argument matches the parameter type in the current
    15971596                                                                // scope
    15981597                                                                ast::ptr< ast::Type > paramType = (*param)->get_type();
    1599                                                                 if ( 
    1600                                                                         ! unify( 
    1601                                                                                 arg->expr->result, paramType, resultEnv, need, have, open, 
    1602                                                                                 symtab ) 
     1598                                                                if (
     1599                                                                        ! unify(
     1600                                                                                arg->expr->result, paramType, resultEnv, need, have, open,
     1601                                                                                symtab )
    16031602                                                                ) {
    16041603                                                                        // Type doesn't match
     
    16271626                                                                } while ( nextMutex( param, paramEnd ) );
    16281627
    1629                                                                 // We ran out of arguments but still have parameters left; this 
     1628                                                                // We ran out of arguments but still have parameters left; this
    16301629                                                                // function doesn't match
    1631                                                                 SemanticError( stmt->location, funcType, 
     1630                                                                SemanticError( stmt->location, funcType,
    16321631                                                                        toString( "candidate function not viable: too few mutex "
    16331632                                                                        "arguments, expected ", n_mutex_param, "\n" ) );
     
    16571656                        // Make sure correct number of arguments
    16581657                        if( funcCandidates.empty() ) {
    1659                                 SemanticErrorException top( stmt->location, 
     1658                                SemanticErrorException top( stmt->location,
    16601659                                        "No alternatives for function in call to waitfor" );
    16611660                                top.append( errors );
     
    16641663
    16651664                        if( argsCandidates.empty() ) {
    1666                                 SemanticErrorException top( stmt->location, 
    1667                                         "No alternatives for arguments in call to waitfor" ); 
     1665                                SemanticErrorException top( stmt->location,
     1666                                        "No alternatives for arguments in call to waitfor" );
    16681667                                top.append( errors );
    16691668                                throw top;
     
    16711670
    16721671                        if( funcCandidates.size() > 1 ) {
    1673                                 SemanticErrorException top( stmt->location, 
     1672                                SemanticErrorException top( stmt->location,
    16741673                                        "Ambiguous function in call to waitfor" );
    16751674                                top.append( errors );
     
    16861685                        // build new clause
    16871686                        ast::WaitForStmt::Clause clause2;
    1688                        
     1687
    16891688                        clause2.target.func = funcCandidates.front()->expr;
    1690                        
     1689
    16911690                        clause2.target.args.reserve( clause.target.args.size() );
    16921691                        for ( auto arg : argsCandidates.front() ) {
     
    17081707                        ast::WaitForStmt::Timeout timeout2;
    17091708
    1710                         ast::ptr< ast::Type > target = 
     1709                        ast::ptr< ast::Type > target =
    17111710                                new ast::BasicType{ ast::BasicType::LongLongUnsignedInt };
    17121711                        timeout2.time = findSingleExpression( stmt->timeout.time, target, symtab );
     
    17401739        const ast::SingleInit * Resolver_new::previsit( const ast::SingleInit * singleInit ) {
    17411740                visit_children = false;
    1742                 // resolve initialization using the possibilities as determined by the `currentObject` 
     1741                // resolve initialization using the possibilities as determined by the `currentObject`
    17431742                // cursor.
    1744                 ast::ptr< ast::Expr > untyped = new ast::UntypedInitExpr{ 
     1743                ast::ptr< ast::Expr > untyped = new ast::UntypedInitExpr{
    17451744                        singleInit->location, singleInit->value, currentObject.getOptions() };
    17461745                ast::ptr<ast::Expr> newExpr = findSingleExpression( untyped, symtab );
     
    17511750
    17521751                // discard InitExpr wrapper and retain relevant pieces.
    1753                 // `initExpr` may have inferred params in the case where the expression specialized a 
    1754                 // function pointer, and newExpr may already have inferParams of its own, so a simple 
     1752                // `initExpr` may have inferred params in the case where the expression specialized a
     1753                // function pointer, and newExpr may already have inferParams of its own, so a simple
    17551754                // swap is not sufficient
    17561755                ast::Expr::InferUnion inferred = initExpr->inferred;
     
    17581757                newExpr.get_and_mutate()->inferred.splice( std::move(inferred) );
    17591758
    1760                 // get the actual object's type (may not exactly match what comes back from the resolver 
     1759                // get the actual object's type (may not exactly match what comes back from the resolver
    17611760                // due to conversions)
    17621761                const ast::Type * initContext = currentObject.getCurrentType();
     
    17701769                                if ( auto pt = newExpr->result.as< ast::PointerType >() ) {
    17711770                                        if ( isCharType( pt->base ) ) {
    1772                                                 // strip cast if we're initializing a char[] with a char* 
     1771                                                // strip cast if we're initializing a char[] with a char*
    17731772                                                // e.g. char x[] = "hello"
    17741773                                                if ( auto ce = newExpr.as< ast::CastExpr >() ) {
     
    17931792                assert( listInit->designations.size() == listInit->initializers.size() );
    17941793                for ( unsigned i = 0; i < listInit->designations.size(); ++i ) {
    1795                         // iterate designations and initializers in pairs, moving the cursor to the current 
     1794                        // iterate designations and initializers in pairs, moving the cursor to the current
    17961795                        // designated object and resolving the initializer against that object
    17971796                        listInit = ast::mutate_field_index(
    1798                                 listInit, &ast::ListInit::designations, i, 
     1797                                listInit, &ast::ListInit::designations, i,
    17991798                                currentObject.findNext( listInit->designations[i] ) );
    18001799                        listInit = ast::mutate_field_index(
     
    18181817                ctorInit = ast::mutate_field( ctorInit, &ast::ConstructorInit::init, nullptr );
    18191818
    1820                 // intrinsic single-parameter constructors and destructors do nothing. Since this was 
    1821                 // implicitly generated, there's no way for it to have side effects, so get rid of it to 
     1819                // intrinsic single-parameter constructors and destructors do nothing. Since this was
     1820                // implicitly generated, there's no way for it to have side effects, so get rid of it to
    18221821                // clean up generated code
    18231822                if ( InitTweak::isIntrinsicSingleArgCallStmt( ctorInit->ctor ) ) {
  • src/ResolvExpr/Unify.cc

    r1f1c102 rf53acdf8  
    9797        bool unifyExact( Type *type1, Type *type2, TypeEnvironment &env, AssertionSet &needAssertions, AssertionSet &haveAssertions, const OpenVarSet &openVars, WidenMode widen, const SymTab::Indexer &indexer );
    9898
    99         bool unifyExact( 
    100                 const ast::Type * type1, const ast::Type * type2, ast::TypeEnvironment & env, 
    101                 ast::AssertionSet & need, ast::AssertionSet & have, const ast::OpenVarSet & open, 
     99        bool unifyExact(
     100                const ast::Type * type1, const ast::Type * type2, ast::TypeEnvironment & env,
     101                ast::AssertionSet & need, ast::AssertionSet & have, const ast::OpenVarSet & open,
    102102                WidenMode widen, const ast::SymbolTable & symtab );
    103103
    104         bool typesCompatible( Type *first, Type *second, const SymTab::Indexer &indexer, const TypeEnvironment &env ) {
     104        bool typesCompatible( const Type * first, const Type * second, const SymTab::Indexer & indexer, const TypeEnvironment & env ) {
    105105                TypeEnvironment newEnv;
    106106                OpenVarSet openVars, closedVars; // added closedVars
    107107                AssertionSet needAssertions, haveAssertions;
    108                 Type *newFirst = first->clone(), *newSecond = second->clone();
     108                Type * newFirst = first->clone(), * newSecond = second->clone();
    109109                env.apply( newFirst );
    110110                env.apply( newSecond );
     
    121121        }
    122122
    123         bool typesCompatible( 
    124                         const ast::Type * first, const ast::Type * second, const ast::SymbolTable & symtab, 
     123        bool typesCompatible(
     124                        const ast::Type * first, const ast::Type * second, const ast::SymbolTable & symtab,
    125125                        const ast::TypeEnvironment & env ) {
    126126                ast::TypeEnvironment newEnv;
     
    135135                findOpenVars( newSecond, open, closed, need, have, FirstOpen );
    136136
    137                 return unifyExact( 
     137                return unifyExact(
    138138                        newFirst, newSecond, newEnv, need, have, open, noWiden(), symtab );
    139139        }
    140140
    141         bool typesCompatibleIgnoreQualifiers( Type *first, Type *second, const SymTab::Indexer &indexer, const TypeEnvironment &env ) {
     141        bool typesCompatibleIgnoreQualifiers( const Type * first, const Type * second, const SymTab::Indexer &indexer, const TypeEnvironment &env ) {
    142142                TypeEnvironment newEnv;
    143143                OpenVarSet openVars;
     
    163163        }
    164164
    165         bool typesCompatibleIgnoreQualifiers( 
    166                         const ast::Type * first, const ast::Type * second, const ast::SymbolTable & symtab, 
     165        bool typesCompatibleIgnoreQualifiers(
     166                        const ast::Type * first, const ast::Type * second, const ast::SymbolTable & symtab,
    167167                        const ast::TypeEnvironment & env ) {
    168168                ast::TypeEnvironment newEnv;
    169169                ast::OpenVarSet open;
    170170                ast::AssertionSet need, have;
    171                
     171
    172172                ast::ptr<ast::Type> newFirst{ first }, newSecond{ second };
    173173                env.apply( newFirst );
     
    176176                reset_qualifiers( newSecond );
    177177
    178                 return unifyExact( 
     178                return unifyExact(
    179179                        newFirst, newSecond, newEnv, need, have, open, noWiden(), symtab );
    180180        }
     
    490490
    491491                        // sizes don't have to match if ttypes are involved; need to be more precise wrt where the ttype is to prevent errors
    492                         if ( 
    493                                         (flatFunc->parameters.size() == flatOther->parameters.size() && 
    494                                                 flatFunc->returnVals.size() == flatOther->returnVals.size()) 
    495                                         || flatFunc->isTtype() 
    496                                         || flatOther->isTtype() 
     492                        if (
     493                                        (flatFunc->parameters.size() == flatOther->parameters.size() &&
     494                                                flatFunc->returnVals.size() == flatOther->returnVals.size())
     495                                        || flatFunc->isTtype()
     496                                        || flatOther->isTtype()
    497497                        ) {
    498498                                if ( unifyDeclList( flatFunc->parameters.begin(), flatFunc->parameters.end(), flatOther->parameters.begin(), flatOther->parameters.end(), env, needAssertions, haveAssertions, openVars, indexer ) ) {
     
    711711                bool result;
    712712
    713                 Unify_new( 
    714                         const ast::Type * type2, ast::TypeEnvironment & env, ast::AssertionSet & need, 
    715                         ast::AssertionSet & have, const ast::OpenVarSet & open, WidenMode widen, 
     713                Unify_new(
     714                        const ast::Type * type2, ast::TypeEnvironment & env, ast::AssertionSet & need,
     715                        ast::AssertionSet & have, const ast::OpenVarSet & open, WidenMode widen,
    716716                        const ast::SymbolTable & symtab )
    717                 : type2(type2), tenv(env), need(need), have(have), open(open), widen(widen), 
     717                : type2(type2), tenv(env), need(need), have(have), open(open), widen(widen),
    718718                  symtab(symtab), result(false) {}
    719719
    720720                void previsit( const ast::Node * ) { visit_children = false; }
    721                
     721
    722722                void postvisit( const ast::VoidType * ) {
    723723                        result = dynamic_cast< const ast::VoidType * >( type2 );
     
    732732                void postvisit( const ast::PointerType * pointer ) {
    733733                        if ( auto pointer2 = dynamic_cast< const ast::PointerType * >( type2 ) ) {
    734                                 result = unifyExact( 
    735                                         pointer->base, pointer2->base, tenv, need, have, open, 
     734                                result = unifyExact(
     735                                        pointer->base, pointer2->base, tenv, need, have, open,
    736736                                        noWiden(), symtab );
    737737                        }
     
    742742                        if ( ! array2 ) return;
    743743
    744                         // to unify, array types must both be VLA or both not VLA and both must have a 
     744                        // to unify, array types must both be VLA or both not VLA and both must have a
    745745                        // dimension expression or not have a dimension
    746746                        if ( array->isVarLen != array2->isVarLen ) return;
    747                         if ( ! array->isVarLen && ! array2->isVarLen 
     747                        if ( ! array->isVarLen && ! array2->isVarLen
    748748                                        && array->dimension && array2->dimension ) {
    749749                                auto ce1 = array->dimension.as< ast::ConstantExpr >();
     
    751751
    752752                                // see C11 Reference Manual 6.7.6.2.6
    753                                 // two array types with size specifiers that are integer constant expressions are 
     753                                // two array types with size specifiers that are integer constant expressions are
    754754                                // compatible if both size specifiers have the same constant value
    755755                                if ( ce1 && ce2 && ce1->intValue() != ce2->intValue() ) return;
    756756                        }
    757757
    758                         result = unifyExact( 
    759                                 array->base, array2->base, tenv, need, have, open, noWiden(), 
     758                        result = unifyExact(
     759                                array->base, array2->base, tenv, need, have, open, noWiden(),
    760760                                symtab );
    761761                }
     
    763763                void postvisit( const ast::ReferenceType * ref ) {
    764764                        if ( auto ref2 = dynamic_cast< const ast::ReferenceType * >( type2 ) ) {
    765                                 result = unifyExact( 
    766                                         ref->base, ref2->base, tenv, need, have, open, noWiden(), 
     765                                result = unifyExact(
     766                                        ref->base, ref2->base, tenv, need, have, open, noWiden(),
    767767                                        symtab );
    768768                        }
     
    771771        private:
    772772                /// Replaces ttype variables with their bound types.
    773                 /// If this isn't done when satifying ttype assertions, then argument lists can have 
     773                /// If this isn't done when satifying ttype assertions, then argument lists can have
    774774                /// different size and structure when they should be compatible.
    775775                struct TtypeExpander_new : public ast::WithShortCircuiting {
     
    800800                                auto types = flatten( d->get_type() );
    801801                                for ( ast::ptr< ast::Type > & t : types ) {
    802                                         // outermost const, volatile, _Atomic qualifiers in parameters should not play 
    803                                         // a role in the unification of function types, since they do not determine 
     802                                        // outermost const, volatile, _Atomic qualifiers in parameters should not play
     803                                        // a role in the unification of function types, since they do not determine
    804804                                        // whether a function is callable.
    805                                         // NOTE: **must** consider at least mutex qualifier, since functions can be 
    806                                         // overloaded on outermost mutex and a mutex function has different 
     805                                        // NOTE: **must** consider at least mutex qualifier, since functions can be
     806                                        // overloaded on outermost mutex and a mutex function has different
    807807                                        // requirements than a non-mutex function
    808808                                        remove_qualifiers( t, ast::CV::Const | ast::CV::Volatile | ast::CV::Atomic );
     
    818818                        std::vector< ast::ptr< ast::Type > > types;
    819819                        while ( crnt != end ) {
    820                                 // it is guaranteed that a ttype variable will be bound to a flat tuple, so ensure 
     820                                // it is guaranteed that a ttype variable will be bound to a flat tuple, so ensure
    821821                                // that this results in a flat tuple
    822822                                flatten( (*crnt)->get_type(), types );
     
    829829
    830830                template< typename Iter >
    831                 static bool unifyDeclList( 
    832                         Iter crnt1, Iter end1, Iter crnt2, Iter end2, ast::TypeEnvironment & env, 
    833                         ast::AssertionSet & need, ast::AssertionSet & have, const ast::OpenVarSet & open, 
     831                static bool unifyDeclList(
     832                        Iter crnt1, Iter end1, Iter crnt2, Iter end2, ast::TypeEnvironment & env,
     833                        ast::AssertionSet & need, ast::AssertionSet & have, const ast::OpenVarSet & open,
    834834                        const ast::SymbolTable & symtab
    835835                ) {
     
    843843                                if ( isTuple1 && ! isTuple2 ) {
    844844                                        // combine remainder of list2, then unify
    845                                         return unifyExact( 
    846                                                 t1, tupleFromDecls( crnt2, end2 ), env, need, have, open, 
     845                                        return unifyExact(
     846                                                t1, tupleFromDecls( crnt2, end2 ), env, need, have, open,
    847847                                                noWiden(), symtab );
    848848                                } else if ( ! isTuple1 && isTuple2 ) {
    849849                                        // combine remainder of list1, then unify
    850                                         return unifyExact( 
    851                                                 tupleFromDecls( crnt1, end1 ), t2, env, need, have, open, 
     850                                        return unifyExact(
     851                                                tupleFromDecls( crnt1, end1 ), t2, env, need, have, open,
    852852                                                noWiden(), symtab );
    853853                                }
    854854
    855                                 if ( ! unifyExact( 
    856                                         t1, t2, env, need, have, open, noWiden(), symtab ) 
     855                                if ( ! unifyExact(
     856                                        t1, t2, env, need, have, open, noWiden(), symtab )
    857857                                ) return false;
    858858
     
    860860                        }
    861861
    862                         // May get to the end of one argument list before the other. This is only okay if the 
     862                        // May get to the end of one argument list before the other. This is only okay if the
    863863                        // other is a ttype
    864864                        if ( crnt1 != end1 ) {
     
    866866                                const ast::Type * t1 = (*crnt1)->get_type();
    867867                                if ( ! Tuples::isTtype( t1 ) ) return false;
    868                                 return unifyExact( 
    869                                         t1, tupleFromDecls( crnt2, end2 ), env, need, have, open, 
     868                                return unifyExact(
     869                                        t1, tupleFromDecls( crnt2, end2 ), env, need, have, open,
    870870                                        noWiden(), symtab );
    871871                        } else if ( crnt2 != end2 ) {
     
    873873                                const ast::Type * t2 = (*crnt2)->get_type();
    874874                                if ( ! Tuples::isTtype( t2 ) ) return false;
    875                                 return unifyExact( 
    876                                         tupleFromDecls( crnt1, end1 ), t2, env, need, have, open, 
     875                                return unifyExact(
     876                                        tupleFromDecls( crnt1, end1 ), t2, env, need, have, open,
    877877                                        noWiden(), symtab );
    878878                        }
     
    881881                }
    882882
    883                 static bool unifyDeclList( 
    884                         const std::vector< ast::ptr< ast::DeclWithType > > & list1, 
    885                         const std::vector< ast::ptr< ast::DeclWithType > > & list2, 
    886                         ast::TypeEnvironment & env, ast::AssertionSet & need, ast::AssertionSet & have, 
     883                static bool unifyDeclList(
     884                        const std::vector< ast::ptr< ast::DeclWithType > > & list1,
     885                        const std::vector< ast::ptr< ast::DeclWithType > > & list2,
     886                        ast::TypeEnvironment & env, ast::AssertionSet & need, ast::AssertionSet & have,
    887887                        const ast::OpenVarSet & open, const ast::SymbolTable & symtab
    888888                ) {
    889                         return unifyDeclList( 
    890                                 list1.begin(), list1.end(), list2.begin(), list2.end(), env, need, have, open, 
     889                        return unifyDeclList(
     890                                list1.begin(), list1.end(), list2.begin(), list2.end(), env, need, have, open,
    891891                                symtab );
    892892                }
     
    900900
    901901                /// mark all assertions in `type` used in both `assn1` and `assn2`
    902                 static void markAssertions( 
    903                         ast::AssertionSet & assn1, ast::AssertionSet & assn2, 
    904                         const ast::ParameterizedType * type 
     902                static void markAssertions(
     903                        ast::AssertionSet & assn1, ast::AssertionSet & assn2,
     904                        const ast::ParameterizedType * type
    905905                ) {
    906906                        for ( const auto & tyvar : type->forall ) {
     
    918918
    919919                        if ( func->isVarArgs != func2->isVarArgs ) return;
    920                        
    921                         // Flatten the parameter lists for both functions so that tuple structure does not 
     920
     921                        // Flatten the parameter lists for both functions so that tuple structure does not
    922922                        // affect unification. Does not actually mutate function parameters.
    923923                        auto params = flattenList( func->params, tenv );
    924924                        auto params2 = flattenList( func2->params, tenv );
    925925
    926                         // sizes don't have to match if ttypes are involved; need to be more precise w.r.t. 
     926                        // sizes don't have to match if ttypes are involved; need to be more precise w.r.t.
    927927                        // where the ttype is to prevent errors
    928                         if ( 
     928                        if (
    929929                                ( params.size() != params2.size() || func->returns.size() != func2->returns.size() )
    930930                                && ! func->isTtype()
     
    933933
    934934                        if ( ! unifyDeclList( params, params2, tenv, need, have, open, symtab ) ) return;
    935                         if ( ! unifyDeclList( 
     935                        if ( ! unifyDeclList(
    936936                                func->returns, func2->returns, tenv, need, have, open, symtab ) ) return;
    937                        
     937
    938938                        markAssertions( have, need, func );
    939939                        markAssertions( have, need, func2 );
     
    941941                        result = true;
    942942                }
    943        
     943
    944944        private:
    945945                template< typename RefType >
     
    953953                /// Creates a tuple type based on a list of TypeExpr
    954954                template< typename Iter >
    955                 static const ast::Type * tupleFromExprs( 
     955                static const ast::Type * tupleFromExprs(
    956956                        const ast::TypeExpr * param, Iter & crnt, Iter end, ast::CV::Qualifiers qs
    957957                ) {
     
    973973                        const RefType * inst2 = handleRefType( inst, other );
    974974                        if ( ! inst2 ) return;
    975                        
     975
    976976                        // check that parameters of types unify, if any
    977977                        const std::vector< ast::ptr< ast::Expr > > & params = inst->params;
     
    10021002                                }
    10031003
    1004                                 if ( ! unifyExact( 
     1004                                if ( ! unifyExact(
    10051005                                                pty, pty2, tenv, need, have, open, noWiden(), symtab ) ) {
    10061006                                        result = false;
     
    10381038        private:
    10391039                /// Creates a tuple type based on a list of Type
    1040                 static ast::ptr< ast::Type > tupleFromTypes( 
     1040                static ast::ptr< ast::Type > tupleFromTypes(
    10411041                        const std::vector< ast::ptr< ast::Type > > & tys
    10421042                ) {
    10431043                        std::vector< ast::ptr< ast::Type > > out;
    10441044                        for ( const ast::Type * ty : tys ) {
    1045                                 // it is guaranteed that a ttype variable will be bound to a flat tuple, so ensure 
     1045                                // it is guaranteed that a ttype variable will be bound to a flat tuple, so ensure
    10461046                                // that this results in a flat tuple
    10471047                                flatten( ty, out );
     
    10511051                }
    10521052
    1053                 static bool unifyList( 
    1054                         const std::vector< ast::ptr< ast::Type > > & list1, 
    1055                         const std::vector< ast::ptr< ast::Type > > & list2, ast::TypeEnvironment & env, 
    1056                         ast::AssertionSet & need, ast::AssertionSet & have, const ast::OpenVarSet & open, 
     1053                static bool unifyList(
     1054                        const std::vector< ast::ptr< ast::Type > > & list1,
     1055                        const std::vector< ast::ptr< ast::Type > > & list2, ast::TypeEnvironment & env,
     1056                        ast::AssertionSet & need, ast::AssertionSet & have, const ast::OpenVarSet & open,
    10571057                        const ast::SymbolTable & symtab
    10581058                ) {
     
    10681068                                if ( isTuple1 && ! isTuple2 ) {
    10691069                                        // combine entirety of list2, then unify
    1070                                         return unifyExact( 
    1071                                                 t1, tupleFromTypes( list2 ), env, need, have, open, 
     1070                                        return unifyExact(
     1071                                                t1, tupleFromTypes( list2 ), env, need, have, open,
    10721072                                                noWiden(), symtab );
    10731073                                } else if ( ! isTuple1 && isTuple2 ) {
    10741074                                        // combine entirety of list1, then unify
    10751075                                        return unifyExact(
    1076                                                 tupleFromTypes( list1 ), t2, env, need, have, open, 
     1076                                                tupleFromTypes( list1 ), t2, env, need, have, open,
    10771077                                                noWiden(), symtab );
    10781078                                }
    10791079
    1080                                 if ( ! unifyExact( 
    1081                                         t1, t2, env, need, have, open, noWiden(), symtab ) 
     1080                                if ( ! unifyExact(
     1081                                        t1, t2, env, need, have, open, noWiden(), symtab )
    10821082                                ) return false;
    10831083
     
    10891089                                const ast::Type * t1 = *crnt1;
    10901090                                if ( ! Tuples::isTtype( t1 ) ) return false;
    1091                                 // xxx - this doesn't generate an empty tuple, contrary to comment; both ported 
     1091                                // xxx - this doesn't generate an empty tuple, contrary to comment; both ported
    10921092                                // from Rob's code
    1093                                 return unifyExact( 
    1094                                                 t1, tupleFromTypes( list2 ), env, need, have, open, 
     1093                                return unifyExact(
     1094                                                t1, tupleFromTypes( list2 ), env, need, have, open,
    10951095                                                noWiden(), symtab );
    10961096                        } else if ( crnt2 != list2.end() ) {
     
    10981098                                const ast::Type * t2 = *crnt2;
    10991099                                if ( ! Tuples::isTtype( t2 ) ) return false;
    1100                                 // xxx - this doesn't generate an empty tuple, contrary to comment; both ported 
     1100                                // xxx - this doesn't generate an empty tuple, contrary to comment; both ported
    11011101                                // from Rob's code
    11021102                                return unifyExact(
    1103                                                 tupleFromTypes( list1 ), t2, env, need, have, open, 
     1103                                                tupleFromTypes( list1 ), t2, env, need, have, open,
    11041104                                                noWiden(), symtab );
    11051105                        }
     
    11331133                void postvisit( const ast::OneType * ) {
    11341134                        result = dynamic_cast< const ast::OneType * >( type2 );
    1135                 }       
     1135                }
    11361136
    11371137          private:
     
    11401140        };
    11411141
    1142         bool unify( 
    1143                         const ast::ptr<ast::Type> & type1, const ast::ptr<ast::Type> & type2, 
    1144                         ast::TypeEnvironment & env, ast::AssertionSet & need, ast::AssertionSet & have, 
     1142        bool unify(
     1143                        const ast::ptr<ast::Type> & type1, const ast::ptr<ast::Type> & type2,
     1144                        ast::TypeEnvironment & env, ast::AssertionSet & need, ast::AssertionSet & have,
    11451145                        ast::OpenVarSet & open, const ast::SymbolTable & symtab
    11461146        ) {
     
    11491149        }
    11501150
    1151         bool unify( 
    1152                         const ast::ptr<ast::Type> & type1, const ast::ptr<ast::Type> & type2, 
    1153                         ast::TypeEnvironment & env, ast::AssertionSet & need, ast::AssertionSet & have, 
    1154                         ast::OpenVarSet & open, const ast::SymbolTable & symtab, ast::ptr<ast::Type> & common 
     1151        bool unify(
     1152                        const ast::ptr<ast::Type> & type1, const ast::ptr<ast::Type> & type2,
     1153                        ast::TypeEnvironment & env, ast::AssertionSet & need, ast::AssertionSet & have,
     1154                        ast::OpenVarSet & open, const ast::SymbolTable & symtab, ast::ptr<ast::Type> & common
    11551155        ) {
    11561156                ast::OpenVarSet closed;
    11571157                findOpenVars( type1, open, closed, need, have, FirstClosed );
    11581158                findOpenVars( type2, open, closed, need, have, FirstOpen );
    1159                 return unifyInexact( 
     1159                return unifyInexact(
    11601160                        type1, type2, env, need, have, open, WidenMode{ true, true }, symtab, common );
    11611161        }
    11621162
    1163         bool unifyExact( 
    1164                         const ast::Type * type1, const ast::Type * type2, ast::TypeEnvironment & env, 
    1165                         ast::AssertionSet & need, ast::AssertionSet & have, const ast::OpenVarSet & open, 
     1163        bool unifyExact(
     1164                        const ast::Type * type1, const ast::Type * type2, ast::TypeEnvironment & env,
     1165                        ast::AssertionSet & need, ast::AssertionSet & have, const ast::OpenVarSet & open,
    11661166                        WidenMode widen, const ast::SymbolTable & symtab
    11671167        ) {
     
    11701170                auto var1 = dynamic_cast< const ast::TypeInstType * >( type1 );
    11711171                auto var2 = dynamic_cast< const ast::TypeInstType * >( type2 );
    1172                 ast::OpenVarSet::const_iterator 
    1173                         entry1 = var1 ? open.find( var1->name ) : open.end(), 
     1172                ast::OpenVarSet::const_iterator
     1173                        entry1 = var1 ? open.find( var1->name ) : open.end(),
    11741174                        entry2 = var2 ? open.find( var2->name ) : open.end();
    11751175                bool isopen1 = entry1 != open.end();
     
    11781178                if ( isopen1 && isopen2 ) {
    11791179                        if ( entry1->second.kind != entry2->second.kind ) return false;
    1180                         return env.bindVarToVar( 
    1181                                 var1, var2, ast::TypeDecl::Data{ entry1->second, entry2->second }, need, have, 
     1180                        return env.bindVarToVar(
     1181                                var1, var2, ast::TypeDecl::Data{ entry1->second, entry2->second }, need, have,
    11821182                                open, widen, symtab );
    11831183                } else if ( isopen1 ) {
     
    11921192        }
    11931193
    1194         bool unifyInexact( 
    1195                         const ast::ptr<ast::Type> & type1, const ast::ptr<ast::Type> & type2, 
    1196                         ast::TypeEnvironment & env, ast::AssertionSet & need, ast::AssertionSet & have, 
    1197                         const ast::OpenVarSet & open, WidenMode widen, const ast::SymbolTable & symtab, 
    1198                         ast::ptr<ast::Type> & common 
     1194        bool unifyInexact(
     1195                        const ast::ptr<ast::Type> & type1, const ast::ptr<ast::Type> & type2,
     1196                        ast::TypeEnvironment & env, ast::AssertionSet & need, ast::AssertionSet & have,
     1197                        const ast::OpenVarSet & open, WidenMode widen, const ast::SymbolTable & symtab,
     1198                        ast::ptr<ast::Type> & common
    11991199        ) {
    12001200                ast::CV::Qualifiers q1 = type1->qualifiers, q2 = type2->qualifiers;
    1201                
    1202                 // force t1 and t2 to be cloned if their qualifiers must be stripped, so that type1 and 
     1201
     1202                // force t1 and t2 to be cloned if their qualifiers must be stripped, so that type1 and
    12031203                // type2 are left unchanged; calling convention forces type{1,2}->strong_ref >= 1
    12041204                ast::ptr<ast::Type> t1{ type1 }, t2{ type2 };
    12051205                reset_qualifiers( t1 );
    12061206                reset_qualifiers( t2 );
    1207                
     1207
    12081208                if ( unifyExact( t1, t2, env, need, have, open, widen, symtab ) ) {
    12091209                        t1 = nullptr; t2 = nullptr; // release t1, t2 to avoid spurious clones
  • src/ResolvExpr/typeops.h

    r1f1c102 rf53acdf8  
    2828#include "SynTree/SynTree.h"
    2929#include "SynTree/Type.h"
    30 #include "SymTab/Indexer.h"
     30
     31namespace SymTab {
     32        class Indexer;
     33}
    3134
    3235namespace ResolvExpr {
     
    6063        // in AdjustExprType.cc
    6164        /// Replaces array types with the equivalent pointer, and function types with a pointer-to-function
    62         void adjustExprType( Type *&type, const TypeEnvironment &env, const SymTab::Indexer &indexer );
     65        void adjustExprType( Type *& type, const TypeEnvironment & env, const SymTab::Indexer & indexer );
    6366
    6467        /// Replaces array types with the equivalent pointer, and function types with a pointer-to-function using empty TypeEnvironment and Indexer
     
    6669
    6770        template< typename ForwardIterator >
    68         void adjustExprTypeList( ForwardIterator begin, ForwardIterator end, const TypeEnvironment &env, const SymTab::Indexer &indexer ) {
     71        void adjustExprTypeList( ForwardIterator begin, ForwardIterator end, const TypeEnvironment & env, const SymTab::Indexer & indexer ) {
    6972                while ( begin != end ) {
    7073                        adjustExprType( *begin++, env, indexer );
     
    7376
    7477        /// Replaces array types with equivalent pointer, and function types with a pointer-to-function
    75         const ast::Type * adjustExprType( 
     78        const ast::Type * adjustExprType(
    7679                const ast::Type * type, const ast::TypeEnvironment & env, const ast::SymbolTable & symtab );
    7780
    7881        // in CastCost.cc
    79         Cost castCost( Type *src, Type *dest, const SymTab::Indexer &indexer, const TypeEnvironment &env );
    80         Cost castCost( 
    81                 const ast::Type * src, const ast::Type * dst, const ast::SymbolTable & symtab, 
     82        Cost castCost( const Type * src, const Type * dest, const SymTab::Indexer & indexer, const TypeEnvironment & env );
     83        Cost castCost(
     84                const ast::Type * src, const ast::Type * dst, const ast::SymbolTable & symtab,
    8285                const ast::TypeEnvironment & env );
    8386
    8487        // in ConversionCost.cc
    85         Cost conversionCost( Type *src, Type *dest, const SymTab::Indexer &indexer, const TypeEnvironment &env );
    86         Cost conversionCost( 
    87                 const ast::Type * src, const ast::Type * dst, const ast::SymbolTable & symtab, 
     88        Cost conversionCost( const Type * src, const Type * dest, const SymTab::Indexer & indexer, const TypeEnvironment & env );
     89        Cost conversionCost(
     90                const ast::Type * src, const ast::Type * dst, const ast::SymbolTable & symtab,
    8891                const ast::TypeEnvironment & env );
    8992
    9093        // in AlternativeFinder.cc
    91         Cost computeConversionCost( Type *actualType, Type *formalType,
    92                 const SymTab::Indexer &indexer, const TypeEnvironment &env );
     94        Cost computeConversionCost( Type * actualType, Type * formalType,
     95                const SymTab::Indexer & indexer, const TypeEnvironment & env );
    9396
    9497        // in PtrsAssignable.cc
    95         int ptrsAssignable( Type *src, Type *dest, const TypeEnvironment &env );
     98        int ptrsAssignable( const Type * src, const Type * dest, const TypeEnvironment & env );
    9699        int ptrsAssignable( const ast::Type * src, const ast::Type * dst,
    97100                const ast::TypeEnvironment & env );
    98101
    99102        // in PtrsCastable.cc
    100         int ptrsCastable( Type *src, Type *dest, const TypeEnvironment &env, const SymTab::Indexer &indexer );
    101         int ptrsCastable( 
    102                 const ast::Type * src, const ast::Type * dst, const ast::SymbolTable & symtab, 
     103        int ptrsCastable( const Type * src, const Type * dest, const TypeEnvironment & env, const SymTab::Indexer & indexer );
     104        int ptrsCastable(
     105                const ast::Type * src, const ast::Type * dst, const ast::SymbolTable & symtab,
    103106                const ast::TypeEnvironment & env );
    104107
    105108        // in Unify.cc
    106         bool typesCompatible( Type *, Type *, const SymTab::Indexer &indexer, const TypeEnvironment &env );
    107         bool typesCompatibleIgnoreQualifiers( Type *, Type *, const SymTab::Indexer &indexer, const TypeEnvironment &env );
    108 
    109         inline bool typesCompatible( Type *t1, Type *t2, const SymTab::Indexer &indexer ) {
     109        bool typesCompatible( const Type *, const Type *, const SymTab::Indexer & indexer, const TypeEnvironment & env );
     110        bool typesCompatibleIgnoreQualifiers( const Type *, const Type *, const SymTab::Indexer & indexer, const TypeEnvironment & env );
     111
     112        inline bool typesCompatible( const Type * t1, const Type * t2, const SymTab::Indexer & indexer ) {
    110113                TypeEnvironment env;
    111114                return typesCompatible( t1, t2, indexer, env );
    112115        }
    113116
    114         inline bool typesCompatibleIgnoreQualifiers( Type *t1, Type *t2, const SymTab::Indexer &indexer ) {
     117        inline bool typesCompatibleIgnoreQualifiers( const Type * t1, const Type * t2, const SymTab::Indexer & indexer ) {
    115118                TypeEnvironment env;
    116119                return typesCompatibleIgnoreQualifiers( t1, t2, indexer, env );
    117120        }
    118121
    119         bool typesCompatible( 
    120                 const ast::Type *, const ast::Type *, const ast::SymbolTable & symtab = {}, 
     122        bool typesCompatible(
     123                const ast::Type *, const ast::Type *, const ast::SymbolTable & symtab = {},
    121124                const ast::TypeEnvironment & env = {} );
    122        
     125
    123126        bool typesCompatibleIgnoreQualifiers(
    124                 const ast::Type *, const ast::Type *, const ast::SymbolTable &, 
     127                const ast::Type *, const ast::Type *, const ast::SymbolTable &,
    125128                const ast::TypeEnvironment & env = {} );
    126129
     
    131134
    132135        // in CommonType.cc
    133         Type * commonType( Type *type1, Type *type2, bool widenFirst, bool widenSecond, const SymTab::Indexer &indexer, TypeEnvironment &env, const OpenVarSet &openVars );
     136        Type * commonType( Type * type1, Type * type2, bool widenFirst, bool widenSecond, const SymTab::Indexer & indexer, TypeEnvironment & env, const OpenVarSet & openVars );
    134137        ast::ptr< ast::Type > commonType(
    135                 const ast::ptr< ast::Type > & type1, const ast::ptr< ast::Type > & type2, WidenMode widen, 
     138                const ast::ptr< ast::Type > & type1, const ast::ptr< ast::Type > & type2, WidenMode widen,
    136139                const ast::SymbolTable & symtab, ast::TypeEnvironment & env, const ast::OpenVarSet & open );
    137140
    138141        // in PolyCost.cc
    139         int polyCost( Type *type, const TypeEnvironment &env, const SymTab::Indexer &indexer );
    140         int polyCost( 
     142        int polyCost( Type * type, const TypeEnvironment & env, const SymTab::Indexer & indexer );
     143        int polyCost(
    141144                const ast::Type * type, const ast::SymbolTable & symtab, const ast::TypeEnvironment & env );
    142145
    143146        // in SpecCost.cc
    144         int specCost( Type *type );
     147        int specCost( Type * type );
    145148        int specCost( const ast::Type * type );
    146149
    147150        // in Occurs.cc
    148         bool occurs( Type *type, std::string varName, const TypeEnvironment &env );
     151        bool occurs( Type * type, std::string varName, const TypeEnvironment & env );
    149152        // new AST version in TypeEnvironment.cpp (only place it was used in old AST)
    150153
    151         template<typename Iter> 
    152         bool occursIn( Type* ty, Iter begin, Iter end, const TypeEnvironment &env ) {
     154        template<typename Iter>
     155        bool occursIn( Type* ty, Iter begin, Iter end, const TypeEnvironment & env ) {
    153156                while ( begin != end ) {
    154157                        if ( occurs( ty, *begin, env ) ) return true;
     
    176179
    177180        /// flatten tuple type into existing list of types
    178         static inline void flatten( 
    179                 const ast::Type * type, std::vector< ast::ptr< ast::Type > > & out 
     181        static inline void flatten(
     182                const ast::Type * type, std::vector< ast::ptr< ast::Type > > & out
    180183        ) {
    181                 if ( auto tupleType = dynamic_cast< const ast::TupleType * >( type ) ) {       
     184                if ( auto tupleType = dynamic_cast< const ast::TupleType * >( type ) ) {
    182185                        for ( const ast::Type * t : tupleType->types ) {
    183186                                flatten( t, out );
     
    197200
    198201        // in TypeEnvironment.cc
    199         bool isFtype( Type *type );
     202        bool isFtype( Type * type );
    200203} // namespace ResolvExpr
    201204
  • src/SymTab/Indexer.cc

    r1f1c102 rf53acdf8  
    7474        }
    7575
    76         Indexer::Indexer() 
    77         : idTable(), typeTable(), structTable(), enumTable(), unionTable(), traitTable(), 
    78           prevScope(), scope( 0 ), repScope( 0 ) { ++*stats().count; }
     76        Indexer::Indexer()
     77        : idTable(), typeTable(), structTable(), enumTable(), unionTable(), traitTable(),
     78          prevScope(), scope( 0 ), repScope( 0 ) { ++* stats().count; }
    7979
    8080        Indexer::~Indexer() {
     
    8484        void Indexer::lazyInitScope() {
    8585                if ( repScope < scope ) {
    86                         ++*stats().lazy_scopes;
     86                        ++* stats().lazy_scopes;
    8787                        // create rollback
    88                         prevScope = std::make_shared<Indexer>( *this );
     88                        prevScope = std::make_shared<Indexer>( * this );
    8989                        // update repScope
    9090                        repScope = scope;
     
    9595                ++scope;
    9696
    97                 ++*stats().new_scopes;
     97                ++* stats().new_scopes;
    9898                stats().avg_scope_depth->push( scope );
    9999                stats().max_scope_depth->push( scope );
     
    103103                if ( repScope == scope ) {
    104104                        Ptr prev = prevScope;           // make sure prevScope stays live
    105                         *this = std::move(*prevScope);  // replace with previous scope
     105                        * this = std::move(* prevScope);  // replace with previous scope
    106106                }
    107107
     
    109109        }
    110110
    111         void Indexer::lookupId( const std::string &id, std::list< IdData > &out ) const {
    112                 ++*stats().lookup_calls;
     111        void Indexer::lookupId( const std::string & id, std::list< IdData > &out ) const {
     112                ++* stats().lookup_calls;
    113113                if ( ! idTable ) return;
    114114
    115                 ++*stats().map_lookups;
     115                ++* stats().map_lookups;
    116116                auto decls = idTable->find( id );
    117117                if ( decls == idTable->end() ) return;
     
    122122        }
    123123
    124         NamedTypeDecl *Indexer::lookupType( const std::string &id ) const {
    125                 ++*stats().lookup_calls;
     124        const NamedTypeDecl * Indexer::lookupType( const std::string & id ) const {
     125                ++* stats().lookup_calls;
    126126                if ( ! typeTable ) return nullptr;
    127                 ++*stats().map_lookups;
     127                ++* stats().map_lookups;
    128128                auto it = typeTable->find( id );
    129129                return it == typeTable->end() ? nullptr : it->second.decl;
    130130        }
    131131
    132         StructDecl *Indexer::lookupStruct( const std::string &id ) const {
    133                 ++*stats().lookup_calls;
     132        const StructDecl * Indexer::lookupStruct( const std::string & id ) const {
     133                ++* stats().lookup_calls;
    134134                if ( ! structTable ) return nullptr;
    135                 ++*stats().map_lookups;
     135                ++* stats().map_lookups;
    136136                auto it = structTable->find( id );
    137137                return it == structTable->end() ? nullptr : it->second.decl;
    138138        }
    139139
    140         EnumDecl *Indexer::lookupEnum( const std::string &id ) const {
    141                 ++*stats().lookup_calls;
     140        const EnumDecl * Indexer::lookupEnum( const std::string & id ) const {
     141                ++* stats().lookup_calls;
    142142                if ( ! enumTable ) return nullptr;
    143                 ++*stats().map_lookups;
     143                ++* stats().map_lookups;
    144144                auto it = enumTable->find( id );
    145145                return it == enumTable->end() ? nullptr : it->second.decl;
    146146        }
    147147
    148         UnionDecl *Indexer::lookupUnion( const std::string &id ) const {
    149                 ++*stats().lookup_calls;
     148        const UnionDecl * Indexer::lookupUnion( const std::string & id ) const {
     149                ++* stats().lookup_calls;
    150150                if ( ! unionTable ) return nullptr;
    151                 ++*stats().map_lookups;
     151                ++* stats().map_lookups;
    152152                auto it = unionTable->find( id );
    153153                return it == unionTable->end() ? nullptr : it->second.decl;
    154154        }
    155155
    156         TraitDecl *Indexer::lookupTrait( const std::string &id ) const {
    157                 ++*stats().lookup_calls;
     156        const TraitDecl * Indexer::lookupTrait( const std::string & id ) const {
     157                ++* stats().lookup_calls;
    158158                if ( ! traitTable ) return nullptr;
    159                 ++*stats().map_lookups;
     159                ++* stats().map_lookups;
    160160                auto it = traitTable->find( id );
    161161                return it == traitTable->end() ? nullptr : it->second.decl;
    162162        }
    163163
    164         const Indexer* Indexer::atScope( unsigned long target ) const {
     164        const Indexer * Indexer::atScope( unsigned long target ) const {
    165165                // by lazy construction, final indexer in list has repScope 0, cannot be > target
    166166                // otherwise, will find first scope representing the target
    167                 const Indexer* indexer = this;
     167                const Indexer * indexer = this;
    168168                while ( indexer->repScope > target ) {
    169169                        indexer = indexer->prevScope.get();
     
    172172        }
    173173
    174         NamedTypeDecl *Indexer::globalLookupType( const std::string &id ) const {
     174        const NamedTypeDecl * Indexer::globalLookupType( const std::string & id ) const {
    175175                return atScope( 0 )->lookupType( id );
    176176        }
    177177
    178         StructDecl *Indexer::globalLookupStruct( const std::string &id ) const {
     178        const StructDecl * Indexer::globalLookupStruct( const std::string & id ) const {
    179179                return atScope( 0 )->lookupStruct( id );
    180180        }
    181181
    182         UnionDecl *Indexer::globalLookupUnion( const std::string &id ) const {
     182        const UnionDecl * Indexer::globalLookupUnion( const std::string & id ) const {
    183183                return atScope( 0 )->lookupUnion( id );
    184184        }
    185185
    186         EnumDecl *Indexer::globalLookupEnum( const std::string &id ) const {
     186        const EnumDecl * Indexer::globalLookupEnum( const std::string & id ) const {
    187187                return atScope( 0 )->lookupEnum( id );
    188188        }
    189189
    190         bool isFunction( DeclarationWithType * decl ) {
     190        bool isFunction( const DeclarationWithType * decl ) {
    191191                return GenPoly::getFunctionType( decl->get_type() );
    192192        }
    193193
    194         bool isObject( DeclarationWithType * decl ) {
     194        bool isObject( const DeclarationWithType * decl ) {
    195195                return ! isFunction( decl );
    196196        }
    197197
    198         bool isDefinition( DeclarationWithType * decl ) {
    199                 if ( FunctionDecl * func = dynamic_cast< FunctionDecl * >( decl ) ) {
     198        bool isDefinition( const DeclarationWithType * decl ) {
     199                if ( const FunctionDecl * func = dynamic_cast< const FunctionDecl * >( decl ) ) {
    200200                        // a function is a definition if it has a body
    201201                        return func->statements;
     
    207207        }
    208208
    209        
    210         bool Indexer::addedIdConflicts( 
    211                         const Indexer::IdData & existing, DeclarationWithType *added,
    212                         Indexer::OnConflict handleConflicts, BaseSyntaxNode * deleteStmt ) {
    213                 // if we're giving the same name mangling to things of different types then there is 
     209
     210        bool Indexer::addedIdConflicts(
     211                        const Indexer::IdData & existing, const DeclarationWithType * added,
     212                        Indexer::OnConflict handleConflicts, const Declaration * deleteStmt ) {
     213                // if we're giving the same name mangling to things of different types then there is
    214214                // something wrong
    215215                assert( (isObject( added ) && isObject( existing.id ) )
     
    219219                        // new definition shadows the autogenerated one, even at the same scope
    220220                        return false;
    221                 } else if ( LinkageSpec::isMangled( added->linkage ) 
    222                                 || ResolvExpr::typesCompatible( 
     221                } else if ( LinkageSpec::isMangled( added->linkage )
     222                                || ResolvExpr::typesCompatible(
    223223                                        added->get_type(), existing.id->get_type(), Indexer() ) ) {
    224224
     
    238238                        if ( isDefinition( added ) && isDefinition( existing.id ) ) {
    239239                                if ( handleConflicts.mode == OnConflict::Error ) {
    240                                         SemanticError( added, 
    241                                                 isFunction( added ) ? 
    242                                                         "duplicate function definition for " : 
     240                                        SemanticError( added,
     241                                                isFunction( added ) ?
     242                                                        "duplicate function definition for " :
    243243                                                        "duplicate object definition for " );
    244244                                }
     
    255255        }
    256256
    257         bool Indexer::hasCompatibleCDecl( const std::string &id, const std::string &mangleName ) const {
     257        bool Indexer::hasCompatibleCDecl( const std::string & id, const std::string &mangleName ) const {
    258258                if ( ! idTable ) return false;
    259259
    260                 ++*stats().map_lookups;
     260                ++* stats().map_lookups;
    261261                auto decls = idTable->find( id );
    262262                if ( decls == idTable->end() ) return false;
     
    270270                        }
    271271                }
    272                
     272
    273273                return false;
    274274        }
    275275
    276         bool Indexer::hasIncompatibleCDecl(
    277                         const std::string &id, const std::string &mangleName ) const {
     276        bool Indexer::hasIncompatibleCDecl(const std::string & id, const std::string &mangleName ) const {
    278277                if ( ! idTable ) return false;
    279278
    280                 ++*stats().map_lookups;
     279                ++* stats().map_lookups;
    281280                auto decls = idTable->find( id );
    282281                if ( decls == idTable->end() ) return false;
     
    295294
    296295        /// gets the base type of the first parameter; decl must be a ctor/dtor/assignment function
    297         std::string getOtypeKey( FunctionDecl* function ) {
     296        std::string getOtypeKey( const FunctionDecl * function ) {
    298297                auto& params = function->type->parameters;
    299298                assert( ! params.empty() );
    300299                // use base type of pointer, so that qualifiers on the pointer type aren't considered.
    301                 Type* base = InitTweak::getPointerBase( params.front()->get_type() );
     300                Type * base = InitTweak::getPointerBase( params.front()->get_type() );
    302301                assert( base );
    303302                return Mangler::mangle( base );
    304303        }
    305304
    306         /// gets the declaration for the function acting on a type specified by otype key, 
     305        /// gets the declaration for the function acting on a type specified by otype key,
    307306        /// nullptr if none such
    308         FunctionDecl * getFunctionForOtype( DeclarationWithType * decl, const std::string& otypeKey ) {
    309                 FunctionDecl * func = dynamic_cast< FunctionDecl * >( decl );
     307        const FunctionDecl * getFunctionForOtype( const DeclarationWithType * decl, const std::string& otypeKey ) {
     308                const FunctionDecl * func = dynamic_cast< const FunctionDecl * >( decl );
    310309                if ( ! func || otypeKey != getOtypeKey( func ) ) return nullptr;
    311310                return func;
    312311        }
    313312
    314         bool Indexer::removeSpecialOverrides(
    315                         Indexer::IdData& data, Indexer::MangleTable::Ptr& mangleTable ) {
    316                 // if a type contains user defined ctor/dtor/assign, then special rules trigger, which
    317                 // determinethe set of ctor/dtor/assign that can be used  by the requester. In particular,
    318                 // if the user defines a default ctor, then the generated default ctor is unavailable,
    319                 // likewise for copy ctor and dtor. If the user defines any ctor/dtor, then no generated
    320                 // field ctors are available. If the user defines any ctor then the generated default ctor
    321                 // is unavailable (intrinsic default ctor must be overridden exactly). If the user defines
    322                 // anything that looks like a copy constructor, then the generated copy constructor is
     313        bool Indexer::removeSpecialOverrides(Indexer::IdData& data, Indexer::MangleTable::Ptr& mangleTable ) {
     314                // if a type contains user defined ctor/dtor/assign, then special rules trigger, which
     315                // determinethe set of ctor/dtor/assign that can be used  by the requester. In particular,
     316                // if the user defines a default ctor, then the generated default ctor is unavailable,
     317                // likewise for copy ctor and dtor. If the user defines any ctor/dtor, then no generated
     318                // field ctors are available. If the user defines any ctor then the generated default ctor
     319                // is unavailable (intrinsic default ctor must be overridden exactly). If the user defines
     320                // anything that looks like a copy constructor, then the generated copy constructor is
    323321                // unavailable, and likewise for the assignment operator.
    324322
    325323                // only relevant on function declarations
    326                 FunctionDecl * function = dynamic_cast< FunctionDecl * >( data.id );
     324                const FunctionDecl * function = dynamic_cast< const FunctionDecl * >( data.id );
    327325                if ( ! function ) return true;
    328326                // only need to perform this check for constructors, destructors, and assignment functions
     
    340338                        std::vector< MangleTable::value_type > deleted;
    341339                        bool alreadyUserDefinedFunc = false;
    342                        
    343                         for ( const auto& entry : *mangleTable ) {
     340
     341                        for ( const auto& entry : * mangleTable ) {
    344342                                // skip decls that aren't functions or are for the wrong type
    345                                 FunctionDecl * decl = getFunctionForOtype( entry.second.id, dataOtypeKey );
     343                                const FunctionDecl * decl = getFunctionForOtype( entry.second.id, dataOtypeKey );
    346344                                if ( ! decl ) continue;
    347345
     
    368366                        // perform removals from mangle table, and deletions if necessary
    369367                        for ( const auto& key : removed ) {
    370                                 ++*stats().map_mutations;
     368                                ++* stats().map_mutations;
    371369                                mangleTable = mangleTable->erase( key );
    372370                        }
    373371                        if ( ! alreadyUserDefinedFunc ) for ( const auto& entry : deleted ) {
    374                                 ++*stats().map_mutations;
     372                                ++* stats().map_mutations;
    375373                                mangleTable = mangleTable->set( entry.first, IdData{ entry.second, function } );
    376374                        }
     
    379377                        // if this is the first user-defined function, delete non-user-defined overloads
    380378                        std::vector< MangleTable::value_type > deleted;
    381                        
    382                         for ( const auto& entry : *mangleTable ) {
     379
     380                        for ( const auto& entry : * mangleTable ) {
    383381                                // skip decls that aren't functions or are for the wrong type
    384                                 FunctionDecl * decl = getFunctionForOtype( entry.second.id, dataOtypeKey );
     382                                const FunctionDecl * decl = getFunctionForOtype( entry.second.id, dataOtypeKey );
    385383                                if ( ! decl ) continue;
    386384
     
    402400                        // this needs to be a separate loop because of iterator invalidation
    403401                        for ( const auto& entry : deleted ) {
    404                                 ++*stats().map_mutations;
     402                                ++* stats().map_mutations;
    405403                                mangleTable = mangleTable->set( entry.first, IdData{ entry.second, function } );
    406404                        }
     
    408406                        // this is an overridable generated function
    409407                        // if there already exists a matching user-defined function, delete this appropriately
    410                         for ( const auto& entry : *mangleTable ) {
     408                        for ( const auto& entry : * mangleTable ) {
    411409                                // skip decls that aren't functions or are for the wrong type
    412                                 FunctionDecl * decl = getFunctionForOtype( entry.second.id, dataOtypeKey );
     410                                const FunctionDecl * decl = getFunctionForOtype( entry.second.id, dataOtypeKey );
    413411                                if ( ! decl ) continue;
    414412
     
    418416                                if ( dataIsCopyFunc ) {
    419417                                        // remove current function if exists a user-defined copy function
    420                                         // since the signatures for copy functions don't need to match exactly, using 
     418                                        // since the signatures for copy functions don't need to match exactly, using
    421419                                        // a delete statement is the wrong approach
    422420                                        if ( InitTweak::isCopyFunction( decl, decl->name ) ) return false;
     
    428426                        }
    429427                }
    430                
     428
    431429                // nothing (more) to fix, return true
    432430                return true;
    433431        }
    434432
    435         void Indexer::addId(
    436                         DeclarationWithType *decl, OnConflict handleConflicts, Expression * baseExpr,
    437                         BaseSyntaxNode * deleteStmt ) {
    438                 ++*stats().add_calls;
     433        void Indexer::addId(const DeclarationWithType * decl, OnConflict handleConflicts, const Expression * baseExpr,
     434                        const Declaration * deleteStmt ) {
     435                ++* stats().add_calls;
    439436                const std::string &name = decl->name;
    440437                if ( name == "" ) return;
    441                
     438
    442439                std::string mangleName;
    443440                if ( LinkageSpec::isOverridable( decl->linkage ) ) {
    444                         // mangle the name without including the appropriate suffix, so overridable routines 
     441                        // mangle the name without including the appropriate suffix, so overridable routines
    445442                        // are placed into the same "bucket" as their user defined versions.
    446443                        mangleName = Mangler::mangle( decl, false );
     
    449446                } // if
    450447
    451                 // this ensures that no two declarations with the same unmangled name at the same scope 
     448                // this ensures that no two declarations with the same unmangled name at the same scope
    452449                // both have C linkage
    453450                if ( LinkageSpec::isMangled( decl->linkage ) ) {
     
    457454                        }
    458455                } else {
    459                         // NOTE: only correct if name mangling is completely isomorphic to C 
     456                        // NOTE: only correct if name mangling is completely isomorphic to C
    460457                        // type-compatibility, which it may not be.
    461458                        if ( hasIncompatibleCDecl( name, mangleName ) ) {
     
    470467                        mangleTable = MangleTable::new_ptr();
    471468                } else {
    472                         ++*stats().map_lookups;
     469                        ++* stats().map_lookups;
    473470                        auto decls = idTable->find( name );
    474471                        if ( decls == idTable->end() ) {
     
    477474                                mangleTable = decls->second;
    478475                                // skip in-scope repeat declarations of same identifier
    479                                 ++*stats().map_lookups;
     476                                ++* stats().map_lookups;
    480477                                auto existing = mangleTable->find( mangleName );
    481478                                if ( existing != mangleTable->end()
     
    486483                                                        // set delete expression for conflicting identifier
    487484                                                        lazyInitScope();
    488                                                         *stats().map_mutations += 2;
     485                                                        * stats().map_mutations += 2;
    489486                                                        idTable = idTable->set(
    490487                                                                name,
    491                                                                 mangleTable->set( 
    492                                                                         mangleName, 
     488                                                                mangleTable->set(
     489                                                                        mangleName,
    493490                                                                        IdData{ existing->second, handleConflicts.deleteStmt } ) );
    494491                                                }
     
    504501                // Ensure that auto-generated ctor/dtor/assignment are deleted if necessary
    505502                if ( ! removeSpecialOverrides( data, mangleTable ) ) return;
    506                 *stats().map_mutations += 2;
     503                * stats().map_mutations += 2;
    507504                idTable = idTable->set( name, mangleTable->set( mangleName, std::move(data) ) );
    508505        }
    509506
    510         void Indexer::addId( DeclarationWithType * decl, Expression * baseExpr ) {
     507        void Indexer::addId( const DeclarationWithType * decl, const Expression * baseExpr ) {
    511508                // default handling of conflicts is to raise an error
    512509                addId( decl, OnConflict::error(), baseExpr, decl->isDeleted ? decl : nullptr );
    513510        }
    514511
    515         void Indexer::addDeletedId( DeclarationWithType * decl, BaseSyntaxNode * deleteStmt ) {
     512        void Indexer::addDeletedId( const DeclarationWithType * decl, const Declaration * deleteStmt ) {
    516513                // default handling of conflicts is to raise an error
    517514                addId( decl, OnConflict::error(), nullptr, deleteStmt );
    518515        }
    519516
    520         bool addedTypeConflicts( NamedTypeDecl *existing, NamedTypeDecl *added ) {
     517        bool addedTypeConflicts( const NamedTypeDecl * existing, const NamedTypeDecl * added ) {
    521518                if ( existing->base == nullptr ) {
    522519                        return false;
     
    530527                        }
    531528                }
    532                 // does not need to be added to the table if both existing and added have a base that are 
     529                // does not need to be added to the table if both existing and added have a base that are
    533530                // the same
    534531                return true;
    535532        }
    536533
    537         void Indexer::addType( NamedTypeDecl *decl ) {
    538                 ++*stats().add_calls;
    539                 const std::string &id = decl->name;
    540 
    541                 if ( ! typeTable ) { 
     534        void Indexer::addType( const NamedTypeDecl * decl ) {
     535                ++* stats().add_calls;
     536                const std::string & id = decl->name;
     537
     538                if ( ! typeTable ) {
    542539                        typeTable = TypeTable::new_ptr();
    543540                } else {
    544                         ++*stats().map_lookups;
     541                        ++* stats().map_lookups;
    545542                        auto existing = typeTable->find( id );
    546                         if ( existing != typeTable->end() 
    547                                 && existing->second.scope == scope 
     543                        if ( existing != typeTable->end()
     544                                && existing->second.scope == scope
    548545                                && addedTypeConflicts( existing->second.decl, decl ) ) return;
    549546                }
    550                
     547
    551548                lazyInitScope();
    552                 ++*stats().map_mutations;
     549                ++* stats().map_mutations;
    553550                typeTable = typeTable->set( id, Scoped<NamedTypeDecl>{ decl, scope } );
    554551        }
    555552
    556         bool addedDeclConflicts( AggregateDecl *existing, AggregateDecl *added ) {
     553        bool addedDeclConflicts( const AggregateDecl * existing, const AggregateDecl * added ) {
    557554                if ( ! existing->body ) {
    558555                        return false;
     
    563560        }
    564561
    565         void Indexer::addStruct( const std::string &id ) {
     562        void Indexer::addStruct( const std::string & id ) {
    566563                addStruct( new StructDecl( id ) );
    567564        }
    568565
    569         void Indexer::addStruct( StructDecl *decl ) {
    570                 ++*stats().add_calls;
    571                 const std::string &id = decl->name;
     566        void Indexer::addStruct( const StructDecl * decl ) {
     567                ++* stats().add_calls;
     568                const std::string & id = decl->name;
    572569
    573570                if ( ! structTable ) {
    574571                        structTable = StructTable::new_ptr();
    575572                } else {
    576                         ++*stats().map_lookups;
     573                        ++* stats().map_lookups;
    577574                        auto existing = structTable->find( id );
    578                         if ( existing != structTable->end() 
    579                                 && existing->second.scope == scope 
     575                        if ( existing != structTable->end()
     576                                && existing->second.scope == scope
    580577                                && addedDeclConflicts( existing->second.decl, decl ) ) return;
    581578                }
    582579
    583580                lazyInitScope();
    584                 ++*stats().map_mutations;
     581                ++* stats().map_mutations;
    585582                structTable = structTable->set( id, Scoped<StructDecl>{ decl, scope } );
    586583        }
    587584
    588         void Indexer::addEnum( EnumDecl *decl ) {
    589                 ++*stats().add_calls;
    590                 const std::string &id = decl->name;
     585        void Indexer::addEnum( const EnumDecl * decl ) {
     586                ++* stats().add_calls;
     587                const std::string & id = decl->name;
    591588
    592589                if ( ! enumTable ) {
    593590                        enumTable = EnumTable::new_ptr();
    594591                } else {
    595                         ++*stats().map_lookups;
     592                        ++* stats().map_lookups;
    596593                        auto existing = enumTable->find( id );
    597                         if ( existing != enumTable->end() 
    598                                 && existing->second.scope == scope 
     594                        if ( existing != enumTable->end()
     595                                && existing->second.scope == scope
    599596                                && addedDeclConflicts( existing->second.decl, decl ) ) return;
    600597                }
    601                
     598
    602599                lazyInitScope();
    603                 ++*stats().map_mutations;
     600                ++* stats().map_mutations;
    604601                enumTable = enumTable->set( id, Scoped<EnumDecl>{ decl, scope } );
    605602        }
    606603
    607         void Indexer::addUnion( const std::string &id ) {
     604        void Indexer::addUnion( const std::string & id ) {
    608605                addUnion( new UnionDecl( id ) );
    609606        }
    610607
    611         void Indexer::addUnion( UnionDecl *decl ) {
    612                 ++*stats().add_calls;
    613                 const std::string &id = decl->name;
     608        void Indexer::addUnion( const UnionDecl * decl ) {
     609                ++* stats().add_calls;
     610                const std::string & id = decl->name;
    614611
    615612                if ( ! unionTable ) {
    616613                        unionTable = UnionTable::new_ptr();
    617614                } else {
    618                         ++*stats().map_lookups;
     615                        ++* stats().map_lookups;
    619616                        auto existing = unionTable->find( id );
    620                         if ( existing != unionTable->end() 
    621                                 && existing->second.scope == scope 
     617                        if ( existing != unionTable->end()
     618                                && existing->second.scope == scope
    622619                                && addedDeclConflicts( existing->second.decl, decl ) ) return;
    623620                }
    624621
    625622                lazyInitScope();
    626                 ++*stats().map_mutations;
     623                ++* stats().map_mutations;
    627624                unionTable = unionTable->set( id, Scoped<UnionDecl>{ decl, scope } );
    628625        }
    629626
    630         void Indexer::addTrait( TraitDecl *decl ) {
    631                 ++*stats().add_calls;
    632                 const std::string &id = decl->name;
     627        void Indexer::addTrait( const TraitDecl * decl ) {
     628                ++* stats().add_calls;
     629                const std::string & id = decl->name;
    633630
    634631                if ( ! traitTable ) {
    635632                        traitTable = TraitTable::new_ptr();
    636633                } else {
    637                         ++*stats().map_lookups;
     634                        ++* stats().map_lookups;
    638635                        auto existing = traitTable->find( id );
    639                         if ( existing != traitTable->end() 
    640                                 && existing->second.scope == scope 
     636                        if ( existing != traitTable->end()
     637                                && existing->second.scope == scope
    641638                                && addedDeclConflicts( existing->second.decl, decl ) ) return;
    642639                }
    643640
    644641                lazyInitScope();
    645                 ++*stats().map_mutations;
     642                ++* stats().map_mutations;
    646643                traitTable = traitTable->set( id, Scoped<TraitDecl>{ decl, scope } );
    647644        }
    648645
    649         void Indexer::addMembers( AggregateDecl * aggr, Expression * expr,
    650                         OnConflict handleConflicts ) {
     646        void Indexer::addMembers( const AggregateDecl * aggr, const Expression * expr, OnConflict handleConflicts ) {
    651647                for ( Declaration * decl : aggr->members ) {
    652648                        if ( DeclarationWithType * dwt = dynamic_cast< DeclarationWithType * >( decl ) ) {
    653649                                addId( dwt, handleConflicts, expr );
    654650                                if ( dwt->name == "" ) {
    655                                         Type * t = dwt->get_type()->stripReferences();
    656                                         if ( dynamic_cast<StructInstType*>( t ) || dynamic_cast<UnionInstType*>( t ) ) {
     651                                        const Type * t = dwt->get_type()->stripReferences();
     652                                        if ( dynamic_cast<const StructInstType *>( t ) || dynamic_cast<const UnionInstType *>( t ) ) {
    657653                                                Expression * base = expr->clone();
    658654                                                ResolvExpr::Cost cost = ResolvExpr::Cost::zero; // xxx - carry this cost into the indexer as a base cost?
     
    665661        }
    666662
    667         void Indexer::addWith( std::list< Expression * > & withExprs, BaseSyntaxNode * withStmt ) {
    668                 for ( Expression * expr : withExprs ) {
     663        void Indexer::addWith( const std::list< Expression * > & withExprs, const Declaration * withStmt ) {
     664                for ( const Expression * expr : withExprs ) {
    669665                        if ( expr->result ) {
    670666                                AggregateDecl * aggr = expr->result->stripReferences()->getAggr();
     
    689685        }
    690686
    691         void Indexer::addFunctionType( FunctionType * ftype ) {
     687        void Indexer::addFunctionType( const FunctionType * ftype ) {
    692688                addTypes( ftype->forall );
    693689                addIds( ftype->returnVals );
     
    700696                        Expression * base = baseExpr->clone();
    701697                        ResolvExpr::referenceToRvalueConversion( base, cost );
    702                         ret = new MemberExpr( id, base );
     698                        ret = new MemberExpr( const_cast<DeclarationWithType *>(id), base );
    703699                        // xxx - this introduces hidden environments, for now remove them.
    704700                        // std::swap( base->env, ret->env );
     
    706702                        base->env = nullptr;
    707703                } else {
    708                         ret = new VariableExpr( id );
    709                 }
    710                 if ( deleteStmt ) ret = new DeletedExpr( ret, deleteStmt );
     704                        ret = new VariableExpr( const_cast<DeclarationWithType *>(id) );
     705                }
     706                if ( deleteStmt ) ret = new DeletedExpr( ret, const_cast<Declaration *>(deleteStmt) );
    711707                return ret;
    712708        }
  • src/SymTab/Indexer.h

    r1f1c102 rf53acdf8  
    3434                virtual ~Indexer();
    3535
    36                 // when using an indexer manually (e.g., within a mutator traversal), it is necessary to 
     36                // when using an indexer manually (e.g., within a mutator traversal), it is necessary to
    3737                // tell the indexer explicitly when scopes begin and end
    3838                void enterScope();
     
    4040
    4141                struct IdData {
    42                         DeclarationWithType * id = nullptr;
    43                         Expression * baseExpr = nullptr; // WithExpr
     42                        const DeclarationWithType * id = nullptr;
     43                        const Expression * baseExpr = nullptr; // WithExpr
    4444
    4545                        /// non-null if this declaration is deleted
    46                         BaseSyntaxNode * deleteStmt = nullptr;
     46                        const Declaration * deleteStmt = nullptr;
    4747                        /// scope of identifier
    4848                        unsigned long scope = 0;
     
    5050                        // NOTE: shouldn't need either of these constructors, but gcc-4 does not properly support initializer lists with default members.
    5151                        IdData() = default;
    52                         IdData( 
    53                                 DeclarationWithType * id, Expression * baseExpr, BaseSyntaxNode * deleteStmt,
    54                                 unsigned long scope ) 
     52                        IdData(
     53                                const DeclarationWithType * id, const Expression * baseExpr, const Declaration * deleteStmt,
     54                                unsigned long scope )
    5555                                : id( id ), baseExpr( baseExpr ), deleteStmt( deleteStmt ), scope( scope ) {}
    56                         IdData( const IdData& o, BaseSyntaxNode * deleteStmt )
     56                        IdData( const IdData& o, const Declaration * deleteStmt )
    5757                                : id( o.id ), baseExpr( o.baseExpr ), deleteStmt( deleteStmt ), scope( o.scope ) {}
    5858
     
    6161
    6262                /// Gets all declarations with the given ID
    63                 void lookupId( const std::string &id, std::list< IdData > &out ) const;
     63                void lookupId( const std::string & id, std::list< IdData > &out ) const;
    6464                /// Gets the top-most type declaration with the given ID
    65                 NamedTypeDecl *lookupType( const std::string &id ) const;
     65                const NamedTypeDecl * lookupType( const std::string & id ) const;
    6666                /// Gets the top-most struct declaration with the given ID
    67                 StructDecl *lookupStruct( const std::string &id ) const;
     67                const StructDecl * lookupStruct( const std::string & id ) const;
    6868                /// Gets the top-most enum declaration with the given ID
    69                 EnumDecl *lookupEnum( const std::string &id ) const;
     69                const EnumDecl * lookupEnum( const std::string & id ) const;
    7070                /// Gets the top-most union declaration with the given ID
    71                 UnionDecl *lookupUnion( const std::string &id ) const;
     71                const UnionDecl * lookupUnion( const std::string & id ) const;
    7272                /// Gets the top-most trait declaration with the given ID
    73                 TraitDecl *lookupTrait( const std::string &id ) const;
     73                const TraitDecl * lookupTrait( const std::string & id ) const;
    7474
    7575                /// Gets the type declaration with the given ID at global scope
    76                 NamedTypeDecl *globalLookupType( const std::string &id ) const;
     76                const NamedTypeDecl * globalLookupType( const std::string & id ) const;
    7777                /// Gets the struct declaration with the given ID at global scope
    78                 StructDecl *globalLookupStruct( const std::string &id ) const;
     78                const StructDecl * globalLookupStruct( const std::string & id ) const;
    7979                /// Gets the union declaration with the given ID at global scope
    80                 UnionDecl *globalLookupUnion( const std::string &id ) const;
     80                const UnionDecl * globalLookupUnion( const std::string & id ) const;
    8181                /// Gets the enum declaration with the given ID at global scope
    82                 EnumDecl *globalLookupEnum( const std::string &id ) const;
     82                const EnumDecl * globalLookupEnum( const std::string & id ) const;
    8383
    84                 void addId( DeclarationWithType * decl, Expression * baseExpr = nullptr );
    85                 void addDeletedId( DeclarationWithType * decl, BaseSyntaxNode * deleteStmt );
     84                void addId( const DeclarationWithType * decl, const Expression * baseExpr = nullptr );
     85                void addDeletedId( const DeclarationWithType * decl, const Declaration * deleteStmt );
    8686
    87                 void addType( NamedTypeDecl *decl );
    88                 void addStruct( const std::string &id );
    89                 void addStruct( StructDecl *decl );
    90                 void addEnum( EnumDecl *decl );
    91                 void addUnion( const std::string &id );
    92                 void addUnion( UnionDecl *decl );
    93                 void addTrait( TraitDecl *decl );
     87                void addType( const NamedTypeDecl * decl );
     88                void addStruct( const std::string & id );
     89                void addStruct( const StructDecl * decl );
     90                void addEnum( const EnumDecl * decl );
     91                void addUnion( const std::string & id );
     92                void addUnion( const UnionDecl * decl );
     93                void addTrait( const TraitDecl * decl );
    9494
    9595                /// adds all of the IDs from WithStmt exprs
    96                 void addWith( std::list< Expression * > & withExprs, BaseSyntaxNode * withStmt );
     96                void addWith( const std::list< Expression * > & withExprs, const Declaration * withStmt );
    9797
    9898                /// convenience function for adding a list of Ids to the indexer
     
    103103
    104104                /// convenience function for adding all of the declarations in a function type to the indexer
    105                 void addFunctionType( FunctionType * ftype );
     105                void addFunctionType( const FunctionType * ftype );
    106106
    107107          private:
    108                 /// Wraps a Decl* with a scope
     108                /// Wraps a Decl * with a scope
    109109                template<typename Decl>
    110110                struct Scoped {
    111                         Decl* decl;           ///< declaration
     111                        const Decl * decl;           ///< declaration
    112112                        unsigned long scope;  ///< scope of this declaration
    113113
    114                         Scoped(Decl* d, unsigned long s) : decl(d), scope(s) {}
     114                        Scoped(const Decl * d, unsigned long s) : decl(d), scope(s) {}
    115115                };
    116116
     
    140140
    141141                /// Gets the indexer at the given scope
    142                 const Indexer* atScope( unsigned long scope ) const;
     142                const Indexer * atScope( unsigned long scope ) const;
    143143
    144                 /// Removes matching autogenerated constructors and destructors so that they will not be 
     144                /// Removes matching autogenerated constructors and destructors so that they will not be
    145145                /// selected. If returns false, passed decl should not be added.
    146                 bool removeSpecialOverrides( IdData& decl, MangleTable::Ptr& mangleTable );
     146                bool removeSpecialOverrides( IdData & decl, MangleTable::Ptr & mangleTable );
    147147
    148148                /// Options for handling identifier conflicts
     
    152152                                Delete  ///< Delete the earlier version with the delete statement
    153153                        } mode;
    154                         BaseSyntaxNode * deleteStmt;  ///< Statement that deletes this expression
     154                        const Declaration * deleteStmt;  ///< Statement that deletes this expression
    155155
    156156                private:
    157157                        OnConflict() : mode(Error), deleteStmt(nullptr) {}
    158                         OnConflict( BaseSyntaxNode * d ) : mode(Delete), deleteStmt(d) {}
     158                        OnConflict( const Declaration * d ) : mode(Delete), deleteStmt(d) {}
    159159                public:
    160160                        OnConflict( const OnConflict& ) = default;
    161161
    162162                        static OnConflict error() { return {}; }
    163                         static OnConflict deleteWith( BaseSyntaxNode * d ) { return { d }; }
     163                        static OnConflict deleteWith( const Declaration * d ) { return { d }; }
    164164                };
    165165
    166166                /// true if the existing identifier conflicts with the added identifier
    167167                bool addedIdConflicts(
    168                         const IdData& existing, DeclarationWithType * added, OnConflict handleConflicts,
    169                         BaseSyntaxNode * deleteStmt );
     168                        const IdData & existing, const DeclarationWithType * added, OnConflict handleConflicts,
     169                        const Declaration * deleteStmt );
    170170
    171171                /// common code for addId, addDeletedId, etc.
    172                 void addId(
    173                         DeclarationWithType * decl, OnConflict handleConflicts,
    174                         Expression * baseExpr = nullptr, BaseSyntaxNode * deleteStmt = nullptr );
     172                void addId(const DeclarationWithType * decl, OnConflict handleConflicts,
     173                        const Expression * baseExpr = nullptr, const Declaration * deleteStmt = nullptr );
    175174
    176175                /// adds all of the members of the Aggregate (addWith helper)
    177                 void addMembers( AggregateDecl * aggr, Expression * expr, OnConflict handleConflicts );
     176                void addMembers( const AggregateDecl * aggr, const Expression * expr, OnConflict handleConflicts );
    178177
    179178                /// returns true if there exists a declaration with C linkage and the given name with the same mangled name
    180                 bool hasCompatibleCDecl( const std::string &id, const std::string &mangleName ) const;
     179                bool hasCompatibleCDecl( const std::string & id, const std::string & mangleName ) const;
    181180                /// returns true if there exists a declaration with C linkage and the given name with a different mangled name
    182                 bool hasIncompatibleCDecl( const std::string &id, const std::string &mangleName ) const;
     181                bool hasIncompatibleCDecl( const std::string & id, const std::string & mangleName ) const;
    183182        };
    184183} // namespace SymTab
  • src/SymTab/Mangler.cc

    r1f1c102 rf53acdf8  
    4242                                Mangler_old( const Mangler_old & ) = delete;
    4343
    44                                 void previsit( BaseSyntaxNode * ) { visit_children = false; }
    45 
    46                                 void postvisit( ObjectDecl * declaration );
    47                                 void postvisit( FunctionDecl * declaration );
    48                                 void postvisit( TypeDecl * declaration );
    49 
    50                                 void postvisit( VoidType * voidType );
    51                                 void postvisit( BasicType * basicType );
    52                                 void postvisit( PointerType * pointerType );
    53                                 void postvisit( ArrayType * arrayType );
    54                                 void postvisit( ReferenceType * refType );
    55                                 void postvisit( FunctionType * functionType );
    56                                 void postvisit( StructInstType * aggregateUseType );
    57                                 void postvisit( UnionInstType * aggregateUseType );
    58                                 void postvisit( EnumInstType * aggregateUseType );
    59                                 void postvisit( TypeInstType * aggregateUseType );
    60                                 void postvisit( TraitInstType * inst );
    61                                 void postvisit( TupleType * tupleType );
    62                                 void postvisit( VarArgsType * varArgsType );
    63                                 void postvisit( ZeroType * zeroType );
    64                                 void postvisit( OneType * oneType );
    65                                 void postvisit( QualifiedType * qualType );
     44                                void previsit( const BaseSyntaxNode * ) { visit_children = false; }
     45
     46                                void postvisit( const ObjectDecl * declaration );
     47                                void postvisit( const FunctionDecl * declaration );
     48                                void postvisit( const TypeDecl * declaration );
     49
     50                                void postvisit( const VoidType * voidType );
     51                                void postvisit( const BasicType * basicType );
     52                                void postvisit( const PointerType * pointerType );
     53                                void postvisit( const ArrayType * arrayType );
     54                                void postvisit( const ReferenceType * refType );
     55                                void postvisit( const FunctionType * functionType );
     56                                void postvisit( const StructInstType * aggregateUseType );
     57                                void postvisit( const UnionInstType * aggregateUseType );
     58                                void postvisit( const EnumInstType * aggregateUseType );
     59                                void postvisit( const TypeInstType * aggregateUseType );
     60                                void postvisit( const TraitInstType * inst );
     61                                void postvisit( const TupleType * tupleType );
     62                                void postvisit( const VarArgsType * varArgsType );
     63                                void postvisit( const ZeroType * zeroType );
     64                                void postvisit( const OneType * oneType );
     65                                void postvisit( const QualifiedType * qualType );
    6666
    6767                                std::string get_mangleName() { return mangleName.str(); }
     
    7979
    8080                          public:
    81                                 Mangler_old( bool mangleOverridable, bool typeMode, bool mangleGenericParams, 
     81                                Mangler_old( bool mangleOverridable, bool typeMode, bool mangleGenericParams,
    8282                                        int nextVarNum, const VarMapType& varNums );
    8383
    8484                          private:
    85                                 void mangleDecl( DeclarationWithType *declaration );
    86                                 void mangleRef( ReferenceToType *refType, std::string prefix );
    87 
    88                                 void printQualifiers( Type *type );
     85                                void mangleDecl( const DeclarationWithType * declaration );
     86                                void mangleRef( const ReferenceToType * refType, std::string prefix );
     87
     88                                void printQualifiers( const Type *type );
    8989                        }; // Mangler_old
    9090                } // namespace
    9191
    92                 std::string mangle( BaseSyntaxNode * decl, bool mangleOverridable, bool typeMode, bool mangleGenericParams ) {
     92                std::string mangle( const BaseSyntaxNode * decl, bool mangleOverridable, bool typeMode, bool mangleGenericParams ) {
    9393                        PassVisitor<Mangler_old> mangler( mangleOverridable, typeMode, mangleGenericParams );
    9494                        maybeAccept( decl, mangler );
     
    9696                }
    9797
    98                 std::string mangleType( Type * ty ) {
     98                std::string mangleType( const Type * ty ) {
    9999                        PassVisitor<Mangler_old> mangler( false, true, true );
    100100                        maybeAccept( ty, mangler );
     
    102102                }
    103103
    104                 std::string mangleConcrete( Type * ty ) {
     104                std::string mangleConcrete( const Type * ty ) {
    105105                        PassVisitor<Mangler_old> mangler( false, false, false );
    106106                        maybeAccept( ty, mangler );
     
    110110                namespace {
    111111                        Mangler_old::Mangler_old( bool mangleOverridable, bool typeMode, bool mangleGenericParams )
    112                                 : nextVarNum( 0 ), isTopLevel( true ), 
    113                                 mangleOverridable( mangleOverridable ), typeMode( typeMode ), 
     112                                : nextVarNum( 0 ), isTopLevel( true ),
     113                                mangleOverridable( mangleOverridable ), typeMode( typeMode ),
    114114                                mangleGenericParams( mangleGenericParams ) {}
    115                        
    116                         Mangler_old::Mangler_old( bool mangleOverridable, bool typeMode, bool mangleGenericParams, 
     115
     116                        Mangler_old::Mangler_old( bool mangleOverridable, bool typeMode, bool mangleGenericParams,
    117117                                int nextVarNum, const VarMapType& varNums )
    118                                 : varNums( varNums ), nextVarNum( nextVarNum ), isTopLevel( false ), 
    119                                 mangleOverridable( mangleOverridable ), typeMode( typeMode ), 
     118                                : varNums( varNums ), nextVarNum( nextVarNum ), isTopLevel( false ),
     119                                mangleOverridable( mangleOverridable ), typeMode( typeMode ),
    120120                                mangleGenericParams( mangleGenericParams ) {}
    121121
    122                         void Mangler_old::mangleDecl( DeclarationWithType * declaration ) {
     122                        void Mangler_old::mangleDecl( const DeclarationWithType * declaration ) {
    123123                                bool wasTopLevel = isTopLevel;
    124124                                if ( isTopLevel ) {
     
    150150                        }
    151151
    152                         void Mangler_old::postvisit( ObjectDecl * declaration ) {
     152                        void Mangler_old::postvisit( const ObjectDecl * declaration ) {
    153153                                mangleDecl( declaration );
    154154                        }
    155155
    156                         void Mangler_old::postvisit( FunctionDecl * declaration ) {
     156                        void Mangler_old::postvisit( const FunctionDecl * declaration ) {
    157157                                mangleDecl( declaration );
    158158                        }
    159159
    160                         void Mangler_old::postvisit( VoidType * voidType ) {
     160                        void Mangler_old::postvisit( const VoidType * voidType ) {
    161161                                printQualifiers( voidType );
    162162                                mangleName << Encoding::void_t;
    163163                        }
    164164
    165                         void Mangler_old::postvisit( BasicType * basicType ) {
     165                        void Mangler_old::postvisit( const BasicType * basicType ) {
    166166                                printQualifiers( basicType );
    167                                 assertf( basicType->get_kind() < BasicType::NUMBER_OF_BASIC_TYPES, "Unhandled basic type: %d", basicType->get_kind() );
    168                                 mangleName << Encoding::basicTypes[ basicType->get_kind() ];
    169                         }
    170 
    171                         void Mangler_old::postvisit( PointerType * pointerType ) {
     167                                assertf( basicType->kind < BasicType::NUMBER_OF_BASIC_TYPES, "Unhandled basic type: %d", basicType->kind );
     168                                mangleName << Encoding::basicTypes[ basicType->kind ];
     169                        }
     170
     171                        void Mangler_old::postvisit( const PointerType * pointerType ) {
    172172                                printQualifiers( pointerType );
    173173                                // mangle void (*f)() and void f() to the same name to prevent overloading on functions and function pointers
     
    176176                        }
    177177
    178                         void Mangler_old::postvisit( ArrayType * arrayType ) {
     178                        void Mangler_old::postvisit( const ArrayType * arrayType ) {
    179179                                // TODO: encode dimension
    180180                                printQualifiers( arrayType );
     
    183183                        }
    184184
    185                         void Mangler_old::postvisit( ReferenceType * refType ) {
     185                        void Mangler_old::postvisit( const ReferenceType * refType ) {
    186186                                // don't print prefix (e.g. 'R') for reference types so that references and non-references do not overload.
    187187                                // Further, do not print the qualifiers for a reference type (but do run printQualifers because of TypeDecls, etc.),
     
    202202                        }
    203203
    204                         void Mangler_old::postvisit( FunctionType * functionType ) {
     204                        void Mangler_old::postvisit( const FunctionType * functionType ) {
    205205                                printQualifiers( functionType );
    206206                                mangleName << Encoding::function;
     
    219219                        }
    220220
    221                         void Mangler_old::mangleRef( ReferenceToType * refType, std::string prefix ) {
     221                        void Mangler_old::mangleRef( const ReferenceToType * refType, std::string prefix ) {
    222222                                printQualifiers( refType );
    223223
     
    225225
    226226                                if ( mangleGenericParams ) {
    227                                         std::list< Expression* >& params = refType->parameters;
     227                                        const std::list< Expression* > & params = refType->parameters;
    228228                                        if ( ! params.empty() ) {
    229229                                                mangleName << "_";
    230                                                 for ( std::list< Expression* >::const_iterator param = params.begin(); param != params.end(); ++param ) {
    231                                                         TypeExpr *paramType = dynamic_cast< TypeExpr* >( *param );
    232                                                         assertf(paramType, "Aggregate parameters should be type expressions: %s", toCString(*param));
     230                                                for ( const Expression * param : params ) {
     231                                                        const TypeExpr * paramType = dynamic_cast< const TypeExpr * >( param );
     232                                                        assertf(paramType, "Aggregate parameters should be type expressions: %s", toCString(param));
    233233                                                        maybeAccept( paramType->type, *visitor );
    234234                                                }
     
    238238                        }
    239239
    240                         void Mangler_old::postvisit( StructInstType * aggregateUseType ) {
     240                        void Mangler_old::postvisit( const StructInstType * aggregateUseType ) {
    241241                                mangleRef( aggregateUseType, Encoding::struct_t );
    242242                        }
    243243
    244                         void Mangler_old::postvisit( UnionInstType * aggregateUseType ) {
     244                        void Mangler_old::postvisit( const UnionInstType * aggregateUseType ) {
    245245                                mangleRef( aggregateUseType, Encoding::union_t );
    246246                        }
    247247
    248                         void Mangler_old::postvisit( EnumInstType * aggregateUseType ) {
     248                        void Mangler_old::postvisit( const EnumInstType * aggregateUseType ) {
    249249                                mangleRef( aggregateUseType, Encoding::enum_t );
    250250                        }
    251251
    252                         void Mangler_old::postvisit( TypeInstType * typeInst ) {
     252                        void Mangler_old::postvisit( const TypeInstType * typeInst ) {
    253253                                VarMapType::iterator varNum = varNums.find( typeInst->get_name() );
    254254                                if ( varNum == varNums.end() ) {
     
    266266                        }
    267267
    268                         void Mangler_old::postvisit( TraitInstType * inst ) {
     268                        void Mangler_old::postvisit( const TraitInstType * inst ) {
    269269                                printQualifiers( inst );
    270270                                mangleName << inst->name.size() << inst->name;
    271271                        }
    272272
    273                         void Mangler_old::postvisit( TupleType * tupleType ) {
     273                        void Mangler_old::postvisit( const TupleType * tupleType ) {
    274274                                printQualifiers( tupleType );
    275275                                mangleName << Encoding::tuple << tupleType->types.size();
     
    277277                        }
    278278
    279                         void Mangler_old::postvisit( VarArgsType * varArgsType ) {
     279                        void Mangler_old::postvisit( const VarArgsType * varArgsType ) {
    280280                                printQualifiers( varArgsType );
    281281                                static const std::string vargs = "__builtin_va_list";
     
    283283                        }
    284284
    285                         void Mangler_old::postvisit( ZeroType * ) {
     285                        void Mangler_old::postvisit( const ZeroType * ) {
    286286                                mangleName << Encoding::zero;
    287287                        }
    288288
    289                         void Mangler_old::postvisit( OneType * ) {
     289                        void Mangler_old::postvisit( const OneType * ) {
    290290                                mangleName << Encoding::one;
    291291                        }
    292292
    293                         void Mangler_old::postvisit( QualifiedType * qualType ) {
     293                        void Mangler_old::postvisit( const QualifiedType * qualType ) {
    294294                                bool inqual = inQualifiedType;
    295295                                if (! inqual ) {
     
    307307                        }
    308308
    309                         void Mangler_old::postvisit( TypeDecl * decl ) {
     309                        void Mangler_old::postvisit( const TypeDecl * decl ) {
    310310                                // TODO: is there any case where mangling a TypeDecl makes sense? If so, this code needs to be
    311311                                // fixed to ensure that two TypeDecls mangle to the same name when they are the same type and vice versa.
     
    314314                                // aside from the assert false.
    315315                                assertf(false, "Mangler_old should not visit typedecl: %s", toCString(decl));
    316                                 assertf( decl->get_kind() < TypeDecl::NUMBER_OF_KINDS, "Unhandled type variable kind: %d", decl->get_kind() );
    317                                 mangleName << Encoding::typeVariables[ decl->get_kind() ] << ( decl->name.length() ) << decl->name;
     316                                assertf( decl->kind < TypeDecl::NUMBER_OF_KINDS, "Unhandled type variable kind: %d", decl->kind );
     317                                mangleName << Encoding::typeVariables[ decl->kind ] << ( decl->name.length() ) << decl->name;
    318318                        }
    319319
     
    324324                        }
    325325
    326                         void Mangler_old::printQualifiers( Type * type ) {
     326                        void Mangler_old::printQualifiers( const Type * type ) {
    327327                                // skip if not including qualifiers
    328328                                if ( typeMode ) return;
    329                                 if ( ! type->get_forall().empty() ) {
     329                                if ( ! type->forall.empty() ) {
    330330                                        std::list< std::string > assertionNames;
    331331                                        int dcount = 0, fcount = 0, vcount = 0, acount = 0;
    332332                                        mangleName << Encoding::forall;
    333                                         for ( Type::ForallList::iterator i = type->forall.begin(); i != type->forall.end(); ++i ) {
    334                                                 switch ( (*i)->get_kind() ) {
     333                                        for ( const TypeDecl * i : type->forall ) {
     334                                                switch ( i->kind ) {
    335335                                                  case TypeDecl::Dtype:
    336336                                                        dcount++;
     
    345345                                                        assert( false );
    346346                                                } // switch
    347                                                 varNums[ (*i)->name ] = std::make_pair( nextVarNum, (int)(*i)->get_kind() );
    348                                                 for ( std::list< DeclarationWithType* >::iterator assert = (*i)->assertions.begin(); assert != (*i)->assertions.end(); ++assert ) {
    349                                                         PassVisitor<Mangler_old> sub_mangler( 
     347                                                varNums[ i->name ] = std::make_pair( nextVarNum, (int)i->kind );
     348                                                for ( const DeclarationWithType * assert : i->assertions ) {
     349                                                        PassVisitor<Mangler_old> sub_mangler(
    350350                                                                mangleOverridable, typeMode, mangleGenericParams, nextVarNum, varNums );
    351                                                         (*assert)->accept( sub_mangler );
     351                                                        assert->accept( sub_mangler );
    352352                                                        assertionNames.push_back( sub_mangler.pass.get_mangleName() );
    353353                                                        acount++;
     
    436436
    437437                  private:
    438                         Mangler_new( bool mangleOverridable, bool typeMode, bool mangleGenericParams, 
     438                        Mangler_new( bool mangleOverridable, bool typeMode, bool mangleGenericParams,
    439439                                int nextVarNum, const VarMapType& varNums );
    440440                        friend class ast::Pass<Mangler_new>;
     
    457457        namespace {
    458458                Mangler_new::Mangler_new( Mangle::Mode mode )
    459                         : nextVarNum( 0 ), isTopLevel( true ), 
     459                        : nextVarNum( 0 ), isTopLevel( true ),
    460460                        mangleOverridable  ( ! mode.no_overrideable   ),
    461                         typeMode           (   mode.type              ), 
     461                        typeMode           (   mode.type              ),
    462462                        mangleGenericParams( ! mode.no_generic_params ) {}
    463                
    464                 Mangler_new::Mangler_new( bool mangleOverridable, bool typeMode, bool mangleGenericParams, 
     463
     464                Mangler_new::Mangler_new( bool mangleOverridable, bool typeMode, bool mangleGenericParams,
    465465                        int nextVarNum, const VarMapType& varNums )
    466                         : varNums( varNums ), nextVarNum( nextVarNum ), isTopLevel( false ), 
    467                         mangleOverridable( mangleOverridable ), typeMode( typeMode ), 
     466                        : varNums( varNums ), nextVarNum( nextVarNum ), isTopLevel( false ),
     467                        mangleOverridable( mangleOverridable ), typeMode( typeMode ),
    468468                        mangleGenericParams( mangleGenericParams ) {}
    469469
     
    693693                                                varNums[ decl->name ] = std::make_pair( nextVarNum, (int)decl->kind );
    694694                                                for ( const ast::DeclWithType * assert : decl->assertions ) {
    695                                                         ast::Pass<Mangler_new> sub_mangler( 
     695                                                        ast::Pass<Mangler_new> sub_mangler(
    696696                                                                mangleOverridable, typeMode, mangleGenericParams, nextVarNum, varNums );
    697697                                                        assert->accept( sub_mangler );
  • src/SymTab/Mangler.h

    r1f1c102 rf53acdf8  
    4040        namespace Mangler {
    4141                /// Mangle syntax tree object; primary interface to clients
    42                 std::string mangle( BaseSyntaxNode * decl, bool mangleOverridable = true, bool typeMode = false, bool mangleGenericParams = true );
     42                std::string mangle( const BaseSyntaxNode * decl, bool mangleOverridable = true, bool typeMode = false, bool mangleGenericParams = true );
    4343
    4444                /// Mangle a type name; secondary interface
    45                 std::string mangleType( Type* ty );
     45                std::string mangleType( const Type * ty );
    4646                /// Mangle ignoring generic type parameters
    47                 std::string mangleConcrete( Type* ty );
     47                std::string mangleConcrete( const Type * ty );
    4848
    4949                namespace Encoding {
  • src/SymTab/Validate.cc

    r1f1c102 rf53acdf8  
    119119
    120120          private:
    121                 template< typename AggDecl > void handleAggregate( AggDecl *aggregateDecl );
     121                template< typename AggDecl > void handleAggregate( AggDecl * aggregateDecl );
    122122
    123123                AggregateDecl * parentAggr = nullptr;
     
    134134        /// Replaces enum types by int, and function or array types in function parameter and return lists by appropriate pointers.
    135135        struct EnumAndPointerDecay_old {
    136                 void previsit( EnumDecl *aggregateDecl );
    137                 void previsit( FunctionType *func );
     136                void previsit( EnumDecl * aggregateDecl );
     137                void previsit( FunctionType * func );
    138138        };
    139139
    140140        /// Associates forward declarations of aggregates with their definitions
    141141        struct LinkReferenceToTypes_old final : public WithIndexer, public WithGuards, public WithVisitorRef<LinkReferenceToTypes_old>, public WithShortCircuiting {
    142                 LinkReferenceToTypes_old( const Indexer *indexer );
    143                 void postvisit( TypeInstType *typeInst );
    144 
    145                 void postvisit( EnumInstType *enumInst );
    146                 void postvisit( StructInstType *structInst );
    147                 void postvisit( UnionInstType *unionInst );
    148                 void postvisit( TraitInstType *traitInst );
     142                LinkReferenceToTypes_old( const Indexer * indexer );
     143                void postvisit( TypeInstType * typeInst );
     144
     145                void postvisit( EnumInstType * enumInst );
     146                void postvisit( StructInstType * structInst );
     147                void postvisit( UnionInstType * unionInst );
     148                void postvisit( TraitInstType * traitInst );
    149149                void previsit( QualifiedType * qualType );
    150150                void postvisit( QualifiedType * qualType );
    151151
    152                 void postvisit( EnumDecl *enumDecl );
    153                 void postvisit( StructDecl *structDecl );
    154                 void postvisit( UnionDecl *unionDecl );
     152                void postvisit( EnumDecl * enumDecl );
     153                void postvisit( StructDecl * structDecl );
     154                void postvisit( UnionDecl * unionDecl );
    155155                void postvisit( TraitDecl * traitDecl );
    156156
    157                 void previsit( StructDecl *structDecl );
    158                 void previsit( UnionDecl *unionDecl );
     157                void previsit( StructDecl * structDecl );
     158                void previsit( UnionDecl * unionDecl );
    159159
    160160                void renameGenericParams( std::list< TypeDecl * > & params );
    161161
    162162          private:
    163                 const Indexer *local_indexer;
     163                const Indexer * local_indexer;
    164164
    165165                typedef std::map< std::string, std::list< EnumInstType * > > ForwardEnumsType;
     
    239239
    240240                template<typename AggDecl>
    241                 void handleAggregate( AggDecl *aggregateDecl );
     241                void handleAggregate( AggDecl * aggregateDecl );
    242242
    243243                void previsit( StructDecl * aggregateDecl );
     
    252252                static void verify( std::list< Declaration * > &translationUnit );
    253253
    254                 void previsit( FunctionDecl *funcDecl );
     254                void previsit( FunctionDecl * funcDecl );
    255255        };
    256256
     
    287287                Type::StorageClasses storageClasses;
    288288
    289                 void premutate( ObjectDecl *objectDecl );
    290                 Expression * postmutate( CompoundLiteralExpr *compLitExpr );
     289                void premutate( ObjectDecl * objectDecl );
     290                Expression * postmutate( CompoundLiteralExpr * compLitExpr );
    291291        };
    292292
     
    393393        }
    394394
    395         void validateType( Type *type, const Indexer *indexer ) {
     395        void validateType( Type * type, const Indexer * indexer ) {
    396396                PassVisitor<EnumAndPointerDecay_old> epc;
    397397                PassVisitor<LinkReferenceToTypes_old> lrt( indexer );
     
    496496        }
    497497
    498         bool shouldHoist( Declaration *decl ) {
     498        bool shouldHoist( Declaration * decl ) {
    499499                return dynamic_cast< StructDecl * >( decl ) || dynamic_cast< UnionDecl * >( decl ) || dynamic_cast< StaticAssertDecl * >( decl );
    500500        }
     
    515515
    516516        template< typename AggDecl >
    517         void HoistStruct::handleAggregate( AggDecl *aggregateDecl ) {
     517        void HoistStruct::handleAggregate( AggDecl * aggregateDecl ) {
    518518                if ( parentAggr ) {
    519519                        aggregateDecl->parent = parentAggr;
     
    560560
    561561
    562         bool isTypedef( Declaration *decl ) {
     562        bool isTypedef( Declaration * decl ) {
    563563                return dynamic_cast< TypedefDecl * >( decl );
    564564        }
     
    571571
    572572        template< typename AggDecl >
    573         void EliminateTypedef::handleAggregate( AggDecl *aggregateDecl ) {
     573        void EliminateTypedef::handleAggregate( AggDecl * aggregateDecl ) {
    574574                filter( aggregateDecl->members, isTypedef, true );
    575575        }
     
    586586                // remove and delete decl stmts
    587587                filter( compoundStmt->kids, [](Statement * stmt) {
    588                         if ( DeclStmt *declStmt = dynamic_cast< DeclStmt * >( stmt ) ) {
     588                        if ( DeclStmt * declStmt = dynamic_cast< DeclStmt * >( stmt ) ) {
    589589                                if ( dynamic_cast< TypedefDecl * >( declStmt->decl ) ) {
    590590                                        return true;
     
    595595        }
    596596
    597         void EnumAndPointerDecay_old::previsit( EnumDecl *enumDecl ) {
     597        void EnumAndPointerDecay_old::previsit( EnumDecl * enumDecl ) {
    598598                // Set the type of each member of the enumeration to be EnumConstant
    599599                for ( std::list< Declaration * >::iterator i = enumDecl->members.begin(); i != enumDecl->members.end(); ++i ) {
    600                         ObjectDecl * obj = dynamic_cast< ObjectDecl * >( *i );
     600                        ObjectDecl * obj = dynamic_cast< ObjectDecl * >( * i );
    601601                        assert( obj );
    602602                        obj->set_type( new EnumInstType( Type::Qualifiers( Type::Const ), enumDecl->name ) );
     
    627627        }
    628628
    629         void EnumAndPointerDecay_old::previsit( FunctionType *func ) {
     629        void EnumAndPointerDecay_old::previsit( FunctionType * func ) {
    630630                // Fix up parameters and return types
    631631                fixFunctionList( func->parameters, func->isVarArgs, func );
     
    633633        }
    634634
    635         LinkReferenceToTypes_old::LinkReferenceToTypes_old( const Indexer *other_indexer ) {
     635        LinkReferenceToTypes_old::LinkReferenceToTypes_old( const Indexer * other_indexer ) {
    636636                if ( other_indexer ) {
    637637                        local_indexer = other_indexer;
     
    641641        }
    642642
    643         void LinkReferenceToTypes_old::postvisit( EnumInstType *enumInst ) {
    644                 EnumDecl *st = local_indexer->lookupEnum( enumInst->name );
     643        void LinkReferenceToTypes_old::postvisit( EnumInstType * enumInst ) {
     644                const EnumDecl * st = local_indexer->lookupEnum( enumInst->name );
    645645                // it's not a semantic error if the enum is not found, just an implicit forward declaration
    646646                if ( st ) {
    647                         enumInst->baseEnum = st;
     647                        enumInst->baseEnum = const_cast<EnumDecl *>(st); // Just linking in the node
    648648                } // if
    649649                if ( ! st || ! st->body ) {
     
    661661        }
    662662
    663         void LinkReferenceToTypes_old::postvisit( StructInstType *structInst ) {
    664                 StructDecl *st = local_indexer->lookupStruct( structInst->name );
     663        void LinkReferenceToTypes_old::postvisit( StructInstType * structInst ) {
     664                const StructDecl * st = local_indexer->lookupStruct( structInst->name );
    665665                // it's not a semantic error if the struct is not found, just an implicit forward declaration
    666666                if ( st ) {
    667                         structInst->baseStruct = st;
     667                        structInst->baseStruct = const_cast<StructDecl *>(st); // Just linking in the node
    668668                } // if
    669669                if ( ! st || ! st->body ) {
     
    674674        }
    675675
    676         void LinkReferenceToTypes_old::postvisit( UnionInstType *unionInst ) {
    677                 UnionDecl *un = local_indexer->lookupUnion( unionInst->name );
     676        void LinkReferenceToTypes_old::postvisit( UnionInstType * unionInst ) {
     677                const UnionDecl * un = local_indexer->lookupUnion( unionInst->name );
    678678                // it's not a semantic error if the union is not found, just an implicit forward declaration
    679679                if ( un ) {
    680                         unionInst->baseUnion = un;
     680                        unionInst->baseUnion = const_cast<UnionDecl *>(un); // Just linking in the node
    681681                } // if
    682682                if ( ! un || ! un->body ) {
     
    693693        void LinkReferenceToTypes_old::postvisit( QualifiedType * qualType ) {
    694694                // linking only makes sense for the 'oldest ancestor' of the qualified type
    695                 qualType->parent->accept( *visitor );
     695                qualType->parent->accept( * visitor );
    696696        }
    697697
     
    762762        void LinkReferenceToTypes_old::postvisit( TraitInstType * traitInst ) {
    763763                // handle other traits
    764                 TraitDecl *traitDecl = local_indexer->lookupTrait( traitInst->name );
     764                const TraitDecl * traitDecl = local_indexer->lookupTrait( traitInst->name );
    765765                if ( ! traitDecl ) {
    766766                        SemanticError( traitInst->location, "use of undeclared trait " + traitInst->name );
     
    769769                        SemanticError( traitInst, "incorrect number of trait parameters: " );
    770770                } // if
    771                 traitInst->baseTrait = traitDecl;
     771                traitInst->baseTrait = const_cast<TraitDecl *>(traitDecl); // Just linking in the node
    772772
    773773                // need to carry over the 'sized' status of each decl in the instance
     
    786786        }
    787787
    788         void LinkReferenceToTypes_old::postvisit( EnumDecl *enumDecl ) {
     788        void LinkReferenceToTypes_old::postvisit( EnumDecl * enumDecl ) {
    789789                // visit enum members first so that the types of self-referencing members are updated properly
    790790                if ( enumDecl->body ) {
     
    792792                        if ( fwds != forwardEnums.end() ) {
    793793                                for ( std::list< EnumInstType * >::iterator inst = fwds->second.begin(); inst != fwds->second.end(); ++inst ) {
    794                                         (*inst)->baseEnum = enumDecl;
     794                                        (* inst)->baseEnum = enumDecl;
    795795                                } // for
    796796                                forwardEnums.erase( fwds );
     
    834834        }
    835835
    836         void LinkReferenceToTypes_old::postvisit( StructDecl *structDecl ) {
     836        void LinkReferenceToTypes_old::postvisit( StructDecl * structDecl ) {
    837837                // visit struct members first so that the types of self-referencing members are updated properly
    838838                // xxx - need to ensure that type parameters match up between forward declarations and definition (most importantly, number of type parameters and their defaults)
     
    841841                        if ( fwds != forwardStructs.end() ) {
    842842                                for ( std::list< StructInstType * >::iterator inst = fwds->second.begin(); inst != fwds->second.end(); ++inst ) {
    843                                         (*inst)->baseStruct = structDecl;
     843                                        (* inst)->baseStruct = structDecl;
    844844                                } // for
    845845                                forwardStructs.erase( fwds );
     
    848848        }
    849849
    850         void LinkReferenceToTypes_old::postvisit( UnionDecl *unionDecl ) {
     850        void LinkReferenceToTypes_old::postvisit( UnionDecl * unionDecl ) {
    851851                if ( unionDecl->body ) {
    852852                        ForwardUnionsType::iterator fwds = forwardUnions.find( unionDecl->name );
    853853                        if ( fwds != forwardUnions.end() ) {
    854854                                for ( std::list< UnionInstType * >::iterator inst = fwds->second.begin(); inst != fwds->second.end(); ++inst ) {
    855                                         (*inst)->baseUnion = unionDecl;
     855                                        (* inst)->baseUnion = unionDecl;
    856856                                } // for
    857857                                forwardUnions.erase( fwds );
     
    860860        }
    861861
    862         void LinkReferenceToTypes_old::postvisit( TypeInstType *typeInst ) {
     862        void LinkReferenceToTypes_old::postvisit( TypeInstType * typeInst ) {
    863863                // ensure generic parameter instances are renamed like the base type
    864864                if ( inGeneric && typeInst->baseType ) typeInst->name = typeInst->baseType->name;
    865                 if ( NamedTypeDecl *namedTypeDecl = local_indexer->lookupType( typeInst->name ) ) {
    866                         if ( TypeDecl *typeDecl = dynamic_cast< TypeDecl * >( namedTypeDecl ) ) {
    867                                 typeInst->set_isFtype( typeDecl->get_kind() == TypeDecl::Ftype );
     865                if ( const NamedTypeDecl * namedTypeDecl = local_indexer->lookupType( typeInst->name ) ) {
     866                        if ( const TypeDecl * typeDecl = dynamic_cast< const TypeDecl * >( namedTypeDecl ) ) {
     867                                typeInst->set_isFtype( typeDecl->kind == TypeDecl::Ftype );
    868868                        } // if
    869869                } // if
     
    877877                        // expand trait instances into their members
    878878                        for ( DeclarationWithType * assertion : asserts ) {
    879                                 if ( TraitInstType *traitInst = dynamic_cast< TraitInstType * >( assertion->get_type() ) ) {
     879                                if ( TraitInstType * traitInst = dynamic_cast< TraitInstType * >( assertion->get_type() ) ) {
    880880                                        // expand trait instance into all of its members
    881881                                        expandAssertions( traitInst, back_inserter( type->assertions ) );
     
    897897        }
    898898
    899         void ForallPointerDecay_old::previsit( ObjectDecl *object ) {
     899        void ForallPointerDecay_old::previsit( ObjectDecl * object ) {
    900900                // ensure that operator names only apply to functions or function pointers
    901901                if ( CodeGen::isOperator( object->name ) && ! dynamic_cast< FunctionType * >( object->type->stripDeclarator() ) ) {
     
    905905        }
    906906
    907         void ForallPointerDecay_old::previsit( FunctionDecl *func ) {
     907        void ForallPointerDecay_old::previsit( FunctionDecl * func ) {
    908908                func->fixUniqueId();
    909909        }
     
    961961        Type * ReplaceTypedef::postmutate( QualifiedType * qualType ) {
    962962                // replacing typedefs only makes sense for the 'oldest ancestor' of the qualified type
    963                 qualType->parent = qualType->parent->acceptMutator( *visitor );
     963                qualType->parent = qualType->parent->acceptMutator( * visitor );
    964964                return qualType;
    965965        }
     
    970970                TypedefMap::const_iterator def = typedefNames.find( typeInst->name );
    971971                if ( def != typedefNames.end() ) {
    972                         Type *ret = def->second.first->base->clone();
     972                        Type * ret = def->second.first->base->clone();
    973973                        ret->location = typeInst->location;
    974974                        ret->get_qualifiers() |= typeInst->get_qualifiers();
     
    982982                        // place instance parameters on the typedef'd type
    983983                        if ( ! typeInst->parameters.empty() ) {
    984                                 ReferenceToType *rtt = dynamic_cast<ReferenceToType*>(ret);
     984                                ReferenceToType * rtt = dynamic_cast<ReferenceToType *>(ret);
    985985                                if ( ! rtt ) {
    986986                                        SemanticError( typeInst->location, "Cannot apply type parameters to base type of " + typeInst->name );
     
    988988                                rtt->parameters.clear();
    989989                                cloneAll( typeInst->parameters, rtt->parameters );
    990                                 mutateAll( rtt->parameters, *visitor );  // recursively fix typedefs on parameters
     990                                mutateAll( rtt->parameters, * visitor );  // recursively fix typedefs on parameters
    991991                        } // if
    992992                        delete typeInst;
     
    10431043                //    struct screen;
    10441044                // because the expansion of the typedef is:
    1045                 //    void rtn( SCREEN *p ) => void rtn( struct screen *p )
     1045                //    void rtn( SCREEN * p ) => void rtn( struct screen * p )
    10461046                // hence the type-name "screen" must be defined.
    10471047                // Note, qualifiers on the typedef are superfluous for the forward declaration.
    10481048
    1049                 Type *designatorType = tyDecl->base->stripDeclarator();
    1050                 if ( StructInstType *aggDecl = dynamic_cast< StructInstType * >( designatorType ) ) {
     1049                Type * designatorType = tyDecl->base->stripDeclarator();
     1050                if ( StructInstType * aggDecl = dynamic_cast< StructInstType * >( designatorType ) ) {
    10511051                        declsToAddBefore.push_back( new StructDecl( aggDecl->name, DeclarationNode::Struct, noAttributes, tyDecl->linkage ) );
    1052                 } else if ( UnionInstType *aggDecl = dynamic_cast< UnionInstType * >( designatorType ) ) {
     1052                } else if ( UnionInstType * aggDecl = dynamic_cast< UnionInstType * >( designatorType ) ) {
    10531053                        declsToAddBefore.push_back( new UnionDecl( aggDecl->name, noAttributes, tyDecl->linkage ) );
    1054                 } else if ( EnumInstType *enumDecl = dynamic_cast< EnumInstType * >( designatorType ) ) {
     1054                } else if ( EnumInstType * enumDecl = dynamic_cast< EnumInstType * >( designatorType ) ) {
    10551055                        declsToAddBefore.push_back( new EnumDecl( enumDecl->name, noAttributes, tyDecl->linkage ) );
    10561056                } // if
     
    10781078
    10791079        DeclarationWithType * ReplaceTypedef::postmutate( ObjectDecl * objDecl ) {
    1080                 if ( FunctionType *funtype = dynamic_cast<FunctionType *>( objDecl->type ) ) { // function type?
     1080                if ( FunctionType * funtype = dynamic_cast<FunctionType *>( objDecl->type ) ) { // function type?
    10811081                        // replace the current object declaration with a function declaration
    10821082                        FunctionDecl * newDecl = new FunctionDecl( objDecl->name, objDecl->get_storageClasses(), objDecl->linkage, funtype, 0, objDecl->attributes, objDecl->get_funcSpec() );
     
    11041104        void ReplaceTypedef::addImplicitTypedef( AggDecl * aggDecl ) {
    11051105                if ( typedefNames.count( aggDecl->get_name() ) == 0 ) {
    1106                         Type *type = nullptr;
     1106                        Type * type = nullptr;
    11071107                        if ( StructDecl * newDeclStructDecl = dynamic_cast< StructDecl * >( aggDecl ) ) {
    11081108                                type = new StructInstType( Type::Qualifiers(), newDeclStructDecl->get_name() );
     
    11301130                GuardScope( typedefNames );
    11311131                GuardScope( typedeclNames );
    1132                 mutateAll( aggr->parameters, *visitor );
     1132                mutateAll( aggr->parameters, * visitor );
    11331133
    11341134                // unroll mutateAll for aggr->members so that implicit typedefs for nested types are added to the aggregate body.
     
    11371137
    11381138                        try {
    1139                                 *i = maybeMutate( *i, *visitor );
     1139                                * i = maybeMutate( * i, * visitor );
    11401140                        } catch ( SemanticErrorException &e ) {
    11411141                                errors.append( e );
     
    12171217                        for ( size_t i = 0; paramIter != params->end(); ++paramIter, ++i ) {
    12181218                                if ( i < args.size() ) {
    1219                                         TypeExpr * expr = strict_dynamic_cast< TypeExpr * >( *std::next( args.begin(), i ) );
    1220                                         sub.add( (*paramIter)->get_name(), expr->get_type()->clone() );
     1219                                        TypeExpr * expr = strict_dynamic_cast< TypeExpr * >( * std::next( args.begin(), i ) );
     1220                                        sub.add( (* paramIter)->get_name(), expr->get_type()->clone() );
    12211221                                } else if ( i == args.size() ) {
    1222                                         Type * defaultType = (*paramIter)->get_init();
     1222                                        Type * defaultType = (* paramIter)->get_init();
    12231223                                        if ( defaultType ) {
    12241224                                                args.push_back( new TypeExpr( defaultType->clone() ) );
    1225                                                 sub.add( (*paramIter)->get_name(), defaultType->clone() );
     1225                                                sub.add( (* paramIter)->get_name(), defaultType->clone() );
    12261226                                        }
    12271227                                }
     
    12421242        }
    12431243
    1244         void CompoundLiteral::premutate( ObjectDecl *objectDecl ) {
     1244        void CompoundLiteral::premutate( ObjectDecl * objectDecl ) {
    12451245                storageClasses = objectDecl->get_storageClasses();
    12461246        }
    12471247
    1248         Expression *CompoundLiteral::postmutate( CompoundLiteralExpr *compLitExpr ) {
     1248        Expression * CompoundLiteral::postmutate( CompoundLiteralExpr * compLitExpr ) {
    12491249                // transform [storage_class] ... (struct S){ 3, ... };
    12501250                // into [storage_class] struct S temp =  { 3, ... };
    12511251                static UniqueName indexName( "_compLit" );
    12521252
    1253                 ObjectDecl *tempvar = new ObjectDecl( indexName.newName(), storageClasses, LinkageSpec::C, nullptr, compLitExpr->get_result(), compLitExpr->get_initializer() );
     1253                ObjectDecl * tempvar = new ObjectDecl( indexName.newName(), storageClasses, LinkageSpec::C, nullptr, compLitExpr->get_result(), compLitExpr->get_initializer() );
    12541254                compLitExpr->set_result( nullptr );
    12551255                compLitExpr->set_initializer( nullptr );
     
    12891289                        TupleType * tupleType = strict_dynamic_cast< TupleType * >( ResolvExpr::extractResultType( ftype ) );
    12901290                        // ensure return value is not destructed by explicitly creating an empty ListInit node wherein maybeConstruct is false.
    1291                         ObjectDecl * newRet = new ObjectDecl( "", Type::StorageClasses(), LinkageSpec::Cforall, 0, tupleType, new ListInit( std::list<Initializer*>(), noDesignators, false ) );
     1291                        ObjectDecl * newRet = new ObjectDecl( "", Type::StorageClasses(), LinkageSpec::Cforall, 0, tupleType, new ListInit( std::list<Initializer *>(), noDesignators, false ) );
    12921292                        deleteAll( retVals );
    12931293                        retVals.clear();
     
    13021302
    13031303        void FixObjectType::previsit( ObjectDecl * objDecl ) {
    1304                 Type *new_type = ResolvExpr::resolveTypeof( objDecl->get_type(), indexer );
     1304                Type * new_type = ResolvExpr::resolveTypeof( objDecl->get_type(), indexer );
    13051305                new_type->get_qualifiers() -= Type::Lvalue; // even if typeof is lvalue, variable can never have lvalue-qualified type
    13061306                objDecl->set_type( new_type );
     
    13081308
    13091309        void FixObjectType::previsit( FunctionDecl * funcDecl ) {
    1310                 Type *new_type = ResolvExpr::resolveTypeof( funcDecl->type, indexer );
     1310                Type * new_type = ResolvExpr::resolveTypeof( funcDecl->type, indexer );
    13111311                new_type->get_qualifiers() -= Type::Lvalue; // even if typeof is lvalue, variable can never have lvalue-qualified type
    13121312                funcDecl->set_type( new_type );
    13131313        }
    13141314
    1315         void FixObjectType::previsit( TypeDecl *typeDecl ) {
     1315        void FixObjectType::previsit( TypeDecl * typeDecl ) {
    13161316                if ( typeDecl->get_base() ) {
    1317                         Type *new_type = ResolvExpr::resolveTypeof( typeDecl->get_base(), indexer );
     1317                        Type * new_type = ResolvExpr::resolveTypeof( typeDecl->get_base(), indexer );
    13181318                        new_type->get_qualifiers() -= Type::Lvalue; // even if typeof is lvalue, variable can never have lvalue-qualified type
    13191319                        typeDecl->set_base( new_type );
     
    13781378
    13791379namespace {
    1380         /// Replaces enum types by int, and function/array types in function parameter and return 
     1380        /// Replaces enum types by int, and function/array types in function parameter and return
    13811381        /// lists by appropriate pointers
    13821382        struct EnumAndPointerDecay_new {
     
    13851385                        for ( unsigned i = 0; i < enumDecl->members.size(); ++i ) {
    13861386                                // build new version of object with EnumConstant
    1387                                 ast::ptr< ast::ObjectDecl > obj = 
     1387                                ast::ptr< ast::ObjectDecl > obj =
    13881388                                        enumDecl->members[i].strict_as< ast::ObjectDecl >();
    1389                                 obj.get_and_mutate()->type = 
     1389                                obj.get_and_mutate()->type =
    13901390                                        new ast::EnumInstType{ enumDecl->name, ast::CV::Const };
    1391                                
     1391
    13921392                                // set into decl
    13931393                                ast::EnumDecl * mut = mutate( enumDecl );
     
    13991399
    14001400                static const ast::FunctionType * fixFunctionList(
    1401                         const ast::FunctionType * func, 
     1401                        const ast::FunctionType * func,
    14021402                        std::vector< ast::ptr< ast::DeclWithType > > ast::FunctionType::* field,
    14031403                        ast::ArgumentFlag isVarArgs = ast::FixedArgs
    14041404                ) {
    1405                         const auto & dwts = func->*field;
     1405                        const auto & dwts = func->* field;
    14061406                        unsigned nvals = dwts.size();
    14071407                        bool hasVoid = false;
     
    14091409                                func = ast::mutate_field_index( func, field, i, fixFunction( dwts[i], hasVoid ) );
    14101410                        }
    1411                        
     1411
    14121412                        // the only case in which "void" is valid is where it is the only one in the list
    14131413                        if ( hasVoid && ( nvals > 1 || isVarArgs ) ) {
    1414                                 SemanticError( 
     1414                                SemanticError(
    14151415                                        dwts.front()->location, func, "invalid type void in function type" );
    14161416                        }
     
    14181418                        // one void is the only thing in the list, remove it
    14191419                        if ( hasVoid ) {
    1420                                 func = ast::mutate_field( 
     1420                                func = ast::mutate_field(
    14211421                                        func, field, std::vector< ast::ptr< ast::DeclWithType > >{} );
    14221422                        }
     
    14321432
    14331433        /// expand assertions from a trait instance, performing appropriate type variable substitutions
    1434         void expandAssertions( 
    1435                 const ast::TraitInstType * inst, std::vector< ast::ptr< ast::DeclWithType > > & out 
     1434        void expandAssertions(
     1435                const ast::TraitInstType * inst, std::vector< ast::ptr< ast::DeclWithType > > & out
    14361436        ) {
    14371437                assertf( inst->base, "Trait instance not linked to base trait: %s", toCString( inst ) );
    14381438
    14391439                // build list of trait members, substituting trait decl parameters for instance parameters
    1440                 ast::TypeSubstitution sub{ 
     1440                ast::TypeSubstitution sub{
    14411441                        inst->base->params.begin(), inst->base->params.end(), inst->params.begin() };
    14421442                // deliberately take ast::ptr by-value to ensure this does not mutate inst->base
     
    14491449
    14501450        /// Associates forward declarations of aggregates with their definitions
    1451         class LinkReferenceToTypes_new final 
    1452         : public ast::WithSymbolTable, public ast::WithGuards, public 
     1451        class LinkReferenceToTypes_new final
     1452        : public ast::WithSymbolTable, public ast::WithGuards, public
    14531453          ast::WithVisitorRef<LinkReferenceToTypes_new>, public ast::WithShortCircuiting {
    1454                
    1455                 // these maps of uses of forward declarations of types need to have the actual type 
    1456                 // declaration switched in *after* they have been traversed. To enable this in the
    1457                 // ast::Pass framework, any node that needs to be so mutated has mutate() called on it 
    1458                 // before it is placed in the map, properly updating its parents in the usual traversal, 
     1454
     1455                // these maps of uses of forward declarations of types need to have the actual type
     1456                // declaration switched in * after * they have been traversed. To enable this in the
     1457                // ast::Pass framework, any node that needs to be so mutated has mutate() called on it
     1458                // before it is placed in the map, properly updating its parents in the usual traversal,
    14591459                // then can have the actual mutation applied later
    14601460                using ForwardEnumsType = std::unordered_multimap< std::string, ast::EnumInstType * >;
    14611461                using ForwardStructsType = std::unordered_multimap< std::string, ast::StructInstType * >;
    14621462                using ForwardUnionsType = std::unordered_multimap< std::string, ast::UnionInstType * >;
    1463                
     1463
    14641464                const CodeLocation & location;
    14651465                const ast::SymbolTable * localSymtab;
    1466                
     1466
    14671467                ForwardEnumsType forwardEnums;
    14681468                ForwardStructsType forwardStructs;
    14691469                ForwardUnionsType forwardUnions;
    14701470
    1471                 /// true if currently in a generic type body, so that type parameter instances can be 
     1471                /// true if currently in a generic type body, so that type parameter instances can be
    14721472                /// renamed appropriately
    14731473                bool inGeneric = false;
     
    14751475        public:
    14761476                /// contstruct using running symbol table
    1477                 LinkReferenceToTypes_new( const CodeLocation & loc ) 
     1477                LinkReferenceToTypes_new( const CodeLocation & loc )
    14781478                : location( loc ), localSymtab( &symtab ) {}
    1479                
     1479
    14801480                /// construct using provided symbol table
    1481                 LinkReferenceToTypes_new( const CodeLocation & loc, const ast::SymbolTable & syms ) 
     1481                LinkReferenceToTypes_new( const CodeLocation & loc, const ast::SymbolTable & syms )
    14821482                : location( loc ), localSymtab( &syms ) {}
    14831483
     
    14851485                        // ensure generic parameter instances are renamed like the base type
    14861486                        if ( inGeneric && typeInst->base ) {
    1487                                 typeInst = ast::mutate_field( 
     1487                                typeInst = ast::mutate_field(
    14881488                                        typeInst, &ast::TypeInstType::name, typeInst->base->name );
    14891489                        }
    14901490
    1491                         if ( 
    1492                                 auto typeDecl = dynamic_cast< const ast::TypeDecl * >( 
    1493                                         localSymtab->lookupType( typeInst->name ) ) 
     1491                        if (
     1492                                auto typeDecl = dynamic_cast< const ast::TypeDecl * >(
     1493                                        localSymtab->lookupType( typeInst->name ) )
    14941494                        ) {
    14951495                                typeInst = ast::mutate_field( typeInst, &ast::TypeInstType::kind, typeDecl->kind );
     
    15171517                        for ( const ast::Expr * param : inst->params ) {
    15181518                                if ( ! dynamic_cast< const ast::TypeExpr * >( param ) ) {
    1519                                         SemanticError( 
     1519                                        SemanticError(
    15201520                                                location, inst, "Expression parameters for generic types are currently "
    15211521                                                "unsupported: " );
     
    15711571                                auto expr = traitInst->params[i].as< ast::TypeExpr >();
    15721572                                if ( ! expr ) {
    1573                                         SemanticError( 
     1573                                        SemanticError(
    15741574                                                traitInst->params[i].get(), "Expression parameters for trait instances "
    15751575                                                "are currently unsupported: " );
     
    15931593                        return traitInst;
    15941594                }
    1595                
     1595
    15961596                void previsit( const ast::QualifiedType * ) { visit_children = false; }
    1597                
     1597
    15981598                const ast::Type * postvisit( const ast::QualifiedType * qualType ) {
    15991599                        // linking only makes sense for the "oldest ancestor" of the qualified type
    1600                         return ast::mutate_field( 
    1601                                 qualType, &ast::QualifiedType::parent, qualType->parent->accept( *visitor ) );
     1600                        return ast::mutate_field(
     1601                                qualType, &ast::QualifiedType::parent, qualType->parent->accept( * visitor ) );
    16021602                }
    16031603
    16041604                const ast::Decl * postvisit( const ast::EnumDecl * enumDecl ) {
    1605                         // visit enum members first so that the types of self-referencing members are updated 
     1605                        // visit enum members first so that the types of self-referencing members are updated
    16061606                        // properly
    16071607                        if ( ! enumDecl->body ) return enumDecl;
     
    16121612                                auto inst = fwds.first;
    16131613                                do {
    1614                                         // forward decl is stored *mutably* in map, can thus be updated
     1614                                        // forward decl is stored * mutably * in map, can thus be updated
    16151615                                        inst->second->base = enumDecl;
    16161616                                } while ( ++inst != fwds.second );
    16171617                                forwardEnums.erase( fwds.first, fwds.second );
    16181618                        }
    1619                        
     1619
    16201620                        // ensure that enumerator initializers are properly set
    16211621                        for ( unsigned i = 0; i < enumDecl->members.size(); ++i ) {
    16221622                                auto field = enumDecl->members[i].strict_as< ast::ObjectDecl >();
    16231623                                if ( field->init ) {
    1624                                         // need to resolve enumerator initializers early so that other passes that 
     1624                                        // need to resolve enumerator initializers early so that other passes that
    16251625                                        // determine if an expression is constexpr have appropriate information
    16261626                                        auto init = field->init.strict_as< ast::SingleInit >();
    1627                                        
    1628                                         enumDecl = ast::mutate_field_index( 
    1629                                                 enumDecl, &ast::EnumDecl::members, i, 
    1630                                                 ast::mutate_field( field, &ast::ObjectDecl::init, 
     1627
     1628                                        enumDecl = ast::mutate_field_index(
     1629                                                enumDecl, &ast::EnumDecl::members, i,
     1630                                                ast::mutate_field( field, &ast::ObjectDecl::init,
    16311631                                                        ast::mutate_field( init, &ast::SingleInit::value,
    1632                                                                 ResolvExpr::findSingleExpression( 
     1632                                                                ResolvExpr::findSingleExpression(
    16331633                                                                        init->value, new ast::BasicType{ ast::BasicType::SignedInt },
    16341634                                                                        symtab ) ) ) );
     
    16391639                }
    16401640
    1641                 /// rename generic type parameters uniquely so that they do not conflict with user defined 
     1641                /// rename generic type parameters uniquely so that they do not conflict with user defined
    16421642                /// function forall parameters, e.g. the T in Box and the T in f, below
    16431643                ///   forall(otype T)
     
    16571657                                const ast::TypeDecl * td = aggr->params[i];
    16581658
    1659                                 aggr = ast::mutate_field_index( 
    1660                                         aggr, &AggrDecl::params, i, 
     1659                                aggr = ast::mutate_field_index(
     1660                                        aggr, &AggrDecl::params, i,
    16611661                                        ast::mutate_field( td, &ast::TypeDecl::name, "__" + td->name + "_generic_" ) );
    16621662                        }
     
    16691669
    16701670                void postvisit( const ast::StructDecl * structDecl ) {
    1671                         // visit struct members first so that the types of self-referencing members are 
     1671                        // visit struct members first so that the types of self-referencing members are
    16721672                        // updated properly
    16731673                        if ( ! structDecl->body ) return;
     
    16781678                                auto inst = fwds.first;
    16791679                                do {
    1680                                         // forward decl is stored *mutably* in map, can thus be updated
     1680                                        // forward decl is stored * mutably * in map, can thus be updated
    16811681                                        inst->second->base = structDecl;
    16821682                                } while ( ++inst != fwds.second );
     
    16901690
    16911691                void postvisit( const ast::UnionDecl * unionDecl ) {
    1692                         // visit union members first so that the types of self-referencing members are updated 
     1692                        // visit union members first so that the types of self-referencing members are updated
    16931693                        // properly
    16941694                        if ( ! unionDecl->body ) return;
     
    16991699                                auto inst = fwds.first;
    17001700                                do {
    1701                                         // forward decl is stored *mutably* in map, can thus be updated
     1701                                        // forward decl is stored * mutably * in map, can thus be updated
    17021702                                        inst->second->base = unionDecl;
    17031703                                } while ( ++inst != fwds.second );
     
    17121712                                        "number of parameters: %zd", traitDecl->params.size() );
    17131713
    1714                                 traitDecl = ast::mutate_field_index( 
    1715                                         traitDecl, &ast::TraitDecl::params, 0, 
    1716                                         ast::mutate_field( 
     1714                                traitDecl = ast::mutate_field_index(
     1715                                        traitDecl, &ast::TraitDecl::params, 0,
     1716                                        ast::mutate_field(
    17171717                                                traitDecl->params.front().get(), &ast::TypeDecl::sized, true ) );
    17181718                        }
     
    17371737                                traitDecl = mut;
    17381738                        }
    1739                        
     1739
    17401740                        return traitDecl;
    17411741                }
    17421742        };
    17431743
    1744         /// Replaces array and function types in forall lists by appropriate pointer type and assigns 
     1744        /// Replaces array and function types in forall lists by appropriate pointer type and assigns
    17451745        /// each object and function declaration a unique ID
    17461746        class ForallPointerDecay_new {
     
    17511751                const ast::ObjectDecl * previsit( const ast::ObjectDecl * obj ) {
    17521752                        // ensure that operator names only apply to functions or function pointers
    1753                         if ( 
    1754                                 CodeGen::isOperator( obj->name ) 
     1753                        if (
     1754                                CodeGen::isOperator( obj->name )
    17551755                                && ! dynamic_cast< const ast::FunctionType * >( obj->type->stripDeclarator() )
    17561756                        ) {
     
    17761776                /// Fix up assertions -- flattens assertion lists, removing all trait instances
    17771777                template< typename node_t, typename parent_t >
    1778                 static const node_t * forallFixer( 
    1779                         const CodeLocation & loc, const node_t * node, 
     1778                static const node_t * forallFixer(
     1779                        const CodeLocation & loc, const node_t * node,
    17801780                        ast::ParameterizedType::ForallList parent_t::* forallField
    17811781                ) {
    1782                         for ( unsigned i = 0; i < (node->*forallField).size(); ++i ) {
    1783                                 const ast::TypeDecl * type = (node->*forallField)[i];
     1782                        for ( unsigned i = 0; i < (node->* forallField).size(); ++i ) {
     1783                                const ast::TypeDecl * type = (node->* forallField)[i];
    17841784                                if ( type->assertions.empty() ) continue;
    17851785
     
    17891789                                // expand trait instances into their members
    17901790                                for ( const ast::DeclWithType * assn : type->assertions ) {
    1791                                         auto traitInst = 
    1792                                                 dynamic_cast< const ast::TraitInstType * >( assn->get_type() ); 
     1791                                        auto traitInst =
     1792                                                dynamic_cast< const ast::TraitInstType * >( assn->get_type() );
    17931793                                        if ( traitInst ) {
    17941794                                                // expand trait instance to all its members
     
    18311831} // anonymous namespace
    18321832
    1833 const ast::Type * validateType( 
     1833const ast::Type * validateType(
    18341834                const CodeLocation & loc, const ast::Type * type, const ast::SymbolTable & symtab ) {
    18351835        ast::Pass< EnumAndPointerDecay_new > epc;
  • src/SymTab/Validate.h

    r1f1c102 rf53acdf8  
    1919#include <list>  // for list
    2020
    21 class CodeLocation;
    22 class Declaration;
    23 class Type;
     21struct CodeLocation;
     22class  Declaration;
     23class  Type;
    2424
    2525namespace ast {
     
    3535        void validateType( Type *type, const Indexer *indexer );
    3636
    37         const ast::Type * validateType( 
     37        const ast::Type * validateType(
    3838                const CodeLocation & loc, const ast::Type * type, const ast::SymbolTable & symtab );
    3939} // namespace SymTab
  • src/SynTree/Attribute.h

    r1f1c102 rf53acdf8  
    5050        Attribute * clone() const override { return new Attribute( *this ); }
    5151        virtual void accept( Visitor & v ) override { v.visit( this ); }
     52        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    5253        virtual Attribute * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
    5354        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
  • src/SynTree/BaseSyntaxNode.h

    r1f1c102 rf53acdf8  
    99// Author           : Thierry Delisle
    1010// Created On       : Tue Feb 14 07:44:20 2017
    11 // Last Modified By : Andrew Beach
    12 // Last Modified On : Thr Aug 17 13:44:00
    13 // Update Count     : 1
     11// Last Modified By : Peter A. Buhr
     12// Last Modified On : Wed Jul 10 16:13:49 2019
     13// Update Count     : 4
    1414//
    1515
     
    2525class BaseSyntaxNode {
    2626  public:
    27   static Stats::Counters::SimpleCounter* new_nodes;
     27        static Stats::Counters::SimpleCounter* new_nodes;
    2828
    2929        CodeLocation location;
    3030
    31   BaseSyntaxNode() { ++*new_nodes; }
    32   BaseSyntaxNode( const BaseSyntaxNode& o ) : location(o.location) { ++*new_nodes; }
     31        BaseSyntaxNode() { ++*new_nodes; }
     32        BaseSyntaxNode( const BaseSyntaxNode & o ) : location(o.location) { ++*new_nodes; }
     33        BaseSyntaxNode & operator=( const BaseSyntaxNode & ) = default;
    3334
    3435        virtual ~BaseSyntaxNode() {}
     
    3637        virtual BaseSyntaxNode * clone() const = 0;
    3738        virtual void accept( Visitor & v ) = 0;
     39        virtual void accept( Visitor & v ) const = 0;
    3840        virtual BaseSyntaxNode * acceptMutator( Mutator & m ) = 0;
    39   /// Notes:
    40   /// * each node is responsible for indenting its children.
    41   /// * Expressions should not finish with a newline, since the expression's parent has better information.
     41        /// Notes:
     42        /// * each node is responsible for indenting its children.
     43        /// * Expressions should not finish with a newline, since the expression's parent has better information.
    4244        virtual void print( std::ostream & os, Indenter indent = {} ) const = 0;
    4345};
  • src/SynTree/Constant.h

    r1f1c102 rf53acdf8  
    99// Author           : Richard C. Bilson
    1010// Created On       : Mon May 18 07:44:20 2015
    11 // Last Modified By : Andrew Beach
    12 // Last Modified On : Fri Spt 28 14:48:00 2018
    13 // Update Count     : 18
     11// Last Modified By : Peter A. Buhr
     12// Last Modified On : Wed Jul 10 15:57:38 2019
     13// Update Count     : 19
    1414//
    1515
     
    3030        Constant( Type * type, std::string rep, std::optional<unsigned long long> i );
    3131        Constant( const Constant & other );
     32        Constant & operator=( const Constant & ) = default;
    3233        virtual ~Constant();
    3334
    34         virtual Constant * clone() const { return new Constant( *this ); }
     35        virtual Constant * clone() const override { return new Constant( *this ); }
    3536
    3637        Type * get_type() { return type; }
     
    5051        static Constant null( Type * ptrtype = nullptr );
    5152
    52         virtual void accept( Visitor & v ) { v.visit( this ); }
    53         virtual Constant * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    54         virtual void print( std::ostream & os, Indenter indent = 0 ) const;
    55   private:
     53        virtual void accept( Visitor & v ) override { v.visit( this ); }
     54        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     55        virtual Constant * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     56        virtual void print( std::ostream & os, Indenter indent = 0 ) const override;
     57
    5658        Type * type;
    5759        std::string rep;
    5860        std::optional<unsigned long long> ival;
    59 
    60         friend class ConverterOldToNew;
    6161};
    6262
  • src/SynTree/Declaration.h

    r1f1c102 rf53acdf8  
    6363        void fixUniqueId( void );
    6464        virtual Declaration *clone() const override = 0;
    65         virtual void accept( Visitor &v ) override = 0;
     65        virtual void accept( Visitor & v ) override = 0;
     66        virtual void accept( Visitor & v ) const override = 0;
    6667        virtual Declaration *acceptMutator( Mutator &m ) override = 0;
    6768        virtual void print( std::ostream &os, Indenter indent = {} ) const override = 0;
     
    139140
    140141        virtual ObjectDecl *clone() const override { return new ObjectDecl( *this ); }
    141         virtual void accept( Visitor &v ) override { v.visit( this ); }
     142        virtual void accept( Visitor & v ) override { v.visit( this ); }
     143        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    142144        virtual DeclarationWithType *acceptMutator( Mutator &m )  override { return m.mutate( this ); }
    143145        virtual void print( std::ostream &os, Indenter indent = {} ) const override;
     
    169171
    170172        virtual FunctionDecl *clone() const override { return new FunctionDecl( *this ); }
    171         virtual void accept( Visitor &v ) override { v.visit( this ); }
     173        virtual void accept( Visitor & v ) override { v.visit( this ); }
     174        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    172175        virtual DeclarationWithType *acceptMutator( Mutator &m )  override { return m.mutate( this ); }
    173176        virtual void print( std::ostream &os, Indenter indent = {} ) const override;
     
    238241
    239242        virtual TypeDecl *clone() const override { return new TypeDecl( *this ); }
    240         virtual void accept( Visitor &v ) override { v.visit( this ); }
     243        virtual void accept( Visitor & v ) override { v.visit( this ); }
     244        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    241245        virtual Declaration *acceptMutator( Mutator &m )  override { return m.mutate( this ); }
    242246        virtual void print( std::ostream &os, Indenter indent = {} ) const override;
     
    256260
    257261        virtual TypedefDecl *clone() const override { return new TypedefDecl( *this ); }
    258         virtual void accept( Visitor &v ) override { v.visit( this ); }
     262        virtual void accept( Visitor & v ) override { v.visit( this ); }
     263        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    259264        virtual Declaration *acceptMutator( Mutator &m )  override { return m.mutate( this ); }
    260265  private:
     
    300305
    301306        virtual StructDecl *clone() const override { return new StructDecl( *this ); }
    302         virtual void accept( Visitor &v ) override { v.visit( this ); }
     307        virtual void accept( Visitor & v ) override { v.visit( this ); }
     308        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    303309        virtual Declaration *acceptMutator( Mutator &m )  override { return m.mutate( this ); }
    304310        DeclarationNode::Aggregate kind;
     
    314320
    315321        virtual UnionDecl *clone() const override { return new UnionDecl( *this ); }
    316         virtual void accept( Visitor &v ) override { v.visit( this ); }
     322        virtual void accept( Visitor & v ) override { v.visit( this ); }
     323        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    317324        virtual Declaration *acceptMutator( Mutator &m )  override { return m.mutate( this ); }
    318325  private:
     
    329336
    330337        virtual EnumDecl *clone() const override { return new EnumDecl( *this ); }
    331         virtual void accept( Visitor &v ) override { v.visit( this ); }
     338        virtual void accept( Visitor & v ) override { v.visit( this ); }
     339        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    332340        virtual Declaration *acceptMutator( Mutator &m )  override { return m.mutate( this ); }
    333341  private:
     
    345353
    346354        virtual TraitDecl *clone() const override { return new TraitDecl( *this ); }
    347         virtual void accept( Visitor &v ) override { v.visit( this ); }
    348         virtual Declaration *acceptMutator( Mutator &m )  override { return m.mutate( this ); }
    349   private:
    350         virtual std::string typeString() const override;
     355        virtual void accept( Visitor & v ) override { v.visit( this ); }
     356        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     357        virtual Declaration *acceptMutator( Mutator &m )  override { return m.mutate( this ); }
     358  private:
     359        virtual std::string typeString() const override;
     360};
     361
     362class WithStmt : public Declaration {
     363public:
     364        std::list< Expression * > exprs;
     365        Statement * stmt;
     366
     367        WithStmt( const std::list< Expression * > & exprs, Statement * stmt );
     368        WithStmt( const WithStmt & other );
     369        virtual ~WithStmt();
     370
     371        virtual WithStmt * clone() const override { return new WithStmt( *this ); }
     372        virtual void accept( Visitor & v ) override { v.visit( this ); }
     373        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     374        virtual Declaration * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
     375        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     376        virtual void printShort( std::ostream & os, Indenter indent = {} ) const override { print(os, indent); }
    351377};
    352378
     
    363389
    364390        virtual AsmDecl *clone() const override { return new AsmDecl( *this ); }
    365         virtual void accept( Visitor &v ) override { v.visit( this ); }
     391        virtual void accept( Visitor & v ) override { v.visit( this ); }
     392        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    366393        virtual AsmDecl *acceptMutator( Mutator &m )  override { return m.mutate( this ); }
    367394        virtual void print( std::ostream &os, Indenter indent = {} ) const override;
     
    379406
    380407        virtual StaticAssertDecl * clone() const override { return new StaticAssertDecl( *this ); }
    381         virtual void accept( Visitor &v ) override { v.visit( this ); }
     408        virtual void accept( Visitor & v ) override { v.visit( this ); }
     409        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    382410        virtual StaticAssertDecl * acceptMutator( Mutator &m )  override { return m.mutate( this ); }
    383411        virtual void print( std::ostream &os, Indenter indent = {} ) const override;
  • src/SynTree/Expression.cc

    r1f1c102 rf53acdf8  
    724724}
    725725
    726 DeletedExpr::DeletedExpr( Expression * expr, BaseSyntaxNode * deleteStmt ) : expr( expr ), deleteStmt( deleteStmt ) {
     726DeletedExpr::DeletedExpr( Expression * expr, Declaration * deleteStmt ) : expr( expr ), deleteStmt( deleteStmt ) {
    727727        assert( expr->result );
    728728        result = expr->result->clone();
  • src/SynTree/Expression.h

    r1f1c102 rf53acdf8  
    8282        virtual Expression * clone() const override = 0;
    8383        virtual void accept( Visitor & v ) override = 0;
     84        virtual void accept( Visitor & v ) const override = 0;
    8485        virtual Expression * acceptMutator( Mutator & m ) override = 0;
    8586        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    101102        std::list<Expression *>& get_args() { return args; }
    102103
    103         virtual ApplicationExpr * clone() const { return new ApplicationExpr( * this ); }
    104         virtual void accept( Visitor & v ) { v.visit( this ); }
    105         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    106         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     104        virtual ApplicationExpr * clone() const override { return new ApplicationExpr( * this ); }
     105        virtual void accept( Visitor & v ) override { v.visit( this ); }
     106        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     107        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     108        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    107109};
    108110
     
    129131        static UntypedExpr * createAssign( Expression * arg1, Expression * arg2 );
    130132
    131         virtual UntypedExpr * clone() const { return new UntypedExpr( * this ); }
    132         virtual void accept( Visitor & v ) { v.visit( this ); }
    133         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    134         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     133        virtual UntypedExpr * clone() const override { return new UntypedExpr( * this ); }
     134        virtual void accept( Visitor & v ) override { v.visit( this ); }
     135        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     136        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     137        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    135138};
    136139
     
    147150        void set_name( std::string newValue ) { name = newValue; }
    148151
    149         virtual NameExpr * clone() const { return new NameExpr( * this ); }
    150         virtual void accept( Visitor & v ) { v.visit( this ); }
    151         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    152         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     152        virtual NameExpr * clone() const override { return new NameExpr( * this ); }
     153        virtual void accept( Visitor & v ) override { v.visit( this ); }
     154        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     155        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     156        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    153157};
    154158
     
    168172        void set_arg(Expression * newValue ) { arg = newValue; }
    169173
    170         virtual AddressExpr * clone() const { return new AddressExpr( * this ); }
    171         virtual void accept( Visitor & v ) { v.visit( this ); }
    172         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    173         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     174        virtual AddressExpr * clone() const override { return new AddressExpr( * this ); }
     175        virtual void accept( Visitor & v ) override { v.visit( this ); }
     176        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     177        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     178        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    174179};
    175180
     
    184189        virtual ~LabelAddressExpr();
    185190
    186         virtual LabelAddressExpr * clone() const { return new LabelAddressExpr( * this ); }
    187         virtual void accept( Visitor & v ) { v.visit( this ); }
    188         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    189         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     191        virtual LabelAddressExpr * clone() const override { return new LabelAddressExpr( * this ); }
     192        virtual void accept( Visitor & v ) override { v.visit( this ); }
     193        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     194        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     195        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    190196};
    191197
     
    205211        void set_arg( Expression * newValue ) { arg = newValue; }
    206212
    207         virtual CastExpr * clone() const { return new CastExpr( * this ); }
    208         virtual void accept( Visitor & v ) { v.visit( this ); }
    209         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    210         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     213        virtual CastExpr * clone() const override { return new CastExpr( * this ); }
     214        virtual void accept( Visitor & v ) override { v.visit( this ); }
     215        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     216        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     217        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    211218};
    212219
     
    225232        const std::string & targetString() const;
    226233
    227         virtual KeywordCastExpr * clone() const { return new KeywordCastExpr( * this ); }
    228         virtual void accept( Visitor & v ) { v.visit( this ); }
    229         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    230         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     234        virtual KeywordCastExpr * clone() const override { return new KeywordCastExpr( * this ); }
     235        virtual void accept( Visitor & v ) override { v.visit( this ); }
     236        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     237        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     238        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    231239};
    232240
     
    243251        void set_arg( Expression * newValue ) { arg = newValue; }
    244252
    245         virtual VirtualCastExpr * clone() const { return new VirtualCastExpr( * this ); }
    246         virtual void accept( Visitor & v ) { v.visit( this ); }
    247         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    248         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     253        virtual VirtualCastExpr * clone() const override { return new VirtualCastExpr( * this ); }
     254        virtual void accept( Visitor & v ) override { v.visit( this ); }
     255        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     256        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     257        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    249258};
    250259
     
    264273        void set_aggregate( Expression * newValue ) { aggregate = newValue; }
    265274
    266         virtual UntypedMemberExpr * clone() const { return new UntypedMemberExpr( * this ); }
    267         virtual void accept( Visitor & v ) { v.visit( this ); }
    268         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    269         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     275        virtual UntypedMemberExpr * clone() const override { return new UntypedMemberExpr( * this ); }
     276        virtual void accept( Visitor & v ) override { v.visit( this ); }
     277        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     278        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     279        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    270280};
    271281
     
    286296        void set_aggregate( Expression * newValue ) { aggregate = newValue; }
    287297
    288         virtual MemberExpr * clone() const { return new MemberExpr( * this ); }
    289         virtual void accept( Visitor & v ) { v.visit( this ); }
    290         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    291         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     298        virtual MemberExpr * clone() const override { return new MemberExpr( * this ); }
     299        virtual void accept( Visitor & v ) override { v.visit( this ); }
     300        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     301        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     302        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    292303};
    293304
     
    308319        static VariableExpr * functionPointer( FunctionDecl * decl );
    309320
    310         virtual VariableExpr * clone() const { return new VariableExpr( * this ); }
    311         virtual void accept( Visitor & v ) { v.visit( this ); }
    312         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    313         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     321        virtual VariableExpr * clone() const override { return new VariableExpr( * this ); }
     322        virtual void accept( Visitor & v ) override { v.visit( this ); }
     323        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     324        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     325        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    314326};
    315327
     
    329341        long long int intValue() const;
    330342
    331         virtual ConstantExpr * clone() const { return new ConstantExpr( * this ); }
    332         virtual void accept( Visitor & v ) { v.visit( this ); }
    333         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    334         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     343        virtual ConstantExpr * clone() const override { return new ConstantExpr( * this ); }
     344        virtual void accept( Visitor & v ) override { v.visit( this ); }
     345        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     346        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     347        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    335348};
    336349
     
    354367        void set_isType( bool newValue ) { isType = newValue; }
    355368
    356         virtual SizeofExpr * clone() const { return new SizeofExpr( * this ); }
    357         virtual void accept( Visitor & v ) { v.visit( this ); }
    358         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    359         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     369        virtual SizeofExpr * clone() const override { return new SizeofExpr( * this ); }
     370        virtual void accept( Visitor & v ) override { v.visit( this ); }
     371        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     372        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     373        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    360374};
    361375
     
    379393        void set_isType( bool newValue ) { isType = newValue; }
    380394
    381         virtual AlignofExpr * clone() const { return new AlignofExpr( * this ); }
    382         virtual void accept( Visitor & v ) { v.visit( this ); }
    383         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    384         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     395        virtual AlignofExpr * clone() const override { return new AlignofExpr( * this ); }
     396        virtual void accept( Visitor & v ) override { v.visit( this ); }
     397        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     398        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     399        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    385400};
    386401
     
    400415        void set_type( Type * newValue ) { type = newValue; }
    401416
    402         virtual UntypedOffsetofExpr * clone() const { return new UntypedOffsetofExpr( * this ); }
    403         virtual void accept( Visitor & v ) { v.visit( this ); }
    404         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    405         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     417        virtual UntypedOffsetofExpr * clone() const override { return new UntypedOffsetofExpr( * this ); }
     418        virtual void accept( Visitor & v ) override { v.visit( this ); }
     419        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     420        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     421        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    406422};
    407423
     
    421437        void set_member( DeclarationWithType * newValue ) { member = newValue; }
    422438
    423         virtual OffsetofExpr * clone() const { return new OffsetofExpr( * this ); }
    424         virtual void accept( Visitor & v ) { v.visit( this ); }
    425         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    426         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     439        virtual OffsetofExpr * clone() const override { return new OffsetofExpr( * this ); }
     440        virtual void accept( Visitor & v ) override { v.visit( this ); }
     441        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     442        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     443        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    427444};
    428445
     
    439456        void set_type( StructInstType * newValue ) { type = newValue; }
    440457
    441         virtual OffsetPackExpr * clone() const { return new OffsetPackExpr( * this ); }
    442         virtual void accept( Visitor & v ) { v.visit( this ); }
    443         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    444         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     458        virtual OffsetPackExpr * clone() const override { return new OffsetPackExpr( * this ); }
     459        virtual void accept( Visitor & v ) override { v.visit( this ); }
     460        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     461        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     462        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    445463};
    446464
     
    467485        void set_isType( bool newValue ) { isType = newValue; }
    468486
    469         virtual AttrExpr * clone() const { return new AttrExpr( * this ); }
    470         virtual void accept( Visitor & v ) { v.visit( this ); }
    471         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    472         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     487        virtual AttrExpr * clone() const override { return new AttrExpr( * this ); }
     488        virtual void accept( Visitor & v ) override { v.visit( this ); }
     489        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     490        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     491        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    473492};
    474493
     
    489508        void set_arg2( Expression * newValue ) { arg2 = newValue; }
    490509
    491         virtual LogicalExpr * clone() const { return new LogicalExpr( * this ); }
    492         virtual void accept( Visitor & v ) { v.visit( this ); }
    493         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    494         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     510        virtual LogicalExpr * clone() const override { return new LogicalExpr( * this ); }
     511        virtual void accept( Visitor & v ) override { v.visit( this ); }
     512        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     513        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     514        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    495515
    496516  private:
     
    516536        void set_arg3( Expression * newValue ) { arg3 = newValue; }
    517537
    518         virtual ConditionalExpr * clone() const { return new ConditionalExpr( * this ); }
    519         virtual void accept( Visitor & v ) { v.visit( this ); }
    520         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    521         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     538        virtual ConditionalExpr * clone() const override { return new ConditionalExpr( * this ); }
     539        virtual void accept( Visitor & v ) override { v.visit( this ); }
     540        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     541        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     542        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    522543};
    523544
     
    537558        void set_arg2( Expression * newValue ) { arg2 = newValue; }
    538559
    539         virtual CommaExpr * clone() const { return new CommaExpr( * this ); }
    540         virtual void accept( Visitor & v ) { v.visit( this ); }
    541         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    542         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     560        virtual CommaExpr * clone() const override { return new CommaExpr( * this ); }
     561        virtual void accept( Visitor & v ) override { v.visit( this ); }
     562        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     563        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     564        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    543565};
    544566
     
    555577        void set_type( Type * newValue ) { type = newValue; }
    556578
    557         virtual TypeExpr * clone() const { return new TypeExpr( * this ); }
    558         virtual void accept( Visitor & v ) { v.visit( this ); }
    559         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    560         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     579        virtual TypeExpr * clone() const override { return new TypeExpr( * this ); }
     580        virtual void accept( Visitor & v ) override { v.visit( this ); }
     581        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     582        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     583        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    561584};
    562585
     
    581604        void set_operand( Expression * newValue ) { operand = newValue; }
    582605
    583         virtual AsmExpr * clone() const { return new AsmExpr( * this ); }
    584         virtual void accept( Visitor & v ) { v.visit( this ); }
    585         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    586         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     606        virtual AsmExpr * clone() const override { return new AsmExpr( * this ); }
     607        virtual void accept( Visitor & v ) override { v.visit( this ); }
     608        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     609        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     610        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    587611
    588612        // https://gcc.gnu.org/onlinedocs/gcc-4.7.1/gcc/Machine-Constraints.html#Machine-Constraints
     
    599623        virtual ~ImplicitCopyCtorExpr();
    600624
    601         virtual ImplicitCopyCtorExpr * clone() const { return new ImplicitCopyCtorExpr( * this ); }
    602         virtual void accept( Visitor & v ) { v.visit( this ); }
    603         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    604         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     625        virtual ImplicitCopyCtorExpr * clone() const override { return new ImplicitCopyCtorExpr( * this ); }
     626        virtual void accept( Visitor & v ) override { v.visit( this ); }
     627        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     628        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     629        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    605630};
    606631
     
    617642        void set_callExpr( Expression * newValue ) { callExpr = newValue; }
    618643
    619         virtual ConstructorExpr * clone() const { return new ConstructorExpr( * this ); }
    620         virtual void accept( Visitor & v ) { v.visit( this ); }
    621         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    622         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     644        virtual ConstructorExpr * clone() const override { return new ConstructorExpr( * this ); }
     645        virtual void accept( Visitor & v ) override { v.visit( this ); }
     646        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     647        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     648        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    623649};
    624650
     
    635661        void set_initializer( Initializer * i ) { initializer = i; }
    636662
    637         virtual CompoundLiteralExpr * clone() const { return new CompoundLiteralExpr( * this ); }
    638         virtual void accept( Visitor & v ) { v.visit( this ); }
    639         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    640         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     663        virtual CompoundLiteralExpr * clone() const override { return new CompoundLiteralExpr( * this ); }
     664        virtual void accept( Visitor & v ) override { v.visit( this ); }
     665        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     666        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     667        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    641668};
    642669
     
    654681        RangeExpr * set_high( Expression * high ) { RangeExpr::high = high; return this; }
    655682
    656         virtual RangeExpr * clone() const { return new RangeExpr( * this ); }
    657         virtual void accept( Visitor & v ) { v.visit( this ); }
    658         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    659         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     683        virtual RangeExpr * clone() const override { return new RangeExpr( * this ); }
     684        virtual void accept( Visitor & v ) override { v.visit( this ); }
     685        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     686        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     687        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    660688};
    661689
     
    671699        std::list<Expression*>& get_exprs() { return exprs; }
    672700
    673         virtual UntypedTupleExpr * clone() const { return new UntypedTupleExpr( * this ); }
    674         virtual void accept( Visitor & v ) { v.visit( this ); }
    675         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    676         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     701        virtual UntypedTupleExpr * clone() const override { return new UntypedTupleExpr( * this ); }
     702        virtual void accept( Visitor & v ) override { v.visit( this ); }
     703        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     704        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     705        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    677706};
    678707
     
    688717        std::list<Expression*>& get_exprs() { return exprs; }
    689718
    690         virtual TupleExpr * clone() const { return new TupleExpr( * this ); }
    691         virtual void accept( Visitor & v ) { v.visit( this ); }
    692         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    693         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     719        virtual TupleExpr * clone() const override { return new TupleExpr( * this ); }
     720        virtual void accept( Visitor & v ) override { v.visit( this ); }
     721        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     722        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     723        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    694724};
    695725
     
    709739        TupleIndexExpr * set_index( unsigned int newValue ) { index = newValue; return this; }
    710740
    711         virtual TupleIndexExpr * clone() const { return new TupleIndexExpr( * this ); }
    712         virtual void accept( Visitor & v ) { v.visit( this ); }
    713         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    714         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     741        virtual TupleIndexExpr * clone() const override { return new TupleIndexExpr( * this ); }
     742        virtual void accept( Visitor & v ) override { v.visit( this ); }
     743        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     744        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     745        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    715746};
    716747
     
    727758        StmtExpr * get_stmtExpr() const { return stmtExpr; }
    728759
    729         virtual TupleAssignExpr * clone() const { return new TupleAssignExpr( * this ); }
    730         virtual void accept( Visitor & v ) { v.visit( this ); }
    731         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    732         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     760        virtual TupleAssignExpr * clone() const override { return new TupleAssignExpr( * this ); }
     761        virtual void accept( Visitor & v ) override { v.visit( this ); }
     762        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     763        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     764        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    733765
    734766        friend class ConverterNewToOld;
     
    760792        std::list< Expression * > & get_dtors() { return dtors; }
    761793
    762         virtual StmtExpr * clone() const { return new StmtExpr( * this ); }
    763         virtual void accept( Visitor & v ) { v.visit( this ); }
    764         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    765         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     794        virtual StmtExpr * clone() const override { return new StmtExpr( * this ); }
     795        virtual void accept( Visitor & v ) override { v.visit( this ); }
     796        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     797        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     798        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    766799};
    767800
     
    787820        int get_id() const { return id; }
    788821
    789         virtual UniqueExpr * clone() const { return new UniqueExpr( * this ); }
    790         virtual void accept( Visitor & v ) { v.visit( this ); }
    791         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    792         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     822        virtual UniqueExpr * clone() const override { return new UniqueExpr( * this ); }
     823        virtual void accept( Visitor & v ) override { v.visit( this ); }
     824        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     825        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     826        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    793827
    794828private:
     
    821855        std::list<InitAlternative> & get_initAlts() { return initAlts; }
    822856
    823         virtual UntypedInitExpr * clone() const { return new UntypedInitExpr( * this ); }
    824         virtual void accept( Visitor & v ) { v.visit( this ); }
    825         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    826         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     857        virtual UntypedInitExpr * clone() const override { return new UntypedInitExpr( * this ); }
     858        virtual void accept( Visitor & v ) override { v.visit( this ); }
     859        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     860        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     861        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    827862};
    828863
     
    842877        InitExpr * set_designation( Designation * newValue ) { designation = newValue; return this; }
    843878
    844         virtual InitExpr * clone() const { return new InitExpr( * this ); }
    845         virtual void accept( Visitor & v ) { v.visit( this ); }
    846         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    847         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     879        virtual InitExpr * clone() const override { return new InitExpr( * this ); }
     880        virtual void accept( Visitor & v ) override { v.visit( this ); }
     881        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     882        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     883        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    848884};
    849885
     
    852888public:
    853889        Expression * expr;
    854         BaseSyntaxNode * deleteStmt;
    855 
    856         DeletedExpr( Expression * expr, BaseSyntaxNode * deleteStmt );
     890        Declaration * deleteStmt;
     891
     892        DeletedExpr( Expression * expr, Declaration * deleteStmt );
    857893        DeletedExpr( const DeletedExpr & other );
    858894        ~DeletedExpr();
    859895
    860         virtual DeletedExpr * clone() const { return new DeletedExpr( * this ); }
    861         virtual void accept( Visitor & v ) { v.visit( this ); }
    862         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    863         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     896        virtual DeletedExpr * clone() const override { return new DeletedExpr( * this ); }
     897        virtual void accept( Visitor & v ) override { v.visit( this ); }
     898        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     899        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     900        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    864901};
    865902
     
    873910        ~DefaultArgExpr();
    874911
    875         virtual DefaultArgExpr * clone() const { return new DefaultArgExpr( * this ); }
    876         virtual void accept( Visitor & v ) { v.visit( this ); }
    877         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    878         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     912        virtual DefaultArgExpr * clone() const override { return new DefaultArgExpr( * this ); }
     913        virtual void accept( Visitor & v ) override { v.visit( this ); }
     914        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     915        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     916        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    879917};
    880918
     
    901939        virtual ~GenericExpr();
    902940
    903         virtual GenericExpr * clone() const { return new GenericExpr( * this ); }
    904         virtual void accept( Visitor & v ) { v.visit( this ); }
    905         virtual Expression * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    906         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     941        virtual GenericExpr * clone() const override { return new GenericExpr( * this ); }
     942        virtual void accept( Visitor & v ) override { v.visit( this ); }
     943        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     944        virtual Expression * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     945        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    907946};
    908947
  • src/SynTree/Initializer.h

    r1f1c102 rf53acdf8  
    3838
    3939        virtual Designation * clone() const override { return new Designation( *this ); };
    40         virtual void accept( Visitor &v ) override { v.visit( this ); }
     40        virtual void accept( Visitor & v ) override { v.visit( this ); }
     41        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    4142        virtual Designation * acceptMutator( Mutator &m ) override { return m.mutate( this ); }
    4243        virtual void print( std::ostream &os, Indenter indent = {} ) const override;
     
    5253        virtual ~Initializer();
    5354
    54         bool get_maybeConstructed() { return maybeConstructed; }
     55        bool get_maybeConstructed() const { return maybeConstructed; }
    5556
    5657        virtual Initializer *clone() const override = 0;
    57         virtual void accept( Visitor &v ) override = 0;
     58        virtual void accept( Visitor & v ) override = 0;
     59        virtual void accept( Visitor & v ) const override = 0;
    5860        virtual Initializer *acceptMutator( Mutator &m ) override = 0;
    5961        virtual void print( std::ostream &os, Indenter indent = {} ) const override = 0;
     
    7678
    7779        virtual SingleInit *clone() const override { return new SingleInit( *this); }
    78         virtual void accept( Visitor &v ) override { v.visit( this ); }
     80        virtual void accept( Visitor & v ) override { v.visit( this ); }
     81        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    7982        virtual Initializer *acceptMutator( Mutator &m )  override { return m.mutate( this ); }
    8083        virtual void print( std::ostream &os, Indenter indent = {} ) const override;
     
    104107
    105108        virtual ListInit *clone() const override { return new ListInit( *this ); }
    106         virtual void accept( Visitor &v ) override { v.visit( this ); }
     109        virtual void accept( Visitor & v ) override { v.visit( this ); }
     110        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    107111        virtual Initializer *acceptMutator( Mutator &m )  override { return m.mutate( this ); }
    108112        virtual void print( std::ostream &os, Indenter indent = {} ) const override;
     
    133137
    134138        ConstructorInit *clone() const override { return new ConstructorInit( *this ); }
    135         virtual void accept( Visitor &v ) override { v.visit( this ); }
     139        virtual void accept( Visitor & v ) override { v.visit( this ); }
     140        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    136141        virtual Initializer *acceptMutator( Mutator &m )  override { return m.mutate( this ); }
    137142        virtual void print( std::ostream &os, Indenter indent = {} ) const override;
  • src/SynTree/Mutator.h

    r1f1c102 rf53acdf8  
    5252        virtual Statement * mutate( FinallyStmt * catchStmt ) = 0;
    5353        virtual Statement * mutate( WaitForStmt * waitforStmt ) = 0;
    54         virtual Statement * mutate( WithStmt * withStmt ) = 0;
     54        virtual Declaration * mutate( WithStmt * withStmt ) = 0;
    5555        virtual NullStmt * mutate( NullStmt * nullStmt ) = 0;
    5656        virtual Statement * mutate( DeclStmt * declStmt ) = 0;
  • src/SynTree/Statement.cc

    r1f1c102 rf53acdf8  
    493493
    494494
    495 WithStmt::WithStmt( const std::list< Expression * > & exprs, Statement * stmt ) : Statement(), exprs( exprs ), stmt( stmt ) {}
    496 WithStmt::WithStmt( const WithStmt & other ) : Statement( other ), stmt( maybeClone( other.stmt ) ) {
     495WithStmt::WithStmt( const std::list< Expression * > & exprs, Statement * stmt ) : Declaration("", noStorageClasses, LinkageSpec::Cforall), exprs( exprs ), stmt( stmt ) {}
     496WithStmt::WithStmt( const WithStmt & other ) : Declaration( other ), stmt( maybeClone( other.stmt ) ) {
    497497        cloneAll( other.exprs, exprs );
    498498}
  • src/SynTree/Statement.h

    r1f1c102 rf53acdf8  
    4545        virtual Statement * clone() const override = 0;
    4646        virtual void accept( Visitor & v ) override = 0;
     47        virtual void accept( Visitor & v ) const override = 0;
    4748        virtual Statement * acceptMutator( Mutator & m ) override = 0;
    4849        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    6465        virtual CompoundStmt * clone() const override { return new CompoundStmt( *this ); }
    6566        virtual void accept( Visitor & v ) override { v.visit( this ); }
     67        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    6668        virtual CompoundStmt * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
    6769        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    7476        virtual NullStmt * clone() const override { return new NullStmt( *this ); }
    7577        virtual void accept( Visitor & v ) override { v.visit( this ); }
     78        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    7679        virtual NullStmt * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
    7780        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    9194        virtual ExprStmt * clone() const override { return new ExprStmt( *this ); }
    9295        virtual void accept( Visitor & v ) override { v.visit( this ); }
     96        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    9397        virtual Statement * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
    9498        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    120124        void set_gotolabels( const std::list<Label> & newValue ) { gotolabels = newValue; }
    121125
    122         virtual AsmStmt * clone() const { return new AsmStmt( *this ); }
    123         virtual void accept( Visitor & v ) { v.visit( this ); }
    124         virtual Statement * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    125         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     126        virtual AsmStmt * clone() const override { return new AsmStmt( *this ); }
     127        virtual void accept( Visitor & v ) override { v.visit( this ); }
     128        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     129        virtual Statement * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     130        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    126131};
    127132
     
    133138        virtual ~DirectiveStmt(){}
    134139
    135         virtual DirectiveStmt * clone() const { return new DirectiveStmt( *this ); }
    136         virtual void accept( Visitor & v ) { v.visit( this ); }
    137         virtual Statement * acceptMutator( Mutator & m ) { return m.mutate( this ); }
    138         virtual void print( std::ostream & os, Indenter indent = {} ) const;
     140        virtual DirectiveStmt * clone() const override { return new DirectiveStmt( *this ); }
     141        virtual void accept( Visitor & v ) override { v.visit( this ); }
     142        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     143        virtual Statement * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
     144        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    139145};
    140146
     
    161167        virtual IfStmt * clone() const override { return new IfStmt( *this ); }
    162168        virtual void accept( Visitor & v ) override { v.visit( this ); }
     169        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    163170        virtual Statement * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
    164171        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    180187
    181188        virtual void accept( Visitor & v ) override { v.visit( this ); }
     189        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    182190        virtual Statement * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
    183191
     
    208216
    209217        virtual void accept( Visitor & v ) override { v.visit( this ); }
     218        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    210219        virtual Statement * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
    211220
     
    236245        virtual WhileStmt * clone() const override { return new WhileStmt( *this ); }
    237246        virtual void accept( Visitor & v ) override { v.visit( this ); }
     247        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    238248        virtual Statement * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
    239249        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    261271        virtual ForStmt * clone() const override { return new ForStmt( *this ); }
    262272        virtual void accept( Visitor & v ) override { v.visit( this ); }
     273        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    263274        virtual Statement * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
    264275        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    290301        virtual BranchStmt * clone() const override { return new BranchStmt( *this ); }
    291302        virtual void accept( Visitor & v ) override { v.visit( this ); }
     303        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    292304        virtual Statement * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
    293305        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    309321        virtual ReturnStmt * clone() const override { return new ReturnStmt( *this ); }
    310322        virtual void accept( Visitor & v ) override { v.visit( this ); }
     323        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    311324        virtual Statement * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
    312325        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    333346        virtual ThrowStmt * clone() const override { return new ThrowStmt( *this ); }
    334347        virtual void accept( Visitor & v ) override { v.visit( this ); }
     348        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    335349        virtual Statement * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
    336350        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    356370        virtual TryStmt * clone() const override { return new TryStmt( *this ); }
    357371        virtual void accept( Visitor & v ) override { v.visit( this ); }
     372        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    358373        virtual Statement * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
    359374        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    384399        virtual CatchStmt * clone() const override { return new CatchStmt( *this ); }
    385400        virtual void accept( Visitor & v ) override { v.visit( this ); }
     401        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    386402        virtual Statement * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
    387403        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    401417        virtual FinallyStmt * clone() const override { return new FinallyStmt( *this ); }
    402418        virtual void accept( Visitor & v ) override { v.visit( this ); }
     419        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    403420        virtual Statement * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
    404421        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    438455        virtual WaitForStmt * clone() const override { return new WaitForStmt( *this ); }
    439456        virtual void accept( Visitor & v ) override { v.visit( this ); }
    440         virtual Statement * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
    441         virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    442 
    443 };
    444 
    445 class WithStmt : public Statement {
    446 public:
    447         std::list< Expression * > exprs;
    448         Statement * stmt;
    449 
    450         WithStmt( const std::list< Expression * > & exprs, Statement * stmt );
    451         WithStmt( const WithStmt & other );
    452         virtual ~WithStmt();
    453 
    454         virtual WithStmt * clone() const override { return new WithStmt( *this ); }
    455         virtual void accept( Visitor & v ) override { v.visit( this ); }
    456         virtual Statement * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
    457         virtual void print( std::ostream & os, Indenter indent = {} ) const override;
    458 };
     457        virtual void accept( Visitor & v ) const override { v.visit( this ); }
     458        virtual Statement * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
     459        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     460
     461};
     462
     463// class WithStmt : public Statement {
     464// public:
     465//      std::list< Expression * > exprs;
     466//      Statement * stmt;
     467
     468//      WithStmt( const std::list< Expression * > & exprs, Statement * stmt );
     469//      WithStmt( const WithStmt & other );
     470//      virtual ~WithStmt();
     471
     472//      virtual WithStmt * clone() const override { return new WithStmt( *this ); }
     473//      virtual void accept( Visitor & v ) override { v.visit( this ); }
     474//      virtual void accept( Visitor & v ) const override { v.visit( this ); }
     475//      virtual Statement * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
     476//      virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     477// };
    459478
    460479
     
    473492        virtual DeclStmt * clone() const override { return new DeclStmt( *this ); }
    474493        virtual void accept( Visitor & v ) override { v.visit( this ); }
     494        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    475495        virtual Statement * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
    476496        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    494514        virtual ImplicitCtorDtorStmt * clone() const override { return new ImplicitCtorDtorStmt( *this ); }
    495515        virtual void accept( Visitor & v ) override { v.visit( this ); }
     516        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    496517        virtual Statement * acceptMutator( Mutator & m )  override { return m.mutate( this ); }
    497518        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
  • src/SynTree/Type.h

    r1f1c102 rf53acdf8  
    144144
    145145        Qualifiers & get_qualifiers() { return tq; }
    146         bool get_const() { return tq.is_const; }
    147         bool get_volatile() { return tq.is_volatile; }
    148         bool get_restrict() { return tq.is_restrict; }
    149         bool get_lvalue() { return tq.is_lvalue; }
    150         bool get_mutex() { return tq.is_mutex; }
    151         bool get_atomic() { return tq.is_atomic; }
     146        bool get_const() const { return tq.is_const; }
     147        bool get_volatile() const { return tq.is_volatile; }
     148        bool get_restrict() const { return tq.is_restrict; }
     149        bool get_lvalue() const { return tq.is_lvalue; }
     150        bool get_mutex() const { return tq.is_mutex; }
     151        bool get_atomic() const { return tq.is_atomic; }
    152152        void set_const( bool newValue ) { tq.is_const = newValue; }
    153153        void set_volatile( bool newValue ) { tq.is_volatile = newValue; }
     
    184184        virtual Type *clone() const = 0;
    185185        virtual void accept( Visitor & v ) = 0;
     186        virtual void accept( Visitor & v ) const = 0;
    186187        virtual Type *acceptMutator( Mutator & m ) = 0;
    187188        virtual void print( std::ostream & os, Indenter indent = {} ) const;
     
    201202        virtual VoidType *clone() const override { return new VoidType( *this ); }
    202203        virtual void accept( Visitor & v ) override { v.visit( this ); }
     204        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    203205        virtual Type *acceptMutator( Mutator & m ) override { return m.mutate( this ); }
    204206        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    259261        virtual BasicType *clone() const override { return new BasicType( *this ); }
    260262        virtual void accept( Visitor & v ) override { v.visit( this ); }
     263        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    261264        virtual Type *acceptMutator( Mutator & m ) override { return m.mutate( this ); }
    262265        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    294297        virtual PointerType *clone() const override { return new PointerType( *this ); }
    295298        virtual void accept( Visitor & v ) override { v.visit( this ); }
     299        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    296300        virtual Type *acceptMutator( Mutator & m ) override { return m.mutate( this ); }
    297301        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    325329        virtual ArrayType *clone() const override { return new ArrayType( *this ); }
    326330        virtual void accept( Visitor & v ) override { v.visit( this ); }
     331        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    327332        virtual Type *acceptMutator( Mutator & m ) override { return m.mutate( this ); }
    328333        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    340345        virtual QualifiedType *clone() const override { return new QualifiedType( *this ); }
    341346        virtual void accept( Visitor & v ) override { v.visit( this ); }
     347        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    342348        virtual Type *acceptMutator( Mutator & m ) override { return m.mutate( this ); }
    343349        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    366372        virtual ReferenceType *clone() const override { return new ReferenceType( *this ); }
    367373        virtual void accept( Visitor & v ) override { v.visit( this ); }
     374        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    368375        virtual Type *acceptMutator( Mutator & m ) override { return m.mutate( this ); }
    369376        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    395402        virtual FunctionType *clone() const override { return new FunctionType( *this ); }
    396403        virtual void accept( Visitor & v ) override { v.visit( this ); }
     404        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    397405        virtual Type *acceptMutator( Mutator & m ) override { return m.mutate( this ); }
    398406        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    455463        virtual StructInstType *clone() const override { return new StructInstType( *this ); }
    456464        virtual void accept( Visitor & v ) override { v.visit( this ); }
     465        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    457466        virtual Type *acceptMutator( Mutator & m ) override { return m.mutate( this ); }
    458467
     
    492501        virtual UnionInstType *clone() const override { return new UnionInstType( *this ); }
    493502        virtual void accept( Visitor & v ) override { v.visit( this ); }
     503        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    494504        virtual Type *acceptMutator( Mutator & m ) override { return m.mutate( this ); }
    495505
     
    519529        virtual EnumInstType *clone() const override { return new EnumInstType( *this ); }
    520530        virtual void accept( Visitor & v ) override { v.visit( this ); }
     531        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    521532        virtual Type *acceptMutator( Mutator & m ) override { return m.mutate( this ); }
    522533
     
    542553        virtual TraitInstType *clone() const override { return new TraitInstType( *this ); }
    543554        virtual void accept( Visitor & v ) override { v.visit( this ); }
     555        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    544556        virtual Type *acceptMutator( Mutator & m ) override { return m.mutate( this ); }
    545557  private:
     
    569581        virtual TypeInstType *clone() const override { return new TypeInstType( *this ); }
    570582        virtual void accept( Visitor & v ) override { v.visit( this ); }
     583        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    571584        virtual Type *acceptMutator( Mutator & m ) override { return m.mutate( this ); }
    572585        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    606619        virtual TupleType *clone() const override { return new TupleType( *this ); }
    607620        virtual void accept( Visitor & v ) override { v.visit( this ); }
     621        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    608622        virtual Type *acceptMutator( Mutator & m ) override { return m.mutate( this ); }
    609623        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    616630
    617631        TypeofType( const Type::Qualifiers & tq, Expression *expr, const std::list< Attribute * > & attributes = std::list< Attribute * >() );
    618         TypeofType( const Type::Qualifiers & tq, Expression *expr, bool is_basetypeof, 
     632        TypeofType( const Type::Qualifiers & tq, Expression *expr, bool is_basetypeof,
    619633                const std::list< Attribute * > & attributes = std::list< Attribute * >() );
    620634        TypeofType( const TypeofType& );
     
    628642        virtual TypeofType *clone() const override { return new TypeofType( *this ); }
    629643        virtual void accept( Visitor & v ) override { v.visit( this ); }
     644        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    630645        virtual Type *acceptMutator( Mutator & m ) override { return m.mutate( this ); }
    631646        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    657672        virtual AttrType *clone() const override { return new AttrType( *this ); }
    658673        virtual void accept( Visitor & v ) override { v.visit( this ); }
     674        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    659675        virtual Type *acceptMutator( Mutator & m ) override { return m.mutate( this ); }
    660676        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    671687        virtual VarArgsType *clone() const override { return new VarArgsType( *this ); }
    672688        virtual void accept( Visitor & v ) override { v.visit( this ); }
     689        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    673690        virtual Type *acceptMutator( Mutator & m ) override { return m.mutate( this ); }
    674691        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    683700        virtual ZeroType *clone() const override { return new ZeroType( *this ); }
    684701        virtual void accept( Visitor & v ) override { v.visit( this ); }
     702        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    685703        virtual Type *acceptMutator( Mutator & m ) override { return m.mutate( this ); }
    686704        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    695713        virtual OneType *clone() const override { return new OneType( *this ); }
    696714        virtual void accept( Visitor & v ) override { v.visit( this ); }
     715        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    697716        virtual Type *acceptMutator( Mutator & m ) override { return m.mutate( this ); }
    698717        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
     
    705724        virtual GlobalScopeType *clone() const override { return new GlobalScopeType( *this ); }
    706725        virtual void accept( Visitor & v ) override { v.visit( this ); }
     726        virtual void accept( Visitor & v ) const override { v.visit( this ); }
    707727        virtual Type *acceptMutator( Mutator & m ) override { return m.mutate( this ); }
    708728        virtual void print( std::ostream & os, Indenter indent = {} ) const override;
  • src/SynTree/Visitor.h

    r1f1c102 rf53acdf8  
    2727        // of the given syntax node, but performs no other action.
    2828
    29         virtual void visit( ObjectDecl * objectDecl ) = 0;
    30         virtual void visit( FunctionDecl * functionDecl ) = 0;
    31         virtual void visit( StructDecl * aggregateDecl ) = 0;
    32         virtual void visit( UnionDecl * aggregateDecl ) = 0;
    33         virtual void visit( EnumDecl * aggregateDecl ) = 0;
    34         virtual void visit( TraitDecl * aggregateDecl ) = 0;
    35         virtual void visit( TypeDecl * typeDecl ) = 0;
    36         virtual void visit( TypedefDecl * typeDecl ) = 0;
    37         virtual void visit( AsmDecl * asmDecl ) = 0;
    38         virtual void visit( StaticAssertDecl * assertDecl ) = 0;
    39 
    40         virtual void visit( CompoundStmt * compoundStmt ) = 0;
    41         virtual void visit( ExprStmt * exprStmt ) = 0;
    42         virtual void visit( AsmStmt * asmStmt ) = 0;
    43         virtual void visit( DirectiveStmt * directiveStmt ) = 0;
    44         virtual void visit( IfStmt * ifStmt ) = 0;
    45         virtual void visit( WhileStmt * whileStmt ) = 0;
    46         virtual void visit( ForStmt * forStmt ) = 0;
    47         virtual void visit( SwitchStmt * switchStmt ) = 0;
    48         virtual void visit( CaseStmt * caseStmt ) = 0;
    49         virtual void visit( BranchStmt * branchStmt ) = 0;
    50         virtual void visit( ReturnStmt * returnStmt ) = 0;
    51         virtual void visit( ThrowStmt * throwStmt ) = 0;
    52         virtual void visit( TryStmt * tryStmt ) = 0;
    53         virtual void visit( CatchStmt * catchStmt ) = 0;
    54         virtual void visit( FinallyStmt * finallyStmt ) = 0;
    55         virtual void visit( WaitForStmt * waitforStmt ) = 0;
    56         virtual void visit( WithStmt * withStmt ) = 0;
    57         virtual void visit( NullStmt * nullStmt ) = 0;
    58         virtual void visit( DeclStmt * declStmt ) = 0;
    59         virtual void visit( ImplicitCtorDtorStmt * impCtorDtorStmt ) = 0;
    60 
    61         virtual void visit( ApplicationExpr * applicationExpr ) = 0;
    62         virtual void visit( UntypedExpr * untypedExpr ) = 0;
    63         virtual void visit( NameExpr * nameExpr ) = 0;
    64         virtual void visit( CastExpr * castExpr ) = 0;
    65         virtual void visit( KeywordCastExpr * castExpr ) = 0;
    66         virtual void visit( VirtualCastExpr * castExpr ) = 0;
    67         virtual void visit( AddressExpr * addressExpr ) = 0;
    68         virtual void visit( LabelAddressExpr * labAddressExpr ) = 0;
    69         virtual void visit( UntypedMemberExpr * memberExpr ) = 0;
    70         virtual void visit( MemberExpr * memberExpr ) = 0;
    71         virtual void visit( VariableExpr * variableExpr ) = 0;
    72         virtual void visit( ConstantExpr * constantExpr ) = 0;
    73         virtual void visit( SizeofExpr * sizeofExpr ) = 0;
    74         virtual void visit( AlignofExpr * alignofExpr ) = 0;
    75         virtual void visit( UntypedOffsetofExpr * offsetofExpr ) = 0;
    76         virtual void visit( OffsetofExpr * offsetofExpr ) = 0;
    77         virtual void visit( OffsetPackExpr * offsetPackExpr ) = 0;
    78         virtual void visit( AttrExpr * attrExpr ) = 0;
    79         virtual void visit( LogicalExpr * logicalExpr ) = 0;
    80         virtual void visit( ConditionalExpr * conditionalExpr ) = 0;
    81         virtual void visit( CommaExpr * commaExpr ) = 0;
    82         virtual void visit( TypeExpr * typeExpr ) = 0;
    83         virtual void visit( AsmExpr * asmExpr ) = 0;
    84         virtual void visit( ImplicitCopyCtorExpr * impCpCtorExpr ) = 0;
    85         virtual void visit( ConstructorExpr *  ctorExpr ) = 0;
    86         virtual void visit( CompoundLiteralExpr * compLitExpr ) = 0;
    87         virtual void visit( RangeExpr * rangeExpr ) = 0;
    88         virtual void visit( UntypedTupleExpr * tupleExpr ) = 0;
    89         virtual void visit( TupleExpr * tupleExpr ) = 0;
    90         virtual void visit( TupleIndexExpr * tupleExpr ) = 0;
    91         virtual void visit( TupleAssignExpr * assignExpr ) = 0;
    92         virtual void visit( StmtExpr *  stmtExpr ) = 0;
    93         virtual void visit( UniqueExpr *  uniqueExpr ) = 0;
    94         virtual void visit( UntypedInitExpr *  initExpr ) = 0;
    95         virtual void visit( InitExpr *  initExpr ) = 0;
    96         virtual void visit( DeletedExpr * delExpr ) = 0;
    97         virtual void visit( DefaultArgExpr * argExpr ) = 0;
    98         virtual void visit( GenericExpr * genExpr ) = 0;
    99 
    100         virtual void visit( VoidType * basicType ) = 0;
    101         virtual void visit( BasicType * basicType ) = 0;
    102         virtual void visit( PointerType * pointerType ) = 0;
    103         virtual void visit( ArrayType * arrayType ) = 0;
    104         virtual void visit( ReferenceType * refType ) = 0;
    105         virtual void visit( QualifiedType * qualType ) = 0;
    106         virtual void visit( FunctionType * functionType ) = 0;
    107         virtual void visit( StructInstType * aggregateUseType ) = 0;
    108         virtual void visit( UnionInstType * aggregateUseType ) = 0;
    109         virtual void visit( EnumInstType * aggregateUseType ) = 0;
    110         virtual void visit( TraitInstType * aggregateUseType ) = 0;
    111         virtual void visit( TypeInstType * aggregateUseType ) = 0;
    112         virtual void visit( TupleType * tupleType ) = 0;
    113         virtual void visit( TypeofType * typeofType ) = 0;
    114         virtual void visit( AttrType * attrType ) = 0;
    115         virtual void visit( VarArgsType * varArgsType ) = 0;
    116         virtual void visit( ZeroType * zeroType ) = 0;
    117         virtual void visit( OneType * oneType ) = 0;
    118         virtual void visit( GlobalScopeType * globalType ) = 0;
    119 
    120         virtual void visit( Designation * designation ) = 0;
    121         virtual void visit( SingleInit * singleInit ) = 0;
    122         virtual void visit( ListInit * listInit ) = 0;
    123         virtual void visit( ConstructorInit * ctorInit ) = 0;
    124 
    125         virtual void visit( Constant * constant ) = 0;
    126 
    127         virtual void visit( Attribute * attribute ) = 0;
     29        virtual void visit( ObjectDecl * node ) { visit( const_cast<const ObjectDecl *>(node) ); }
     30        virtual void visit( const ObjectDecl * objectDecl ) = 0;
     31        virtual void visit( FunctionDecl * node ) { visit( const_cast<const FunctionDecl *>(node) ); }
     32        virtual void visit( const FunctionDecl * functionDecl ) = 0;
     33        virtual void visit( StructDecl * node ) { visit( const_cast<const StructDecl *>(node) ); }
     34        virtual void visit( const StructDecl * aggregateDecl ) = 0;
     35        virtual void visit( UnionDecl * node ) { visit( const_cast<const UnionDecl *>(node) ); }
     36        virtual void visit( const UnionDecl * aggregateDecl ) = 0;
     37        virtual void visit( EnumDecl * node ) { visit( const_cast<const EnumDecl *>(node) ); }
     38        virtual void visit( const EnumDecl * aggregateDecl ) = 0;
     39        virtual void visit( TraitDecl * node ) { visit( const_cast<const TraitDecl *>(node) ); }
     40        virtual void visit( const TraitDecl * aggregateDecl ) = 0;
     41        virtual void visit( TypeDecl * node ) { visit( const_cast<const TypeDecl *>(node) ); }
     42        virtual void visit( const TypeDecl * typeDecl ) = 0;
     43        virtual void visit( TypedefDecl * node ) { visit( const_cast<const TypedefDecl *>(node) ); }
     44        virtual void visit( const TypedefDecl * typeDecl ) = 0;
     45        virtual void visit( AsmDecl * node ) { visit( const_cast<const AsmDecl *>(node) ); }
     46        virtual void visit( const AsmDecl * asmDecl ) = 0;
     47        virtual void visit( StaticAssertDecl * node ) { visit( const_cast<const StaticAssertDecl *>(node) ); }
     48        virtual void visit( const StaticAssertDecl * assertDecl ) = 0;
     49
     50        virtual void visit( CompoundStmt * node ) { visit( const_cast<const CompoundStmt *>(node) ); }
     51        virtual void visit( const CompoundStmt * compoundStmt ) = 0;
     52        virtual void visit( ExprStmt * node ) { visit( const_cast<const ExprStmt *>(node) ); }
     53        virtual void visit( const ExprStmt * exprStmt ) = 0;
     54        virtual void visit( AsmStmt * node ) { visit( const_cast<const AsmStmt *>(node) ); }
     55        virtual void visit( const AsmStmt * asmStmt ) = 0;
     56        virtual void visit( DirectiveStmt * node ) { visit( const_cast<const DirectiveStmt *>(node) ); }
     57        virtual void visit( const DirectiveStmt * directiveStmt ) = 0;
     58        virtual void visit( IfStmt * node ) { visit( const_cast<const IfStmt *>(node) ); }
     59        virtual void visit( const IfStmt * ifStmt ) = 0;
     60        virtual void visit( WhileStmt * node ) { visit( const_cast<const WhileStmt *>(node) ); }
     61        virtual void visit( const WhileStmt * whileStmt ) = 0;
     62        virtual void visit( ForStmt * node ) { visit( const_cast<const ForStmt *>(node) ); }
     63        virtual void visit( const ForStmt * forStmt ) = 0;
     64        virtual void visit( SwitchStmt * node ) { visit( const_cast<const SwitchStmt *>(node) ); }
     65        virtual void visit( const SwitchStmt * switchStmt ) = 0;
     66        virtual void visit( CaseStmt * node ) { visit( const_cast<const CaseStmt *>(node) ); }
     67        virtual void visit( const CaseStmt * caseStmt ) = 0;
     68        virtual void visit( BranchStmt * node ) { visit( const_cast<const BranchStmt *>(node) ); }
     69        virtual void visit( const BranchStmt * branchStmt ) = 0;
     70        virtual void visit( ReturnStmt * node ) { visit( const_cast<const ReturnStmt *>(node) ); }
     71        virtual void visit( const ReturnStmt * returnStmt ) = 0;
     72        virtual void visit( ThrowStmt * node ) { visit( const_cast<const ThrowStmt *>(node) ); }
     73        virtual void visit( const ThrowStmt * throwStmt ) = 0;
     74        virtual void visit( TryStmt * node ) { visit( const_cast<const TryStmt *>(node) ); }
     75        virtual void visit( const TryStmt * tryStmt ) = 0;
     76        virtual void visit( CatchStmt * node ) { visit( const_cast<const CatchStmt *>(node) ); }
     77        virtual void visit( const CatchStmt * catchStmt ) = 0;
     78        virtual void visit( FinallyStmt * node ) { visit( const_cast<const FinallyStmt *>(node) ); }
     79        virtual void visit( const FinallyStmt * finallyStmt ) = 0;
     80        virtual void visit( WaitForStmt * node ) { visit( const_cast<const WaitForStmt *>(node) ); }
     81        virtual void visit( const WaitForStmt * waitforStmt ) = 0;
     82        virtual void visit( WithStmt * node ) { visit( const_cast<const WithStmt *>(node) ); }
     83        virtual void visit( const WithStmt * withStmt ) = 0;
     84        virtual void visit( NullStmt * node ) { visit( const_cast<const NullStmt *>(node) ); }
     85        virtual void visit( const NullStmt * nullStmt ) = 0;
     86        virtual void visit( DeclStmt * node ) { visit( const_cast<const DeclStmt *>(node) ); }
     87        virtual void visit( const DeclStmt * declStmt ) = 0;
     88        virtual void visit( ImplicitCtorDtorStmt * node ) { visit( const_cast<const ImplicitCtorDtorStmt *>(node) ); }
     89        virtual void visit( const ImplicitCtorDtorStmt * impCtorDtorStmt ) = 0;
     90
     91        virtual void visit( ApplicationExpr * node ) { visit( const_cast<const ApplicationExpr *>(node) ); }
     92        virtual void visit( const ApplicationExpr * applicationExpr ) = 0;
     93        virtual void visit( UntypedExpr * node ) { visit( const_cast<const UntypedExpr *>(node) ); }
     94        virtual void visit( const UntypedExpr * untypedExpr ) = 0;
     95        virtual void visit( NameExpr * node ) { visit( const_cast<const NameExpr *>(node) ); }
     96        virtual void visit( const NameExpr * nameExpr ) = 0;
     97        virtual void visit( CastExpr * node ) { visit( const_cast<const CastExpr *>(node) ); }
     98        virtual void visit( const CastExpr * castExpr ) = 0;
     99        virtual void visit( KeywordCastExpr * node ) { visit( const_cast<const KeywordCastExpr *>(node) ); }
     100        virtual void visit( const KeywordCastExpr * castExpr ) = 0;
     101        virtual void visit( VirtualCastExpr * node ) { visit( const_cast<const VirtualCastExpr *>(node) ); }
     102        virtual void visit( const VirtualCastExpr * castExpr ) = 0;
     103        virtual void visit( AddressExpr * node ) { visit( const_cast<const AddressExpr *>(node) ); }
     104        virtual void visit( const AddressExpr * addressExpr ) = 0;
     105        virtual void visit( LabelAddressExpr * node ) { visit( const_cast<const LabelAddressExpr *>(node) ); }
     106        virtual void visit( const LabelAddressExpr * labAddressExpr ) = 0;
     107        virtual void visit( UntypedMemberExpr * node ) { visit( const_cast<const UntypedMemberExpr *>(node) ); }
     108        virtual void visit( const UntypedMemberExpr * memberExpr ) = 0;
     109        virtual void visit( MemberExpr * node ) { visit( const_cast<const MemberExpr *>(node) ); }
     110        virtual void visit( const MemberExpr * memberExpr ) = 0;
     111        virtual void visit( VariableExpr * node ) { visit( const_cast<const VariableExpr *>(node) ); }
     112        virtual void visit( const VariableExpr * variableExpr ) = 0;
     113        virtual void visit( ConstantExpr * node ) { visit( const_cast<const ConstantExpr *>(node) ); }
     114        virtual void visit( const ConstantExpr * constantExpr ) = 0;
     115        virtual void visit( SizeofExpr * node ) { visit( const_cast<const SizeofExpr *>(node) ); }
     116        virtual void visit( const SizeofExpr * sizeofExpr ) = 0;
     117        virtual void visit( AlignofExpr * node ) { visit( const_cast<const AlignofExpr *>(node) ); }
     118        virtual void visit( const AlignofExpr * alignofExpr ) = 0;
     119        virtual void visit( UntypedOffsetofExpr * node ) { visit( const_cast<const UntypedOffsetofExpr *>(node) ); }
     120        virtual void visit( const UntypedOffsetofExpr * offsetofExpr ) = 0;
     121        virtual void visit( OffsetofExpr * node ) { visit( const_cast<const OffsetofExpr *>(node) ); }
     122        virtual void visit( const OffsetofExpr * offsetofExpr ) = 0;
     123        virtual void visit( OffsetPackExpr * node ) { visit( const_cast<const OffsetPackExpr *>(node) ); }
     124        virtual void visit( const OffsetPackExpr * offsetPackExpr ) = 0;
     125        virtual void visit( AttrExpr * node ) { visit( const_cast<const AttrExpr *>(node) ); }
     126        virtual void visit( const AttrExpr * attrExpr ) = 0;
     127        virtual void visit( LogicalExpr * node ) { visit( const_cast<const LogicalExpr *>(node) ); }
     128        virtual void visit( const LogicalExpr * logicalExpr ) = 0;
     129        virtual void visit( ConditionalExpr * node ) { visit( const_cast<const ConditionalExpr *>(node) ); }
     130        virtual void visit( const ConditionalExpr * conditionalExpr ) = 0;
     131        virtual void visit( CommaExpr * node ) { visit( const_cast<const CommaExpr *>(node) ); }
     132        virtual void visit( const CommaExpr * commaExpr ) = 0;
     133        virtual void visit( TypeExpr * node ) { visit( const_cast<const TypeExpr *>(node) ); }
     134        virtual void visit( const TypeExpr * typeExpr ) = 0;
     135        virtual void visit( AsmExpr * node ) { visit( const_cast<const AsmExpr *>(node) ); }
     136        virtual void visit( const AsmExpr * asmExpr ) = 0;
     137        virtual void visit( ImplicitCopyCtorExpr * node ) { visit( const_cast<const ImplicitCopyCtorExpr *>(node) ); }
     138        virtual void visit( const ImplicitCopyCtorExpr * impCpCtorExpr ) = 0;
     139        virtual void visit( ConstructorExpr * node ) { visit( const_cast<const ConstructorExpr *>(node) ); }
     140        virtual void visit( const ConstructorExpr *  ctorExpr ) = 0;
     141        virtual void visit( CompoundLiteralExpr * node ) { visit( const_cast<const CompoundLiteralExpr *>(node) ); }
     142        virtual void visit( const CompoundLiteralExpr * compLitExpr ) = 0;
     143        virtual void visit( RangeExpr * node ) { visit( const_cast<const RangeExpr *>(node) ); }
     144        virtual void visit( const RangeExpr * rangeExpr ) = 0;
     145        virtual void visit( UntypedTupleExpr * node ) { visit( const_cast<const UntypedTupleExpr *>(node) ); }
     146        virtual void visit( const UntypedTupleExpr * tupleExpr ) = 0;
     147        virtual void visit( TupleExpr * node ) { visit( const_cast<const TupleExpr *>(node) ); }
     148        virtual void visit( const TupleExpr * tupleExpr ) = 0;
     149        virtual void visit( TupleIndexExpr * node ) { visit( const_cast<const TupleIndexExpr *>(node) ); }
     150        virtual void visit( const TupleIndexExpr * tupleExpr ) = 0;
     151        virtual void visit( TupleAssignExpr * node ) { visit( const_cast<const TupleAssignExpr *>(node) ); }
     152        virtual void visit( const TupleAssignExpr * assignExpr ) = 0;
     153        virtual void visit( StmtExpr * node ) { visit( const_cast<const StmtExpr *>(node) ); }
     154        virtual void visit( const StmtExpr *  stmtExpr ) = 0;
     155        virtual void visit( UniqueExpr * node ) { visit( const_cast<const UniqueExpr *>(node) ); }
     156        virtual void visit( const UniqueExpr *  uniqueExpr ) = 0;
     157        virtual void visit( UntypedInitExpr * node ) { visit( const_cast<const UntypedInitExpr *>(node) ); }
     158        virtual void visit( const UntypedInitExpr *  initExpr ) = 0;
     159        virtual void visit( InitExpr * node ) { visit( const_cast<const InitExpr *>(node) ); }
     160        virtual void visit( const InitExpr *  initExpr ) = 0;
     161        virtual void visit( DeletedExpr * node ) { visit( const_cast<const DeletedExpr *>(node) ); }
     162        virtual void visit( const DeletedExpr * delExpr ) = 0;
     163        virtual void visit( DefaultArgExpr * node ) { visit( const_cast<const DefaultArgExpr *>(node) ); }
     164        virtual void visit( const DefaultArgExpr * argExpr ) = 0;
     165        virtual void visit( GenericExpr * node ) { visit( const_cast<const GenericExpr *>(node) ); }
     166        virtual void visit( const GenericExpr * genExpr ) = 0;
     167
     168        virtual void visit( VoidType * node ) { visit( const_cast<const VoidType *>(node) ); }
     169        virtual void visit( const VoidType * basicType ) = 0;
     170        virtual void visit( BasicType * node ) { visit( const_cast<const BasicType *>(node) ); }
     171        virtual void visit( const BasicType * basicType ) = 0;
     172        virtual void visit( PointerType * node ) { visit( const_cast<const PointerType *>(node) ); }
     173        virtual void visit( const PointerType * pointerType ) = 0;
     174        virtual void visit( ArrayType * node ) { visit( const_cast<const ArrayType *>(node) ); }
     175        virtual void visit( const ArrayType * arrayType ) = 0;
     176        virtual void visit( ReferenceType * node ) { visit( const_cast<const ReferenceType *>(node) ); }
     177        virtual void visit( const ReferenceType * refType ) = 0;
     178        virtual void visit( QualifiedType * node ) { visit( const_cast<const QualifiedType *>(node) ); }
     179        virtual void visit( const QualifiedType * qualType ) = 0;
     180        virtual void visit( FunctionType * node ) { visit( const_cast<const FunctionType *>(node) ); }
     181        virtual void visit( const FunctionType * functionType ) = 0;
     182        virtual void visit( StructInstType * node ) { visit( const_cast<const StructInstType *>(node) ); }
     183        virtual void visit( const StructInstType * aggregateUseType ) = 0;
     184        virtual void visit( UnionInstType * node ) { visit( const_cast<const UnionInstType *>(node) ); }
     185        virtual void visit( const UnionInstType * aggregateUseType ) = 0;
     186        virtual void visit( EnumInstType * node ) { visit( const_cast<const EnumInstType *>(node) ); }
     187        virtual void visit( const EnumInstType * aggregateUseType ) = 0;
     188        virtual void visit( TraitInstType * node ) { visit( const_cast<const TraitInstType *>(node) ); }
     189        virtual void visit( const TraitInstType * aggregateUseType ) = 0;
     190        virtual void visit( TypeInstType * node ) { visit( const_cast<const TypeInstType *>(node) ); }
     191        virtual void visit( const TypeInstType * aggregateUseType ) = 0;
     192        virtual void visit( TupleType * node ) { visit( const_cast<const TupleType *>(node) ); }
     193        virtual void visit( const TupleType * tupleType ) = 0;
     194        virtual void visit( TypeofType * node ) { visit( const_cast<const TypeofType *>(node) ); }
     195        virtual void visit( const TypeofType * typeofType ) = 0;
     196        virtual void visit( AttrType * node ) { visit( const_cast<const AttrType *>(node) ); }
     197        virtual void visit( const AttrType * attrType ) = 0;
     198        virtual void visit( VarArgsType * node ) { visit( const_cast<const VarArgsType *>(node) ); }
     199        virtual void visit( const VarArgsType * varArgsType ) = 0;
     200        virtual void visit( ZeroType * node ) { visit( const_cast<const ZeroType *>(node) ); }
     201        virtual void visit( const ZeroType * zeroType ) = 0;
     202        virtual void visit( OneType * node ) { visit( const_cast<const OneType *>(node) ); }
     203        virtual void visit( const OneType * oneType ) = 0;
     204        virtual void visit( GlobalScopeType * node ) { visit( const_cast<const GlobalScopeType *>(node) ); }
     205        virtual void visit( const GlobalScopeType * globalType ) = 0;
     206
     207        virtual void visit( Designation * node ) { visit( const_cast<const Designation *>(node) ); }
     208        virtual void visit( const Designation * designation ) = 0;
     209        virtual void visit( SingleInit * node ) { visit( const_cast<const SingleInit *>(node) ); }
     210        virtual void visit( const SingleInit * singleInit ) = 0;
     211        virtual void visit( ListInit * node ) { visit( const_cast<const ListInit *>(node) ); }
     212        virtual void visit( const ListInit * listInit ) = 0;
     213        virtual void visit( ConstructorInit * node ) { visit( const_cast<const ConstructorInit *>(node) ); }
     214        virtual void visit( const ConstructorInit * ctorInit ) = 0;
     215
     216        virtual void visit( Constant * node ) { visit( const_cast<const Constant *>(node) ); }
     217        virtual void visit( const Constant * constant ) = 0;
     218
     219        virtual void visit( Attribute * node ) { visit( const_cast<const Attribute *>(node) ); }
     220        virtual void visit( const Attribute * attribute ) = 0;
    128221};
    129222
    130223template< typename TreeType, typename VisitorType >
    131 inline void maybeAccept( TreeType *tree, VisitorType &visitor ) {
     224inline void maybeAccept( TreeType * tree, VisitorType & visitor ) {
    132225        if ( tree ) {
    133226                tree->accept( visitor );
     
    135228}
    136229
     230template< typename TreeType, typename VisitorType >
     231inline void maybeAccept( const TreeType * tree, VisitorType & visitor ) {
     232        if ( tree ) {
     233                tree->accept( visitor );
     234        }
     235}
     236
    137237template< typename Container, typename VisitorType >
    138 inline void acceptAll( Container &container, VisitorType &visitor ) {
     238inline void acceptAll( Container & container, VisitorType & visitor ) {
    139239        SemanticErrorException errors;
    140         for ( typename Container::iterator i = container.begin(); i != container.end(); ++i ) {
     240        for ( auto * i : container ) {
    141241                try {
    142                         if ( *i ) {
    143                                 (*i)->accept( visitor );
     242                        if ( i ) {
     243                                i->accept( visitor );
     244                        }
     245                } catch( SemanticErrorException & e ) {
     246                        errors.append( e );
     247                }
     248        }
     249        if ( ! errors.isEmpty() ) {
     250                throw errors;
     251        }
     252}
     253
     254template< typename Container, typename VisitorType >
     255inline void acceptAll( const Container & container, VisitorType & visitor ) {
     256        SemanticErrorException errors;
     257        for ( const auto * i : container ) {
     258                try {
     259                        if ( i ) {
     260                                i->accept( visitor );
    144261                        }
    145262                } catch( SemanticErrorException &e ) {
  • src/Tuples/Explode.h

    r1f1c102 rf53acdf8  
    5151        template<typename OutputIterator>
    5252        void append( OutputIterator out, Expression* expr, const ResolvExpr::TypeEnvironment& env,
    53                         const ResolvExpr::OpenVarSet& openVars, const ResolvExpr::AssertionList& need, 
     53                        const ResolvExpr::OpenVarSet& openVars, const ResolvExpr::AssertionList& need,
    5454                        const ResolvExpr::Cost& cost, const ResolvExpr::Cost& cvtCost ) {
    5555                *out++ = ResolvExpr::Alternative{ expr, env, openVars, need, cost, cvtCost };
     
    5858        /// Append alternative to an ExplodedActual
    5959        static inline void append( ResolvExpr::ExplodedActual& ea, Expression* expr,
    60                         const ResolvExpr::TypeEnvironment&, const ResolvExpr::OpenVarSet&, 
     60                        const ResolvExpr::TypeEnvironment&, const ResolvExpr::OpenVarSet&,
    6161                        const ResolvExpr::AssertionList&, const ResolvExpr::Cost&, const ResolvExpr::Cost& ) {
    6262                ea.exprs.emplace_back( expr );
     
    111111                } else {
    112112                        // atomic (non-tuple) type - output a clone of the expression in a new alternative
    113                         append( std::forward<Output>(out), expr->clone(), alt.env, alt.openVars, alt.need, 
     113                        append( std::forward<Output>(out), expr->clone(), alt.env, alt.openVars, alt.need,
    114114                                alt.cost, alt.cvtCost );
    115115                }
     
    174174template< typename Output >
    175175void explodeRecursive(
    176         const ast::CastExpr * expr, const ResolvExpr::Candidate & arg,
    177         const ast::SymbolTable & symtab, Output && out
     176        const ast::CastExpr *, const ResolvExpr::Candidate &,
     177        const ast::SymbolTable &, Output &&
    178178) {
    179179}
     
    239239/// explode list of candidates into flattened list of candidates
    240240template< typename Output >
    241 void explode( 
    242         const ResolvExpr::CandidateList & cands, const ast::SymbolTable & symtab, Output && out, 
     241void explode(
     242        const ResolvExpr::CandidateList & cands, const ast::SymbolTable & symtab, Output && out,
    243243        bool isTupleAssign = false
    244244) {
  • src/Tuples/TupleAssignment.cc

    r1f1c102 rf53acdf8  
    6767                struct Matcher {
    6868                  public:
    69                         Matcher( TupleAssignSpotter_old &spotter, const ResolvExpr::AltList& lhs, 
     69                        Matcher( TupleAssignSpotter_old &spotter, const ResolvExpr::AltList& lhs,
    7070                                const ResolvExpr::AltList& rhs );
    7171                        virtual ~Matcher() {}
    72                        
     72
    7373                        virtual void match( std::list< Expression * > &out ) = 0;
    7474                        ObjectDecl * newObject( UniqueName & namer, Expression * expr );
     
    8383                                for ( const ResolvExpr::Alternative& alt : alts ) { combineState( alt ); }
    8484                        }
    85                        
     85
    8686                        ResolvExpr::AltList lhs, rhs;
    8787                        TupleAssignSpotter_old &spotter;
     
    264264                }
    265265
    266                 // extract expressions from the assignment alternatives to produce a list of assignments 
     266                // extract expressions from the assignment alternatives to produce a list of assignments
    267267                // that together form a single alternative
    268268                std::list< Expression *> solved_assigns;
     
    271271                        matcher->combineState( alt );
    272272                }
    273                
     273
    274274                // xxx -- was push_front
    275275                currentFinder.get_alternatives().push_back( ResolvExpr::Alternative{
    276                         new TupleAssignExpr{ solved_assigns, matcher->tmpDecls }, matcher->compositeEnv, 
    277                         matcher->openVars, 
    278                         ResolvExpr::AssertionList( matcher->need.begin(), matcher->need.end() ), 
     276                        new TupleAssignExpr{ solved_assigns, matcher->tmpDecls }, matcher->compositeEnv,
     277                        matcher->openVars,
     278                        ResolvExpr::AssertionList( matcher->need.begin(), matcher->need.end() ),
    279279                        ResolvExpr::sumCost( current ) + matcher->baseCost } );
    280280        }
     
    284284        : lhs(lhs), rhs(rhs), spotter(spotter),
    285285          baseCost( ResolvExpr::sumCost( lhs ) + ResolvExpr::sumCost( rhs ) ) {
    286                 combineState( lhs ); 
     286                combineState( lhs );
    287287                combineState( rhs );
    288288        }
     
    390390                return dynamic_cast< const ast::TupleType * >( expr->result->stripReferences() );
    391391        }
    392        
     392
    393393        /// true if `expr` is of tuple type or a reference to one
    394394        bool refToTuple( const ast::Expr * expr ) {
     
    421421                        }
    422422
    423                         Matcher( 
     423                        Matcher(
    424424                                TupleAssignSpotter_new & s, const CodeLocation & loc,
    425425                                const ResolvExpr::CandidateList & l, const ResolvExpr::CandidateList & r )
    426                         : lhs( l ), rhs( r ), spotter( s ), location( loc ), 
    427                           baseCost( ResolvExpr::sumCost( lhs ) + ResolvExpr::sumCost( rhs ) ), tmpDecls(), 
     426                        : lhs( l ), rhs( r ), spotter( s ), location( loc ),
     427                          baseCost( ResolvExpr::sumCost( lhs ) + ResolvExpr::sumCost( rhs ) ), tmpDecls(),
    428428                          env(), open(), need() {
    429429                                for ( auto & cand : lhs ) combineState( *cand );
    430430                                for ( auto & cand : rhs ) combineState( *cand );
    431431                        }
     432                        virtual ~Matcher() = default;
    432433
    433434                        virtual std::vector< ast::ptr< ast::Expr > > match() = 0;
    434435
    435                         /// removes environments from subexpressions within statement expressions, which could 
    436                         /// throw off later passes like those in Box which rely on PolyMutator, and adds the 
     436                        /// removes environments from subexpressions within statement expressions, which could
     437                        /// throw off later passes like those in Box which rely on PolyMutator, and adds the
    437438                        /// bindings to the env
    438439                        struct EnvRemover {
     
    455456                        ast::ObjectDecl * newObject( UniqueName & namer, const ast::Expr * expr ) {
    456457                                assert( expr->result && ! expr->result->isVoid() );
    457                                
    458                                 ast::ObjectDecl * ret = new ast::ObjectDecl{ 
    459                                         location, namer.newName(), expr->result, new ast::SingleInit{ location, expr }, 
     458
     459                                ast::ObjectDecl * ret = new ast::ObjectDecl{
     460                                        location, namer.newName(), expr->result, new ast::SingleInit{ location, expr },
    460461                                        ast::Storage::Classes{}, ast::Linkage::Cforall };
    461                                
     462
    462463                                // if expression type is a reference, just need an initializer, otherwise construct
    463464                                if ( ! expr->result.as< ast::ReferenceType >() ) {
    464465                                        // resolve ctor/dtor for the new object
    465                                         ast::ptr< ast::Init > ctorInit = ResolvExpr::resolveCtorInit( 
     466                                        ast::ptr< ast::Init > ctorInit = ResolvExpr::resolveCtorInit(
    466467                                                        InitTweak::genCtorInit( location, ret ), spotter.crntFinder.localSyms );
    467468                                        // remove environments from subexpressions of stmtExpr
     
    474475                        }
    475476
    476                         ast::UntypedExpr * createFunc( 
    477                                 const std::string & fname, const ast::ObjectDecl * left, 
    478                                 const ast::ObjectDecl * right 
     477                        ast::UntypedExpr * createFunc(
     478                                const std::string & fname, const ast::ObjectDecl * left,
     479                                const ast::ObjectDecl * right
    479480                        ) {
    480481                                assert( left );
     
    486487                                        args.front() = new ast::AddressExpr{ location, args.front() };
    487488                                        if ( right ) { args.back() = new ast::AddressExpr{ location, args.back() }; }
    488                                         return new ast::UntypedExpr{ 
     489                                        return new ast::UntypedExpr{
    489490                                                location, new ast::NameExpr{ location, "?=?" }, std::move(args) };
    490491                                } else {
    491                                         return new ast::UntypedExpr{ 
     492                                        return new ast::UntypedExpr{
    492493                                                location, new ast::NameExpr{ location, fname }, std::move(args) };
    493494                                }
     
    498499                struct MassAssignMatcher final : public Matcher {
    499500                        MassAssignMatcher(
    500                                 TupleAssignSpotter_new & s, const CodeLocation & loc, 
     501                                TupleAssignSpotter_new & s, const CodeLocation & loc,
    501502                                const ResolvExpr::CandidateList & l, const ResolvExpr::CandidateList & r )
    502503                        : Matcher( s, loc, l, r ) {}
     
    508509                                assert( lhs.empty() ? rhs.empty() : rhs.size() <= 1 );
    509510
    510                                 ast::ptr< ast::ObjectDecl > rtmp = 
     511                                ast::ptr< ast::ObjectDecl > rtmp =
    511512                                        rhs.size() == 1 ? newObject( rhsNamer, rhs.front()->expr ) : nullptr;
    512513
    513514                                std::vector< ast::ptr< ast::Expr > > out;
    514515                                for ( ResolvExpr::CandidateRef & lhsCand : lhs ) {
    515                                         // create a temporary object for each value in the LHS and create a call 
     516                                        // create a temporary object for each value in the LHS and create a call
    516517                                        // involving the RHS
    517518                                        ast::ptr< ast::ObjectDecl > ltmp = newObject( lhsNamer, lhsCand->expr );
     
    528529                struct MultipleAssignMatcher final : public Matcher {
    529530                        MultipleAssignMatcher(
    530                                 TupleAssignSpotter_new & s, const CodeLocation & loc, 
     531                                TupleAssignSpotter_new & s, const CodeLocation & loc,
    531532                                const ResolvExpr::CandidateList & l, const ResolvExpr::CandidateList & r )
    532533                        : Matcher( s, loc, l, r ) {}
     
    538539                                if ( lhs.size() != rhs.size() ) return {};
    539540
    540                                 // produce a new temporary object for each value in the LHS and RHS and pairwise 
     541                                // produce a new temporary object for each value in the LHS and RHS and pairwise
    541542                                // create the calls
    542543                                std::vector< ast::ptr< ast::ObjectDecl > > ltmp, rtmp;
     
    547548                                        ResolvExpr::CandidateRef & rhsCand = rhs[i];
    548549
    549                                         // convert RHS to LHS type minus one reference -- important for case where LHS 
     550                                        // convert RHS to LHS type minus one reference -- important for case where LHS
    550551                                        // is && and RHS is lvalue
    551552                                        auto lhsType = lhsCand->expr->result.strict_as< ast::ReferenceType >();
     
    557558                                        rtmp.emplace_back( std::move( robj ) );
    558559
    559                                         // resolve the cast expression so that rhsCand return type is bound by the cast 
     560                                        // resolve the cast expression so that rhsCand return type is bound by the cast
    560561                                        // type as needed, and transfer the resulting environment
    561562                                        ResolvExpr::CandidateFinder finder{ spotter.crntFinder.localSyms, env };
     
    564565                                        env = std::move( finder.candidates.front()->env );
    565566                                }
    566                                
     567
    567568                                splice( tmpDecls, ltmp );
    568569                                splice( tmpDecls, rtmp );
    569                                
     570
    570571                                return out;
    571572                        }
     
    575576                std::string fname;
    576577                std::unique_ptr< Matcher > matcher;
    577        
     578
    578579        public:
    579                 TupleAssignSpotter_new( ResolvExpr::CandidateFinder & f ) 
     580                TupleAssignSpotter_new( ResolvExpr::CandidateFinder & f )
    580581                : crntFinder( f ), fname(), matcher() {}
    581582
    582583                // find left- and right-hand-sides for mass or multiple assignment
    583                 void spot( 
    584                         const ast::UntypedExpr * expr, std::vector< ResolvExpr::CandidateFinder > & args 
     584                void spot(
     585                        const ast::UntypedExpr * expr, std::vector< ResolvExpr::CandidateFinder > & args
    585586                ) {
    586587                        if ( auto op = expr->func.as< ast::NameExpr >() ) {
     
    599600                                        if ( ! refToTuple( lhsCand->expr ) ) continue;
    600601
    601                                         // explode is aware of casts - ensure every LHS is sent into explode with a 
     602                                        // explode is aware of casts - ensure every LHS is sent into explode with a
    602603                                        // reference cast
    603604                                        if ( ! lhsCand->expr.as< ast::CastExpr >() ) {
    604                                                 lhsCand->expr = new ast::CastExpr{ 
     605                                                lhsCand->expr = new ast::CastExpr{
    605606                                                        lhsCand->expr, new ast::ReferenceType{ lhsCand->expr->result } };
    606607                                        }
     
    610611                                        explode( *lhsCand, crntFinder.localSyms, back_inserter(lhs), true );
    611612                                        for ( ResolvExpr::CandidateRef & cand : lhs ) {
    612                                                 // each LHS value must be a reference - some come in with a cast, if not 
     613                                                // each LHS value must be a reference - some come in with a cast, if not
    613614                                                // just cast to reference here
    614615                                                if ( ! cand->expr->result.as< ast::ReferenceType >() ) {
     
    629630                                                                // multiple assignment
    630631                                                                explode( *rhsCand, crntFinder.localSyms, back_inserter(rhs), true );
    631                                                                 matcher.reset( 
     632                                                                matcher.reset(
    632633                                                                        new MultipleAssignMatcher{ *this, expr->location, lhs, rhs } );
    633634                                                        } else {
    634635                                                                // mass assignment
    635636                                                                rhs.emplace_back( rhsCand );
    636                                                                 matcher.reset( 
     637                                                                matcher.reset(
    637638                                                                        new MassAssignMatcher{ *this, expr->location, lhs, rhs } );
    638639                                                        }
     
    642643                                                // expand all possible RHS possibilities
    643644                                                std::vector< ResolvExpr::CandidateList > rhsCands;
    644                                                 combos( 
     645                                                combos(
    645646                                                        std::next( args.begin(), 1 ), args.end(), back_inserter( rhsCands ) );
    646647                                                for ( const ResolvExpr::CandidateList & rhsCand : rhsCands ) {
     
    648649                                                        ResolvExpr::CandidateList rhs;
    649650                                                        explode( rhsCand, crntFinder.localSyms, back_inserter(rhs), true );
    650                                                         matcher.reset( 
     651                                                        matcher.reset(
    651652                                                                new MultipleAssignMatcher{ *this, expr->location, lhs, rhs } );
    652653                                                        match();
     
    663664
    664665                        if ( ! ( matcher->lhs.empty() && matcher->rhs.empty() ) ) {
    665                                 // if both LHS and RHS are empty than this is the empty tuple case, wherein it's 
    666                                 // okay for newAssigns to be empty. Otherwise, return early so that no new 
     666                                // if both LHS and RHS are empty than this is the empty tuple case, wherein it's
     667                                // okay for newAssigns to be empty. Otherwise, return early so that no new
    667668                                // candidates are generated
    668669                                if ( newAssigns.empty() ) return;
     
    692693                        }
    693694
    694                         // extract expressions from the assignment candidates to produce a list of assignments 
     695                        // extract expressions from the assignment candidates to produce a list of assignments
    695696                        // that together form a sigle candidate
    696697                        std::vector< ast::ptr< ast::Expr > > solved;
     
    701702
    702703                        crntFinder.candidates.emplace_back( std::make_shared< ResolvExpr::Candidate >(
    703                                 new ast::TupleAssignExpr{ 
    704                                         matcher->location, std::move( solved ), std::move( matcher->tmpDecls ) }, 
    705                                 std::move( matcher->env ), std::move( matcher->open ), std::move( matcher->need ), 
     704                                new ast::TupleAssignExpr{
     705                                        matcher->location, std::move( solved ), std::move( matcher->tmpDecls ) },
     706                                std::move( matcher->env ), std::move( matcher->open ), std::move( matcher->need ),
    706707                                ResolvExpr::sumCost( crnt ) + matcher->baseCost ) );
    707708                }
     
    709710} // anonymous namespace
    710711
    711 void handleTupleAssignment( 
    712         ResolvExpr::CandidateFinder & finder, const ast::UntypedExpr * assign, 
     712void handleTupleAssignment(
     713        ResolvExpr::CandidateFinder & finder, const ast::UntypedExpr * assign,
    713714        std::vector< ResolvExpr::CandidateFinder > & args
    714715) {
  • src/main.cc

    r1f1c102 rf53acdf8  
    460460        const char * descript;
    461461} printopts[] = {
    462         { "altexpr", expraltp, true, "alternatives for expressions" },
    463         { "ascodegen", codegenp, true, "as codegen rather than AST" },
    464         { "ast", astp, true, "AST after parsing" },
    465         { "astdecl", validp, true, "AST after declaration validation pass" },
    466         { "asterr", errorp, true, "AST on error" },
    467         { "astexpr", exprp, true, "AST after expression analysis" },
    468         { "astgen", genericsp, true, "AST after instantiate generics" },
    469         { "box", bboxp, true, "before box step" },
    470         { "ctordtor", ctorinitp, true, "after ctor/dtor are replaced" },
    471         { "codegen", bcodegenp, true, "before code generation" },
     462        { "ascodegen", codegenp, true, "print AST as codegen rather than AST" },
     463        { "asterr", errorp, true, "print AST on error" },
    472464        { "declstats", declstatsp, true, "code property statistics" },
    473465        { "parse", yydebug, true, "yacc (parsing) debug information" },
    474466        { "pretty", prettycodegenp, true, "prettyprint for ascodegen flag" },
    475         { "resolver", bresolvep, true, "before resolver step" },
    476467        { "rproto", resolvprotop, true, "resolver-proto instance" },
    477         { "rsteps", resolvep, true, "resolver steps" },
    478         { "symevt", symtabp, true, "symbol table events" },
    479         { "tree", parsep, true, "parse tree" },
    480         { "tuple", tuplep, true, "after tuple expansion" },
     468        { "rsteps", resolvep, true, "print resolver steps" },
     469        { "tree", parsep, true, "print parse tree" },
     470        // code dumps
     471        { "ast", astp, true, "print AST after parsing" },
     472        { "symevt", symtabp, true, "print AST after symbol table events" },
     473        { "altexpr", expraltp, true, "print alternatives for expressions" },
     474        { "astdecl", validp, true, "print AST after declaration validation pass" },
     475        { "resolver", bresolvep, true, "print AST before resolver step" },
     476        { "astexpr", exprp, true, "print AST after expression analysis" },
     477        { "ctordtor", ctorinitp, true, "print AST after ctor/dtor are replaced" },
     478        { "tuple", tuplep, true, "print AST after tuple expansion" },
     479        { "astgen", genericsp, true, "print AST after instantiate generics" },
     480        { "box", bboxp, true, "print AST before box step" },
     481        { "codegen", bcodegenp, true, "print AST before code generation" },
    481482};
    482483enum { printoptsSize = sizeof( printopts ) / sizeof( printopts[0] ) };
Note: See TracChangeset for help on using the changeset viewer.