Changeset d1685588


Ignore:
Timestamp:
Jul 18, 2017, 4:44:46 PM (7 years ago)
Author:
Rob Schluntz <rschlunt@…>
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:
9a34b5a
Parents:
870d1f0
Message:

Resolve anonymous conversions when the expression is reference-typed

File:
1 edited

Legend:

Unmodified
Added
Removed
  • src/ResolvExpr/AlternativeFinder.cc

    r870d1f0 rd1685588  
    213213        void AlternativeFinder::addAnonConversions( const Alternative & alt ) {
    214214                // adds anonymous member interpretations whenever an aggregate value type is seen.
    215                 Expression * expr = alt.expr->clone();
    216                 std::unique_ptr< Expression > manager( expr ); // RAII for expr
    217                 alt.env.apply( expr->get_result() );
    218                 if ( StructInstType *structInst = dynamic_cast< StructInstType* >( expr->get_result() ) ) {
     215                // it's okay for the aggregate expression to have reference type -- cast it to the base type to treat the aggregate as the referenced value
     216                std::unique_ptr<Expression> aggrExpr( alt.expr->clone() );
     217                alt.env.apply( aggrExpr->get_result() );
     218                Type * aggrType = aggrExpr->get_result();
     219                if ( dynamic_cast< ReferenceType * >( aggrType ) ) {
     220                        aggrType = aggrType->stripReferences();
     221                        aggrExpr.reset( new CastExpr( aggrExpr.release(), aggrType->clone() ) );
     222                }
     223
     224                if ( StructInstType *structInst = dynamic_cast< StructInstType* >( aggrExpr->get_result() ) ) {
    219225                        NameExpr nameExpr( "" );
    220                         addAggMembers( structInst, expr, alt.cost+Cost::safe, alt.env, &nameExpr );
    221                 } else if ( UnionInstType *unionInst = dynamic_cast< UnionInstType* >( expr->get_result() ) ) {
     226                        addAggMembers( structInst, aggrExpr.get(), alt.cost+Cost::safe, alt.env, &nameExpr );
     227                } else if ( UnionInstType *unionInst = dynamic_cast< UnionInstType* >( aggrExpr->get_result() ) ) {
    222228                        NameExpr nameExpr( "" );
    223                         addAggMembers( unionInst, expr, alt.cost+Cost::safe, alt.env, &nameExpr );
     229                        addAggMembers( unionInst, aggrExpr.get(), alt.cost+Cost::safe, alt.env, &nameExpr );
    224230                } // if
    225231        }
     
    412418                        )
    413419                        if ( ! unify( formalType, actualType, resultEnv, resultNeed, resultHave, openVars, indexer ) ) {
     420                                // std::cerr << "unify failed" << std::endl;
    414421                                return false;
    415422                        }
     
    895902                                aggrExpr.reset( new CastExpr( aggrExpr.release(), aggrType->clone() ) );
    896903                        }
    897 
    898904                        // find member of the given type
    899905                        if ( StructInstType *structInst = dynamic_cast< StructInstType* >( aggrExpr->get_result() ) ) {
Note: See TracChangeset for help on using the changeset viewer.