Changeset e6cee92 for src/ResolvExpr


Ignore:
Timestamp:
Jul 17, 2017, 3:25:58 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:
795d450
Parents:
7ebaa56
Message:

Fix TupleAssignment? code for references

Location:
src/ResolvExpr
Files:
3 edited

Legend:

Unmodified
Added
Removed
  • src/ResolvExpr/AlternativeFinder.cc

    r7ebaa56 re6cee92  
    815815
    816816        Expression * restructureCast( Expression * argExpr, Type * toType ) {
    817                 if ( argExpr->get_result()->size() > 1 && ! toType->isVoid() ) {
    818                         // Argument expression is a tuple and the target type is not void. Cast each member of the tuple
    819                         // to its corresponding target type, producing the tuple of those cast expressions. If there are
    820                         // more components of the tuple than components in the target type, then excess components do not
    821                         // come out in the result expression (but UniqueExprs ensure that side effects will still be done).
     817                if ( argExpr->get_result()->size() > 1 && ! toType->isVoid() && ! dynamic_cast<ReferenceType *>( toType ) ) {
     818                        // Argument expression is a tuple and the target type is not void and not a reference type.
     819                        // Cast each member of the tuple to its corresponding target type, producing the tuple of those
     820                        // cast expressions. If there are more components of the tuple than components in the target type,
     821                        // then excess components do not come out in the result expression (but UniqueExprs ensure that
     822                        // side effects will still be done).
    822823                        if ( Tuples::maybeImpure( argExpr ) && ! dynamic_cast< UniqueExpr * >( argExpr ) ) {
    823824                                // expressions which may contain side effects require a single unique instance of the expression.
  • src/ResolvExpr/CommonType.cc

    r7ebaa56 re6cee92  
    8181                CommonType visitor( type2, widenFirst, widenSecond, indexer, env, openVars );
    8282
    83                 ReferenceType * refType1 = dynamic_cast< ReferenceType * >( type1 );
    84                 ReferenceType * refType2 = dynamic_cast< ReferenceType * >( type2 );
    85                 if ( (refType1 || refType2) && (! refType1 || ! refType2) ) {
    86                         // handle the case where exactly one of the types is a reference type specially
    87                         if ( refType1 ) {
    88                                 return handleReference( refType1, type2, widenFirst, widenSecond, indexer, env, openVars );
    89                         } else if ( refType2 ) {
    90                                 return handleReference( refType2, type1, widenSecond, widenFirst, indexer, env, openVars );
    91                         }
     83                int depth1 = type1->referenceDepth();
     84                int depth2 = type2->referenceDepth();
     85                if ( depth1 > 0 || depth2 > 0 ) {
     86                        int diff = depth1-depth2;
     87                        // TODO: should it be possible for commonType to generate complicated conversions? I would argue no, only conversions that involve types of the same reference level or a difference of 1 should be allowed.
     88                        if ( diff > 1 || diff < -1 ) return nullptr;
     89
     90                        // special case where one type has a reference depth of 1 larger than the other
     91                        if ( diff > 0 ) {
     92                                return handleReference( safe_dynamic_cast<ReferenceType *>( type1 ), type2, widenFirst, widenSecond, indexer, env, openVars );
     93                        } else if ( diff < 0 ) {
     94                                return handleReference( safe_dynamic_cast<ReferenceType *>( type2 ), type1, widenSecond, widenFirst, indexer, env, openVars );
     95                        }
     96                        // otherwise, both are reference types of the same depth and this is handled by the CommonType visitor.
    9297                }
    9398
  • src/ResolvExpr/Unify.cc

    r7ebaa56 re6cee92  
    377377                                } // if
    378378                        } else {
     379                                common = type1->clone();
     380                                common->get_qualifiers() = tq1 | tq2;
    379381                                result = true;
    380382                        } // if
Note: See TracChangeset for help on using the changeset viewer.