Ignore:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • src/Tuples/Explode.h

    r6b0b624 r6d267ca  
    99// Author           : Rob Schluntz
    1010// Created On       : Wed Nov 9 13:12:24 2016
    11 // Last Modified By : Peter A. Buhr
    12 // Last Modified On : Sat Jul 22 09:55:16 2017
    13 // Update Count     : 3
     11// Last Modified By : Rob Schluntz
     12// Last Modified On : Wed Nov 9 13:20:24 2016
     13// Update Count     : 2
    1414//
    1515
    16 #pragma once
     16#ifndef _EXPLODE_H_
     17#define _EXPLODE_H_
    1718
    1819#include "ResolvExpr/AlternativeFinder.h"
     
    2627
    2728namespace Tuples {
    28         /// helper function used by explode to properly distribute
    29         /// '&' across a tuple expression
    30         Expression * distributeAddr( Expression * expr );
    31 
    3229        /// helper function used by explode
    3330        template< typename OutputIterator >
    3431        void explodeUnique( Expression * expr, const ResolvExpr::Alternative & alt, const SymTab::Indexer & indexer, OutputIterator out, bool isTupleAssign ) {
    35                 if ( isTupleAssign ) {
    36                         // tuple assignment needs AddressExprs to be recursively exploded to easily get at all of the components
    37                         if ( AddressExpr * addrExpr = dynamic_cast< AddressExpr * >( expr ) ) {
    38                                 ResolvExpr::AltList alts;
    39                                 explodeUnique( addrExpr->get_arg(), alt, indexer, back_inserter( alts ), isTupleAssign );
    40                                 for ( ResolvExpr::Alternative & alt : alts ) {
    41                                         // distribute '&' over all components
    42                                         alt.expr = distributeAddr( alt.expr );
    43                                         *out++ = alt;
    44                                 }
    45                                 // in tuple assignment, still need to handle the other cases, but only if not already handled here (don't want to output too many alternatives)
    46                                 return;
    47                         }
    48                 }
    49                 Type * res = expr->get_result();
     32                Type * res = expr->get_result()->stripReferences();
    5033                if ( TupleType * tupleType = dynamic_cast< TupleType * > ( res ) ) {
    5134                        if ( TupleExpr * tupleExpr = dynamic_cast< TupleExpr * >( expr ) ) {
     
    5538                                }
    5639                        } else {
    57                                 // tuple type, but not tuple expr - recursively index into its components
     40                                // tuple type, but not tuple expr - recursively index into its components.
     41                                // if expr type is reference, convert to value type
    5842                                Expression * arg = expr->clone();
     43
     44                                if ( dynamic_cast<ReferenceType *>( arg->get_result() ) ) {
     45                                        // TODO: does this go here (inside uniqueexpr) or outside uniqueexpr? I'm guessing probably should go after...
     46                                        arg = new CastExpr( arg, tupleType->clone() );
     47                                }
    5948                                if ( Tuples::maybeImpure( arg ) && ! dynamic_cast< UniqueExpr * >( arg ) ) {
    6049                                        // expressions which may contain side effects require a single unique instance of the expression.
     
    9483} // namespace Tuples
    9584
     85#endif // _TUPLE_ASSIGNMENT_H_
     86
    9687// Local Variables: //
    9788// tab-width: 4 //
Note: See TracChangeset for help on using the changeset viewer.