Changeset 141b786 for src/InitTweak/FixInit.cc
- Timestamp:
- Nov 9, 2016, 2:21:05 PM (8 years ago)
- Branches:
- ADT, aaron-thesis, arm-eh, ast-experimental, cleanup-dtors, deferred_resn, demangler, enum, forall-pointer-decay, jacob/cs343-translation, jenkins-sandbox, master, new-ast, new-ast-unique-expr, new-env, no_list, persistent-indexer, pthread-emulation, qualifiedEnum, resolv-new, with_gc
- Children:
- b726084
- Parents:
- 23bb1b9
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
src/InitTweak/FixInit.cc
r23bb1b9 r141b786 65 65 static void resolveImplicitCalls( std::list< Declaration * > & translationUnit ); 66 66 67 typedef SymTab::Indexer Parent; 68 using Parent::visit; 69 67 70 virtual void visit( ImplicitCopyCtorExpr * impCpCtorExpr ); 71 virtual void visit( UniqueExpr * unqExpr ); 68 72 69 73 /// create and resolve ctor/dtor expression: fname(var, [cpArg]) … … 178 182 179 183 virtual Expression * mutate( ImplicitCopyCtorExpr * impCpCtorExpr ); 184 virtual Expression * mutate( UniqueExpr * unqExpr ); 180 185 }; 181 186 … … 421 426 void ResolveCopyCtors::visit( ImplicitCopyCtorExpr *impCpCtorExpr ) { 422 427 CP_CTOR_PRINT( std::cerr << "ResolveCopyCtors: " << impCpCtorExpr << std::endl; ) 423 Visitor::visit( impCpCtorExpr );428 Parent::visit( impCpCtorExpr ); 424 429 env = impCpCtorExpr->get_env(); // xxx - maybe we really should just have a PolyIndexer... 425 430 … … 455 460 } 456 461 462 void ResolveCopyCtors::visit( UniqueExpr * unqExpr ) { 463 static std::unordered_set< int > vars; 464 if ( vars.count( unqExpr->get_id() ) ) { 465 // xxx - hack to prevent double-handling of unique exprs, otherwise too many temporary variables and destructors are generated 466 return; 467 } 468 469 Parent::visit( unqExpr ); 470 // it should never be necessary to wrap a void-returning expression in a UniqueExpr - if this assumption changes, this needs to be rethought 471 assert( unqExpr->get_result() ); 472 if ( ImplicitCopyCtorExpr * impCpCtorExpr = dynamic_cast<ImplicitCopyCtorExpr*>( unqExpr->get_expr() ) ) { 473 // note the variable used as the result from the call 474 assert( impCpCtorExpr->get_result() && impCpCtorExpr->get_returnDecls().size() == 1 ); 475 unqExpr->set_var( new VariableExpr( impCpCtorExpr->get_returnDecls().front() ) ); 476 } else { 477 // expr isn't a call expr, so create a new temporary variable to use to hold the value of the unique expression 478 unqExpr->set_object( new ObjectDecl( toString("_unq_expr_", unqExpr->get_id()), DeclarationNode::NoStorageClass, LinkageSpec::C, nullptr, unqExpr->get_result()->clone(), nullptr ) ); 479 unqExpr->set_var( new VariableExpr( unqExpr->get_object() ) ); 480 } 481 vars.insert( unqExpr->get_id() ); 482 } 483 457 484 458 485 Expression * FixCopyCtors::mutate( ImplicitCopyCtorExpr * impCpCtorExpr ) { … … 526 553 return callExpr; 527 554 } // if 555 } 556 557 Expression * FixCopyCtors::mutate( UniqueExpr * unqExpr ) { 558 static std::unordered_map< int, UniqueExpr * > unqMap; 559 static std::unordered_set< int > addDeref; 560 // has to be done to clean up ImplicitCopyCtorExpr nodes, even when this node was skipped in previous passes 561 unqExpr = safe_dynamic_cast< UniqueExpr * >( Parent::mutate( unqExpr ) ); 562 if ( unqMap.count( unqExpr->get_id() ) ) { 563 // take data from other UniqueExpr to ensure consistency 564 delete unqExpr->get_expr(); 565 unqExpr->set_expr( unqMap[unqExpr->get_id()]->get_expr()->clone() ); 566 delete unqExpr->get_result(); 567 unqExpr->set_result( maybeClone( unqExpr->get_expr()->get_result() ) ); 568 if ( addDeref.count( unqExpr->get_id() ) ) { 569 // other UniqueExpr was dereferenced because it was an lvalue return, so this one should be too 570 return UntypedExpr::createDeref( unqExpr ); 571 } 572 return unqExpr; 573 } 574 unqMap[unqExpr->get_id()] = unqExpr; 575 if ( UntypedExpr * deref = dynamic_cast< UntypedExpr * >( unqExpr->get_expr() ) ) { 576 // unique expression is now a dereference, because the inner expression is an lvalue returning function call. 577 // Normalize the expression by dereferencing the unique expression, rather than the inner expression 578 // (i.e. move the dereference out a level) 579 assert( getFunctionName( deref ) == "*?" ); 580 unqExpr->set_expr( getCallArg( deref, 0 ) ); 581 getCallArg( deref, 0 ) = unqExpr; 582 addDeref.insert( unqExpr->get_id() ); 583 return deref; 584 } 585 return unqExpr; 528 586 } 529 587
Note: See TracChangeset
for help on using the changeset viewer.