Changes in src/Tuples/TupleAssignment.cc [82f3226:bd4f2e9]
- File:
-
- 1 edited
-
src/Tuples/TupleAssignment.cc (modified) (16 diffs)
Legend:
- Unmodified
- Added
- Removed
-
src/Tuples/TupleAssignment.cc
r82f3226 rbd4f2e9 23 23 24 24 #include "CodeGen/OperatorTable.h" 25 #include "Common/PassVisitor.h"26 25 #include "Common/UniqueName.h" // for UniqueName 27 26 #include "Common/utility.h" // for zipWith … … 62 61 struct Matcher { 63 62 public: 64 Matcher( TupleAssignSpotter &spotter, const ResolvExpr::AltList& lhs, const 63 Matcher( TupleAssignSpotter &spotter, const ResolvExpr::AltList& lhs, const 65 64 ResolvExpr::AltList& rhs ); 66 65 virtual ~Matcher() {} … … 76 75 struct MassAssignMatcher : public Matcher { 77 76 public: 78 MassAssignMatcher( TupleAssignSpotter &spotter, const ResolvExpr::AltList& lhs, 77 MassAssignMatcher( TupleAssignSpotter &spotter, const ResolvExpr::AltList& lhs, 79 78 const ResolvExpr::AltList& rhs ) : Matcher(spotter, lhs, rhs) {} 80 79 virtual void match( std::list< Expression * > &out ); … … 83 82 struct MultipleAssignMatcher : public Matcher { 84 83 public: 85 MultipleAssignMatcher( TupleAssignSpotter &spotter, const ResolvExpr::AltList& lhs, 84 MultipleAssignMatcher( TupleAssignSpotter &spotter, const ResolvExpr::AltList& lhs, 86 85 const ResolvExpr::AltList& rhs ) : Matcher(spotter, lhs, rhs) {} 87 86 virtual void match( std::list< Expression * > &out ); … … 120 119 } 121 120 122 void handleTupleAssignment( ResolvExpr::AlternativeFinder & currentFinder, UntypedExpr * expr, 121 void handleTupleAssignment( ResolvExpr::AlternativeFinder & currentFinder, UntypedExpr * expr, 123 122 std::vector<ResolvExpr::AlternativeFinder> &args ) { 124 123 TupleAssignSpotter spotter( currentFinder ); … … 129 128 : currentFinder(f) {} 130 129 131 void TupleAssignSpotter::spot( UntypedExpr * expr, 130 void TupleAssignSpotter::spot( UntypedExpr * expr, 132 131 std::vector<ResolvExpr::AlternativeFinder> &args ) { 133 132 if ( NameExpr *op = dynamic_cast< NameExpr * >(expr->get_function()) ) { … … 138 137 if ( args.size() == 0 ) return; 139 138 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 141 140 // the function, in which case AlternativeFinder will handle it normally 142 141 if ( args.size() == 1 && CodeGen::isAssignment( fname ) ) return; … … 147 146 if ( ! refToTuple(lhsAlt.expr) ) continue; 148 147 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 150 149 // 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 152 151 // AlternativeFinder flow; maybe this is desired? 153 152 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(), 156 155 lhsAlt.expr->get_result()->clone() ) ); 157 156 } … … 161 160 explode( lhsAlt, currentFinder.get_indexer(), back_inserter(lhs), true ); 162 161 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, 164 163 // if not just cast to reference here 165 164 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(), 168 167 alt.expr->get_result()->clone() ) ); 169 168 } … … 179 178 // TODO build iterative version of this instead of using combos 180 179 std::vector< ResolvExpr::AltList > rhsAlts; 181 combos( std::next(args.begin(), 1), args.end(), 180 combos( std::next(args.begin(), 1), args.end(), 182 181 std::back_inserter( rhsAlts ) ); 183 182 for ( const ResolvExpr::AltList& rhsAlt : rhsAlts ) { 184 183 // multiple assignment 185 184 ResolvExpr::AltList rhs; 186 explode( rhsAlt, currentFinder.get_indexer(), 185 explode( rhsAlt, currentFinder.get_indexer(), 187 186 std::back_inserter(rhs), true ); 188 187 matcher.reset( new MultipleAssignMatcher( *this, lhs, rhs ) ); … … 194 193 if ( isTuple(rhsAlt.expr) ) { 195 194 // multiple assignment 196 explode( rhsAlt, currentFinder.get_indexer(), 195 explode( rhsAlt, currentFinder.get_indexer(), 197 196 std::back_inserter(rhs), true ); 198 197 matcher.reset( new MultipleAssignMatcher( *this, lhs, rhs ) ); … … 223 222 ResolvExpr::AltList current; 224 223 // now resolve new assignments 225 for ( std::list< Expression * >::iterator i = new_assigns.begin(); 224 for ( std::list< Expression * >::iterator i = new_assigns.begin(); 226 225 i != new_assigns.end(); ++i ) { 227 226 PRINT( … … 230 229 ) 231 230 232 ResolvExpr::AlternativeFinder finder{ currentFinder.get_indexer(), 231 ResolvExpr::AlternativeFinder finder{ currentFinder.get_indexer(), 233 232 currentFinder.get_environ() }; 234 233 try { … … 254 253 // xxx -- was push_front 255 254 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, 257 256 ResolvExpr::sumCost( current ) + matcher->baseCost ) ); 258 257 } 259 258 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), 263 262 baseCost( ResolvExpr::sumCost( lhs ) + ResolvExpr::sumCost( rhs ) ) { 264 263 simpleCombineEnvironments( lhs.begin(), lhs.end(), compositeEnv ); … … 278 277 // xxx - maybe this should happen in alternative finder for every StmtExpr? 279 278 // 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 ); 284 284 } 285 285 }; … … 293 293 ret->set_init( ctorInit ); 294 294 ResolvExpr::resolveCtorInit( ctorInit, spotter.currentFinder.get_indexer() ); // resolve ctor/dtors for the new object 295 PassVisitor<EnvRemover>rm; // remove environments from subexpressions of StmtExprs295 EnvRemover rm; // remove environments from subexpressions of StmtExprs 296 296 ctorInit->accept( rm ); 297 297 }
Note:
See TracChangeset
for help on using the changeset viewer.