Ignore:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • src/ResolvExpr/Resolver.cc

    ra4ca48c re3e16bc  
    2121#include "Alternative.h"                 // for Alternative, AltList
    2222#include "AlternativeFinder.h"           // for AlternativeFinder, resolveIn...
    23 #include "Common/PassVisitor.h"          // for PassVisitor
    2423#include "Common/SemanticError.h"        // for SemanticError
    2524#include "Common/utility.h"              // for ValueGuard, group_iterate
     
    4443
    4544namespace ResolvExpr {
    46         struct Resolver final : public WithIndexer, public WithGuards, public WithVisitorRef<Resolver>, public WithShortCircuiting {
    47                 Resolver() {}
    48                 Resolver( const SymTab::Indexer & other ) {
    49                         indexer = other;
    50                 }
    51 
    52                 void previsit( FunctionDecl *functionDecl );
    53                 void postvisit( FunctionDecl *functionDecl );
    54                 void previsit( ObjectDecl *functionDecl );
    55                 void previsit( TypeDecl *typeDecl );
    56                 void previsit( EnumDecl * enumDecl );
    57 
    58                 void previsit( ArrayType * at );
    59                 void previsit( PointerType * at );
    60 
    61                 void previsit( ExprStmt *exprStmt );
    62                 void previsit( AsmExpr *asmExpr );
    63                 void previsit( AsmStmt *asmStmt );
    64                 void previsit( IfStmt *ifStmt );
    65                 void previsit( WhileStmt *whileStmt );
    66                 void previsit( ForStmt *forStmt );
    67                 void previsit( SwitchStmt *switchStmt );
    68                 void previsit( CaseStmt *caseStmt );
    69                 void previsit( BranchStmt *branchStmt );
    70                 void previsit( ReturnStmt *returnStmt );
    71                 void previsit( ThrowStmt *throwStmt );
    72                 void previsit( CatchStmt *catchStmt );
    73 
    74                 void previsit( SingleInit *singleInit );
    75                 void previsit( ListInit *listInit );
    76                 void previsit( ConstructorInit *ctorInit );
     45        class Resolver final : public SymTab::Indexer {
     46          public:
     47                Resolver() : SymTab::Indexer( false ) {}
     48                Resolver( const SymTab:: Indexer & other ) : SymTab::Indexer( other ) {
     49                        if ( const Resolver * res = dynamic_cast< const Resolver * >( &other ) ) {
     50                                functionReturn = res->functionReturn;
     51                                currentObject = res->currentObject;
     52                                inEnumDecl = res->inEnumDecl;
     53                        }
     54                }
     55
     56                typedef SymTab::Indexer Parent;
     57                using Parent::visit;
     58                virtual void visit( FunctionDecl *functionDecl ) override;
     59                virtual void visit( ObjectDecl *functionDecl ) override;
     60                virtual void visit( TypeDecl *typeDecl ) override;
     61                virtual void visit( EnumDecl * enumDecl ) override;
     62
     63                virtual void visit( ArrayType * at ) override;
     64                virtual void visit( PointerType * at ) override;
     65
     66                virtual void visit( ExprStmt *exprStmt ) override;
     67                virtual void visit( AsmExpr *asmExpr ) override;
     68                virtual void visit( AsmStmt *asmStmt ) override;
     69                virtual void visit( IfStmt *ifStmt ) override;
     70                virtual void visit( WhileStmt *whileStmt ) override;
     71                virtual void visit( ForStmt *forStmt ) override;
     72                virtual void visit( SwitchStmt *switchStmt ) override;
     73                virtual void visit( CaseStmt *caseStmt ) override;
     74                virtual void visit( BranchStmt *branchStmt ) override;
     75                virtual void visit( ReturnStmt *returnStmt ) override;
     76                virtual void visit( ThrowStmt *throwStmt ) override;
     77                virtual void visit( CatchStmt *catchStmt ) override;
     78
     79                virtual void visit( SingleInit *singleInit ) override;
     80                virtual void visit( ListInit *listInit ) override;
     81                virtual void visit( ConstructorInit *ctorInit ) override;
    7782          private:
    7883        typedef std::list< Initializer * >::iterator InitIterator;
     
    9196
    9297        void resolve( std::list< Declaration * > translationUnit ) {
    93                 PassVisitor<Resolver> resolver;
     98                Resolver resolver;
    9499                acceptAll( translationUnit, resolver );
    95100        }
    96101
    97         // used in resolveTypeof
    98102        Expression *resolveInVoidContext( Expression *expr, const SymTab::Indexer &indexer ) {
    99103                TypeEnvironment env;
    100104                return resolveInVoidContext( expr, indexer, env );
    101105        }
     106
    102107
    103108        namespace {
     
    185190        }
    186191
    187         void Resolver::previsit( ObjectDecl *objectDecl ) {
    188                 Type *new_type = resolveTypeof( objectDecl->get_type(), indexer );
     192        void Resolver::visit( ObjectDecl *objectDecl ) {
     193                Type *new_type = resolveTypeof( objectDecl->get_type(), *this );
    189194                objectDecl->set_type( new_type );
    190195                // To handle initialization of routine pointers, e.g., int (*fp)(int) = foo(), means that class-variable
     
    193198                // each value of initContext is retained, so the type on the first analysis is preserved and used for selecting
    194199                // the RHS.
    195                 GuardValue( currentObject );
     200                ValueGuard<CurrentObject> temp( currentObject );
    196201                currentObject = CurrentObject( objectDecl->get_type() );
    197202                if ( inEnumDecl && dynamic_cast< EnumInstType * >( objectDecl->get_type() ) ) {
     
    200205                        currentObject = CurrentObject( new BasicType( Type::Qualifiers(), BasicType::SignedInt ) );
    201206                }
     207                Parent::visit( objectDecl );
     208                if ( inEnumDecl && dynamic_cast< EnumInstType * >( objectDecl->get_type() ) ) {
     209                        // delete newly created signed int type
     210                        // delete currentObject.getType();
     211                }
    202212        }
    203213
     
    206216                if ( type->get_dimension() ) {
    207217                        CastExpr *castExpr = new CastExpr( type->get_dimension(), SymTab::SizeType->clone() );
    208                         Expression *newExpr = findSingleExpression( castExpr, indexer );
     218                        Expression *newExpr = findSingleExpression( castExpr, *this );
    209219                        delete type->get_dimension();
    210220                        type->set_dimension( newExpr );
     
    212222        }
    213223
    214         void Resolver::previsit( ArrayType * at ) {
     224        void Resolver::visit( ArrayType * at ) {
    215225                handlePtrType( at );
    216         }
    217 
    218         void Resolver::previsit( PointerType * pt ) {
     226                Parent::visit( at );
     227        }
     228
     229        void Resolver::visit( PointerType * pt ) {
    219230                handlePtrType( pt );
    220         }
    221 
    222         void Resolver::previsit( TypeDecl *typeDecl ) {
     231                Parent::visit( pt );
     232        }
     233
     234        void Resolver::visit( TypeDecl *typeDecl ) {
    223235                if ( typeDecl->get_base() ) {
    224                         Type *new_type = resolveTypeof( typeDecl->get_base(), indexer );
     236                        Type *new_type = resolveTypeof( typeDecl->get_base(), *this );
    225237                        typeDecl->set_base( new_type );
    226238                } // if
    227         }
    228 
    229         void Resolver::previsit( FunctionDecl *functionDecl ) {
     239                Parent::visit( typeDecl );
     240        }
     241
     242        void Resolver::visit( FunctionDecl *functionDecl ) {
    230243#if 0
    231                 std::cerr << "resolver visiting functiondecl ";
    232                 functionDecl->print( std::cerr );
    233                 std::cerr << std::endl;
     244                std::cout << "resolver visiting functiondecl ";
     245                functionDecl->print( std::cout );
     246                std::cout << std::endl;
    234247#endif
    235                 Type *new_type = resolveTypeof( functionDecl->get_type(), indexer );
     248                Type *new_type = resolveTypeof( functionDecl->get_type(), *this );
    236249                functionDecl->set_type( new_type );
    237                 GuardValue( functionReturn );
     250                ValueGuard< Type * > oldFunctionReturn( functionReturn );
    238251                functionReturn = ResolvExpr::extractResultType( functionDecl->get_functionType() );
    239         }
    240 
    241 
    242         void Resolver::postvisit( FunctionDecl *functionDecl ) {
     252                Parent::visit( functionDecl );
     253
    243254                // default value expressions have an environment which shouldn't be there and trips up later passes.
    244255                // xxx - it might be necessary to somehow keep the information from this environment, but I can't currently
     
    254265        }
    255266
    256         void Resolver::previsit( EnumDecl * ) {
     267        void Resolver::visit( EnumDecl * enumDecl ) {
    257268                // in case we decide to allow nested enums
    258                 GuardValue( inEnumDecl );
     269                ValueGuard< bool > oldInEnumDecl( inEnumDecl );
    259270                inEnumDecl = true;
    260         }
    261 
    262         void Resolver::previsit( ExprStmt *exprStmt ) {
    263                 visit_children = false;
     271                Parent::visit( enumDecl );
     272        }
     273
     274        void Resolver::visit( ExprStmt *exprStmt ) {
    264275                assertf( exprStmt->get_expr(), "ExprStmt has null Expression in resolver" );
    265                 Expression *newExpr = findVoidExpression( exprStmt->get_expr(), indexer );
     276                Expression *newExpr = findVoidExpression( exprStmt->get_expr(), *this );
    266277                delete exprStmt->get_expr();
    267278                exprStmt->set_expr( newExpr );
    268279        }
    269280
    270         void Resolver::previsit( AsmExpr *asmExpr ) {
    271                 visit_children = false;
    272                 Expression *newExpr = findVoidExpression( asmExpr->get_operand(), indexer );
     281        void Resolver::visit( AsmExpr *asmExpr ) {
     282                Expression *newExpr = findVoidExpression( asmExpr->get_operand(), *this );
    273283                delete asmExpr->get_operand();
    274284                asmExpr->set_operand( newExpr );
    275285                if ( asmExpr->get_inout() ) {
    276                         newExpr = findVoidExpression( asmExpr->get_inout(), indexer );
     286                        newExpr = findVoidExpression( asmExpr->get_inout(), *this );
    277287                        delete asmExpr->get_inout();
    278288                        asmExpr->set_inout( newExpr );
     
    280290        }
    281291
    282         void Resolver::previsit( AsmStmt *asmStmt ) {
    283                 visit_children = false;
    284                 acceptAll( asmStmt->get_input(), *visitor );
    285                 acceptAll( asmStmt->get_output(), *visitor );
    286         }
    287 
    288         void Resolver::previsit( IfStmt *ifStmt ) {
    289                 Expression *newExpr = findSingleExpression( ifStmt->get_condition(), indexer );
     292        void Resolver::visit( AsmStmt *asmStmt ) {
     293                acceptAll( asmStmt->get_input(), *this);
     294                acceptAll( asmStmt->get_output(), *this);
     295        }
     296
     297        void Resolver::visit( IfStmt *ifStmt ) {
     298                Expression *newExpr = findSingleExpression( ifStmt->get_condition(), *this );
    290299                delete ifStmt->get_condition();
    291300                ifStmt->set_condition( newExpr );
    292         }
    293 
    294         void Resolver::previsit( WhileStmt *whileStmt ) {
    295                 Expression *newExpr = findSingleExpression( whileStmt->get_condition(), indexer );
     301                Parent::visit( ifStmt );
     302        }
     303
     304        void Resolver::visit( WhileStmt *whileStmt ) {
     305                Expression *newExpr = findSingleExpression( whileStmt->get_condition(), *this );
    296306                delete whileStmt->get_condition();
    297307                whileStmt->set_condition( newExpr );
    298         }
    299 
    300         void Resolver::previsit( ForStmt *forStmt ) {
     308                Parent::visit( whileStmt );
     309        }
     310
     311        void Resolver::visit( ForStmt *forStmt ) {
     312                Parent::visit( forStmt );
     313
    301314                if ( forStmt->get_condition() ) {
    302                         Expression * newExpr = findSingleExpression( forStmt->get_condition(), indexer );
     315                        Expression * newExpr = findSingleExpression( forStmt->get_condition(), *this );
    303316                        delete forStmt->get_condition();
    304317                        forStmt->set_condition( newExpr );
     
    306319
    307320                if ( forStmt->get_increment() ) {
    308                         Expression * newExpr = findVoidExpression( forStmt->get_increment(), indexer );
     321                        Expression * newExpr = findVoidExpression( forStmt->get_increment(), *this );
    309322                        delete forStmt->get_increment();
    310323                        forStmt->set_increment( newExpr );
     
    312325        }
    313326
    314         void Resolver::previsit( SwitchStmt *switchStmt ) {
    315                 GuardValue( currentObject );
     327        void Resolver::visit( SwitchStmt *switchStmt ) {
     328                ValueGuard< CurrentObject > oldCurrentObject( currentObject );
    316329                Expression *newExpr;
    317                 newExpr = findIntegralExpression( switchStmt->get_condition(), indexer );
     330                newExpr = findIntegralExpression( switchStmt->get_condition(), *this );
    318331                delete switchStmt->get_condition();
    319332                switchStmt->set_condition( newExpr );
    320333
    321334                currentObject = CurrentObject( newExpr->get_result() );
    322         }
    323 
    324         void Resolver::previsit( CaseStmt *caseStmt ) {
     335                Parent::visit( switchStmt );
     336        }
     337
     338        void Resolver::visit( CaseStmt *caseStmt ) {
    325339                if ( caseStmt->get_condition() ) {
    326340                        std::list< InitAlternative > initAlts = currentObject.getOptions();
    327341                        assertf( initAlts.size() == 1, "SwitchStmt did not correctly resolve an integral expression." );
    328342                        CastExpr * castExpr = new CastExpr( caseStmt->get_condition(), initAlts.front().type->clone() );
    329                         Expression * newExpr = findSingleExpression( castExpr, indexer );
     343                        Expression * newExpr = findSingleExpression( castExpr, *this );
    330344                        castExpr = strict_dynamic_cast< CastExpr * >( newExpr );
    331345                        caseStmt->set_condition( castExpr->get_arg() );
     
    333347                        delete castExpr;
    334348                }
    335         }
    336 
    337         void Resolver::previsit( BranchStmt *branchStmt ) {
    338                 visit_children = false;
     349                Parent::visit( caseStmt );
     350        }
     351
     352        void Resolver::visit( BranchStmt *branchStmt ) {
    339353                // must resolve the argument for a computed goto
    340354                if ( branchStmt->get_type() == BranchStmt::Goto ) { // check for computed goto statement
     
    343357                                PointerType pt( Type::Qualifiers(), v.clone() );
    344358                                CastExpr * castExpr = new CastExpr( arg, pt.clone() );
    345                                 Expression * newExpr = findSingleExpression( castExpr, indexer ); // find best expression
     359                                Expression * newExpr = findSingleExpression( castExpr, *this ); // find best expression
    346360                                branchStmt->set_target( newExpr );
    347361                        } // if
     
    349363        }
    350364
    351         void Resolver::previsit( ReturnStmt *returnStmt ) {
    352                 visit_children = false;
     365        void Resolver::visit( ReturnStmt *returnStmt ) {
    353366                if ( returnStmt->get_expr() ) {
    354367                        CastExpr *castExpr = new CastExpr( returnStmt->get_expr(), functionReturn->clone() );
    355                         Expression *newExpr = findSingleExpression( castExpr, indexer );
     368                        Expression *newExpr = findSingleExpression( castExpr, *this );
    356369                        delete castExpr;
    357370                        returnStmt->set_expr( newExpr );
     
    359372        }
    360373
    361         void Resolver::previsit( ThrowStmt *throwStmt ) {
    362                 visit_children = false;
     374        void Resolver::visit( ThrowStmt *throwStmt ) {
    363375                // TODO: Replace *exception type with &exception type.
    364376                if ( throwStmt->get_expr() ) {
    365377                        StructDecl * exception_decl =
    366                                 indexer.lookupStruct( "__cfaehm__base_exception_t" );
     378                                lookupStruct( "__cfaehm__base_exception_t" );
    367379                        assert( exception_decl );
    368380                        Expression * wrapped = new CastExpr(
     
    376388                                        )
    377389                                );
    378                         Expression * newExpr = findSingleExpression( wrapped, indexer );
     390                        Expression * newExpr = findSingleExpression( wrapped, *this );
    379391                        throwStmt->set_expr( newExpr );
    380392                }
    381393        }
    382394
    383         void Resolver::previsit( CatchStmt *catchStmt ) {
     395        void Resolver::visit( CatchStmt *catchStmt ) {
     396                // inline Indexer::visit so that the exception variable is still in-scope for
     397                // findSingleExpression() below
     398                Parent::enterScope();
     399                Visitor::visit( catchStmt );
     400
    384401                if ( catchStmt->get_cond() ) {
    385402                        Expression * wrapped = new CastExpr(
     
    387404                                new BasicType( noQualifiers, BasicType::Bool )
    388405                                );
    389                         catchStmt->set_cond( findSingleExpression( wrapped, indexer ) );
    390                 }
     406                        catchStmt->set_cond( findSingleExpression( wrapped, *this ) );
     407                }
     408
     409                Parent::leaveScope();
    391410        }
    392411
     
    400419        }
    401420
    402         void Resolver::previsit( SingleInit *singleInit ) {
    403                 visit_children = false;
     421        void Resolver::visit( SingleInit *singleInit ) {
    404422                // resolve initialization using the possibilities as determined by the currentObject cursor
    405423                UntypedInitExpr * untyped = new UntypedInitExpr( singleInit->get_value(), currentObject.getOptions() );
    406                 Expression * newExpr = findSingleExpression( untyped, indexer );
     424                Expression * newExpr = findSingleExpression( untyped, *this );
    407425                InitExpr * initExpr = strict_dynamic_cast< InitExpr * >( newExpr );
    408426
     
    443461        }
    444462
    445         void Resolver::previsit( ListInit * listInit ) {
    446                 visit_children = false;
     463        void Resolver::visit( ListInit * listInit ) {
    447464                // move cursor into brace-enclosed initializer-list
    448465                currentObject.enterListInit();
     
    455472                        Initializer * init = std::get<1>(p);
    456473                        newDesignations.push_back( currentObject.findNext( des ) );
    457                         init->accept( *visitor );
     474                        init->accept( *this );
    458475                }
    459476                // set the set of 'resolved' designations and leave the brace-enclosed initializer-list
     
    484501                delete ctorInit->get_dtor();
    485502                ctorInit->set_dtor( NULL );
    486                 maybeAccept( ctorInit->get_init(), *visitor );
     503                maybeAccept( ctorInit->get_init(), *this );
    487504        }
    488505
     
    490507        void resolveCtorInit( ConstructorInit * ctorInit, const SymTab::Indexer & indexer ) {
    491508                assert( ctorInit );
    492                 PassVisitor<Resolver> resolver( indexer );
     509                Resolver resolver( indexer );
    493510                ctorInit->accept( resolver );
    494511        }
     
    496513        void resolveStmtExpr( StmtExpr * stmtExpr, const SymTab::Indexer & indexer ) {
    497514                assert( stmtExpr );
    498                 PassVisitor<Resolver> resolver( indexer );
     515                Resolver resolver( indexer );
    499516                stmtExpr->accept( resolver );
    500517        }
    501518
    502         void Resolver::previsit( ConstructorInit *ctorInit ) {
    503                 visit_children = false;
     519        void Resolver::visit( ConstructorInit *ctorInit ) {
    504520                // xxx - fallback init has been removed => remove fallbackInit function and remove complexity from FixInit and remove C-init from ConstructorInit
    505                 maybeAccept( ctorInit->get_ctor(), *visitor );
    506                 maybeAccept( ctorInit->get_dtor(), *visitor );
     521                maybeAccept( ctorInit->get_ctor(), *this );
     522                maybeAccept( ctorInit->get_dtor(), *this );
    507523
    508524                // found a constructor - can get rid of C-style initializer
Note: See TracChangeset for help on using the changeset viewer.