| [51587aa] | 1 | //
 | 
|---|
 | 2 | // Cforall Version 1.0.0 Copyright (C) 2015 University of Waterloo
 | 
|---|
 | 3 | //
 | 
|---|
 | 4 | // The contents of this file are covered under the licence agreement in the
 | 
|---|
 | 5 | // file "LICENCE" distributed with Cforall.
 | 
|---|
 | 6 | //
 | 
|---|
 | 7 | // AssignExpand.cc -- 
 | 
|---|
 | 8 | //
 | 
|---|
| [843054c2] | 9 | // Author           : Rodolfo G. Esteves
 | 
|---|
| [51587aa] | 10 | // Created On       : Mon May 18 07:44:20 2015
 | 
|---|
 | 11 | // Last Modified By : Peter A. Buhr
 | 
|---|
| [68cd1ce] | 12 | // Last Modified On : Sat Jun 13 08:16:39 2015
 | 
|---|
 | 13 | // Update Count     : 4
 | 
|---|
| [51587aa] | 14 | //
 | 
|---|
 | 15 | 
 | 
|---|
| [51b73452] | 16 | #include <ctime>
 | 
|---|
 | 17 | #include <cstdlib>
 | 
|---|
 | 18 | 
 | 
|---|
 | 19 | #include <list>
 | 
|---|
 | 20 | #include <cassert>
 | 
|---|
 | 21 | #include <algorithm>
 | 
|---|
 | 22 | 
 | 
|---|
 | 23 | #include "AssignExpand.h"
 | 
|---|
 | 24 | 
 | 
|---|
| [68cd1ce] | 25 | #include "Parser/ParseNode.h"
 | 
|---|
 | 26 | 
 | 
|---|
| [51b73452] | 27 | #include "SynTree/Type.h"
 | 
|---|
 | 28 | #include "SynTree/Declaration.h"
 | 
|---|
| [68cd1ce] | 29 | #include "SynTree/Expression.h"
 | 
|---|
 | 30 | #include "SynTree/Statement.h"
 | 
|---|
| [51b73452] | 31 | 
 | 
|---|
 | 32 | namespace Tuples {
 | 
|---|
| [51587aa] | 33 |         AssignExpander::AssignExpander() : temporaryNamer("__tpl") {}
 | 
|---|
 | 34 | 
 | 
|---|
 | 35 |         Statement *AssignExpander::mutate( ExprStmt *exprStmt ) {
 | 
|---|
 | 36 |                 replace.clear();
 | 
|---|
 | 37 |                 extra.clear();
 | 
|---|
 | 38 |                 extra2.clear();
 | 
|---|
 | 39 |                 exprStmt->set_expr( maybeMutate( exprStmt->get_expr(), *this ) );
 | 
|---|
 | 40 | 
 | 
|---|
 | 41 |                 CompoundStmt *newSt = 0;
 | 
|---|
| [a08ba92] | 42 |                 if ( ! extra.empty() ) {
 | 
|---|
| [51587aa] | 43 |                         if ( ! newSt )
 | 
|---|
 | 44 |                                 newSt= new CompoundStmt(std::list<Label>());
 | 
|---|
 | 45 | 
 | 
|---|
 | 46 |                         newSt->get_kids().splice(newSt->get_kids().end(), extra);
 | 
|---|
 | 47 |                 } // if
 | 
|---|
 | 48 | 
 | 
|---|
 | 49 |                 if ( ! extra2.empty() ) {
 | 
|---|
 | 50 |                         if ( ! newSt )
 | 
|---|
 | 51 |                                 newSt= new CompoundStmt(std::list<Label>());
 | 
|---|
 | 52 | 
 | 
|---|
 | 53 |                         newSt->get_kids().splice(newSt->get_kids().end(), extra2);
 | 
|---|
 | 54 |                 }
 | 
|---|
 | 55 | 
 | 
|---|
 | 56 |                 if ( ! replace.empty() ) {
 | 
|---|
 | 57 |                         if ( ! newSt )
 | 
|---|
 | 58 |                                 newSt= new CompoundStmt(std::list<Label>());
 | 
|---|
 | 59 | 
 | 
|---|
 | 60 |                         for ( std::list<Expression *>::iterator r = replace.begin(); r != replace.end(); r++ )
 | 
|---|
 | 61 |                                 newSt->get_kids().push_back( new ExprStmt( std::list<Label>(), *r ));
 | 
|---|
 | 62 |                 }
 | 
|---|
 | 63 | 
 | 
|---|
 | 64 |                 if ( newSt ) return newSt; else return exprStmt;
 | 
|---|
 | 65 |         }
 | 
|---|
 | 66 | 
 | 
|---|
 | 67 |         Expression *AssignExpander::mutate( SolvedTupleExpr *tupleExpr ) {
 | 
|---|
 | 68 |                 /* 
 | 
|---|
 | 69 |                    std::list<Expression *> &exprs = tupleExpr->get_exprs();
 | 
|---|
 | 70 | 
 | 
|---|
 | 71 |                    if ( tupleExpr->get_type() == SolvedTupleExpr::MASS ) {
 | 
|---|
 | 72 |                    // extract lhs of assignments, assert that rhs is the same, create temporaries
 | 
|---|
| [a08ba92] | 73 |                    assert ( ! exprs.empty());
 | 
|---|
| [51587aa] | 74 |                    ApplicationExpr *ap1 = dynamic_cast< ApplicationExpr * >( exprs.front() );
 | 
|---|
 | 75 |                    std::list<Expression *> &args = ap1->get_args();
 | 
|---|
 | 76 |                    assert(args.size() == 2);
 | 
|---|
 | 77 |                    std::list<Type *> &temp_types = args.back()->get_results();
 | 
|---|
 | 78 |                    assert(temp_types.size() == 1);
 | 
|---|
 | 79 |                    extra.push_back(new DeclStmt( std::list<Label>(), new ObjectDecl(temporaryNamer.newName(), Declaration::Auto, LinkageSpec::C, 0, temp_types.front(), 0 ) ));
 | 
|---|
 | 80 | 
 | 
|---|
 | 81 |                    for ( std::list<Expression *>::iterator e = exprs.begin(); e != exprs.end(); e++ ) {
 | 
|---|
 | 82 |                    ApplicationExpr *ap = dynamic_cast< ApplicationExpr * >( *e );
 | 
|---|
 | 83 |                    assert( ap != 0 );
 | 
|---|
 | 84 |                    replace.push_back(ap);
 | 
|---|
 | 85 |                    }
 | 
|---|
 | 86 | 
 | 
|---|
 | 87 |                    return tupleExpr;
 | 
|---|
 | 88 |                    } else if ( tupleExpr->get_type() == SolvedTupleExpr::MULTIPLE ||
 | 
|---|
| [51b73452] | 89 |                    tupleExpr->get_type() == SolvedTupleExpr::MASS ) */ {
 | 
|---|
| [51587aa] | 90 |                         std::list<Expression *> &comps = tupleExpr->get_exprs();
 | 
|---|
 | 91 |                         for ( std::list<Expression *>::iterator i = comps.begin(); i != comps.end(); ++i ) {
 | 
|---|
 | 92 |                                 std::list<Statement *> decls;
 | 
|---|
 | 93 |                                 std::list<Statement *> temps;
 | 
|---|
 | 94 |                                 std::list<Statement *> assigns;
 | 
|---|
 | 95 |                                 if ( ApplicationExpr *app = dynamic_cast< ApplicationExpr * >(*i) ) {
 | 
|---|
 | 96 |                                         assert( app->get_args().size() == 2 );
 | 
|---|
 | 97 | 
 | 
|---|
 | 98 |                                         Expression *lhsT = app->get_args().front();
 | 
|---|
 | 99 |                                         Expression *rhsT = app->get_args().back();
 | 
|---|
 | 100 |                                         // after the round of type analysis this should be true
 | 
|---|
 | 101 |                                         assert( lhsT->get_results().size() == 1 );
 | 
|---|
 | 102 |                                         assert( rhsT->get_results().size() == 1 );
 | 
|---|
 | 103 |                                         // declare temporaries
 | 
|---|
| [68cd1ce] | 104 |                                         ObjectDecl *lhs = new ObjectDecl( temporaryNamer.newName("_lhs_"), DeclarationNode::NoStorageClass, LinkageSpec::Intrinsic, 0,
 | 
|---|
| [51587aa] | 105 |                                                                                                           lhsT->get_results().front(), 0 );
 | 
|---|
 | 106 |                                         decls.push_back( new DeclStmt( std::list< Label >(), lhs ) );
 | 
|---|
| [68cd1ce] | 107 |                                         ObjectDecl *rhs = new ObjectDecl( temporaryNamer.newName("_rhs_"), DeclarationNode::NoStorageClass, LinkageSpec::Intrinsic, 0,
 | 
|---|
| [51587aa] | 108 |                                                                                                           rhsT->get_results().front(), 0);
 | 
|---|
 | 109 |                                         decls.push_back( new DeclStmt( std::list< Label >(), rhs ));
 | 
|---|
 | 110 | 
 | 
|---|
 | 111 | 
 | 
|---|
 | 112 |                                         // create temporary for lhs, assign address
 | 
|---|
 | 113 |                                         UntypedExpr *assgnL = new UntypedExpr( new NameExpr( "?=?" ) );
 | 
|---|
 | 114 |                                         assgnL->get_args().push_back( new VariableExpr( lhs ) );
 | 
|---|
 | 115 |                                         assgnL->get_args().push_back( lhsT );
 | 
|---|
 | 116 |                                         temps.push_back( new ExprStmt(std::list<Label>(), assgnL) );
 | 
|---|
 | 117 | 
 | 
|---|
 | 118 |                                         // create temporary for rhs, assign value
 | 
|---|
 | 119 |                                         UntypedExpr *assgnR = new UntypedExpr( new NameExpr( "?=?" ) );
 | 
|---|
 | 120 |                                         assgnR->get_args().push_back( new VariableExpr( rhs ) );
 | 
|---|
 | 121 |                                         assgnR->get_args().push_back( rhsT );
 | 
|---|
 | 122 |                                         temps.push_back( new ExprStmt(std::list<Label>(), assgnR) );
 | 
|---|
 | 123 | 
 | 
|---|
 | 124 |                                         // assign rhs to lhs
 | 
|---|
 | 125 |                                         UntypedExpr *assgn = new UntypedExpr( new NameExpr( "?=?" ) );
 | 
|---|
 | 126 |                                         UntypedExpr *deref = new UntypedExpr( new NameExpr( "*?" ) );
 | 
|---|
 | 127 |                                         deref->get_args().push_back( new VariableExpr( lhs ) );
 | 
|---|
 | 128 |                                         assgn->get_args().push_back( deref );
 | 
|---|
 | 129 |                                         assgn->get_args().push_back( new VariableExpr( rhs ) );
 | 
|---|
 | 130 |                                         assigns.push_back( new ExprStmt(std::list<Label>(), assgn) );
 | 
|---|
 | 131 |                                 } else
 | 
|---|
 | 132 |                                         throw CompilerError("Solved Tuple should contain only assignment statements");
 | 
|---|
| [51b73452] | 133 |           
 | 
|---|
| [51587aa] | 134 |                                 extra.splice( extra.begin(), decls );
 | 
|---|
 | 135 |                                 extra.splice( extra.end(), temps );
 | 
|---|
 | 136 |                                 extra2.splice( extra2.end(), assigns );
 | 
|---|
 | 137 |                         } // for
 | 
|---|
 | 138 |                         return tupleExpr;
 | 
|---|
 | 139 |                 }
 | 
|---|
 | 140 |                 throw 0; // shouldn't be here
 | 
|---|
 | 141 |         }
 | 
|---|
| [51b73452] | 142 | } // namespace Tuples
 | 
|---|
 | 143 | 
 | 
|---|
| [51587aa] | 144 | // Local Variables: //
 | 
|---|
 | 145 | // tab-width: 4 //
 | 
|---|
 | 146 | // mode: c++ //
 | 
|---|
 | 147 | // compile-command: "make install" //
 | 
|---|
 | 148 | // End: //
 | 
|---|