Ignore:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • src/Tuples/TupleAssignment.cc

    r82f3226 rbd4f2e9  
    2323
    2424#include "CodeGen/OperatorTable.h"
    25 #include "Common/PassVisitor.h"
    2625#include "Common/UniqueName.h"             // for UniqueName
    2726#include "Common/utility.h"                // for zipWith
     
    6261                struct Matcher {
    6362                  public:
    64                         Matcher( TupleAssignSpotter &spotter, const ResolvExpr::AltList& lhs, const
     63                        Matcher( TupleAssignSpotter &spotter, const ResolvExpr::AltList& lhs, const 
    6564                                ResolvExpr::AltList& rhs );
    6665                        virtual ~Matcher() {}
     
    7675                struct MassAssignMatcher : public Matcher {
    7776                  public:
    78                         MassAssignMatcher( TupleAssignSpotter &spotter, const ResolvExpr::AltList& lhs,
     77                        MassAssignMatcher( TupleAssignSpotter &spotter, const ResolvExpr::AltList& lhs, 
    7978                                const ResolvExpr::AltList& rhs ) : Matcher(spotter, lhs, rhs) {}
    8079                        virtual void match( std::list< Expression * > &out );
     
    8382                struct MultipleAssignMatcher : public Matcher {
    8483                  public:
    85                         MultipleAssignMatcher( TupleAssignSpotter &spotter, const ResolvExpr::AltList& lhs,
     84                        MultipleAssignMatcher( TupleAssignSpotter &spotter, const ResolvExpr::AltList& lhs, 
    8685                                const ResolvExpr::AltList& rhs ) : Matcher(spotter, lhs, rhs) {}
    8786                        virtual void match( std::list< Expression * > &out );
     
    120119        }
    121120
    122         void handleTupleAssignment( ResolvExpr::AlternativeFinder & currentFinder, UntypedExpr * expr,
     121        void handleTupleAssignment( ResolvExpr::AlternativeFinder & currentFinder, UntypedExpr * expr, 
    123122                                std::vector<ResolvExpr::AlternativeFinder> &args ) {
    124123                TupleAssignSpotter spotter( currentFinder );
     
    129128                : currentFinder(f) {}
    130129
    131         void TupleAssignSpotter::spot( UntypedExpr * expr,
     130        void TupleAssignSpotter::spot( UntypedExpr * expr, 
    132131                        std::vector<ResolvExpr::AlternativeFinder> &args ) {
    133132                if (  NameExpr *op = dynamic_cast< NameExpr * >(expr->get_function()) ) {
     
    138137                                if ( args.size() == 0 ) return;
    139138
    140                                 // if an assignment only takes 1 argument, that's odd, but maybe someone wrote
     139                                // if an assignment only takes 1 argument, that's odd, but maybe someone wrote 
    141140                                // the function, in which case AlternativeFinder will handle it normally
    142141                                if ( args.size() == 1 && CodeGen::isAssignment( fname ) ) return;
     
    147146                                        if ( ! refToTuple(lhsAlt.expr) ) continue;
    148147
    149                                         // explode is aware of casts - ensure every LHS expression is sent into explode
     148                                        // explode is aware of casts - ensure every LHS expression is sent into explode 
    150149                                        // with a reference cast
    151                                         // xxx - this seems to change the alternatives before the normal
     150                                        // xxx - this seems to change the alternatives before the normal 
    152151                                        //  AlternativeFinder flow; maybe this is desired?
    153152                                        if ( ! dynamic_cast<CastExpr*>( lhsAlt.expr ) ) {
    154                                                 lhsAlt.expr = new CastExpr( lhsAlt.expr,
    155                                                                 new ReferenceType( Type::Qualifiers(),
     153                                                lhsAlt.expr = new CastExpr( lhsAlt.expr, 
     154                                                                new ReferenceType( Type::Qualifiers(), 
    156155                                                                        lhsAlt.expr->get_result()->clone() ) );
    157156                                        }
     
    161160                                        explode( lhsAlt, currentFinder.get_indexer(), back_inserter(lhs), true );
    162161                                        for ( ResolvExpr::Alternative& alt : lhs ) {
    163                                                 // each LHS value must be a reference - some come in with a cast expression,
     162                                                // each LHS value must be a reference - some come in with a cast expression, 
    164163                                                // if not just cast to reference here
    165164                                                if ( ! dynamic_cast<ReferenceType*>( alt.expr->get_result() ) ) {
    166                                                         alt.expr = new CastExpr( alt.expr,
    167                                                                 new ReferenceType( Type::Qualifiers(),
     165                                                        alt.expr = new CastExpr( alt.expr, 
     166                                                                new ReferenceType( Type::Qualifiers(), 
    168167                                                                        alt.expr->get_result()->clone() ) );
    169168                                                }
     
    179178                                                // TODO build iterative version of this instead of using combos
    180179                                                std::vector< ResolvExpr::AltList > rhsAlts;
    181                                                 combos( std::next(args.begin(), 1), args.end(),
     180                                                combos( std::next(args.begin(), 1), args.end(), 
    182181                                                        std::back_inserter( rhsAlts ) );
    183182                                                for ( const ResolvExpr::AltList& rhsAlt : rhsAlts ) {
    184183                                                        // multiple assignment
    185184                                                        ResolvExpr::AltList rhs;
    186                                                         explode( rhsAlt, currentFinder.get_indexer(),
     185                                                        explode( rhsAlt, currentFinder.get_indexer(), 
    187186                                                                std::back_inserter(rhs), true );
    188187                                                        matcher.reset( new MultipleAssignMatcher( *this, lhs, rhs ) );
     
    194193                                                        if ( isTuple(rhsAlt.expr) ) {
    195194                                                                // multiple assignment
    196                                                                 explode( rhsAlt, currentFinder.get_indexer(),
     195                                                                explode( rhsAlt, currentFinder.get_indexer(), 
    197196                                                                        std::back_inserter(rhs), true );
    198197                                                                matcher.reset( new MultipleAssignMatcher( *this, lhs, rhs ) );
     
    223222                ResolvExpr::AltList current;
    224223                // now resolve new assignments
    225                 for ( std::list< Expression * >::iterator i = new_assigns.begin();
     224                for ( std::list< Expression * >::iterator i = new_assigns.begin(); 
    226225                                i != new_assigns.end(); ++i ) {
    227226                        PRINT(
     
    230229                        )
    231230
    232                         ResolvExpr::AlternativeFinder finder{ currentFinder.get_indexer(),
     231                        ResolvExpr::AlternativeFinder finder{ currentFinder.get_indexer(), 
    233232                                currentFinder.get_environ() };
    234233                        try {
     
    254253                // xxx -- was push_front
    255254                currentFinder.get_alternatives().push_back( ResolvExpr::Alternative(
    256                         new TupleAssignExpr(solved_assigns, matcher->tmpDecls), matcher->compositeEnv,
     255                        new TupleAssignExpr(solved_assigns, matcher->tmpDecls), matcher->compositeEnv, 
    257256                        ResolvExpr::sumCost( current ) + matcher->baseCost ) );
    258257        }
    259258
    260         TupleAssignSpotter::Matcher::Matcher( TupleAssignSpotter &spotter,
    261                 const ResolvExpr::AltList &lhs, const ResolvExpr::AltList &rhs )
    262         : lhs(lhs), rhs(rhs), spotter(spotter),
     259        TupleAssignSpotter::Matcher::Matcher( TupleAssignSpotter &spotter, 
     260                const ResolvExpr::AltList &lhs, const ResolvExpr::AltList &rhs ) 
     261        : lhs(lhs), rhs(rhs), spotter(spotter), 
    263262          baseCost( ResolvExpr::sumCost( lhs ) + ResolvExpr::sumCost( rhs ) ) {
    264263                simpleCombineEnvironments( lhs.begin(), lhs.end(), compositeEnv );
     
    278277        // xxx - maybe this should happen in alternative finder for every StmtExpr?
    279278        // xxx - it's possible that these environments could contain some useful information. Maybe the right thing to do is aggregate the environments and pass the aggregate back to be added into the compositeEnv
    280         struct EnvRemover {
    281                 void previsit( ExprStmt * stmt ) {
    282                         delete stmt->expr->env;
    283                         stmt->expr->env = nullptr;
     279        struct EnvRemover : public Visitor {
     280                virtual void visit( ExprStmt * stmt ) {
     281                        delete stmt->get_expr()->get_env();
     282                        stmt->get_expr()->set_env( nullptr );
     283                        Visitor::visit( stmt );
    284284                }
    285285        };
     
    293293                        ret->set_init( ctorInit );
    294294                        ResolvExpr::resolveCtorInit( ctorInit, spotter.currentFinder.get_indexer() ); // resolve ctor/dtors for the new object
    295                         PassVisitor<EnvRemover> rm; // remove environments from subexpressions of StmtExprs
     295                        EnvRemover rm; // remove environments from subexpressions of StmtExprs
    296296                        ctorInit->accept( rm );
    297297                }
Note: See TracChangeset for help on using the changeset viewer.