Changeset c86b08d for src/AST


Ignore:
Timestamp:
May 1, 2023, 4:06:07 PM (2 years ago)
Author:
caparsons <caparson@…>
Branches:
ADT, ast-experimental, master
Children:
a33a5e2
Parents:
73bf7ddc
Message:

added support for the waituntil statement in the compiler

Location:
src/AST
Files:
8 edited

Legend:

Unmodified
Added
Removed
  • src/AST/Convert.cpp

    r73bf7ddc rc86b08d  
    567567        }
    568568
     569    const ast::WhenClause * visit( const ast::WhenClause * node ) override final {
     570                // There is no old-AST WhenClause, so this should never be called.
     571                assert( !node );
     572                return nullptr;
     573        }
     574
    569575        const ast::Stmt * visit( const ast::WaitForStmt * node ) override final {
    570576                if ( inCache( node ) ) return nullptr;
     
    573579                for ( auto clause : node->clauses ) {
    574580                        stmt->clauses.push_back({{
    575                                         get<Expression>().accept1( clause->target_func ),
     581                                        get<Expression>().accept1( clause->target ),
    576582                                        get<Expression>().acceptL( clause->target_args ),
    577583                                },
    578584                                get<Statement>().accept1( clause->stmt ),
    579                                 get<Expression>().accept1( clause->cond ),
     585                                get<Expression>().accept1( clause->when_cond ),
    580586                        });
    581587                }
     
    594600        const ast::WaitForClause * visit( const ast::WaitForClause * node ) override final {
    595601                // There is no old-AST WaitForClause, so this should never be called.
     602                assert( !node );
     603                return nullptr;
     604        }
     605
     606    const ast::Stmt * visit( const ast::WaitUntilStmt * node ) override final {
     607        // There is no old-AST WaitUntilStmt, so this should never be called.
    596608                assert( !node );
    597609                return nullptr;
     
    21582170                        auto clause = new ast::WaitForClause( old->location );
    21592171
    2160                         clause->target_func = GET_ACCEPT_1(clauses[i].target.function, Expr);
     2172                        clause->target = GET_ACCEPT_1(clauses[i].target.function, Expr);
    21612173                        clause->target_args = GET_ACCEPT_V(clauses[i].target.arguments, Expr);
    21622174                        clause->stmt = GET_ACCEPT_1(clauses[i].statement, Stmt);
    2163                         clause->cond = GET_ACCEPT_1(clauses[i].condition, Expr);
     2175                        clause->when_cond = GET_ACCEPT_1(clauses[i].condition, Expr);
    21642176
    21652177                        stmt->clauses.push_back( clause );
  • src/AST/Fwd.hpp

    r73bf7ddc rc86b08d  
    5858class FinallyClause;
    5959class SuspendStmt;
     60class WhenClause;
    6061class WaitForStmt;
    6162class WaitForClause;
     63class WaitUntilStmt;
    6264class WithStmt;
    6365class DeclStmt;
  • src/AST/Node.cpp

    r73bf7ddc rc86b08d  
    174174template class ast::ptr_base< ast::FinallyClause, ast::Node::ref_type::weak >;
    175175template class ast::ptr_base< ast::FinallyClause, ast::Node::ref_type::strong >;
     176template class ast::ptr_base< ast::WhenClause, ast::Node::ref_type::weak >;
     177template class ast::ptr_base< ast::WhenClause, ast::Node::ref_type::strong >;
    176178template class ast::ptr_base< ast::WaitForStmt, ast::Node::ref_type::weak >;
    177179template class ast::ptr_base< ast::WaitForStmt, ast::Node::ref_type::strong >;
    178180template class ast::ptr_base< ast::WaitForClause, ast::Node::ref_type::weak >;
    179181template class ast::ptr_base< ast::WaitForClause, ast::Node::ref_type::strong >;
     182template class ast::ptr_base< ast::WaitUntilStmt, ast::Node::ref_type::weak >;
     183template class ast::ptr_base< ast::WaitUntilStmt, ast::Node::ref_type::strong >;
    180184template class ast::ptr_base< ast::WithStmt, ast::Node::ref_type::weak >;
    181185template class ast::ptr_base< ast::WithStmt, ast::Node::ref_type::strong >;
  • src/AST/Pass.hpp

    r73bf7ddc rc86b08d  
    162162        const ast::FinallyClause *    visit( const ast::FinallyClause        * ) override final;
    163163        const ast::Stmt *             visit( const ast::SuspendStmt          * ) override final;
     164    const ast::WhenClause *       visit( const ast::WhenClause           * ) override final;
    164165        const ast::Stmt *             visit( const ast::WaitForStmt          * ) override final;
    165166        const ast::WaitForClause *    visit( const ast::WaitForClause        * ) override final;
     167    const ast::Stmt *             visit( const ast::WaitUntilStmt        * ) override final;
    166168        const ast::Decl *             visit( const ast::WithStmt             * ) override final;
    167169        const ast::NullStmt *         visit( const ast::NullStmt             * ) override final;
  • src/AST/Pass.impl.hpp

    r73bf7ddc rc86b08d  
    10661066
    10671067//--------------------------------------------------------------------------
     1068// WhenClause
     1069template< typename core_t >
     1070const ast::WhenClause * ast::Pass< core_t >::visit( const ast::WhenClause * node ) {
     1071        VISIT_START( node );
     1072
     1073        if ( __visit_children() ) {
     1074                maybe_accept( node, &WhenClause::target );
     1075                maybe_accept( node, &WhenClause::stmt );
     1076                maybe_accept( node, &WhenClause::when_cond );
     1077        }
     1078
     1079        VISIT_END( WhenClause, node );
     1080}
     1081
     1082//--------------------------------------------------------------------------
    10681083// WaitForStmt
    10691084template< typename core_t >
     
    10901105
    10911106        if ( __visit_children() ) {
    1092                 maybe_accept( node, &WaitForClause::target_func );
     1107                maybe_accept( node, &WaitForClause::target );
    10931108                maybe_accept( node, &WaitForClause::target_args );
    10941109                maybe_accept( node, &WaitForClause::stmt );
    1095                 maybe_accept( node, &WaitForClause::cond );
     1110                maybe_accept( node, &WaitForClause::when_cond );
    10961111        }
    10971112
    10981113        VISIT_END( WaitForClause, node );
     1114}
     1115
     1116//--------------------------------------------------------------------------
     1117// WaitUntilStmt
     1118template< typename core_t >
     1119const ast::Stmt * ast::Pass< core_t >::visit( const ast::WaitUntilStmt * node ) {
     1120        VISIT_START( node );
     1121
     1122        if ( __visit_children() ) {
     1123                maybe_accept( node, &WaitUntilStmt::clauses );
     1124                maybe_accept( node, &WaitUntilStmt::timeout_time );
     1125                maybe_accept( node, &WaitUntilStmt::timeout_stmt );
     1126                maybe_accept( node, &WaitUntilStmt::timeout_cond );
     1127                maybe_accept( node, &WaitUntilStmt::else_stmt );
     1128                maybe_accept( node, &WaitUntilStmt::else_cond );
     1129        }
     1130
     1131        VISIT_END( Stmt, node );
    10991132}
    11001133
  • src/AST/Print.cpp

    r73bf7ddc rc86b08d  
    208208        }
    209209
     210    void print( const ast::WaitStmt * node ) {
     211                if ( node->timeout_time ) {
     212                        os << indent-1 << "timeout of:" << endl;
     213                        node->timeout_time->accept( *this );
     214
     215                        if ( node->timeout_stmt ) {
     216                                os << indent-1 << "... with statment:" << endl;
     217                                node->timeout_stmt->accept( *this );
     218                        }
     219
     220                        if ( node->timeout_cond ) {
     221                                os << indent-1 << "... with condition:" << endl;
     222                                node->timeout_cond->accept( *this );
     223                        }
     224                }
     225
     226                if ( node->else_stmt ) {
     227                        os << indent-1 << "else:" << endl;
     228                        node->else_stmt->accept( *this );
     229
     230                        if ( node->else_cond ) {
     231                                os << indent-1 << "... with condition:" << endl;
     232                                node->else_cond->accept( *this );
     233                        }
     234                }
     235        }
     236
    210237        void preprint( const ast::NamedTypeDecl * node ) {
    211238                if ( ! node->name.empty() ) {
     
    756783        }
    757784
     785        virtual const ast::WhenClause * visit( const ast::WhenClause * node ) override final {
     786                os << indent-1 << "target: ";
     787                safe_print( node->target );
     788
     789                if ( node->stmt ) {
     790                        os << indent-1 << "... with statment:" << endl;
     791                        node->stmt->accept( *this );
     792                }
     793
     794                if ( node->when_cond ) {
     795                        os << indent-1 << "... with when condition:" << endl;
     796                        node->when_cond->accept( *this );
     797                }
     798
     799                return node;
     800        }
     801
    758802        virtual const ast::Stmt * visit( const ast::WaitForStmt * node ) override final {
    759803                os << "Waitfor Statement" << endl;
     
    793837        virtual const ast::WaitForClause * visit( const ast::WaitForClause * node ) override final {
    794838                os << indent-1 << "target function: ";
    795                 safe_print( node->target_func );
     839                safe_print( node->target );
    796840
    797841                if ( !node->target_args.empty() ) {
     
    807851                }
    808852
    809                 if ( node->cond ) {
     853                if ( node->when_cond ) {
    810854                        os << indent-1 << "... with condition:" << endl;
    811                         node->cond->accept( *this );
    812                 }
    813 
     855                        node->when_cond->accept( *this );
     856                }
     857
     858                return node;
     859        }
     860
     861    virtual const ast::Stmt * visit( const ast::WaitUntilStmt * node ) override final {
     862                os << "Waituntil Statement" << endl;
     863                indent += 2;
     864                for( const auto & clause : node->clauses ) {
     865                        clause->accept( *this );
     866                }
     867        print(node);    // calls print( const ast::WaitStmt * node )
    814868                return node;
    815869        }
  • src/AST/Stmt.hpp

    r73bf7ddc rc86b08d  
    375375};
    376376
    377 // Waitfor statement: when (...) waitfor (... , ...) ... timeout(...) ... else ...
    378 class WaitForStmt final : public Stmt {
    379   public:
    380         std::vector<ptr<WaitForClause>> clauses;
    381         ptr<Expr> timeout_time;
     377// Base class of WaitFor/WaitUntil statements
     378// form: KEYWORD(...) ... timeout(...) ... else ...
     379class WaitStmt : public Stmt {
     380  public:
     381    ptr<Expr> timeout_time;
    382382        ptr<Stmt> timeout_stmt;
    383383        ptr<Expr> timeout_cond;
     
    385385        ptr<Expr> else_cond;
    386386
     387    WaitStmt( const CodeLocation & loc, const std::vector<Label> && labels = {} )
     388                : Stmt(loc, std::move(labels)) {}
     389
     390  private:
     391    WaitStmt * clone() const override = 0;
     392        MUTATE_FRIEND
     393};
     394
     395// Base class for WaitFor/WaitUntil clauses
     396// form: when( when_cond ) KEYWORD( target ) stmt
     397class WhenClause : public StmtClause {
     398  public:
     399        ptr<Expr> target;
     400        ptr<Stmt> stmt;
     401        ptr<Expr> when_cond;
     402
     403        WhenClause( const CodeLocation & loc )
     404                : StmtClause( loc ) {}
     405
     406        const WhenClause * accept( Visitor & v ) const override { return v.visit( this ); }
     407  private:
     408        WhenClause * clone() const override { return new WhenClause{ *this }; }
     409        MUTATE_FRIEND
     410};
     411
     412// Waitfor statement: when (...) waitfor (... , ...) ... timeout(...) ... else ...
     413class WaitForStmt final : public WaitStmt {
     414  public:
     415        std::vector<ptr<WaitForClause>> clauses;
     416
    387417        WaitForStmt( const CodeLocation & loc, const std::vector<Label> && labels = {} )
    388                 : Stmt(loc, std::move(labels)) {}
     418                : WaitStmt(loc, std::move(labels)) {}
    389419
    390420        const Stmt * accept( Visitor & v ) const override { return v.visit( this ); }
     
    394424};
    395425
    396 class WaitForClause final : public StmtClause {
    397   public:
    398         ptr<Expr> target_func;
     426class WaitForClause final : public WhenClause {
     427  public:
    399428        std::vector<ptr<Expr>> target_args;
    400         ptr<Stmt> stmt;
    401         ptr<Expr> cond;
    402429
    403430        WaitForClause( const CodeLocation & loc )
    404                 : StmtClause( loc ) {}
     431                : WhenClause( loc ) {}
    405432
    406433        const WaitForClause * accept( Visitor & v ) const override { return v.visit( this ); }
    407434  private:
    408435        WaitForClause * clone() const override { return new WaitForClause{ *this }; }
     436        MUTATE_FRIEND
     437};
     438
     439// waituntil statement: when (...) waituntil (...) ... timeout(...) ... else ...
     440class WaitUntilStmt final : public WaitStmt {
     441  public:
     442    // Non-ast node used during compilation to store data needed to generate predicates
     443    //    and set initial status values for clauses
     444    // Used to create a tree corresponding to the structure of the clauses in a WaitUntil
     445    struct ClauseNode {
     446        enum Op { AND, OR, LEFT_OR, LEAF, ELSE, TIMEOUT } op; // operation/type tag
     447        // LEFT_OR used with TIMEOUT/ELSE to indicate that we ignore right hand side after parsing
     448
     449        ClauseNode * left;
     450        ClauseNode * right;
     451        WhenClause * leaf;  // only set if this node is a leaf (points into vector of clauses)
     452
     453        bool ambiguousWhen; // used to paint nodes of predicate tree based on when() clauses
     454        bool whenState;     // used to track if when_cond is toggled on or off for generating init values
     455        bool childOfAnd;      // true on leaf nodes that are children of AND, false otherwise
     456
     457        ClauseNode( Op op, ClauseNode * left, ClauseNode * right )
     458            : op(op), left(left), right(right), leaf(nullptr),
     459            ambiguousWhen(false), whenState(true), childOfAnd(false) {}
     460        ClauseNode( Op op, WhenClause * leaf )
     461            : op(op), left(nullptr), right(nullptr), leaf(leaf),
     462            ambiguousWhen(false), whenState(true), childOfAnd(false) {}
     463        ClauseNode( WhenClause * leaf ) : ClauseNode(LEAF, leaf) {}
     464       
     465        ~ClauseNode() {
     466            if ( left ) delete left;
     467            if ( right ) delete right;
     468        }
     469    };
     470
     471        std::vector<ptr<WhenClause>> clauses;
     472    ClauseNode * predicateTree;
     473
     474        WaitUntilStmt( const CodeLocation & loc, const std::vector<Label> && labels = {} )
     475                : WaitStmt(loc, std::move(labels)) {}
     476
     477    ~WaitUntilStmt() { delete predicateTree; }
     478
     479        const Stmt * accept( Visitor & v ) const override { return v.visit( this ); }
     480  private:
     481        WaitUntilStmt * clone() const override { return new WaitUntilStmt{ *this }; }
    409482        MUTATE_FRIEND
    410483};
  • src/AST/Visitor.hpp

    r73bf7ddc rc86b08d  
    5050    virtual const ast::FinallyClause *    visit( const ast::FinallyClause        * ) = 0;
    5151    virtual const ast::Stmt *             visit( const ast::SuspendStmt          * ) = 0;
     52    virtual const ast::WhenClause *       visit( const ast::WhenClause           * ) = 0;
    5253    virtual const ast::Stmt *             visit( const ast::WaitForStmt          * ) = 0;
    5354    virtual const ast::WaitForClause *    visit( const ast::WaitForClause        * ) = 0;
     55    virtual const ast::Stmt *             visit( const ast::WaitUntilStmt        * ) = 0;
    5456    virtual const ast::Decl *             visit( const ast::WithStmt             * ) = 0;
    5557    virtual const ast::NullStmt *         visit( const ast::NullStmt             * ) = 0;
Note: See TracChangeset for help on using the changeset viewer.