Changeset a9b1b0c


Ignore:
Timestamp:
Mar 22, 2018, 10:48:37 AM (4 years ago)
Author:
Rob Schluntz <rschlunt@…>
Branches:
aaron-thesis, arm-eh, 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, with_gc
Children:
b5563e1
Parents:
101a4d2
git-author:
Rob Schluntz <rschlunt@…> (03/21/18 12:13:18)
git-committer:
Rob Schluntz <rschlunt@…> (03/22/18 10:48:37)
Message:

Tweak the conditions in FixIntrinsicArgs? to add &/* more correctly when converting between intrinsic and non-intrinsic contexts

File:
1 edited

Legend:

Unmodified
Added
Removed
  • src/GenPoly/Lvalue.cc

    r101a4d2 ra9b1b0c  
    4545                Expression * mkDeref( Expression * arg ) {
    4646                        if ( SymTab::dereferenceOperator ) {
     47                                // note: reference depth can be arbitrarily deep here, so peel off the outermost pointer/reference, not just pointer because they are effecitvely equivalent in this pass
    4748                                VariableExpr * deref = new VariableExpr( SymTab::dereferenceOperator );
    4849                                deref->result = new PointerType( Type::Qualifiers(), deref->result );
     
    197198                                        PRINT(
    198199                                                std::cerr << "pair<0>: " << arg << std::endl;
     200                                                std::cerr << " -- " << arg->result << std::endl;
    199201                                                std::cerr << "pair<1>: " << formal << std::endl;
    200202                                        )
    201203                                        if ( dynamic_cast<ReferenceType*>( formal ) ) {
    202                                                 if ( isIntrinsicReference( arg ) ) { // do not combine conditions, because that changes the meaning of the else if
    203                                                         if ( function->get_linkage() != LinkageSpec::Intrinsic ) { // intrinsic functions that turn pointers into references
    204                                                                 // if argument is dereference or array subscript, the result isn't REALLY a reference, so it's not necessary to fix the argument
    205                                                                 PRINT(
    206                                                                         std::cerr << "===is intrinsic arg in non-intrinsic call - adding address" << std::endl;
    207                                                                 )
    208                                                                 arg = new AddressExpr( arg );
    209                                                         }
    210                                                 } else if ( function->get_linkage() == LinkageSpec::Intrinsic ) {
    211                                                         // std::cerr << "===adding deref to arg" << std::endl;
    212                                                         // if the parameter is a reference, add a dereference to the reference-typed argument.
     204                                                PRINT(
     205                                                        std::cerr << "===formal is reference" << std::endl;
     206                                                )
     207                                                // TODO: it's likely that the second condition should be ... && ! isIntrinsicReference( arg ), but this requires investigation.
     208                                                if ( function->get_linkage() != LinkageSpec::Intrinsic && isIntrinsicReference( arg ) ) {
     209                                                        // if argument is dereference or array subscript, the result isn't REALLY a reference, but non-intrinsic functions expect a reference: take address
     210                                                        PRINT(
     211                                                                std::cerr << "===is intrinsic arg in non-intrinsic call - adding address" << std::endl;
     212                                                        )
     213                                                        arg = new AddressExpr( arg );
     214                                                } else if ( function->get_linkage() == LinkageSpec::Intrinsic && arg->result->referenceDepth() != 0 ) {
     215                                                        // argument is a 'real' reference, but function expects a C lvalue: add a dereference to the reference-typed argument
     216                                                        PRINT(
     217                                                                std::cerr << "===is non-intrinsic arg in intrinsic call - adding deref to arg" << std::endl;
     218                                                        )
    213219                                                        Type * baseType = InitTweak::getPointerBase( arg->result );
    214220                                                        assertf( baseType, "parameter is reference, arg must be pointer or reference: %s", toString( arg->result ).c_str() );
     
    217223                                                        arg->set_result( ptrType );
    218224                                                        arg = mkDeref( arg );
     225                                                        assertf( arg->result->referenceDepth() == 0, "Reference types should have been eliminated from intrinsic function calls, but weren't: %s", toCString( arg->result ) );
    219226                                                }
    220227                                        }
Note: See TracChangeset for help on using the changeset viewer.