Changes in src/ResolvExpr/Resolver.cc [7b3f66b:10a7775]
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
src/ResolvExpr/Resolver.cc
r7b3f66b r10a7775 52 52 virtual void visit( BranchStmt *branchStmt ); 53 53 virtual void visit( ReturnStmt *returnStmt ); 54 virtual void visit( ImplicitCtorDtorStmt * impCtorDtorStmt ); 54 55 55 56 virtual void visit( SingleInit *singleInit ); … … 492 493 } catch ( SemanticError ) { 493 494 // no alternatives for the constructor initializer - fallback on C-style initializer 494 // xxx - not sure if this makes a ton of sense - should maybe never be able to have this situation?495 // xxx - not sure if this makes a ton of sense - should maybe never be able to have this situation? 495 496 fallbackInit( ctorInit ); 496 497 return; … … 513 514 } 514 515 } 516 517 void Resolver::visit( ImplicitCtorDtorStmt * impCtorDtorStmt ) { 518 // this code is fairly gross. If VariableExpr didn't have its own results list then this could be cleaned up a bit 519 // by remembering the ObjectDecl in the ImplicitCtorDtorStmt and changing the ObjectDecl's type temporarily, but currently 520 // VariableExprs have their own type list which is manipulated in AlternativeFinder (e.g. in inferRecursive). 521 522 // before resolving ctor/dtor, need to remove type qualifiers from the first argument (the object being constructed) 523 Expression * callExpr = InitTweak::getCtorDtorCall( impCtorDtorStmt ); 524 assert( callExpr ); 525 Expression * constructee = InitTweak::getCallArg( callExpr, 0 ); 526 Type * type = 0; 527 if ( UntypedExpr * plusExpr = dynamic_cast< UntypedExpr * >( constructee ) ) { 528 // constructee is <array>+<index> 529 // get Variable <array>, then get the base type of the VariableExpr - this is the type that needs to be fixed 530 Expression * arr = InitTweak::getCallArg( plusExpr, 0 ); 531 assert( dynamic_cast< VariableExpr * >( arr ) ); 532 assert( arr && arr->get_results().size() == 1 ); 533 type = InitTweak::getPointerBase( arr->get_results().front() ); 534 assert( type ); 535 } else { 536 // otherwise, constructing a plain object, which means the object's address is being taken. 537 // Need to get the type of the VariableExpr object, because the AddressExpr is rebuilt and uses the 538 // type of the VariableExpr to do so. 539 assert( constructee->get_results().size() == 1 ); 540 AddressExpr * addrExpr = dynamic_cast< AddressExpr * > ( constructee ); 541 assert( addrExpr ); 542 VariableExpr * varExpr = dynamic_cast< VariableExpr * >( addrExpr->get_arg() ); 543 assert( varExpr && varExpr->get_results().size() == 1 ); 544 type = varExpr->get_results().front(); 545 } 546 // remember qualifiers so they can be replaced 547 Type::Qualifiers qualifiers = type->get_qualifiers(); 548 549 // unfortunately, lvalue is considered a qualifier. For AddressExpr to resolve, its argument 550 // must have an lvalue qualified type, so remove all qualifiers except lvalue. If we ever 551 // remove lvalue as a qualifier, this can change to 552 // type->get_qualifiers() = Type::Qualifiers(); 553 type->get_qualifiers() -= Type::Qualifiers(true, true, true, false, true, true); 554 555 // finally, resolve the ctor/dtor 556 impCtorDtorStmt->get_callStmt()->accept( *this ); 557 558 // reset type qualifiers, but first need to figure out where everything is again 559 // because the expressions are often changed by the resolver. 560 callExpr = InitTweak::getCtorDtorCall( impCtorDtorStmt ); 561 assert( callExpr ); 562 constructee = InitTweak::getCallArg( callExpr, 0 ); 563 if ( ApplicationExpr * plusExpr = dynamic_cast< ApplicationExpr * >( constructee ) ) { 564 // constructee is <array>+<index> 565 // get Variable <array>, then get the base type of the VariableExpr - this is the type that needs to be fixed 566 Expression * arr = InitTweak::getCallArg( plusExpr, 0 ); 567 assert( dynamic_cast< VariableExpr * >( arr ) ); 568 assert( arr && arr->get_results().size() == 1 ); 569 type = InitTweak::getPointerBase( arr->get_results().front() ); 570 assert( type ); 571 type->get_qualifiers() = qualifiers; 572 } else { 573 // otherwise constructing a plain object 574 // replace qualifiers on AddressExpr and on inner VariableExpr 575 assert( constructee->get_results().size() == 1 ); 576 AddressExpr * addrExpr = dynamic_cast< AddressExpr * > ( constructee ); 577 assert( addrExpr ); 578 type = InitTweak::getPointerBase( addrExpr->get_results().front() ); 579 assert( type ); 580 type->get_qualifiers() = qualifiers; 581 582 VariableExpr * varExpr = dynamic_cast< VariableExpr * >( addrExpr->get_arg() ); 583 assert( varExpr && varExpr->get_results().size() == 1 ); 584 type = varExpr->get_results().front(); 585 type->get_qualifiers() = qualifiers; 586 } 587 } 515 588 } // namespace ResolvExpr 516 589
Note: See TracChangeset
for help on using the changeset viewer.