Ignore:
Timestamp:
Nov 9, 2017, 5:42:35 PM (4 years ago)
Author:
Rob Schluntz <rschlunt@…>
Branches:
arm-eh, cleanup-dtors, jacob/cs343-translation, jenkins-sandbox, master, new-ast, new-ast-unique-expr
Children:
10dc6908
Parents:
96fc67b
Message:

Replace variable in tuple destructor with dereference, fix assertion failure from multiple destructor calls (e.g., from a statement expression)

File:
1 edited

Legend:

Unmodified
Added
Removed
  • src/InitTweak/FixInit.cc

    r96fc67b r20eacb7  
    653653                }
    654654
    655                 DeclarationWithType * getDtorFunc( ObjectDecl * objDecl, Statement * dtor, std::list< Statement * > & stmtsToAdd ) {
     655                DeclarationWithType * getDtorFunc( ObjectDecl * objDecl, Statement * input, std::list< Statement * > & stmtsToAdd ) {
     656                        // unwrap implicit statement wrapper
     657                        assert( dtor );
     658                        std::list< Expression * > matches;
     659                        collectCtorDtorCalls( dtor, matches );
     660
    656661                        if ( dynamic_cast< ExprStmt * >( dtor ) ) {
    657                                 if ( DeclarationWithType * func = getFunction( getCtorDtorCall( dtor ) ) ) {
     662                                // only one destructor call in the expression
     663                                if ( matches.size() == 1 ) {
     664                                        DeclarationWithType * func = getFunction( matches.front() );
     665                                        assertf( func, "getFunction failed to find function in %s", toString( matches.front() ).c_str() );
     666
    658667                                        // cleanup argument must be a function, not an object (including function pointer)
    659668                                        if ( FunctionDecl * dtorFunc = dynamic_cast< FunctionDecl * > ( func ) ) {
     
    677686                        ObjectDecl * thisParam = getParamThis( dtorFunc->type );
    678687                        Expression * replacement = new VariableExpr( thisParam );
    679                         if ( ArrayType * at = dynamic_cast< ArrayType * >( replacement->result->stripReferences() ) ) {
     688
     689                        Type * base = replacement->result->stripReferences();
     690                        if ( dynamic_cast< ArrayType * >( base ) || dynamic_cast< TupleType * > ( base ) ) {
    680691                                // need to cast away reference for array types, since the destructor is generated without the reference type
    681                                 replacement = new CastExpr( replacement, at->clone() );
     692                                replacement = new CastExpr( replacement, base->clone() );
    682693                        }
    683694                        VarExprReplacer::replace( dtor, { std::make_pair( objDecl, replacement ) } );
     
    804815                                                        ImplicitCtorDtorStmt * implicit = strict_dynamic_cast< ImplicitCtorDtorStmt * >( dtor );
    805816                                                        Statement * dtorStmt = implicit->callStmt;
     817
    806818                                                        // don't need to call intrinsic dtor, because it does nothing, but
    807819                                                        // non-intrinsic dtors must be called
     
    810822                                                                DeclarationWithType * dtorFunc = getDtorFunc( objDecl, dtorStmt, stmtsToAddBefore );
    811823                                                                objDecl->attributes.push_back( new Attribute( "cleanup", { new VariableExpr( dtorFunc ) } ) );
    812                                                                 // objDecl->attributes.push_back( new Attribute( "cleanup", { new NameExpr( dtorFunc->name ) } ) );
    813824                                                                ctorInit->dtor = nullptr;
    814825                                                        } // if
Note: See TracChangeset for help on using the changeset viewer.