Changeset a32b204
- Timestamp:
- May 17, 2015, 1:19:35 PM (9 years ago)
- Branches:
- ADT, aaron-thesis, arm-eh, ast-experimental, cleanup-dtors, ctor, deferred_resn, demangler, enum, forall-pointer-decay, gc_noraii, jacob/cs343-translation, jenkins-sandbox, master, memory, new-ast, new-ast-unique-expr, new-env, no_list, persistent-indexer, pthread-emulation, qualifiedEnum, resolv-new, string, with_gc
- Children:
- 0dd3a2f
- Parents:
- b87a5ed
- Location:
- translator
- Files:
-
- 1 deleted
- 110 edited
Legend:
- Unmodified
- Added
- Removed
-
translator/ArgTweak/FunctionFixer.cc
rb87a5ed ra32b204 56 56 if ( ( candidateExists = align( f->get_parameters(), untypedExpr->get_args(), Matcher() ) ) ) break; 57 57 58 if ( ! candidateExists ) throw SemanticError("Error in function call");58 if ( ! candidateExists ) throw SemanticError("Error in function call"); 59 59 } // if 60 60 } // for -
translator/CodeGen/CodeGenerator2.cc
rb87a5ed ra32b204 553 553 before << "do" ; 554 554 else { 555 before << "while (" ;555 before << "while (" ; 556 556 whileStmt->get_condition()->accept(*this ); 557 557 after += ")"; … … 565 565 566 566 if ( whileStmt->get_isDoWhile() ) { 567 before << " while (" ;567 before << " while (" ; 568 568 whileStmt->get_condition()->accept(*this ); 569 569 after += ");"; -
translator/CodeGen/CodeGenerator2.h
rb87a5ed ra32b204 97 97 inline bool doSemicolon( Declaration* decl ) { 98 98 if ( FunctionDecl* func = dynamic_cast< FunctionDecl* >( decl ) ) { 99 return ! func->get_statements();99 return ! func->get_statements(); 100 100 } 101 101 return true; -
translator/CodeGen/FixNames.cc
rb87a5ed ra32b204 32 32 fixDWT( DeclarationWithType *dwt ) 33 33 { 34 if ( dwt->get_name() != "" ) {35 if ( LinkageSpec::isDecoratable( dwt->get_linkage() ) ) {34 if ( dwt->get_name() != "" ) { 35 if ( LinkageSpec::isDecoratable( dwt->get_linkage() ) ) { 36 36 dwt->set_mangleName( SymTab::Mangler::mangle( dwt ) ); 37 37 } -
translator/CodeGen/OperatorTable.cc
rb87a5ed ra32b204 64 64 initialize() 65 65 { 66 for ( int i = 0; i < numOps; ++i ) {66 for ( int i = 0; i < numOps; ++i ) { 67 67 table[ tableValues[i].inputName ] = tableValues[i]; 68 68 } … … 75 75 { 76 76 static bool init = false; 77 if ( !init ) {77 if ( ! init ) { 78 78 initialize(); 79 79 } 80 80 std::map< std::string, OperatorInfo >::const_iterator i = table.find( funcName ); 81 if ( i == table.end() ) {81 if ( i == table.end() ) { 82 82 return false; 83 83 } else { -
translator/Common/utility.h
rb87a5ed ra32b204 22 22 maybeClone( const T *orig ) 23 23 { 24 if ( orig ) {24 if ( orig ) { 25 25 return orig->clone(); 26 26 } else { … … 33 33 maybeBuild( const U *orig ) 34 34 { 35 if ( orig ) {35 if ( orig ) { 36 36 return orig->build(); 37 37 } else { … … 44 44 printEnums( Input_iterator begin, Input_iterator end, const char * const *name_array, std::ostream &os ) 45 45 { 46 for ( Input_iterator i = begin; i != end; ++i ) {46 for ( Input_iterator i = begin; i != end; ++i ) { 47 47 os << name_array[ *i ] << ' '; 48 48 } … … 53 53 deleteAll( Container &container ) 54 54 { 55 for ( typename Container::iterator i = container.begin(); i != container.end(); ++i ) {55 for ( typename Container::iterator i = container.begin(); i != container.end(); ++i ) { 56 56 delete *i; 57 57 } … … 62 62 printAll( const Container &container, std::ostream &os, int indent = 0 ) 63 63 { 64 for ( typename Container::const_iterator i = container.begin(); i != container.end(); ++i ) {65 if ( *i ) {64 for ( typename Container::const_iterator i = container.begin(); i != container.end(); ++i ) { 65 if ( *i ) { 66 66 os << std::string(indent, ' '); 67 67 (*i)->print( os, indent + 2 ); … … 77 77 typename SrcContainer::const_iterator in = src.begin(); 78 78 std::back_insert_iterator< DestContainer > out( dest ); 79 while ( in != src.end() ) {79 while ( in != src.end() ) { 80 80 *out++ = (*in++)->clone(); 81 81 } … … 87 87 { 88 88 int count = 0; 89 for ( typename Container::const_iterator i = container.begin(); i != container.end(); ++i ) {90 if ( !(*i) ) {89 for ( typename Container::const_iterator i = container.begin(); i != container.end(); ++i ) { 90 if ( !(*i) ) { 91 91 std::cerr << count << " is null" << std::endl; 92 92 } … … 97 97 assign_strptr( std::string *str ) 98 98 { 99 if ( str == 0 ) {99 if ( str == 0 ) { 100 100 return ""; 101 101 } else { … … 115 115 std::list<T> tail( std::list<T> l ) 116 116 { 117 if (! l.empty()){117 if (! l.empty()){ 118 118 std::list<T> ret(++(l.begin()), l.end()); 119 119 return ret; … … 127 127 Ts ret; 128 128 129 switch ( l.size() ){129 switch ( l.size() ){ 130 130 case 0: 131 131 return ret; … … 193 193 { 194 194 while ( begin++ != end ) 195 if ( pred(*begin) ) *out++ = *begin;195 if ( pred(*begin) ) *out++ = *begin; 196 196 197 197 return; … … 200 200 template< class InputIterator1, class InputIterator2, class OutputIterator > 201 201 void zip( InputIterator1 b1, InputIterator1 e1, InputIterator2 b2, InputIterator2 e2, OutputIterator out ) { 202 while ( b1 != e1 && b2 != e2 )202 while ( b1 != e1 && b2 != e2 ) 203 203 *out++ = std::pair<typename InputIterator1::value_type, typename InputIterator2::value_type>(*b1++, *b2++); 204 204 } … … 206 206 template< class InputIterator1, class InputIterator2, class OutputIterator, class BinFunction > 207 207 void zipWith( InputIterator1 b1, InputIterator1 e1, InputIterator2 b2, InputIterator2 e2, OutputIterator out, BinFunction func ) { 208 while ( b1 != e1 && b2 != e2 )208 while ( b1 != e1 && b2 != e2 ) 209 209 *out++ = func(*b1++, *b2++); 210 210 } -
translator/ControlStruct/CaseRangeMutator.cc
rb87a5ed ra32b204 117 117 if ( ch_lo > ch_hi ) { char t=ch_lo; ch_lo=ch_hi; ch_hi=t; } 118 118 119 for ( char c = ch_lo; c <= ch_hi; c++ ){119 for ( char c = ch_lo; c <= ch_hi; c++ ){ 120 120 Type::Qualifiers q; 121 121 Constant cnst( new BasicType(q, BasicType::Char), … … 154 154 if ( i_lo > i_hi ) { int t=i_lo; i_lo=i_hi; i_hi=t; } 155 155 156 for ( int c = i_lo; c <= i_hi; c++ ){156 for ( int c = i_lo; c <= i_hi; c++ ){ 157 157 Type::Qualifiers q; 158 158 Constant cnst( new BasicType(q, ty_hi->get_kind()), // figure can't hurt (used to think in positives) -
translator/ControlStruct/MLEMutator.cc
rb87a5ed ra32b204 23 23 *k = (*k)->acceptMutator(*this); 24 24 25 if ( ! get_breakLabel().empty() ) {25 if ( ! get_breakLabel().empty() ) { 26 26 std::list< Statement * >::iterator next = k; next++; 27 27 if ( next == kids.end() ) { … … 98 98 99 99 Label newLabel; 100 switch ( branchStmt->get_type() ) {100 switch ( branchStmt->get_type() ) { 101 101 case BranchStmt::Break: 102 102 if ( check->get_breakExit() != "" ) -
translator/GenPoly/Box.cc
rb87a5ed ra32b204 110 110 void printAllNotBuiltin( const std::list< Declaration *>& translationUnit, std::ostream &os ) { 111 111 for ( std::list< Declaration *>::const_iterator i = translationUnit.begin(); i != translationUnit.end(); ++i ) { 112 if ( ! LinkageSpec::isBuiltin( (*i)->get_linkage() ) ) {112 if ( ! LinkageSpec::isBuiltin( (*i)->get_linkage() ) ) { 113 113 (*i)->print( os ); 114 114 os << std::endl; … … 135 135 bool isPolyRet( FunctionType *function, std::string &name, const TyVarMap &otherTyVars ) { 136 136 bool doTransform = false; 137 if ( ! function->get_returnVals().empty() ) {137 if ( ! function->get_returnVals().empty() ) { 138 138 if ( TypeInstType *typeInst = dynamic_cast< TypeInstType *>( function->get_returnVals().front()->get_type() ) ) { 139 139 … … 146 146 } // if 147 147 } // for 148 if ( ! doTransform && otherTyVars.find( typeInst->get_name() ) != otherTyVars.end() ) {148 if ( ! doTransform && otherTyVars.find( typeInst->get_name() ) != otherTyVars.end() ) { 149 149 doTransform = true; 150 150 } // if … … 304 304 ObjectDecl *newObj = makeTemporary( retType->clone() ); 305 305 Expression *paramExpr = new VariableExpr( newObj ); 306 if ( ! isPolyType( newObj->get_type(), env, scopeTyVars ) ) {306 if ( ! isPolyType( newObj->get_type(), env, scopeTyVars ) ) { 307 307 paramExpr = new AddressExpr( paramExpr ); 308 308 } // if … … 330 330 Expression *Pass1::applyAdapter( ApplicationExpr *appExpr, FunctionType *function, std::list< Expression *>::iterator &arg, const TyVarMap &tyVars ) { 331 331 Expression *ret = appExpr; 332 if ( ! function->get_returnVals().empty() && isPolyVal( function->get_returnVals().front()->get_type(), tyVars ) ) {332 if ( ! function->get_returnVals().empty() && isPolyVal( function->get_returnVals().front()->get_type(), tyVars ) ) { 333 333 ret = addRetParam( appExpr, function, function->get_returnVals().front()->get_type(), arg ); 334 334 } // if … … 343 343 344 344 void Pass1::boxParam( Type *param, Expression *&arg, const TyVarMap &exprTyVars ) { 345 assert( ! arg->get_results().empty() );346 /// if ( ! dynamic_cast< PointerType *>( arg->get_results().front() ) ) {345 assert( ! arg->get_results().empty() ); 346 /// if ( ! dynamic_cast< PointerType *>( arg->get_results().front() ) ) { 347 347 TypeInstType *typeInst = dynamic_cast< TypeInstType *>( param ); 348 348 if ( typeInst && exprTyVars.find( typeInst->get_name() ) != exprTyVars.end() ) { … … 373 373 // any function mentioning a polymorphic type 374 374 findAndReplaceFunction( newType, functions, tyVars, needsAdapter ); 375 if ( ! functions.empty() ) {375 if ( ! functions.empty() ) { 376 376 actual = new CastExpr( actual, newType ); 377 377 } else { … … 422 422 // actually make the adapter type 423 423 FunctionType *adapter = adaptee->clone(); 424 if ( ! adapter->get_returnVals().empty() && isPolyVal( adapter->get_returnVals().front()->get_type(), tyVars ) ) {424 if ( ! adapter->get_returnVals().empty() && isPolyVal( adapter->get_returnVals().front()->get_type(), tyVars ) ) { 425 425 makeRetParm( adapter ); 426 426 } // if … … 611 611 if ( varExpr->get_var()->get_linkage() == LinkageSpec::Intrinsic ) { 612 612 if ( varExpr->get_var()->get_name() == "?[?]" ) { 613 assert( ! appExpr->get_results().empty() );613 assert( ! appExpr->get_results().empty() ); 614 614 assert( appExpr->get_args().size() == 2 ); 615 615 TypeInstType *typeInst1 = isPolyPtr( appExpr->get_args().front()->get_results().front(), env, scopeTyVars ); 616 616 TypeInstType *typeInst2 = isPolyPtr( appExpr->get_args().back()->get_results().front(), env, scopeTyVars ); 617 assert( ! typeInst1 || !typeInst2 );617 assert( ! typeInst1 || ! typeInst2 ); 618 618 UntypedExpr *ret = 0; 619 619 if ( typeInst1 || typeInst2 ) { … … 644 644 } // if 645 645 } else if ( varExpr->get_var()->get_name() == "*?" ) { 646 assert( ! appExpr->get_results().empty() );647 assert( ! appExpr->get_args().empty() );646 assert( ! appExpr->get_results().empty() ); 647 assert( ! appExpr->get_args().empty() ); 648 648 if ( isPolyType( appExpr->get_results().front(), env, scopeTyVars ) ) { 649 649 Expression *ret = appExpr->get_args().front(); … … 659 659 } // if 660 660 } else if ( varExpr->get_var()->get_name() == "?++" || varExpr->get_var()->get_name() == "?--" ) { 661 assert( ! appExpr->get_results().empty() );661 assert( ! appExpr->get_results().empty() ); 662 662 assert( appExpr->get_args().size() == 1 ); 663 663 if ( TypeInstType *typeInst = isPolyPtr( appExpr->get_results().front(), env, scopeTyVars ) ) { … … 679 679 } // if 680 680 } else if ( varExpr->get_var()->get_name() == "++?" || varExpr->get_var()->get_name() == "--?" ) { 681 assert( ! appExpr->get_results().empty() );681 assert( ! appExpr->get_results().empty() ); 682 682 assert( appExpr->get_args().size() == 1 ); 683 683 if ( TypeInstType *typeInst = isPolyPtr( appExpr->get_results().front(), env, scopeTyVars ) ) { … … 685 685 } // if 686 686 } else if ( varExpr->get_var()->get_name() == "?+?" || varExpr->get_var()->get_name() == "?-?" ) { 687 assert( ! appExpr->get_results().empty() );687 assert( ! appExpr->get_results().empty() ); 688 688 assert( appExpr->get_args().size() == 2 ); 689 689 TypeInstType *typeInst1 = isPolyPtr( appExpr->get_args().front()->get_results().front(), env, scopeTyVars ); … … 711 711 } // if 712 712 } else if ( varExpr->get_var()->get_name() == "?+=?" || varExpr->get_var()->get_name() == "?-=?" ) { 713 assert( ! appExpr->get_results().empty() );713 assert( ! appExpr->get_results().empty() ); 714 714 assert( appExpr->get_args().size() == 2 ); 715 715 TypeInstType *typeInst = isPolyPtr( appExpr->get_results().front(), env, scopeTyVars ); … … 739 739 useRetval = oldUseRetval; 740 740 741 assert( ! appExpr->get_function()->get_results().empty() );741 assert( ! appExpr->get_function()->get_results().empty() ); 742 742 PointerType *pointer = dynamic_cast< PointerType *>( appExpr->get_function()->get_results().front() ); 743 743 assert( pointer ); … … 784 784 785 785 Expression *Pass1::mutate( UntypedExpr *expr ) { 786 if ( ! expr->get_results().empty() && isPolyType( expr->get_results().front(), env, scopeTyVars ) ) {786 if ( ! expr->get_results().empty() && isPolyType( expr->get_results().front(), env, scopeTyVars ) ) { 787 787 if ( NameExpr *name = dynamic_cast< NameExpr *>( expr->get_function() ) ) { 788 788 if ( name->get_name() == "*?" ) { … … 798 798 799 799 Expression *Pass1::mutate( AddressExpr *addrExpr ) { 800 assert( ! addrExpr->get_arg()->get_results().empty() );800 assert( ! addrExpr->get_arg()->get_results().empty() ); 801 801 addrExpr->set_arg( mutateExpression( addrExpr->get_arg() ) ); 802 802 if ( isPolyType( addrExpr->get_arg()->get_results().front(), env, scopeTyVars ) ) { … … 823 823 } 824 824 if ( retval && retStmt->get_expr() ) { 825 assert( ! retStmt->get_expr()->get_results().empty() );825 assert( ! retStmt->get_expr()->get_results().empty() ); 826 826 if ( retStmt->get_expr()->get_results().front()->get_isLvalue() ) { 827 827 /// retStmt->set_expr( mutateExpression( retStmt->get_expr() ) ); -
translator/GenPoly/CopyParams.cc
rb87a5ed ra32b204 46 46 } // if 47 47 } // for 48 for ( std::list< DeclarationWithType* >::iterator param = funcDecl->get_functionType()->get_parameters().begin(); param != funcDecl->get_functionType()->get_parameters().end(); ++param ) {48 for ( std::list< DeclarationWithType* >::iterator param = funcDecl->get_functionType()->get_parameters().begin(); param != funcDecl->get_functionType()->get_parameters().end(); ++param ) { 49 49 std::set< UniqueId >::const_iterator var = modVars.find( (*param)->get_uniqueId() ); 50 50 if ( var != modVars.end() ) { -
translator/GenPoly/FindFunction.cc
rb87a5ed ra32b204 52 52 FindFunction::handleForall( const std::list< TypeDecl* > &forall ) 53 53 { 54 for ( std::list< TypeDecl* >::const_iterator i = forall.begin(); i != forall.end(); ++i ) {54 for ( std::list< TypeDecl* >::const_iterator i = forall.begin(); i != forall.end(); ++i ) { 55 55 TyVarMap::iterator var = tyVars.find( (*i)->get_name() ); 56 if ( var != tyVars.end() ) {56 if ( var != tyVars.end() ) { 57 57 tyVars.erase( var ); 58 58 } … … 67 67 mutateAll( functionType->get_returnVals(), *this ); 68 68 Type *ret = functionType; 69 if ( predicate( functionType, tyVars ) ) {69 if ( predicate( functionType, tyVars ) ) { 70 70 functions.push_back( functionType ); 71 if ( replaceMode ) {71 if ( replaceMode ) { 72 72 ret = new FunctionType( Type::Qualifiers(), true ); 73 73 } -
translator/GenPoly/GenPoly.cc
rb87a5ed ra32b204 26 26 isPolyVal( Type *type, const TyVarMap &tyVars, bool considerAllTyVars ) 27 27 { 28 if ( TypeInstType *typeInst = dynamic_cast< TypeInstType* >( type ) ) {29 if ( tyVars.find( typeInst->get_name() ) != tyVars.end() ) {28 if ( TypeInstType *typeInst = dynamic_cast< TypeInstType* >( type ) ) { 29 if ( tyVars.find( typeInst->get_name() ) != tyVars.end() ) { 30 30 return true; 31 31 } … … 41 41 { 42 42 bool needsAdapter = false; 43 if ( !adaptee->get_returnVals().empty() && isPolyVal( adaptee->get_returnVals().front()->get_type(), tyVars, considerAllTyVars ) ) {43 if ( ! adaptee->get_returnVals().empty() && isPolyVal( adaptee->get_returnVals().front()->get_type(), tyVars, considerAllTyVars ) ) { 44 44 needsAdapter = true; 45 45 } 46 for ( std::list< DeclarationWithType* >::const_iterator innerArg = adaptee->get_parameters().begin(); !needsAdapter && innerArg != adaptee->get_parameters().end(); ++innerArg ) {47 if ( isPolyVal( (*innerArg)->get_type(), tyVars, considerAllTyVars ) ) {46 for ( std::list< DeclarationWithType* >::const_iterator innerArg = adaptee->get_parameters().begin(); ! needsAdapter && innerArg != adaptee->get_parameters().end(); ++innerArg ) { 47 if ( isPolyVal( (*innerArg)->get_type(), tyVars, considerAllTyVars ) ) { 48 48 needsAdapter = true; 49 49 } … … 56 56 printTyVarMap( std::ostream &os, const TyVarMap &tyVarMap ) 57 57 { 58 for ( TyVarMap::const_iterator i = tyVarMap.begin(); i != tyVarMap.end(); ++i ) {58 for ( TyVarMap::const_iterator i = tyVarMap.begin(); i != tyVarMap.end(); ++i ) { 59 59 os << i->first << " (" << i->second << ") "; 60 60 } -
translator/GenPoly/Lvalue.cc
rb87a5ed ra32b204 67 67 isLvalueRet( FunctionType *function ) 68 68 { 69 if ( !function->get_returnVals().empty() ) {69 if ( ! function->get_returnVals().empty() ) { 70 70 return function->get_returnVals().front()->get_type()->get_isLvalue(); 71 71 } else { … … 77 77 isIntrinsicApp( ApplicationExpr *appExpr ) 78 78 { 79 if ( VariableExpr *varExpr = dynamic_cast< VariableExpr* >( appExpr->get_function() ) ) {79 if ( VariableExpr *varExpr = dynamic_cast< VariableExpr* >( appExpr->get_function() ) ) { 80 80 return varExpr->get_var()->get_linkage() == LinkageSpec::Intrinsic; 81 81 } else { … … 91 91 Pass1::mutate( FunctionDecl *funcDecl ) 92 92 { 93 if ( funcDecl->get_statements() ) {93 if ( funcDecl->get_statements() ) { 94 94 DeclarationWithType* oldRetval = retval; 95 95 retval = 0; 96 if ( !LinkageSpec::isBuiltin( funcDecl->get_linkage() ) && isLvalueRet( funcDecl->get_functionType() ) ) {96 if ( ! LinkageSpec::isBuiltin( funcDecl->get_linkage() ) && isLvalueRet( funcDecl->get_functionType() ) ) { 97 97 retval = funcDecl->get_functionType()->get_returnVals().front(); 98 98 } … … 110 110 mutateAll( appExpr->get_args(), *this ); 111 111 112 assert( ! appExpr->get_function()->get_results().empty() );112 assert( ! appExpr->get_function()->get_results().empty() ); 113 113 114 114 PointerType *pointer = dynamic_cast< PointerType* >( appExpr->get_function()->get_results().front() ); … … 118 118 119 119 std::string typeName; 120 if ( isLvalueRet( function ) && !isIntrinsicApp( appExpr ) ) {120 if ( isLvalueRet( function ) && ! isIntrinsicApp( appExpr ) ) { 121 121 UntypedExpr *deref = new UntypedExpr( new NameExpr( "*?" ) ); 122 122 deref->get_results().push_back( appExpr->get_results().front() ); … … 132 132 Pass1::mutate(ReturnStmt *retStmt) 133 133 { 134 if ( retval && retStmt->get_expr() ) {135 assert( ! retStmt->get_expr()->get_results().empty() );136 while ( CastExpr *castExpr = dynamic_cast< CastExpr* >( retStmt->get_expr() ) ) {134 if ( retval && retStmt->get_expr() ) { 135 assert( ! retStmt->get_expr()->get_results().empty() ); 136 while ( CastExpr *castExpr = dynamic_cast< CastExpr* >( retStmt->get_expr() ) ) { 137 137 retStmt->set_expr( castExpr->get_arg() ); 138 138 retStmt->get_expr()->set_env( castExpr->get_env() ); … … 141 141 delete castExpr; 142 142 } 143 if ( retStmt->get_expr()->get_results().front()->get_isLvalue() ) {143 if ( retStmt->get_expr()->get_results().front()->get_isLvalue() ) { 144 144 retStmt->set_expr( new AddressExpr( retStmt->get_expr()->acceptMutator( *this ) ) ); 145 145 } else { … … 154 154 { 155 155 std::string typeName; 156 if ( isLvalueRet( funType ) ) {156 if ( isLvalueRet( funType ) ) { 157 157 DeclarationWithType *retParm = funType->get_returnVals().front(); 158 158 -
translator/GenPoly/PolyMutator.cc
rb87a5ed ra32b204 28 28 PolyMutator::mutateStatementList( std::list< Statement* > &statements ) 29 29 { 30 for ( std::list< Statement* >::iterator i = statements.begin(); i != statements.end(); ++i ) {31 if ( !stmtsToAddAfter.empty() ) {30 for ( std::list< Statement* >::iterator i = statements.begin(); i != statements.end(); ++i ) { 31 if ( ! stmtsToAddAfter.empty() ) { 32 32 statements.splice( i, stmtsToAddAfter ); 33 33 } 34 34 *i = (*i)->acceptMutator( *this ); 35 if ( !stmtsToAdd.empty() ) {35 if ( ! stmtsToAdd.empty() ) { 36 36 statements.splice( i, stmtsToAdd ); 37 37 } 38 38 } 39 if ( !stmtsToAddAfter.empty() ) {39 if ( ! stmtsToAddAfter.empty() ) { 40 40 statements.splice( statements.end(), stmtsToAddAfter ); 41 41 } … … 46 46 { 47 47 Statement *newStmt = maybeMutate( stmt, *this ); 48 if ( !stmtsToAdd.empty() || !stmtsToAddAfter.empty() ) {48 if ( ! stmtsToAdd.empty() || ! stmtsToAddAfter.empty() ) { 49 49 CompoundStmt *compound = new CompoundStmt( noLabels ); 50 50 compound->get_kids().splice( compound->get_kids().end(), stmtsToAdd ); … … 61 61 PolyMutator::mutateExpression( Expression *expr ) 62 62 { 63 if ( expr ) {64 if ( expr->get_env() ) {63 if ( expr ) { 64 if ( expr->get_env() ) { 65 65 env = expr->get_env(); 66 66 } … … 167 167 PolyMutator::mutate(UntypedExpr *untypedExpr) 168 168 { 169 for ( std::list< Expression* >::iterator i = untypedExpr->get_args().begin(); i != untypedExpr->get_args().end(); ++i ) {169 for ( std::list< Expression* >::iterator i = untypedExpr->get_args().begin(); i != untypedExpr->get_args().end(); ++i ) { 170 170 *i = mutateExpression( *i ); 171 171 } … … 177 177 PolyMutator::makeTyVarMap( Type *type, TyVarMap &tyVarMap ) 178 178 { 179 for ( std::list< TypeDecl* >::const_iterator tyVar = type->get_forall().begin(); tyVar != type->get_forall().end(); ++tyVar ) {179 for ( std::list< TypeDecl* >::const_iterator tyVar = type->get_forall().begin(); tyVar != type->get_forall().end(); ++tyVar ) { 180 180 assert( *tyVar ); 181 181 tyVarMap[ (*tyVar)->get_name() ] = (*tyVar)->get_kind(); 182 182 } 183 if ( PointerType *pointer = dynamic_cast< PointerType* >( type ) ) {183 if ( PointerType *pointer = dynamic_cast< PointerType* >( type ) ) { 184 184 makeTyVarMap( pointer->get_base(), tyVarMap ); 185 185 } -
translator/GenPoly/ScrubTyVars.cc
rb87a5ed ra32b204 11 11 TyVarMap::const_iterator tyVar = tyVars.find( typeInst->get_name() ); 12 12 if ( doAll || tyVar != tyVars.end() ) { 13 switch ( tyVar->second ) {13 switch ( tyVar->second ) { 14 14 case TypeDecl::Any: 15 15 case TypeDecl::Dtype: -
translator/GenPoly/Specialize.cc
rb87a5ed ra32b204 61 61 needsSpecialization( Type *formalType, Type *actualType, TypeSubstitution *env ) 62 62 { 63 if ( env ) {63 if ( env ) { 64 64 using namespace ResolvExpr; 65 65 OpenVarSet openVars, closedVars; … … 67 67 findOpenVars( formalType, openVars, closedVars, need, have, false ); 68 68 findOpenVars( actualType, openVars, closedVars, need, have, true ); 69 for ( OpenVarSet::const_iterator openVar = openVars.begin(); openVar != openVars.end(); ++openVar ) {69 for ( OpenVarSet::const_iterator openVar = openVars.begin(); openVar != openVars.end(); ++openVar ) { 70 70 Type *boundType = env->lookup( openVar->first ); 71 if ( !boundType ) continue;72 if ( TypeInstType *typeInst = dynamic_cast< TypeInstType* >( boundType ) ) {73 if ( closedVars.find( typeInst->get_name() ) == closedVars.end() ) {71 if ( ! boundType ) continue; 72 if ( TypeInstType *typeInst = dynamic_cast< TypeInstType* >( boundType ) ) { 73 if ( closedVars.find( typeInst->get_name() ) == closedVars.end() ) { 74 74 return true; 75 75 } … … 87 87 Specialize::doSpecialization( Type *formalType, Expression *actual, InferredParams *inferParams ) 88 88 { 89 if ( needsSpecialization( formalType, actual->get_results().front(), env ) ) {89 if ( needsSpecialization( formalType, actual->get_results().front(), env ) ) { 90 90 PointerType *ptrType; 91 91 FunctionType *funType; 92 if ( ( ptrType = dynamic_cast< PointerType* >( formalType ) ) && ( funType = dynamic_cast< FunctionType* >( ptrType->get_base() ) ) ) {92 if ( ( ptrType = dynamic_cast< PointerType* >( formalType ) ) && ( funType = dynamic_cast< FunctionType* >( ptrType->get_base() ) ) ) { 93 93 FunctionType *newType = funType->clone(); 94 if ( env ) {94 if ( env ) { 95 95 TypeSubstitution newEnv( *env ); 96 96 // it is important to replace only occurrences of type variables that occur free in the … … 103 103 UniqueName paramNamer( paramPrefix ); 104 104 ApplicationExpr *appExpr = new ApplicationExpr( actual ); 105 for ( std::list< DeclarationWithType* >::iterator param = thunkFunc->get_functionType()->get_parameters().begin(); param != thunkFunc->get_functionType()->get_parameters().end(); ++param ) {105 for ( std::list< DeclarationWithType* >::iterator param = thunkFunc->get_functionType()->get_parameters().begin(); param != thunkFunc->get_functionType()->get_parameters().end(); ++param ) { 106 106 (*param)->set_name( paramNamer.newName() ); 107 107 appExpr->get_args().push_back( new VariableExpr( *param ) ); 108 108 } 109 109 appExpr->set_env( maybeClone( env ) ); 110 if ( inferParams ) {110 if ( inferParams ) { 111 111 appExpr->get_inferParams() = *inferParams; 112 112 } … … 123 123 124 124 Statement *appStmt; 125 if ( funType->get_returnVals().empty() ) {125 if ( funType->get_returnVals().empty() ) { 126 126 appStmt = new ExprStmt( noLabels, appExpr ); 127 127 } else { … … 143 143 { 144 144 // create thunks for the explicit parameters 145 assert( ! appExpr->get_function()->get_results().empty() );145 assert( ! appExpr->get_function()->get_results().empty() ); 146 146 PointerType *pointer = dynamic_cast< PointerType* >( appExpr->get_function()->get_results().front() ); 147 147 assert( pointer ); … … 149 149 std::list< DeclarationWithType* >::iterator formal; 150 150 std::list< Expression* >::iterator actual; 151 for ( formal = function->get_parameters().begin(), actual = appExpr->get_args().begin(); formal != function->get_parameters().end() && actual != appExpr->get_args().end(); ++formal, ++actual ) {151 for ( formal = function->get_parameters().begin(), actual = appExpr->get_args().begin(); formal != function->get_parameters().end() && actual != appExpr->get_args().end(); ++formal, ++actual ) { 152 152 *actual = doSpecialization( (*formal)->get_type(), *actual, &appExpr->get_inferParams() ); 153 153 } … … 161 161 162 162 // create thunks for the inferred parameters 163 for ( InferredParams::iterator inferParam = appExpr->get_inferParams().begin(); inferParam != appExpr->get_inferParams().end(); ++inferParam ) {163 for ( InferredParams::iterator inferParam = appExpr->get_inferParams().begin(); inferParam != appExpr->get_inferParams().end(); ++inferParam ) { 164 164 inferParam->second.expr = doSpecialization( inferParam->second.formalType, inferParam->second.expr, &appExpr->get_inferParams() ); 165 165 } -
translator/InitTweak/Association.h
rb87a5ed ra32b204 70 70 71 71 virtual long int add_single( long int idx, Expression *newExpr) { 72 if ( expr == 0 ) //|| *expr == *newExpr )72 if ( expr == 0 ) //|| *expr == *newExpr ) 73 73 expr = newExpr; 74 74 return 0; … … 76 76 77 77 virtual long int add_single( std::string str, Expression *newExpr) { 78 if ( expr == 0 ) //|| *expr == *newExpr )78 if ( expr == 0 ) //|| *expr == *newExpr ) 79 79 expr = newExpr; 80 80 return 0; … … 114 114 long int ret; 115 115 116 if ( idx >= (long int)ordering.size() ) throw AssocException("extra (spurious) members");116 if ( idx >= (long int)ordering.size() ) throw AssocException("extra (spurious) members"); 117 117 118 118 if ( ordering[ idx ] == "") … … 127 127 128 128 virtual long int add_single( std::string idx, Expression *expr) { 129 if ( idx == "" )129 if ( idx == "" ) 130 130 std::cerr << "Checkpoint 1" << std::endl; 131 131 else { … … 143 143 if ( table.find( str ) != table.end() ) return; 144 144 ordering.push_back( str ); 145 if ( str != "" ) {145 if ( str != "" ) { 146 146 std::pair<long int, Association *> p( ordering.size() - 1, 0 ); 147 147 table.insert( std::pair< std::string, std::pair<long int, Association *> >(str, p) ); … … 151 151 152 152 virtual void set_member( std::string str, Association *assoc ) { 153 if ( str == "" )153 if ( str == "" ) 154 154 anonym.push_back( assoc ); 155 155 else if ( table.find( str ) == table.end() ) … … 162 162 163 163 virtual Association *operator[]( int idx ) { 164 if ( ordering[idx] == "" ) {164 if ( ordering[idx] == "" ) { 165 165 std::cerr << "Error, anonymous members not implemented yet" << std::endl; 166 166 throw 0; … … 187 187 virtual void display( std::ostream &os ) { 188 188 os << "Point association: " << std::endl; 189 for ( map_type::iterator i = table.begin(); i != table.end(); i++ ) {189 for ( map_type::iterator i = table.begin(); i != table.end(); i++ ) { 190 190 os << "Member [" << i->first << ", index = " << i->second.first << "]"; 191 191 if ( i->second.second != 0 ) … … 244 244 diet::diet_tree<int> tree; 245 245 /* 246 for ( diet_tree<int>::iterator i = tree.begin(); i != tree.end(); i++ )246 for ( diet_tree<int>::iterator i = tree.begin(); i != tree.end(); i++ ) 247 247 std::cout << "--(" << (*i).first << ", " << (*i).second << ")--" << std::endl; 248 248 diet_tree<int> tree; -
translator/InitTweak/BasicInit.cc
rb87a5ed ra32b204 50 50 ObjectDecl *odecl = 0; 51 51 52 if ( ( odecl = dynamic_cast<ObjectDecl *>(declStmt->get_decl()) ) != 0 ){52 if ( ( odecl = dynamic_cast<ObjectDecl *>(declStmt->get_decl()) ) != 0 ){ 53 53 54 54 Initializer *init = odecl->get_init(); … … 133 133 134 134 ReferenceToType *reftype; 135 if ( (reftype = dynamic_cast< StructInstType * >( objdecl->get_type() )) != 0 ){135 if ( (reftype = dynamic_cast< StructInstType * >( objdecl->get_type() )) != 0 ){ 136 136 StructDecl *strDecl = index->lookupStruct( reftype->get_name() ); 137 137 if ( strDecl != 0 ) { … … 169 169 170 170 if ( li != 0 ) { 171 for ( std::list<Initializer *>::iterator i = li->begin_initializers();171 for ( std::list<Initializer *>::iterator i = li->begin_initializers(); 172 172 i != li->end_initializers(); 173 173 i++) { … … 181 181 std::back_inserter( des ), cast_ptr<Expression, NameExpr > ); 182 182 183 for ( std::list<NameExpr *>::iterator j = des.begin(); j != des.end(); j++ ) {183 for ( std::list<NameExpr *>::iterator j = des.begin(); j != des.end(); j++ ) { 184 184 // check for existence of the element 185 185 … … 230 230 if ( col->isComposite() ) { 231 231 VariousNames *vc = dynamic_cast< VariousNames * >( col ); 232 for ( VariousNames::key_iterator it = vc->keys_begin(); it != vc->keys_end(); it++ ) {232 for ( VariousNames::key_iterator it = vc->keys_begin(); it != vc->keys_end(); it++ ) { 233 233 prefix.push_back( *it ); 234 234 if ( (*assoc)[ *it ] != 0 ) -
translator/InitTweak/BasicInit.h
rb87a5ed ra32b204 102 102 std::list<Expression *> temp; 103 103 104 if ( ( sinit=dynamic_cast< SingleInit * >(_init) ) != 0 ) {104 if ( ( sinit=dynamic_cast< SingleInit * >(_init) ) != 0 ) { 105 105 kind = SINGLE; 106 106 temp = sinit->get_designators(); … … 179 179 blown_struct.push_front( me->get_member() ); 180 180 prfx = me->get_aggregate(); 181 } while ( prfx != 0 );181 } while ( prfx != 0 ); 182 182 183 183 NameExpr *ne; -
translator/InitTweak/DeclarationHoister.cc
rb87a5ed ra32b204 24 24 25 25 while ( result != kids.end() ) { 26 result = std::find_if (result, kids.end(), cast_ptr< Statement, DeclStmt > );26 result = std::find_if (result, kids.end(), cast_ptr< Statement, DeclStmt > ); 27 27 28 28 if ( result != kids.end() ) { … … 32 32 } 33 33 34 for ( std::list< stmt_it >::reverse_iterator i = decls.rbegin(); i!= decls.rend(); i++ ){34 for ( std::list< stmt_it >::reverse_iterator i = decls.rbegin(); i!= decls.rend(); i++ ){ 35 35 kids.push_front( **i ); 36 36 kids.erase( *i ); -
translator/InitTweak/InitExpander.cc
rb87a5ed ra32b204 18 18 index.visit( objectDecl ); 19 19 20 if ( objectDecl->get_init() == 0 ) return objectDecl;20 if ( objectDecl->get_init() == 0 ) return objectDecl; 21 21 22 22 InitModelBuilder builder( objectDecl ); -
translator/InitTweak/InitModel.cc
rb87a5ed ra32b204 16 16 17 17 /* this to be replaced by dynamic dispatch */ 18 if ( dynamic_cast< BasicType * >(objectType) != 0 ) {19 if ( building == 0 ) building = new SingleName;20 } else if ( ReferenceToType *rt = dynamic_cast< ReferenceToType * >(objectType) ) {18 if ( dynamic_cast< BasicType * >(objectType) != 0 ) { 19 if ( building == 0 ) building = new SingleName; 20 } else if ( ReferenceToType *rt = dynamic_cast< ReferenceToType * >(objectType) ) { 21 21 rt->accept( *this ); 22 } else if ( ArrayType *at = dynamic_cast< ArrayType * >(objectType) ) {22 } else if ( ArrayType *at = dynamic_cast< ArrayType * >(objectType) ) { 23 23 at->accept( *this ); 24 24 } else // if (tuples) … … 28 28 } 29 29 30 InitModelBuilder::~InitModelBuilder() { if ( !taken ) { delete building; building = 0; } }30 InitModelBuilder::~InitModelBuilder() { if ( ! taken ) { delete building; building = 0; } } 31 31 32 32 void InitModelBuilder::init() { … … 37 37 // Visitor interface 38 38 void InitModelBuilder::visit( ArrayType *at ) { 39 if ( building == 0 ) building = new RangeAssociation(interpretDimension( at->get_dimension() ));39 if ( building == 0 ) building = new RangeAssociation(interpretDimension( at->get_dimension() )); 40 40 decl = 0; 41 41 return; … … 43 43 44 44 void InitModelBuilder::visit( StructInstType *st ) { 45 if ( building == 0 ) building = new PointAssociation;45 if ( building == 0 ) building = new PointAssociation; 46 46 decl = st->get_baseStruct(); 47 47 return; … … 59 59 std::list< Declaration * > mem = aggregateDecl->get_members(); 60 60 61 for ( std::list<Declaration *>::iterator i = mem.begin(); i != mem.end(); i++ ) {61 for ( std::list<Declaration *>::iterator i = mem.begin(); i != mem.end(); i++ ) { 62 62 pa->add_member( (*i)->get_name() ); 63 63 InitModelBuilder rec(*i); … … 76 76 assert (c != 0); 77 77 if ( BasicType *bt = dynamic_cast<BasicType *>( c->get_type() ) ) { 78 if ( bt->isInteger() ) {78 if ( bt->isInteger() ) { 79 79 // need more intelligence here, not necessarily base 10 80 80 value = std::strtol( c->get_value().c_str(), NULL, 10 ); … … 102 102 std::list< Expression *> &des = singleInit->get_designators(); 103 103 104 if ( topLevel ) {104 if ( topLevel ) { 105 105 assert ( des.empty() ); 106 106 assert ( dynamic_cast< SingleName * >(model) != 0 ); … … 113 113 } 114 114 115 if ( des.empty() ) {115 if ( des.empty() ) { 116 116 assert( model != 0 ); 117 117 try { … … 160 160 for ( std::list<Expression *>::iterator i = des2.begin(); i != des2.end(); i++ ) { 161 161 Association * newModel = 0; 162 if ( NameExpr *n = dynamic_cast< NameExpr * >( *i ) )162 if ( NameExpr *n = dynamic_cast< NameExpr * >( *i ) ) 163 163 try { 164 164 newModel = (*model)[ n->get_name() ]; … … 166 166 std::cerr << "Didn't find member: " << e.get_what() << std::endl; 167 167 } 168 else // if ( RangeExpr *r = dynamic_cast< RangeExpr * >( *i ) )168 else // if ( RangeExpr *r = dynamic_cast< RangeExpr * >( *i ) ) 169 169 std::cerr << "Invalid designator specification" << std::endl; 170 170 … … 193 193 194 194 std::list< Initializer * > contents; 195 for ( int i = 0; i < pa->size(); i++ )195 for ( int i = 0; i < pa->size(); i++ ) 196 196 if ( (*pa)[i] != 0 ) { 197 197 InitUnspooler rec; -
translator/InitTweak/InitModel.h
rb87a5ed ra32b204 92 92 public: 93 93 InitUnspooler() : init(0), taken( false ) {} 94 virtual ~InitUnspooler() { if (! taken && (init != 0)) { delete init; init = 0; } }94 virtual ~InitUnspooler() { if (! taken && (init != 0)) { delete init; init = 0; } } 95 95 Initializer *get_initializer() { return init; } 96 96 Initializer *grab_initializer() { taken = true; return init; } -
translator/InitTweak/RemoveInit.cc
rb87a5ed ra32b204 19 19 20 20 void RemoveInit::mutateStatementList( std::list< Statement* > &statements ) { 21 for ( std::list< Statement* >::iterator i = statements.begin(); i != statements.end(); ++i ) {22 if ( !stmtsToAddAfter.empty() ) {21 for ( std::list< Statement* >::iterator i = statements.begin(); i != statements.end(); ++i ) { 22 if ( ! stmtsToAddAfter.empty() ) { 23 23 statements.splice( i, stmtsToAddAfter ); 24 24 } 25 25 *i = (*i)->acceptMutator( *this ); 26 26 } 27 if ( !stmtsToAddAfter.empty() ) {27 if ( ! stmtsToAddAfter.empty() ) { 28 28 statements.splice( statements.end(), stmtsToAddAfter ); 29 29 } -
translator/InitTweak/diet_map.h
rb87a5ed ra32b204 34 34 diet_tree() : root(0), left(0), right(0) {} 35 35 ~diet_tree() { 36 if ( root != 0 ) { delete root; root = 0; }37 if ( left != 0 ) { delete left; left = 0; }38 if ( right != 0 ) { delete right; right = 0; }36 if ( root != 0 ) { delete root; root = 0; } 37 if ( left != 0 ) { delete left; left = 0; } 38 if ( right != 0 ) { delete right; right = 0; } 39 39 } 40 40 … … 45 45 else { 46 46 value_type lo = root->get_lo(), hi = root->get_hi(); 47 if ( _lo < lo ) {48 if ( _hi > hi ) {47 if ( _lo < lo ) { 48 if ( _hi > hi ) { 49 49 /* can either minimize the work or minimize the number of nodes. 50 50 Let's minimize the work. */ … … 54 54 right->insert( _hi, hi ); 55 55 return; 56 } else if ( _hi < lo ) {56 } else if ( _hi < lo ) { 57 57 if ( left == 0 ) left = new diet_tree<T>(); 58 58 left->insert( _lo, _hi ); 59 } else if ( _hi <= hi ) {59 } else if ( _hi <= hi ) { 60 60 if ( left == 0 ) left = new diet_tree<T>(); 61 61 left->insert( _lo, _hi ); … … 65 65 root->set_range(_lo,_hi); 66 66 } else if ( _hi > hi) { 67 if ( _lo > hi ) {67 if ( _lo > hi ) { 68 68 if ( right == 0 ) right = new diet_tree<T>(); 69 69 right->insert( _lo, _hi ); 70 } else if ( _lo < hi ) {70 } else if ( _lo < hi ) { 71 71 root->set_range(lo, _lo); 72 72 if ( right == 0 ) right = new diet_tree<T>(); … … 152 152 assert(current != 0); 153 153 if ( current->right == 0 ) 154 if ( ! st.empty() )154 if ( ! st.empty() ) 155 155 { current = st.top(); st.pop(); } 156 156 else … … 173 173 assert(current != 0); 174 174 diet_tree<T> *next = 0; 175 while ( current->left != 0 ) {175 while ( current->left != 0 ) { 176 176 next = current->left; st.push( current ); current = next; 177 177 } -
translator/MakeLibCfa.cc
rb87a5ed ra32b204 48 48 bool lookResult = CodeGen::operatorLookup( funcDecl->get_name(), opInfo ); 49 49 assert( lookResult ); 50 assert( ! funcDecl->get_statements() );50 assert( ! funcDecl->get_statements() ); 51 51 UntypedExpr *newExpr = new UntypedExpr( new NameExpr( funcDecl->get_name() ) ); 52 52 UniqueName paramNamer( "_p" ); … … 59 59 } // if 60 60 61 switch ( opInfo.type ) {61 switch ( opInfo.type ) { 62 62 case CodeGen::OT_INDEX: 63 63 case CodeGen::OT_CALL: … … 97 97 98 98 ObjectDecl *objDecl = origObjDecl->clone(); 99 assert( ! objDecl->get_init() );99 assert( ! objDecl->get_init() ); 100 100 std::list< Expression* > noDesignators; 101 101 objDecl->set_init( new SingleInit( new NameExpr( objDecl->get_name() ), noDesignators ) ); -
translator/Parser/DeclarationNode.cc
rb87a5ed ra32b204 531 531 TypeData *prevBase = type; 532 532 TypeData *curBase = type->base; 533 while ( curBase != 0 ) {533 while ( curBase != 0 ) { 534 534 prevBase = curBase; 535 535 curBase = curBase->base; … … 591 591 assert( a ); 592 592 TypeData *cur = a; 593 while ( cur->base ) {593 while ( cur->base ) { 594 594 cur = cur->base; 595 595 } … … 660 660 DeclarationNode *newnode = new DeclarationNode; 661 661 TypeData *srcType = type; 662 while ( srcType->base ) {662 while ( srcType->base ) { 663 663 srcType = srcType->base; 664 664 } … … 686 686 if ( type ) { 687 687 TypeData *srcType = type; 688 while ( srcType->base ) {688 while ( srcType->base ) { 689 689 srcType = srcType->base; 690 690 } … … 763 763 std::back_insert_iterator< std::list< Declaration* > > out( outputList ); 764 764 const DeclarationNode *cur = firstNode; 765 while ( cur ) {765 while ( cur ) { 766 766 try { 767 767 if ( DeclarationNode *extr = cur->extractAggregate() ) { … … 790 790 std::back_insert_iterator< std::list< DeclarationWithType* > > out( outputList ); 791 791 const DeclarationNode *cur = firstNode; 792 while ( cur ) {792 while ( cur ) { 793 793 try { 794 794 /// if ( DeclarationNode *extr = cur->extractAggregate() ) { … … 827 827 std::back_insert_iterator< std::list< Type* > > out( outputList ); 828 828 const DeclarationNode *cur = firstNode; 829 while ( cur ) {829 while ( cur ) { 830 830 try { 831 831 *out++ = cur->buildType(); -
translator/Parser/ExpressionNode.cc
rb87a5ed ra32b204 120 120 int i = str.length() - 1; 121 121 122 while ( i >= 0 && ! isxdigit( c = str.at( i--)) )122 while ( i >= 0 && ! isxdigit( c = str.at( i--)) ) 123 123 sfx += c; 124 124 … … 371 371 case OperatorNode::OrAssn: 372 372 // the rewrite rules for these expressions specify that the first argument has its address taken 373 assert( ! args.empty() );373 assert( ! args.empty() ); 374 374 args.front() = new AddressExpr( args.front() ); 375 375 break; … … 490 490 VarRefNode *var = dynamic_cast<VarRefNode *>( get_args()); 491 491 assert( var ); 492 if ( ! get_args()->get_link() ) {492 if ( ! get_args()->get_link() ) { 493 493 return new AttrExpr( var->build(), ( Expression*)0); 494 494 } else if ( TypeValueNode * arg = dynamic_cast<TypeValueNode *>( get_args()->get_link()) ) { -
translator/Parser/InitializerNode.cc
rb87a5ed ra32b204 56 56 os << "designated by: ("; 57 57 ExpressionNode *curdes = designator; 58 while ( curdes != 0) {58 while ( curdes != 0) { 59 59 curdes->printOneLine(os); 60 60 curdes = (ExpressionNode *)(curdes->get_link()); -
translator/Parser/ParseNode.cc
rb87a5ed ra32b204 50 50 ParseNode *current = this; 51 51 52 while ( current->get_link() != 0 )52 while ( current->get_link() != 0 ) 53 53 current = current->get_link(); 54 54 -
translator/Parser/ParseNode.h
rb87a5ed ra32b204 493 493 cur = dynamic_cast< NodeType *>( cur->get_link() ); 494 494 } // while 495 if ( ! errors.isEmpty() ) {495 if ( ! errors.isEmpty() ) { 496 496 throw errors; 497 497 } // if -
translator/Parser/StatementNode.cc
rb87a5ed ra32b204 171 171 void StatementNode::print( std::ostream &os, int indent ) const { 172 172 if ( labels != 0 ) 173 if (! labels->empty()) {173 if (! labels->empty()) { 174 174 std::list<std::string>::const_iterator i; 175 175 176 176 os << '\r' << string( indent, ' '); 177 for ( i = labels->begin(); i != labels->end(); i++ )177 for ( i = labels->begin(); i != labels->end(); i++ ) 178 178 os << *i << ":"; 179 179 os << endl; 180 180 } 181 181 182 switch ( type ) {182 switch ( type ) { 183 183 case Decl: 184 184 decl->print( os, indent ); … … 232 232 buildList<Statement, StatementNode>( get_block(), branches ); 233 233 234 switch ( type ) {234 switch ( type ) { 235 235 case Decl: 236 236 return new DeclStmt( labs, maybeBuild< Declaration >( decl ) ); … … 251 251 thenb = branches.front(); 252 252 branches.pop_front(); 253 if ( ! branches.empty() ) {253 if ( ! branches.empty() ) { 254 254 elseb = branches.front(); 255 255 branches.pop_front(); -
translator/Parser/TypeData.cc
rb87a5ed ra32b204 405 405 switch ( kind ) { 406 406 case Aggregate: 407 if ( ! toplevel && aggregate->members ) {407 if ( ! toplevel && aggregate->members ) { 408 408 ret = clone(); 409 409 ret->qualifiers.clear(); … … 411 411 break; 412 412 case Enum: 413 if ( ! toplevel && enumeration->constants ) {413 if ( ! toplevel && enumeration->constants ) { 414 414 ret = clone(); 415 415 ret->qualifiers.clear(); … … 556 556 557 557 for ( std::list< DeclarationNode::BasicType >::const_iterator i = basic->typeSpec.begin(); i != basic->typeSpec.end(); ++i ) { 558 if ( ! init ) {558 if ( ! init ) { 559 559 init = true; 560 560 if ( *i == DeclarationNode::Void ) { 561 if ( basic->typeSpec.size() != 1 || ! basic->modifiers.empty() ) {561 if ( basic->typeSpec.size() != 1 || ! basic->modifiers.empty() ) { 562 562 throw SemanticError( "invalid type specifier \"void\" in type: ", this ); 563 563 } else { … … 635 635 switch ( *i ) { 636 636 case DeclarationNode::Long: 637 if ( ! init ) {637 if ( ! init ) { 638 638 init = true; 639 639 ret = BasicType::LongSignedInt; … … 667 667 break; 668 668 case DeclarationNode::Short: 669 if ( ! init ) {669 if ( ! init ) { 670 670 init = true; 671 671 ret = BasicType::ShortSignedInt; … … 684 684 break; 685 685 case DeclarationNode::Signed: 686 if ( ! init ) {686 if ( ! init ) { 687 687 init = true; 688 688 ret = BasicType::SignedInt; … … 709 709 break; 710 710 case DeclarationNode::Unsigned: 711 if ( ! init ) {711 if ( ! init ) { 712 712 init = true; 713 713 ret = BasicType::UnsignedInt; … … 744 744 745 745 BasicType *bt; 746 if ( ! init ) {746 if ( ! init ) { 747 747 bt = new BasicType( buildQualifiers(), BasicType::SignedInt ); 748 748 } else { … … 781 781 assert( kind == Function ); 782 782 bool hasEllipsis = function->params ? function->params->get_hasEllipsis() : true; 783 if ( ! function->params ) hasEllipsis = !function->newStyle;783 if ( ! function->params ) hasEllipsis = ! function->newStyle; 784 784 FunctionType *ft = new FunctionType( buildQualifiers(), hasEllipsis ); 785 785 buildList( function->params, ft->get_parameters() ); -
translator/Parser/TypedefTable.cc
rb87a5ed ra32b204 64 64 } else { 65 65 list<Entry>::iterator listPos = (*curPos ).second.begin(); 66 while ( listPos != (*curPos ).second.end() && listPos->scope > scope ) {66 while ( listPos != (*curPos ).second.end() && listPos->scope > scope ) { 67 67 listPos++; 68 68 } … … 123 123 for ( tableType::iterator i = table.begin(); i != table.end(); ) { 124 124 list<Entry> &declList = (*i ).second; 125 while (! declList.empty() && declList.front().scope == currentScope ) {125 while (! declList.empty() && declList.front().scope == currentScope ) { 126 126 declList.pop_front(); 127 127 } -
translator/ResolvExpr/AdjustExprType.cc
rb87a5ed ra32b204 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 // AdjustExprType.cc -- 8 // 9 // Author : Richard C. Bilson 10 // Created On : Sat May 16 23:41:42 2015 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sat May 16 23:54:02 2015 13 // Update Count : 3 14 // 15 1 16 #include "typeops.h" 2 17 #include "SynTree/Type.h" … … 5 20 6 21 namespace ResolvExpr { 7 class AdjustExprType : public Mutator { 8 typedef Mutator Parent; 9 public: 10 AdjustExprType( const TypeEnvironment &env, const SymTab::Indexer &indexer ); 11 private: 12 virtual Type* mutate(VoidType *voidType); 13 virtual Type* mutate(BasicType *basicType); 14 virtual Type* mutate(PointerType *pointerType); 15 virtual Type* mutate(ArrayType *arrayType); 16 virtual Type* mutate(FunctionType *functionType); 17 virtual Type* mutate(StructInstType *aggregateUseType); 18 virtual Type* mutate(UnionInstType *aggregateUseType); 19 virtual Type* mutate(EnumInstType *aggregateUseType); 20 virtual Type* mutate(ContextInstType *aggregateUseType); 21 virtual Type* mutate(TypeInstType *aggregateUseType); 22 virtual Type* mutate(TupleType *tupleType); 23 24 const TypeEnvironment &env; 25 const SymTab::Indexer &indexer; 26 }; 22 class AdjustExprType : public Mutator { 23 typedef Mutator Parent; 24 public: 25 AdjustExprType( const TypeEnvironment &env, const SymTab::Indexer &indexer ); 26 private: 27 virtual Type* mutate( VoidType *voidType ); 28 virtual Type* mutate( BasicType *basicType ); 29 virtual Type* mutate( PointerType *pointerType ); 30 virtual Type* mutate( ArrayType *arrayType ); 31 virtual Type* mutate( FunctionType *functionType ); 32 virtual Type* mutate( StructInstType *aggregateUseType ); 33 virtual Type* mutate( UnionInstType *aggregateUseType ); 34 virtual Type* mutate( EnumInstType *aggregateUseType ); 35 virtual Type* mutate( ContextInstType *aggregateUseType ); 36 virtual Type* mutate( TypeInstType *aggregateUseType ); 37 virtual Type* mutate( TupleType *tupleType ); 27 38 28 void adjustExprType( Type *&type, const TypeEnvironment &env, const SymTab::Indexer &indexer ) { 29 AdjustExprType adjuster( env, indexer ); 30 Type *newType = type->acceptMutator( adjuster ); 31 type = newType; 32 } 39 const TypeEnvironment &env; 40 const SymTab::Indexer &indexer; 41 }; 33 42 34 AdjustExprType::AdjustExprType( const TypeEnvironment &env, const SymTab::Indexer &indexer ) 35 : env( env ), indexer( indexer ) { 36 } 43 void adjustExprType( Type *&type, const TypeEnvironment &env, const SymTab::Indexer &indexer ) { 44 AdjustExprType adjuster( env, indexer ); 45 Type *newType = type->acceptMutator( adjuster ); 46 type = newType; 47 } 37 48 38 Type *AdjustExprType::mutate(VoidType *voidType) { 39 return voidType;40 49 AdjustExprType::AdjustExprType( const TypeEnvironment &env, const SymTab::Indexer &indexer ) 50 : env( env ), indexer( indexer ) { 51 } 41 52 42 Type *AdjustExprType::mutate(BasicType *basicType) {43 return basicType;44 53 Type *AdjustExprType::mutate( VoidType *voidType ) { 54 return voidType; 55 } 45 56 46 Type *AdjustExprType::mutate(PointerType *pointerType) {47 return pointerType;48 57 Type *AdjustExprType::mutate( BasicType *basicType ) { 58 return basicType; 59 } 49 60 50 Type *AdjustExprType::mutate(ArrayType *arrayType) { 51 PointerType *pointerType = new PointerType( arrayType->get_qualifiers(), arrayType->get_base()->clone() ); 52 delete arrayType; 53 return pointerType; 54 } 61 Type *AdjustExprType::mutate( PointerType *pointerType ) { 62 return pointerType; 63 } 55 64 56 Type *AdjustExprType::mutate(FunctionType *functionType) { 57 PointerType *pointerType = new PointerType( Type::Qualifiers(), functionType ); 58 return pointerType; 59 } 65 Type *AdjustExprType::mutate( ArrayType *arrayType ) { 66 PointerType *pointerType = new PointerType( arrayType->get_qualifiers(), arrayType->get_base()->clone() ); 67 delete arrayType; 68 return pointerType; 69 } 60 70 61 Type *AdjustExprType::mutate(StructInstType *aggregateUseType) { 62 return aggregateUseType; 63 } 71 Type *AdjustExprType::mutate( FunctionType *functionType ) { 72 PointerType *pointerType = new PointerType( Type::Qualifiers(), functionType ); 73 return pointerType; 74 } 64 75 65 Type *AdjustExprType::mutate(UnionInstType *aggregateUseType) {66 return aggregateUseType;67 76 Type *AdjustExprType::mutate( StructInstType *aggregateUseType ) { 77 return aggregateUseType; 78 } 68 79 69 Type *AdjustExprType::mutate(EnumInstType *aggregateUseType) {70 return aggregateUseType;71 80 Type *AdjustExprType::mutate( UnionInstType *aggregateUseType ) { 81 return aggregateUseType; 82 } 72 83 73 Type *AdjustExprType::mutate(ContextInstType *aggregateUseType) {74 return aggregateUseType;75 84 Type *AdjustExprType::mutate( EnumInstType *aggregateUseType ) { 85 return aggregateUseType; 86 } 76 87 77 Type *AdjustExprType::mutate(TypeInstType *typeInst) { 78 EqvClass eqvClass; 79 if ( env.lookup( typeInst->get_name(), eqvClass ) ) { 80 if ( eqvClass.kind == TypeDecl::Ftype ) { 81 PointerType *pointerType = new PointerType( Type::Qualifiers(), typeInst ); 82 return pointerType; 83 } 84 } else if ( NamedTypeDecl *ntDecl = indexer.lookupType( typeInst->get_name() ) ) { 85 if ( TypeDecl *tyDecl = dynamic_cast< TypeDecl* >( ntDecl ) ) { 86 if ( tyDecl->get_kind() == TypeDecl::Ftype ) { 87 PointerType *pointerType = new PointerType( Type::Qualifiers(), typeInst ); 88 return pointerType; 89 } 90 } 88 Type *AdjustExprType::mutate( ContextInstType *aggregateUseType ) { 89 return aggregateUseType; 91 90 } 92 return typeInst;93 }94 91 95 Type *AdjustExprType::mutate(TupleType *tupleType) { 96 return tupleType; 97 } 92 Type *AdjustExprType::mutate( TypeInstType *typeInst ) { 93 EqvClass eqvClass; 94 if ( env.lookup( typeInst->get_name(), eqvClass ) ) { 95 if ( eqvClass.kind == TypeDecl::Ftype ) { 96 PointerType *pointerType = new PointerType( Type::Qualifiers(), typeInst ); 97 return pointerType; 98 } 99 } else if ( NamedTypeDecl *ntDecl = indexer.lookupType( typeInst->get_name() ) ) { 100 if ( TypeDecl *tyDecl = dynamic_cast< TypeDecl* >( ntDecl ) ) { 101 if ( tyDecl->get_kind() == TypeDecl::Ftype ) { 102 PointerType *pointerType = new PointerType( Type::Qualifiers(), typeInst ); 103 return pointerType; 104 } // if 105 } // if 106 } // if 107 return typeInst; 108 } 109 110 Type *AdjustExprType::mutate( TupleType *tupleType ) { 111 return tupleType; 112 } 98 113 } // namespace ResolvExpr 114 115 // Local Variables: // 116 // tab-width: 4 // 117 // mode: c++ // 118 // compile-command: "make install" // 119 // End: // -
translator/ResolvExpr/Alternative.cc
rb87a5ed ra32b204 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 // Alternative.cc -- 8 // 9 // Author : Richard C. Bilson 10 // Created On : Sat May 16 23:44:23 2015 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sat May 16 23:54:23 2015 13 // Update Count : 2 14 // 15 1 16 #include "Alternative.h" 2 17 #include "SynTree/Type.h" … … 5 20 6 21 namespace ResolvExpr { 7 22 Alternative::Alternative() : expr( 0 ) {} 8 23 9 10 : cost( cost ), cvtCost( Cost::zero ), expr( expr ), env( env ) {}24 Alternative::Alternative( Expression *expr, const TypeEnvironment &env, const Cost& cost ) 25 : cost( cost ), cvtCost( Cost::zero ), expr( expr ), env( env ) {} 11 26 12 13 : cost( cost ), cvtCost( cvtCost ), expr( expr ), env( env ) {}27 Alternative::Alternative( Expression *expr, const TypeEnvironment &env, const Cost& cost, const Cost &cvtCost ) 28 : cost( cost ), cvtCost( cvtCost ), expr( expr ), env( env ) {} 14 29 15 16 initialize( other, *this );17 30 Alternative::Alternative( const Alternative &other ) { 31 initialize( other, *this ); 32 } 18 33 19 20 if ( &other == this ) return *this;21 initialize( other, *this );22 return *this;23 34 Alternative &Alternative::operator=( const Alternative &other ) { 35 if ( &other == this ) return *this; 36 initialize( other, *this ); 37 return *this; 38 } 24 39 25 26 dest.cost = src.cost;27 dest.cvtCost = src.cvtCost;28 dest.expr = maybeClone( src.expr );29 dest.env = src.env;30 40 void Alternative::initialize( const Alternative &src, Alternative &dest ) { 41 dest.cost = src.cost; 42 dest.cvtCost = src.cvtCost; 43 dest.expr = maybeClone( src.expr ); 44 dest.env = src.env; 45 } 31 46 32 33 delete expr;34 47 Alternative::~Alternative() { 48 delete expr; 49 } 35 50 36 void Alternative::print( std::ostream &os, int indent ) const { 37 os << std::string( indent, ' ' ) << "Cost " << cost << ": "; 38 if ( expr ) { 39 expr->print( os, indent ); 40 os << "(types:" << std::endl; 41 printAll( expr->get_results(), os, indent + 4 ); 42 os << ")" << std::endl; 43 } else { 44 os << "Null expression!" << std::endl; 51 void Alternative::print( std::ostream &os, int indent ) const { 52 os << std::string( indent, ' ' ) << "Cost " << cost << ": "; 53 if ( expr ) { 54 expr->print( os, indent ); 55 os << "(types:" << std::endl; 56 printAll( expr->get_results(), os, indent + 4 ); 57 os << ")" << std::endl; 58 } else { 59 os << "Null expression!" << std::endl; 60 } // if 61 os << std::string( indent, ' ' ) << "Environment: "; 62 env.print( os, indent+2 ); 63 os << std::endl; 45 64 } 46 os << std::string( indent, ' ' ) << "Environment: ";47 env.print( os, indent+2 );48 os << std::endl;49 }50 65 } // namespace ResolvExpr 66 67 // Local Variables: // 68 // tab-width: 4 // 69 // mode: c++ // 70 // compile-command: "make install" // 71 // End: // -
translator/ResolvExpr/Alternative.h
rb87a5ed ra32b204 1 #ifndef RESOLVEXPR_ALTERNATIVE_H 2 #define RESOLVEXPR_ALTERNATIVE_H 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 // Alternative.h -- 8 // 9 // Author : Richard C. Bilson 10 // Created On : Sat May 16 23:45:43 2015 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sat May 16 23:54:39 2015 13 // Update Count : 2 14 // 15 16 #ifndef ALTERNATIVE_H 17 #define ALTERNATIVE_H 3 18 4 19 #include <list> … … 8 23 9 24 namespace ResolvExpr { 10 11 25 struct Alternative; 26 typedef std::list< Alternative > AltList; 12 27 13 14 Alternative();15 Alternative( Expression *expr, const TypeEnvironment &env, const Cost&cost );16 Alternative( Expression *expr, const TypeEnvironment &env, const Cost&cost, const Cost &cvtCost );17 Alternative( const Alternative &other );18 Alternative &operator=( const Alternative &other );19 ~Alternative();28 struct Alternative { 29 Alternative(); 30 Alternative( Expression *expr, const TypeEnvironment &env, const Cost &cost ); 31 Alternative( Expression *expr, const TypeEnvironment &env, const Cost &cost, const Cost &cvtCost ); 32 Alternative( const Alternative &other ); 33 Alternative &operator=( const Alternative &other ); 34 ~Alternative(); 20 35 21 void initialize( const Alternative &src, Alternative &dest );36 void initialize( const Alternative &src, Alternative &dest ); 22 37 23 void print( std::ostream &os, int indent = 0 ) const;38 void print( std::ostream &os, int indent = 0 ) const; 24 39 25 Cost cost;26 Cost cvtCost;27 Expression *expr;28 TypeEnvironment env;29 40 Cost cost; 41 Cost cvtCost; 42 Expression *expr; 43 TypeEnvironment env; 44 }; 30 45 } // namespace ResolvExpr 31 46 32 #endif // RESOLVEXPR_ALTERNATIVE_H 47 #endif // ALTERNATIVE_H 48 49 // Local Variables: // 50 // tab-width: 4 // 51 // mode: c++ // 52 // compile-command: "make install" // 53 // End: // -
translator/ResolvExpr/AlternativeFinder.cc
rb87a5ed ra32b204 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 // AlternativeFinder.cc -- 8 // 9 // Author : Richard C. Bilson 10 // Created On : Sat May 16 23:52:08 2015 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sat May 16 23:55:30 2015 13 // Update Count : 3 14 // 15 1 16 #include <list> 2 17 #include <iterator> … … 30 45 31 46 namespace ResolvExpr { 32 Expression *resolveInVoidContext( Expression *expr, const SymTab::Indexer &indexer, TypeEnvironment &env ) { 33 CastExpr *castToVoid = new CastExpr( expr ); 34 35 AlternativeFinder finder( indexer, env ); 36 finder.findWithAdjustment( castToVoid ); 37 38 // it's a property of the language that a cast expression has either 1 or 0 interpretations; if it has 0 39 // interpretations, an exception has already been thrown. 40 assert( finder.get_alternatives().size() == 1 ); 41 CastExpr *newExpr = dynamic_cast< CastExpr* >( finder.get_alternatives().front().expr ); 42 assert( newExpr ); 43 env = finder.get_alternatives().front().env; 44 return newExpr->get_arg()->clone(); 45 } 46 47 namespace { 48 void printAlts( const AltList &list, std::ostream &os, int indent = 0 ) { 49 for ( AltList::const_iterator i = list.begin(); i != list.end(); ++i ) { 50 i->print( os, indent ); 51 os << std::endl; 52 } 53 } 54 55 void makeExprList( const AltList &in, std::list< Expression* > &out ) { 56 for ( AltList::const_iterator i = in.begin(); i != in.end(); ++i ) { 57 out.push_back( i->expr->clone() ); 58 } 59 } 60 61 Cost sumCost( const AltList &in ) { 62 Cost total; 63 for ( AltList::const_iterator i = in.begin(); i != in.end(); ++i ) { 64 total += i->cost; 65 } 66 return total; 67 } 68 69 struct PruneStruct { 70 bool isAmbiguous; 71 AltList::iterator candidate; 72 PruneStruct() {} 73 PruneStruct( AltList::iterator candidate ): isAmbiguous( false ), candidate( candidate ) {} 74 }; 47 Expression *resolveInVoidContext( Expression *expr, const SymTab::Indexer &indexer, TypeEnvironment &env ) { 48 CastExpr *castToVoid = new CastExpr( expr ); 49 50 AlternativeFinder finder( indexer, env ); 51 finder.findWithAdjustment( castToVoid ); 52 53 // it's a property of the language that a cast expression has either 1 or 0 interpretations; if it has 0 54 // interpretations, an exception has already been thrown. 55 assert( finder.get_alternatives().size() == 1 ); 56 CastExpr *newExpr = dynamic_cast< CastExpr* >( finder.get_alternatives().front().expr ); 57 assert( newExpr ); 58 env = finder.get_alternatives().front().env; 59 return newExpr->get_arg()->clone(); 60 } 61 62 namespace { 63 void printAlts( const AltList &list, std::ostream &os, int indent = 0 ) { 64 for ( AltList::const_iterator i = list.begin(); i != list.end(); ++i ) { 65 i->print( os, indent ); 66 os << std::endl; 67 } 68 } 69 70 void makeExprList( const AltList &in, std::list< Expression* > &out ) { 71 for ( AltList::const_iterator i = in.begin(); i != in.end(); ++i ) { 72 out.push_back( i->expr->clone() ); 73 } 74 } 75 76 Cost sumCost( const AltList &in ) { 77 Cost total; 78 for ( AltList::const_iterator i = in.begin(); i != in.end(); ++i ) { 79 total += i->cost; 80 } 81 return total; 82 } 83 84 struct PruneStruct { 85 bool isAmbiguous; 86 AltList::iterator candidate; 87 PruneStruct() {} 88 PruneStruct( AltList::iterator candidate ): isAmbiguous( false ), candidate( candidate ) {} 89 }; 90 91 template< typename InputIterator, typename OutputIterator > 92 void pruneAlternatives( InputIterator begin, InputIterator end, OutputIterator out, const SymTab::Indexer &indexer ) { 93 // select the alternatives that have the minimum conversion cost for a particular set of result types 94 std::map< std::string, PruneStruct > selected; 95 for ( AltList::iterator candidate = begin; candidate != end; ++candidate ) { 96 PruneStruct current( candidate ); 97 std::string mangleName; 98 for ( std::list< Type* >::const_iterator retType = candidate->expr->get_results().begin(); retType != candidate->expr->get_results().end(); ++retType ) { 99 Type *newType = (*retType)->clone(); 100 candidate->env.apply( newType ); 101 mangleName += SymTab::Mangler::mangle( newType ); 102 delete newType; 103 } 104 std::map< std::string, PruneStruct >::iterator mapPlace = selected.find( mangleName ); 105 if ( mapPlace != selected.end() ) { 106 if ( candidate->cost < mapPlace->second.candidate->cost ) { 107 PRINT( 108 std::cout << "cost " << candidate->cost << " beats " << mapPlace->second.candidate->cost << std::endl; 109 ) 110 selected[ mangleName ] = current; 111 } else if ( candidate->cost == mapPlace->second.candidate->cost ) { 112 PRINT( 113 std::cout << "marking ambiguous" << std::endl; 114 ) 115 mapPlace->second.isAmbiguous = true; 116 } 117 } else { 118 selected[ mangleName ] = current; 119 } 120 } 121 122 PRINT( 123 std::cout << "there are " << selected.size() << " alternatives before elimination" << std::endl; 124 ) 125 126 // accept the alternatives that were unambiguous 127 for ( std::map< std::string, PruneStruct >::iterator target = selected.begin(); target != selected.end(); ++target ) { 128 if ( ! target->second.isAmbiguous ) { 129 Alternative &alt = *target->second.candidate; 130 for ( std::list< Type* >::iterator result = alt.expr->get_results().begin(); result != alt.expr->get_results().end(); ++result ) { 131 alt.env.applyFree( *result ); 132 } 133 *out++ = alt; 134 } 135 } 136 137 } 138 139 template< typename InputIterator, typename OutputIterator > 140 void findMinCost( InputIterator begin, InputIterator end, OutputIterator out ) { 141 AltList alternatives; 142 143 // select the alternatives that have the minimum parameter cost 144 Cost minCost = Cost::infinity; 145 for ( AltList::iterator i = begin; i != end; ++i ) { 146 if ( i->cost < minCost ) { 147 minCost = i->cost; 148 i->cost = i->cvtCost; 149 alternatives.clear(); 150 alternatives.push_back( *i ); 151 } else if ( i->cost == minCost ) { 152 i->cost = i->cvtCost; 153 alternatives.push_back( *i ); 154 } 155 } 156 std::copy( alternatives.begin(), alternatives.end(), out ); 157 } 158 159 template< typename InputIterator > 160 void simpleCombineEnvironments( InputIterator begin, InputIterator end, TypeEnvironment &result ) { 161 while ( begin != end ) { 162 result.simpleCombine( (*begin++).env ); 163 } 164 } 165 166 void renameTypes( Expression *expr ) { 167 for ( std::list< Type* >::iterator i = expr->get_results().begin(); i != expr->get_results().end(); ++i ) { 168 (*i)->accept( global_renamer ); 169 } 170 } 171 } 75 172 76 173 template< typename InputIterator, typename OutputIterator > 77 void pruneAlternatives( InputIterator begin, InputIterator end, OutputIterator out, const SymTab::Indexer &indexer ) { 78 // select the alternatives that have the minimum conversion cost for a particular set of result types 79 std::map< std::string, PruneStruct > selected; 80 for ( AltList::iterator candidate = begin; candidate != end; ++candidate ) { 81 PruneStruct current( candidate ); 82 std::string mangleName; 83 for ( std::list< Type* >::const_iterator retType = candidate->expr->get_results().begin(); retType != candidate->expr->get_results().end(); ++retType ) { 84 Type *newType = (*retType)->clone(); 85 candidate->env.apply( newType ); 86 mangleName += SymTab::Mangler::mangle( newType ); 87 delete newType; 88 } 89 std::map< std::string, PruneStruct >::iterator mapPlace = selected.find( mangleName ); 90 if ( mapPlace != selected.end() ) { 91 if ( candidate->cost < mapPlace->second.candidate->cost ) { 174 void AlternativeFinder::findSubExprs( InputIterator begin, InputIterator end, OutputIterator out ) { 175 while ( begin != end ) { 176 AlternativeFinder finder( indexer, env ); 177 finder.findWithAdjustment( *begin ); 178 // XXX either this 179 //Designators::fixDesignations( finder, (*begin++)->get_argName() ); 180 // or XXX this 181 begin++; 92 182 PRINT( 93 std::cout << "cost " << candidate->cost << " beats " << mapPlace->second.candidate->cost << std::endl; 94 ) 95 selected[ mangleName ] = current; 96 } else if ( candidate->cost == mapPlace->second.candidate->cost ) { 183 std::cout << "findSubExprs" << std::endl; 184 printAlts( finder.alternatives, std::cout ); 185 ) 186 *out++ = finder; 187 } 188 } 189 190 AlternativeFinder::AlternativeFinder( const SymTab::Indexer &indexer, const TypeEnvironment &env ) 191 : indexer( indexer ), env( env ) { 192 } 193 194 void AlternativeFinder::find( Expression *expr, bool adjust ) { 195 expr->accept( *this ); 196 if ( alternatives.empty() ) { 197 throw SemanticError( "No reasonable alternatives for expression ", expr ); 198 } 199 for ( AltList::iterator i = alternatives.begin(); i != alternatives.end(); ++i ) { 200 if ( adjust ) { 201 adjustExprTypeList( i->expr->get_results().begin(), i->expr->get_results().end(), i->env, indexer ); 202 } 203 } 204 PRINT( 205 std::cout << "alternatives before prune:" << std::endl; 206 printAlts( alternatives, std::cout ); 207 ) 208 AltList::iterator oldBegin = alternatives.begin(); 209 pruneAlternatives( alternatives.begin(), alternatives.end(), front_inserter( alternatives ), indexer ); 210 if ( alternatives.begin() == oldBegin ) { 211 std::ostrstream stream; 212 stream << "Can't choose between alternatives for expression "; 213 expr->print( stream ); 214 stream << "Alternatives are:"; 215 AltList winners; 216 findMinCost( alternatives.begin(), alternatives.end(), back_inserter( winners ) ); 217 printAlts( winners, stream, 8 ); 218 throw SemanticError( std::string( stream.str(), stream.pcount() ) ); 219 } 220 alternatives.erase( oldBegin, alternatives.end() ); 221 PRINT( 222 std::cout << "there are " << alternatives.size() << " alternatives after elimination" << std::endl; 223 ) 224 } 225 226 void AlternativeFinder::findWithAdjustment( Expression *expr ) { 227 find( expr, true ); 228 } 229 230 template< typename StructOrUnionType > 231 void AlternativeFinder::addAggMembers( StructOrUnionType *aggInst, Expression *expr, const Cost &newCost, const std::string &name ) { 232 std::list< Declaration* > members; 233 aggInst->lookup( name, members ); 234 for ( std::list< Declaration* >::const_iterator i = members.begin(); i != members.end(); ++i ) { 235 if ( DeclarationWithType *dwt = dynamic_cast< DeclarationWithType* >( *i ) ) { 236 alternatives.push_back( Alternative( new MemberExpr( dwt->clone(), expr->clone() ), env, newCost ) ); 237 renameTypes( alternatives.back().expr ); 238 } else { 239 assert( false ); 240 } 241 } 242 } 243 244 void AlternativeFinder::visit( ApplicationExpr *applicationExpr ) { 245 alternatives.push_back( Alternative( applicationExpr->clone(), env, Cost::zero ) ); 246 } 247 248 Cost computeConversionCost( Alternative &alt, const SymTab::Indexer &indexer ) { 249 ApplicationExpr *appExpr = dynamic_cast< ApplicationExpr* >( alt.expr ); 250 assert( appExpr ); 251 PointerType *pointer = dynamic_cast< PointerType* >( appExpr->get_function()->get_results().front() ); 252 assert( pointer ); 253 FunctionType *function = dynamic_cast< FunctionType* >( pointer->get_base() ); 254 assert( function ); 255 256 Cost convCost( 0, 0, 0 ); 257 std::list< DeclarationWithType* >& formals = function->get_parameters(); 258 std::list< DeclarationWithType* >::iterator formal = formals.begin(); 259 std::list< Expression* >& actuals = appExpr->get_args(); 260 for ( std::list< Expression* >::iterator actualExpr = actuals.begin(); actualExpr != actuals.end(); ++actualExpr ) { 97 261 PRINT( 98 std::cout << "marking ambiguous" << std::endl; 99 ) 100 mapPlace->second.isAmbiguous = true; 101 } 102 } else { 103 selected[ mangleName ] = current; 104 } 105 } 106 107 PRINT( 108 std::cout << "there are " << selected.size() << " alternatives before elimination" << std::endl; 109 ) 110 111 // accept the alternatives that were unambiguous 112 for ( std::map< std::string, PruneStruct >::iterator target = selected.begin(); target != selected.end(); ++target ) { 113 if ( !target->second.isAmbiguous ) { 114 Alternative &alt = *target->second.candidate; 115 for ( std::list< Type* >::iterator result = alt.expr->get_results().begin(); result != alt.expr->get_results().end(); ++result ) { 116 alt.env.applyFree( *result ); 117 } 118 *out++ = alt; 119 } 120 } 121 122 } 123 124 template< typename InputIterator, typename OutputIterator > 125 void findMinCost( InputIterator begin, InputIterator end, OutputIterator out ) { 126 AltList alternatives; 127 128 // select the alternatives that have the minimum parameter cost 129 Cost minCost = Cost::infinity; 130 for ( AltList::iterator i = begin; i != end; ++i ) { 131 if ( i->cost < minCost ) { 132 minCost = i->cost; 133 i->cost = i->cvtCost; 134 alternatives.clear(); 135 alternatives.push_back( *i ); 136 } else if ( i->cost == minCost ) { 137 i->cost = i->cvtCost; 138 alternatives.push_back( *i ); 139 } 140 } 141 std::copy( alternatives.begin(), alternatives.end(), out ); 142 } 143 144 template< typename InputIterator > 145 void simpleCombineEnvironments( InputIterator begin, InputIterator end, TypeEnvironment &result ) { 146 while ( begin != end ) { 147 result.simpleCombine( (*begin++).env ); 148 } 149 } 150 151 void renameTypes( Expression *expr ) { 152 for ( std::list< Type* >::iterator i = expr->get_results().begin(); i != expr->get_results().end(); ++i ) { 153 (*i)->accept( global_renamer ); 154 } 155 } 156 } 157 158 template< typename InputIterator, typename OutputIterator > 159 void AlternativeFinder::findSubExprs( InputIterator begin, InputIterator end, OutputIterator out ) { 160 while ( begin != end ) { 161 AlternativeFinder finder( indexer, env ); 162 finder.findWithAdjustment( *begin ); 163 // XXX either this 164 //Designators::fixDesignations( finder, (*begin++)->get_argName() ); 165 // or XXX this 166 begin++; 167 PRINT( 168 std::cout << "findSubExprs" << std::endl; 169 printAlts( finder.alternatives, std::cout ); 170 ) 171 *out++ = finder; 172 } 173 } 174 175 AlternativeFinder::AlternativeFinder( const SymTab::Indexer &indexer, const TypeEnvironment &env ) 176 : indexer( indexer ), env( env ) { 177 } 178 179 void AlternativeFinder::find( Expression *expr, bool adjust ) { 180 expr->accept( *this ); 181 if ( alternatives.empty() ) { 182 throw SemanticError( "No reasonable alternatives for expression ", expr ); 183 } 184 for ( AltList::iterator i = alternatives.begin(); i != alternatives.end(); ++i ) { 185 if ( adjust ) { 186 adjustExprTypeList( i->expr->get_results().begin(), i->expr->get_results().end(), i->env, indexer ); 187 } 188 } 189 PRINT( 190 std::cout << "alternatives before prune:" << std::endl; 191 printAlts( alternatives, std::cout ); 192 ) 193 AltList::iterator oldBegin = alternatives.begin(); 194 pruneAlternatives( alternatives.begin(), alternatives.end(), front_inserter( alternatives ), indexer ); 195 if ( alternatives.begin() == oldBegin ) { 196 std::ostrstream stream; 197 stream << "Can't choose between alternatives for expression "; 198 expr->print( stream ); 199 stream << "Alternatives are:"; 200 AltList winners; 201 findMinCost( alternatives.begin(), alternatives.end(), back_inserter( winners ) ); 202 printAlts( winners, stream, 8 ); 203 throw SemanticError( std::string( stream.str(), stream.pcount() ) ); 204 } 205 alternatives.erase( oldBegin, alternatives.end() ); 206 PRINT( 207 std::cout << "there are " << alternatives.size() << " alternatives after elimination" << std::endl; 208 ) 209 } 210 211 void AlternativeFinder::findWithAdjustment( Expression *expr ) { 212 find( expr, true ); 213 } 214 215 template< typename StructOrUnionType > 216 void AlternativeFinder::addAggMembers( StructOrUnionType *aggInst, Expression *expr, const Cost &newCost, const std::string &name ) { 217 std::list< Declaration* > members; 218 aggInst->lookup( name, members ); 219 for ( std::list< Declaration* >::const_iterator i = members.begin(); i != members.end(); ++i ) { 220 if ( DeclarationWithType *dwt = dynamic_cast< DeclarationWithType* >( *i ) ) { 221 alternatives.push_back( Alternative( new MemberExpr( dwt->clone(), expr->clone() ), env, newCost ) ); 222 renameTypes( alternatives.back().expr ); 223 } else { 224 assert( false ); 225 } 226 } 227 } 228 229 void AlternativeFinder::visit( ApplicationExpr *applicationExpr ) { 230 alternatives.push_back( Alternative( applicationExpr->clone(), env, Cost::zero ) ); 231 } 232 233 Cost computeConversionCost( Alternative &alt, const SymTab::Indexer &indexer ) { 234 ApplicationExpr *appExpr = dynamic_cast< ApplicationExpr* >( alt.expr ); 235 assert( appExpr ); 236 PointerType *pointer = dynamic_cast< PointerType* >( appExpr->get_function()->get_results().front() ); 237 assert( pointer ); 238 FunctionType *function = dynamic_cast< FunctionType* >( pointer->get_base() ); 239 assert( function ); 240 241 Cost convCost( 0, 0, 0 ); 242 std::list< DeclarationWithType* >& formals = function->get_parameters(); 243 std::list< DeclarationWithType* >::iterator formal = formals.begin(); 244 std::list< Expression* >& actuals = appExpr->get_args(); 245 for ( std::list< Expression* >::iterator actualExpr = actuals.begin(); actualExpr != actuals.end(); ++actualExpr ) { 246 PRINT( 247 std::cout << "actual expression:" << std::endl; 248 (*actualExpr)->print( std::cout, 8 ); 249 std::cout << "--- results are" << std::endl; 250 printAll( (*actualExpr)->get_results(), std::cout, 8 ); 251 ) 252 std::list< DeclarationWithType* >::iterator startFormal = formal; 253 Cost actualCost; 254 for ( std::list< Type* >::iterator actual = (*actualExpr)->get_results().begin(); actual != (*actualExpr)->get_results().end(); ++actual ) { 255 if ( formal == formals.end() ) { 256 if ( function->get_isVarArgs() ) { 257 convCost += Cost( 1, 0, 0 ); 258 break; 259 } else { 262 std::cout << "actual expression:" << std::endl; 263 (*actualExpr)->print( std::cout, 8 ); 264 std::cout << "--- results are" << std::endl; 265 printAll( (*actualExpr)->get_results(), std::cout, 8 ); 266 ) 267 std::list< DeclarationWithType* >::iterator startFormal = formal; 268 Cost actualCost; 269 for ( std::list< Type* >::iterator actual = (*actualExpr)->get_results().begin(); actual != (*actualExpr)->get_results().end(); ++actual ) { 270 if ( formal == formals.end() ) { 271 if ( function->get_isVarArgs() ) { 272 convCost += Cost( 1, 0, 0 ); 273 break; 274 } else { 275 return Cost::infinity; 276 } 277 } 278 PRINT( 279 std::cout << std::endl << "converting "; 280 (*actual)->print( std::cout, 8 ); 281 std::cout << std::endl << " to "; 282 (*formal)->get_type()->print( std::cout, 8 ); 283 ) 284 Cost newCost = conversionCost( *actual, (*formal)->get_type(), indexer, alt.env ); 285 PRINT( 286 std::cout << std::endl << "cost is" << newCost << std::endl; 287 ) 288 289 if ( newCost == Cost::infinity ) { 290 return newCost; 291 } 292 convCost += newCost; 293 actualCost += newCost; 294 295 convCost += Cost( 0, polyCost( (*formal)->get_type(), alt.env, indexer ) + polyCost( *actual, alt.env, indexer ), 0 ); 296 297 formal++; 298 } 299 if ( actualCost != Cost( 0, 0, 0 ) ) { 300 std::list< DeclarationWithType* >::iterator startFormalPlusOne = startFormal; 301 startFormalPlusOne++; 302 if ( formal == startFormalPlusOne ) { 303 // not a tuple type 304 Type *newType = (*startFormal)->get_type()->clone(); 305 alt.env.apply( newType ); 306 *actualExpr = new CastExpr( *actualExpr, newType ); 307 } else { 308 TupleType *newType = new TupleType( Type::Qualifiers() ); 309 for ( std::list< DeclarationWithType* >::iterator i = startFormal; i != formal; ++i ) { 310 newType->get_types().push_back( (*i)->get_type()->clone() ); 311 } 312 alt.env.apply( newType ); 313 *actualExpr = new CastExpr( *actualExpr, newType ); 314 } 315 } 316 317 } 318 if ( formal != formals.end() ) { 260 319 return Cost::infinity; 261 } 262 } 320 } 321 322 for ( InferredParams::const_iterator assert = appExpr->get_inferParams().begin(); assert != appExpr->get_inferParams().end(); ++assert ) { 323 PRINT( 324 std::cout << std::endl << "converting "; 325 assert->second.actualType->print( std::cout, 8 ); 326 std::cout << std::endl << " to "; 327 assert->second.formalType->print( std::cout, 8 ); 328 ) 329 Cost newCost = conversionCost( assert->second.actualType, assert->second.formalType, indexer, alt.env ); 330 PRINT( 331 std::cout << std::endl << "cost of conversion is " << newCost << std::endl; 332 ) 333 if ( newCost == Cost::infinity ) { 334 return newCost; 335 } 336 convCost += newCost; 337 338 convCost += Cost( 0, polyCost( assert->second.formalType, alt.env, indexer ) + polyCost( assert->second.actualType, alt.env, indexer ), 0 ); 339 } 340 341 return convCost; 342 } 343 344 void makeUnifiableVars( Type *type, OpenVarSet &unifiableVars, AssertionSet &needAssertions ) { 345 for ( std::list< TypeDecl* >::const_iterator tyvar = type->get_forall().begin(); tyvar != type->get_forall().end(); ++tyvar ) { 346 unifiableVars[ (*tyvar)->get_name() ] = (*tyvar)->get_kind(); 347 for ( std::list< DeclarationWithType* >::iterator assert = (*tyvar)->get_assertions().begin(); assert != (*tyvar)->get_assertions().end(); ++assert ) { 348 needAssertions[ *assert ] = true; 349 } 350 /// needAssertions.insert( needAssertions.end(), (*tyvar)->get_assertions().begin(), (*tyvar)->get_assertions().end() ); 351 } 352 } 353 354 bool AlternativeFinder::instantiateFunction( std::list< DeclarationWithType* >& formals, /*const*/ AltList &actuals, bool isVarArgs, OpenVarSet& openVars, TypeEnvironment &resultEnv, AssertionSet &resultNeed, AssertionSet &resultHave ) { 355 std::list< TypeEnvironment > toBeDone; 356 simpleCombineEnvironments( actuals.begin(), actuals.end(), resultEnv ); 357 // make sure we don't widen any existing bindings 358 for ( TypeEnvironment::iterator i = resultEnv.begin(); i != resultEnv.end(); ++i ) { 359 i->allowWidening = false; 360 } 361 resultEnv.extractOpenVars( openVars ); 362 363 /* 364 Tuples::NameMatcher matcher( formals ); 365 try { 366 matcher.match( actuals ); 367 } catch ( Tuples::NoMatch &e ) { 368 std::cerr << "Alternative doesn't match: " << e.message << std::endl; 369 } 370 */ 371 std::list< DeclarationWithType* >::iterator formal = formals.begin(); 372 for ( AltList::const_iterator actualExpr = actuals.begin(); actualExpr != actuals.end(); ++actualExpr ) { 373 for ( std::list< Type* >::iterator actual = actualExpr->expr->get_results().begin(); actual != actualExpr->expr->get_results().end(); ++actual ) { 374 if ( formal == formals.end() ) { 375 return isVarArgs; 376 } 377 PRINT( 378 std::cerr << "formal type is "; 379 (*formal)->get_type()->print( std::cerr ); 380 std::cerr << std::endl << "actual type is "; 381 (*actual)->print( std::cerr ); 382 std::cerr << std::endl; 383 ) 384 if ( ! unify( (*formal)->get_type(), *actual, resultEnv, resultNeed, resultHave, openVars, indexer ) ) { 385 return false; 386 } 387 formal++; 388 } 389 } 390 // Handling of default values 391 while ( formal != formals.end() ) { 392 if ( ObjectDecl *od = dynamic_cast<ObjectDecl *>( *formal ) ) 393 if ( SingleInit *si = dynamic_cast<SingleInit *>( od->get_init() )) 394 // so far, only constant expressions are accepted as default values 395 if ( ConstantExpr *cnstexpr = dynamic_cast<ConstantExpr *>( si->get_value()) ) 396 if ( Constant *cnst = dynamic_cast<Constant *>( cnstexpr->get_constant() ) ) 397 if ( unify( (*formal)->get_type(), cnst->get_type(), resultEnv, resultNeed, resultHave, openVars, indexer ) ) { 398 // XXX Don't know if this is right 399 actuals.push_back( Alternative( cnstexpr->clone(), env, Cost::zero ) ); 400 formal++; 401 if ( formal == formals.end()) break; 402 } 403 return false; 404 } 405 return true; 406 } 407 408 static const int recursionLimit = 10; 409 410 void addToIndexer( AssertionSet &assertSet, SymTab::Indexer &indexer ) { 411 for ( AssertionSet::iterator i = assertSet.begin(); i != assertSet.end(); ++i ) { 412 if ( i->second == true ) { 413 i->first->accept( indexer ); 414 } 415 } 416 } 417 418 template< typename ForwardIterator, typename OutputIterator > 419 void inferRecursive( ForwardIterator begin, ForwardIterator end, const Alternative &newAlt, OpenVarSet &openVars, const SymTab::Indexer &decls, const AssertionSet &newNeed, int level, const SymTab::Indexer &indexer, OutputIterator out ) { 420 if ( begin == end ) { 421 if ( newNeed.empty() ) { 422 *out++ = newAlt; 423 return; 424 } else if ( level >= recursionLimit ) { 425 throw SemanticError( "Too many recursive assertions" ); 426 } else { 427 AssertionSet newerNeed; 428 PRINT( 429 std::cerr << "recursing with new set:" << std::endl; 430 printAssertionSet( newNeed, std::cerr, 8 ); 431 ) 432 inferRecursive( newNeed.begin(), newNeed.end(), newAlt, openVars, decls, newerNeed, level+1, indexer, out ); 433 return; 434 } 435 } 436 437 ForwardIterator cur = begin++; 438 if ( ! cur->second ) { 439 inferRecursive( begin, end, newAlt, openVars, decls, newNeed, level, indexer, out ); 440 } 441 DeclarationWithType *curDecl = cur->first; 263 442 PRINT( 264 std::cout << std::endl << "converting "; 265 (*actual)->print( std::cout, 8 ); 266 std::cout << std::endl << " to "; 267 (*formal)->get_type()->print( std::cout, 8 ); 268 ) 269 Cost newCost = conversionCost( *actual, (*formal)->get_type(), indexer, alt.env ); 270 PRINT( 271 std::cout << std::endl << "cost is" << newCost << std::endl; 272 ) 273 274 if ( newCost == Cost::infinity ) { 275 return newCost; 276 } 277 convCost += newCost; 278 actualCost += newCost; 279 280 convCost += Cost( 0, polyCost( (*formal)->get_type(), alt.env, indexer ) + polyCost( *actual, alt.env, indexer ), 0 ); 281 282 formal++; 283 } 284 if ( actualCost != Cost( 0, 0, 0 ) ) { 285 std::list< DeclarationWithType* >::iterator startFormalPlusOne = startFormal; 286 startFormalPlusOne++; 287 if ( formal == startFormalPlusOne ) { 288 // not a tuple type 289 Type *newType = (*startFormal)->get_type()->clone(); 290 alt.env.apply( newType ); 291 *actualExpr = new CastExpr( *actualExpr, newType ); 292 } else { 293 TupleType *newType = new TupleType( Type::Qualifiers() ); 294 for ( std::list< DeclarationWithType* >::iterator i = startFormal; i != formal; ++i ) { 295 newType->get_types().push_back( (*i)->get_type()->clone() ); 296 } 297 alt.env.apply( newType ); 298 *actualExpr = new CastExpr( *actualExpr, newType ); 299 } 300 } 301 302 } 303 if ( formal != formals.end() ) { 304 return Cost::infinity; 305 } 306 307 for ( InferredParams::const_iterator assert = appExpr->get_inferParams().begin(); assert != appExpr->get_inferParams().end(); ++assert ) { 308 PRINT( 309 std::cout << std::endl << "converting "; 310 assert->second.actualType->print( std::cout, 8 ); 311 std::cout << std::endl << " to "; 312 assert->second.formalType->print( std::cout, 8 ); 313 ) 314 Cost newCost = conversionCost( assert->second.actualType, assert->second.formalType, indexer, alt.env ); 315 PRINT( 316 std::cout << std::endl << "cost of conversion is " << newCost << std::endl; 317 ) 318 if ( newCost == Cost::infinity ) { 319 return newCost; 320 } 321 convCost += newCost; 322 323 convCost += Cost( 0, polyCost( assert->second.formalType, alt.env, indexer ) + polyCost( assert->second.actualType, alt.env, indexer ), 0 ); 324 } 325 326 return convCost; 327 } 328 329 void makeUnifiableVars( Type *type, OpenVarSet &unifiableVars, AssertionSet &needAssertions ) { 330 for ( std::list< TypeDecl* >::const_iterator tyvar = type->get_forall().begin(); tyvar != type->get_forall().end(); ++tyvar ) { 331 unifiableVars[ (*tyvar)->get_name() ] = (*tyvar)->get_kind(); 332 for ( std::list< DeclarationWithType* >::iterator assert = (*tyvar)->get_assertions().begin(); assert != (*tyvar)->get_assertions().end(); ++assert ) { 333 needAssertions[ *assert ] = true; 334 } 335 /// needAssertions.insert( needAssertions.end(), (*tyvar)->get_assertions().begin(), (*tyvar)->get_assertions().end() ); 336 } 337 } 338 339 bool AlternativeFinder::instantiateFunction( std::list< DeclarationWithType* >& formals, /*const*/ AltList &actuals, bool isVarArgs, OpenVarSet& openVars, TypeEnvironment &resultEnv, AssertionSet &resultNeed, AssertionSet &resultHave ) { 340 std::list< TypeEnvironment > toBeDone; 341 simpleCombineEnvironments( actuals.begin(), actuals.end(), resultEnv ); 342 // make sure we don't widen any existing bindings 343 for ( TypeEnvironment::iterator i = resultEnv.begin(); i != resultEnv.end(); ++i ) { 344 i->allowWidening = false; 345 } 346 resultEnv.extractOpenVars( openVars ); 347 348 /* 349 Tuples::NameMatcher matcher( formals ); 350 try { 351 matcher.match( actuals ); 352 } catch ( Tuples::NoMatch &e ) { 353 std::cerr << "Alternative doesn't match: " << e.message << std::endl; 354 } 355 */ 356 std::list< DeclarationWithType* >::iterator formal = formals.begin(); 357 for ( AltList::const_iterator actualExpr = actuals.begin(); actualExpr != actuals.end(); ++actualExpr ) { 358 for ( std::list< Type* >::iterator actual = actualExpr->expr->get_results().begin(); actual != actualExpr->expr->get_results().end(); ++actual ) { 359 if ( formal == formals.end() ) { 360 return isVarArgs; 361 } 362 PRINT( 363 std::cerr << "formal type is "; 364 (*formal)->get_type()->print( std::cerr ); 365 std::cerr << std::endl << "actual type is "; 366 (*actual)->print( std::cerr ); 367 std::cerr << std::endl; 368 ) 369 if ( !unify( (*formal)->get_type(), *actual, resultEnv, resultNeed, resultHave, openVars, indexer ) ) { 370 return false; 371 } 372 formal++; 373 } 374 } 375 // Handling of default values 376 while ( formal != formals.end() ) { 377 if ( ObjectDecl *od = dynamic_cast<ObjectDecl *>( *formal ) ) 378 if ( SingleInit *si = dynamic_cast<SingleInit *>( od->get_init() )) 379 // so far, only constant expressions are accepted as default values 380 if ( ConstantExpr *cnstexpr = dynamic_cast<ConstantExpr *>( si->get_value()) ) 381 if ( Constant *cnst = dynamic_cast<Constant *>( cnstexpr->get_constant() ) ) 382 if ( unify( (*formal)->get_type(), cnst->get_type(), resultEnv, resultNeed, resultHave, openVars, indexer ) ) { 383 // XXX Don't know if this is right 384 actuals.push_back( Alternative( cnstexpr->clone(), env, Cost::zero ) ); 385 formal++; 386 if ( formal == formals.end()) break; 387 } 388 return false; 389 } 390 return true; 391 } 392 393 static const int recursionLimit = 10; 394 395 void addToIndexer( AssertionSet &assertSet, SymTab::Indexer &indexer ) { 396 for ( AssertionSet::iterator i = assertSet.begin(); i != assertSet.end(); ++i ) { 397 if ( i->second == true ) { 398 i->first->accept( indexer ); 399 } 400 } 401 } 402 403 template< typename ForwardIterator, typename OutputIterator > 404 void inferRecursive( ForwardIterator begin, ForwardIterator end, const Alternative &newAlt, OpenVarSet &openVars, const SymTab::Indexer &decls, const AssertionSet &newNeed, int level, const SymTab::Indexer &indexer, OutputIterator out ) { 405 if ( begin == end ) { 406 if ( newNeed.empty() ) { 407 *out++ = newAlt; 408 return; 409 } else if ( level >= recursionLimit ) { 410 throw SemanticError( "Too many recursive assertions" ); 411 } else { 412 AssertionSet newerNeed; 413 PRINT( 414 std::cerr << "recursing with new set:" << std::endl; 415 printAssertionSet( newNeed, std::cerr, 8 ); 416 ) 417 inferRecursive( newNeed.begin(), newNeed.end(), newAlt, openVars, decls, newerNeed, level+1, indexer, out ); 418 return; 419 } 420 } 421 422 ForwardIterator cur = begin++; 423 if ( !cur->second ) { 424 inferRecursive( begin, end, newAlt, openVars, decls, newNeed, level, indexer, out ); 425 } 426 DeclarationWithType *curDecl = cur->first; 427 PRINT( 428 std::cerr << "inferRecursive: assertion is "; 429 curDecl->print( std::cerr ); 430 std::cerr << std::endl; 431 ) 432 std::list< DeclarationWithType* > candidates; 433 decls.lookupId( curDecl->get_name(), candidates ); 443 std::cerr << "inferRecursive: assertion is "; 444 curDecl->print( std::cerr ); 445 std::cerr << std::endl; 446 ) 447 std::list< DeclarationWithType* > candidates; 448 decls.lookupId( curDecl->get_name(), candidates ); 434 449 /// if ( candidates.empty() ) { std::cout << "no candidates!" << std::endl; } 435 for ( std::list< DeclarationWithType* >::const_iterator candidate = candidates.begin(); candidate != candidates.end(); ++candidate ) {436 437 std::cout << "inferRecursive: candidate is ";438 (*candidate)->print( std::cout );439 std::cout << std::endl;440 )441 442 443 444 445 446 447 448 std::cerr << "unifying ";449 curDecl->get_type()->print( std::cerr );450 std::cerr << " with ";451 adjType->print( std::cerr );452 std::cerr << std::endl;453 )454 455 PRINT(456 457 458 SymTab::Indexer newDecls( decls );459 addToIndexer( newHave, newDecls );460 Alternative newerAlt( newAlt );461 newerAlt.env = newEnv;462 assert( (*candidate)->get_uniqueId() );463 Expression *varExpr = new VariableExpr( static_cast< DeclarationWithType* >( Declaration::declFromId( (*candidate)->get_uniqueId() ) ) );464 deleteAll( varExpr->get_results() );465 varExpr->get_results().clear();466 varExpr->get_results().push_front( adjType->clone() );467 PRINT(468 469 470 471 472 473 474 ApplicationExpr *appExpr = static_cast< ApplicationExpr* >( newerAlt.expr );475 // XXX: this is a memory leak, but adjType can't be deleted because it might contain assertions476 appExpr->get_inferParams()[ curDecl->get_uniqueId() ] = ParamEntry( (*candidate)->get_uniqueId(), adjType->clone(), curDecl->get_type()->clone(), varExpr );477 inferRecursive( begin, end, newerAlt, newOpenVars, newDecls, newerNeed, level, indexer, out );478 479 delete adjType;480 481 }482 483 484 485 450 for ( std::list< DeclarationWithType* >::const_iterator candidate = candidates.begin(); candidate != candidates.end(); ++candidate ) { 451 PRINT( 452 std::cout << "inferRecursive: candidate is "; 453 (*candidate)->print( std::cout ); 454 std::cout << std::endl; 455 ) 456 AssertionSet newHave, newerNeed( newNeed ); 457 TypeEnvironment newEnv( newAlt.env ); 458 OpenVarSet newOpenVars( openVars ); 459 Type *adjType = (*candidate)->get_type()->clone(); 460 adjustExprType( adjType, newEnv, indexer ); 461 adjType->accept( global_renamer ); 462 PRINT( 463 std::cerr << "unifying "; 464 curDecl->get_type()->print( std::cerr ); 465 std::cerr << " with "; 466 adjType->print( std::cerr ); 467 std::cerr << std::endl; 468 ) 469 if ( unify( curDecl->get_type(), adjType, newEnv, newerNeed, newHave, newOpenVars, indexer ) ) { 470 PRINT( 471 std::cerr << "success!" << std::endl; 472 ) 473 SymTab::Indexer newDecls( decls ); 474 addToIndexer( newHave, newDecls ); 475 Alternative newerAlt( newAlt ); 476 newerAlt.env = newEnv; 477 assert( (*candidate)->get_uniqueId() ); 478 Expression *varExpr = new VariableExpr( static_cast< DeclarationWithType* >( Declaration::declFromId( (*candidate)->get_uniqueId() ) ) ); 479 deleteAll( varExpr->get_results() ); 480 varExpr->get_results().clear(); 481 varExpr->get_results().push_front( adjType->clone() ); 482 PRINT( 483 std::cout << "satisfying assertion " << curDecl->get_uniqueId() << " "; 484 curDecl->print( std::cout ); 485 std::cout << " with declaration " << (*candidate)->get_uniqueId() << " "; 486 (*candidate)->print( std::cout ); 487 std::cout << std::endl; 488 ) 489 ApplicationExpr *appExpr = static_cast< ApplicationExpr* >( newerAlt.expr ); 490 // XXX: this is a memory leak, but adjType can't be deleted because it might contain assertions 491 appExpr->get_inferParams()[ curDecl->get_uniqueId() ] = ParamEntry( (*candidate)->get_uniqueId(), adjType->clone(), curDecl->get_type()->clone(), varExpr ); 492 inferRecursive( begin, end, newerAlt, newOpenVars, newDecls, newerNeed, level, indexer, out ); 493 } else { 494 delete adjType; 495 } 496 } 497 } 498 499 template< typename OutputIterator > 500 void AlternativeFinder::inferParameters( const AssertionSet &need, AssertionSet &have, const Alternative &newAlt, OpenVarSet &openVars, OutputIterator out ) { 486 501 // PRINT( 487 502 // std::cout << "inferParameters: assertions needed are" << std::endl; 488 503 // printAll( need, std::cout, 8 ); 489 504 // ) 490 SymTab::Indexer decls( indexer );491 PRINT(492 493 494 495 496 497 addToIndexer( have, decls );498 AssertionSet newNeed;499 inferRecursive( need.begin(), need.end(), newAlt, openVars, decls, newNeed, 0, indexer, out );505 SymTab::Indexer decls( indexer ); 506 PRINT( 507 std::cout << "============= original indexer" << std::endl; 508 indexer.print( std::cout ); 509 std::cout << "============= new indexer" << std::endl; 510 decls.print( std::cout ); 511 ) 512 addToIndexer( have, decls ); 513 AssertionSet newNeed; 514 inferRecursive( need.begin(), need.end(), newAlt, openVars, decls, newNeed, 0, indexer, out ); 500 515 // PRINT( 501 516 // std::cout << "declaration 14 is "; … … 503 518 // *out++ = newAlt; 504 519 // ) 505 } 506 507 template< typename OutputIterator > 508 void AlternativeFinder::makeFunctionAlternatives( const Alternative &func, FunctionType *funcType, AltList &actualAlt, OutputIterator out ) { 509 OpenVarSet openVars; 510 AssertionSet resultNeed, resultHave; 511 TypeEnvironment resultEnv; 512 makeUnifiableVars( funcType, openVars, resultNeed ); 513 if ( instantiateFunction( funcType->get_parameters(), actualAlt, funcType->get_isVarArgs(), openVars, resultEnv, resultNeed, resultHave ) ) { 514 ApplicationExpr *appExpr = new ApplicationExpr( func.expr->clone() ); 515 Alternative newAlt( appExpr, resultEnv, sumCost( actualAlt ) ); 516 makeExprList( actualAlt, appExpr->get_args() ); 517 PRINT( 518 std::cout << "need assertions:" << std::endl; 519 printAssertionSet( resultNeed, std::cout, 8 ); 520 ) 521 inferParameters( resultNeed, resultHave, newAlt, openVars, out ); 522 } 523 } 524 525 void AlternativeFinder::visit( UntypedExpr *untypedExpr ) { 526 bool doneInit = false; 527 AlternativeFinder funcOpFinder( indexer, env ); 528 529 AlternativeFinder funcFinder( indexer, env ); { 530 NameExpr *fname; 531 if ( ( fname = dynamic_cast<NameExpr *>( untypedExpr->get_function())) 532 && ( fname->get_name() == std::string("LabAddress")) ) { 533 alternatives.push_back( Alternative( untypedExpr, env, Cost()) ); 534 return; 535 } 536 } 537 538 funcFinder.findWithAdjustment( untypedExpr->get_function() ); 539 std::list< AlternativeFinder > argAlternatives; 540 findSubExprs( untypedExpr->begin_args(), untypedExpr->end_args(), back_inserter( argAlternatives ) ); 541 542 std::list< AltList > possibilities; 543 combos( argAlternatives.begin(), argAlternatives.end(), back_inserter( possibilities ) ); 544 545 Tuples::TupleAssignSpotter tassign( this ); 546 if ( tassign.isTupleAssignment( untypedExpr, possibilities ) ) { 547 // take care of possible tuple assignments, or discard expression 548 return; 549 } // else ... 550 551 AltList candidates; 552 553 for ( AltList::const_iterator func = funcFinder.alternatives.begin(); func != funcFinder.alternatives.end(); ++func ) { 554 PRINT( 555 std::cout << "working on alternative: " << std::endl; 556 func->print( std::cout, 8 ); 557 ) 558 // check if the type is pointer to function 559 PointerType *pointer; 560 if ( func->expr->get_results().size() == 1 && ( pointer = dynamic_cast< PointerType* >( func->expr->get_results().front() ) ) ) { 561 if ( FunctionType *function = dynamic_cast< FunctionType* >( pointer->get_base() ) ) { 562 for ( std::list< AltList >::iterator actualAlt = possibilities.begin(); actualAlt != possibilities.end(); ++actualAlt ) { 563 // XXX 564 //Designators::check_alternative( function, *actualAlt ); 565 makeFunctionAlternatives( *func, function, *actualAlt, std::back_inserter( candidates ) ); 566 } 567 } else if ( TypeInstType *typeInst = dynamic_cast< TypeInstType* >( pointer->get_base() ) ) { 568 EqvClass eqvClass; 569 if ( func->env.lookup( typeInst->get_name(), eqvClass ) && eqvClass.type ) { 570 if ( FunctionType *function = dynamic_cast< FunctionType* >( eqvClass.type ) ) { 571 for ( std::list< AltList >::iterator actualAlt = possibilities.begin(); actualAlt != possibilities.end(); ++actualAlt ) { 572 makeFunctionAlternatives( *func, function, *actualAlt, std::back_inserter( candidates ) ); 573 } 574 } 575 } 576 } 577 } else { 578 // seek a function operator that's compatible 579 if ( !doneInit ) { 580 doneInit = true; 581 NameExpr *opExpr = new NameExpr( "?()" ); 582 try { 583 funcOpFinder.findWithAdjustment( opExpr ); 584 } catch( SemanticError &e ) { 585 // it's ok if there aren't any defined function ops 586 } 587 PRINT( 588 std::cout << "known function ops:" << std::endl; 589 printAlts( funcOpFinder.alternatives, std::cout, 8 ); 520 } 521 522 template< typename OutputIterator > 523 void AlternativeFinder::makeFunctionAlternatives( const Alternative &func, FunctionType *funcType, AltList &actualAlt, OutputIterator out ) { 524 OpenVarSet openVars; 525 AssertionSet resultNeed, resultHave; 526 TypeEnvironment resultEnv; 527 makeUnifiableVars( funcType, openVars, resultNeed ); 528 if ( instantiateFunction( funcType->get_parameters(), actualAlt, funcType->get_isVarArgs(), openVars, resultEnv, resultNeed, resultHave ) ) { 529 ApplicationExpr *appExpr = new ApplicationExpr( func.expr->clone() ); 530 Alternative newAlt( appExpr, resultEnv, sumCost( actualAlt ) ); 531 makeExprList( actualAlt, appExpr->get_args() ); 532 PRINT( 533 std::cout << "need assertions:" << std::endl; 534 printAssertionSet( resultNeed, std::cout, 8 ); 535 ) 536 inferParameters( resultNeed, resultHave, newAlt, openVars, out ); 537 } 538 } 539 540 void AlternativeFinder::visit( UntypedExpr *untypedExpr ) { 541 bool doneInit = false; 542 AlternativeFinder funcOpFinder( indexer, env ); 543 544 AlternativeFinder funcFinder( indexer, env ); { 545 NameExpr *fname; 546 if ( ( fname = dynamic_cast<NameExpr *>( untypedExpr->get_function())) 547 && ( fname->get_name() == std::string("LabAddress")) ) { 548 alternatives.push_back( Alternative( untypedExpr, env, Cost()) ); 549 return; 550 } 551 } 552 553 funcFinder.findWithAdjustment( untypedExpr->get_function() ); 554 std::list< AlternativeFinder > argAlternatives; 555 findSubExprs( untypedExpr->begin_args(), untypedExpr->end_args(), back_inserter( argAlternatives ) ); 556 557 std::list< AltList > possibilities; 558 combos( argAlternatives.begin(), argAlternatives.end(), back_inserter( possibilities ) ); 559 560 Tuples::TupleAssignSpotter tassign( this ); 561 if ( tassign.isTupleAssignment( untypedExpr, possibilities ) ) { 562 // take care of possible tuple assignments, or discard expression 563 return; 564 } // else ... 565 566 AltList candidates; 567 568 for ( AltList::const_iterator func = funcFinder.alternatives.begin(); func != funcFinder.alternatives.end(); ++func ) { 569 PRINT( 570 std::cout << "working on alternative: " << std::endl; 571 func->print( std::cout, 8 ); 572 ) 573 // check if the type is pointer to function 574 PointerType *pointer; 575 if ( func->expr->get_results().size() == 1 && ( pointer = dynamic_cast< PointerType* >( func->expr->get_results().front() ) ) ) { 576 if ( FunctionType *function = dynamic_cast< FunctionType* >( pointer->get_base() ) ) { 577 for ( std::list< AltList >::iterator actualAlt = possibilities.begin(); actualAlt != possibilities.end(); ++actualAlt ) { 578 // XXX 579 //Designators::check_alternative( function, *actualAlt ); 580 makeFunctionAlternatives( *func, function, *actualAlt, std::back_inserter( candidates ) ); 581 } 582 } else if ( TypeInstType *typeInst = dynamic_cast< TypeInstType* >( pointer->get_base() ) ) { 583 EqvClass eqvClass; 584 if ( func->env.lookup( typeInst->get_name(), eqvClass ) && eqvClass.type ) { 585 if ( FunctionType *function = dynamic_cast< FunctionType* >( eqvClass.type ) ) { 586 for ( std::list< AltList >::iterator actualAlt = possibilities.begin(); actualAlt != possibilities.end(); ++actualAlt ) { 587 makeFunctionAlternatives( *func, function, *actualAlt, std::back_inserter( candidates ) ); 588 } // for 589 } // if 590 } // if 591 } // if 592 } else { 593 // seek a function operator that's compatible 594 if ( ! doneInit ) { 595 doneInit = true; 596 NameExpr *opExpr = new NameExpr( "?()" ); 597 try { 598 funcOpFinder.findWithAdjustment( opExpr ); 599 } catch( SemanticError &e ) { 600 // it's ok if there aren't any defined function ops 601 } 602 PRINT( 603 std::cout << "known function ops:" << std::endl; 604 printAlts( funcOpFinder.alternatives, std::cout, 8 ); 605 ) 606 } 607 608 for ( AltList::const_iterator funcOp = funcOpFinder.alternatives.begin(); funcOp != funcOpFinder.alternatives.end(); ++funcOp ) { 609 // check if the type is pointer to function 610 PointerType *pointer; 611 if ( funcOp->expr->get_results().size() == 1 612 && ( pointer = dynamic_cast< PointerType* >( funcOp->expr->get_results().front() ) ) ) { 613 if ( FunctionType *function = dynamic_cast< FunctionType* >( pointer->get_base() ) ) { 614 for ( std::list< AltList >::iterator actualAlt = possibilities.begin(); actualAlt != possibilities.end(); ++actualAlt ) { 615 AltList currentAlt; 616 currentAlt.push_back( *func ); 617 currentAlt.insert( currentAlt.end(), actualAlt->begin(), actualAlt->end() ); 618 makeFunctionAlternatives( *funcOp, function, currentAlt, std::back_inserter( candidates ) ); 619 } // for 620 } // if 621 } // if 622 } // for 623 } // if 624 } // for 625 626 for ( AltList::iterator withFunc = candidates.begin(); withFunc != candidates.end(); ++withFunc ) { 627 Cost cvtCost = computeConversionCost( *withFunc, indexer ); 628 629 PRINT( 630 ApplicationExpr *appExpr = dynamic_cast< ApplicationExpr* >( withFunc->expr ); 631 assert( appExpr ); 632 PointerType *pointer = dynamic_cast< PointerType* >( appExpr->get_function()->get_results().front() ); 633 assert( pointer ); 634 FunctionType *function = dynamic_cast< FunctionType* >( pointer->get_base() ); 635 assert( function ); 636 std::cout << "Case +++++++++++++" << std::endl; 637 std::cout << "formals are:" << std::endl; 638 printAll( function->get_parameters(), std::cout, 8 ); 639 std::cout << "actuals are:" << std::endl; 640 printAll( appExpr->get_args(), std::cout, 8 ); 641 std::cout << "bindings are:" << std::endl; 642 withFunc->env.print( std::cout, 8 ); 643 std::cout << "cost of conversion is:" << cvtCost << std::endl; 644 ) 645 if ( cvtCost != Cost::infinity ) { 646 withFunc->cvtCost = cvtCost; 647 alternatives.push_back( *withFunc ); 648 } // if 649 } // for 650 candidates.clear(); 651 candidates.splice( candidates.end(), alternatives ); 652 653 findMinCost( candidates.begin(), candidates.end(), std::back_inserter( alternatives ) ); 654 } 655 656 bool isLvalue( Expression *expr ) { 657 for ( std::list< Type* >::const_iterator i = expr->get_results().begin(); i != expr->get_results().end(); ++i ) { 658 if ( !(*i)->get_isLvalue() ) return false; 659 } // for 660 return true; 661 } 662 663 void AlternativeFinder::visit( AddressExpr *addressExpr ) { 664 AlternativeFinder finder( indexer, env ); 665 finder.find( addressExpr->get_arg() ); 666 for ( std::list< Alternative >::iterator i = finder.alternatives.begin(); i != finder.alternatives.end(); ++i ) { 667 if ( isLvalue( i->expr ) ) { 668 alternatives.push_back( Alternative( new AddressExpr( i->expr->clone() ), i->env, i->cost ) ); 669 } // if 670 } // for 671 } 672 673 void AlternativeFinder::visit( CastExpr *castExpr ) { 674 for ( std::list< Type* >::iterator i = castExpr->get_results().begin(); i != castExpr->get_results().end(); ++i ) { 675 SymTab::validateType( *i, &indexer ); 676 adjustExprType( *i, env, indexer ); 677 } // for 678 679 AlternativeFinder finder( indexer, env ); 680 finder.findWithAdjustment( castExpr->get_arg() ); 681 682 AltList candidates; 683 for ( std::list< Alternative >::iterator i = finder.alternatives.begin(); i != finder.alternatives.end(); ++i ) { 684 AssertionSet needAssertions, haveAssertions; 685 OpenVarSet openVars; 686 687 // It's possible that a cast can throw away some values in a multiply-valued expression. (An example is a 688 // cast-to-void, which casts from one value to zero.) Figure out the prefix of the subexpression results 689 // that are cast directly. The candidate is invalid if it has fewer results than there are types to cast 690 // to. 691 int discardedValues = (*i).expr->get_results().size() - castExpr->get_results().size(); 692 if ( discardedValues < 0 ) continue; 693 std::list< Type* >::iterator candidate_end = (*i).expr->get_results().begin(); 694 std::advance( candidate_end, castExpr->get_results().size() ); 695 if ( ! unifyList( (*i).expr->get_results().begin(), candidate_end, 696 castExpr->get_results().begin(), castExpr->get_results().end(), i->env, needAssertions, haveAssertions, openVars, indexer ) ) continue; 697 Cost thisCost = castCostList( (*i).expr->get_results().begin(), candidate_end, 698 castExpr->get_results().begin(), castExpr->get_results().end(), indexer, i->env ); 699 if ( thisCost != Cost::infinity ) { 700 // count one safe conversion for each value that is thrown away 701 thisCost += Cost( 0, 0, discardedValues ); 702 CastExpr *newExpr = castExpr->clone(); 703 newExpr->set_arg( i->expr->clone() ); 704 candidates.push_back( Alternative( newExpr, i->env, i->cost, thisCost ) ); 705 } // if 706 } // for 707 708 // findMinCost selects the alternatives with the lowest "cost" members, but has the side effect of copying the 709 // cvtCost member to the cost member (since the old cost is now irrelevant). Thus, calling findMinCost twice 710 // selects first based on argument cost, then on conversion cost. 711 AltList minArgCost; 712 findMinCost( candidates.begin(), candidates.end(), std::back_inserter( minArgCost ) ); 713 findMinCost( minArgCost.begin(), minArgCost.end(), std::back_inserter( alternatives ) ); 714 } 715 716 void AlternativeFinder::visit( UntypedMemberExpr *memberExpr ) { 717 AlternativeFinder funcFinder( indexer, env ); 718 funcFinder.findWithAdjustment( memberExpr->get_aggregate() ); 719 720 for ( AltList::const_iterator agg = funcFinder.alternatives.begin(); agg != funcFinder.alternatives.end(); ++agg ) { 721 if ( agg->expr->get_results().size() == 1 ) { 722 if ( StructInstType *structInst = dynamic_cast< StructInstType* >( agg->expr->get_results().front() ) ) { 723 addAggMembers( structInst, agg->expr, agg->cost, memberExpr->get_member() ); 724 } else if ( UnionInstType *unionInst = dynamic_cast< UnionInstType* >( agg->expr->get_results().front() ) ) { 725 addAggMembers( unionInst, agg->expr, agg->cost, memberExpr->get_member() ); 726 } // if 727 } // if 728 } // for 729 } 730 731 void AlternativeFinder::visit( MemberExpr *memberExpr ) { 732 alternatives.push_back( Alternative( memberExpr->clone(), env, Cost::zero ) ); 733 } 734 735 void AlternativeFinder::visit( NameExpr *nameExpr ) { 736 std::list< DeclarationWithType* > declList; 737 indexer.lookupId( nameExpr->get_name(), declList ); 738 PRINT( std::cerr << "nameExpr is " << nameExpr->get_name() << std::endl; ) 739 for ( std::list< DeclarationWithType* >::iterator i = declList.begin(); i != declList.end(); ++i ) { 740 VariableExpr newExpr( *i, nameExpr->get_argName() ); 741 alternatives.push_back( Alternative( newExpr.clone(), env, Cost() ) ); 742 PRINT( 743 std::cerr << "decl is "; 744 (*i)->print( std::cerr ); 745 std::cerr << std::endl; 746 std::cerr << "newExpr is "; 747 newExpr.print( std::cerr ); 748 std::cerr << std::endl; 749 ) 750 renameTypes( alternatives.back().expr ); 751 if ( StructInstType *structInst = dynamic_cast< StructInstType* >( (*i)->get_type() ) ) { 752 addAggMembers( structInst, &newExpr, Cost( 0, 0, 1 ), "" ); 753 } else if ( UnionInstType *unionInst = dynamic_cast< UnionInstType* >( (*i)->get_type() ) ) { 754 addAggMembers( unionInst, &newExpr, Cost( 0, 0, 1 ), "" ); 755 } // if 756 } // for 757 } 758 759 void AlternativeFinder::visit( VariableExpr *variableExpr ) { 760 alternatives.push_back( Alternative( variableExpr->clone(), env, Cost::zero ) ); 761 } 762 763 void AlternativeFinder::visit( ConstantExpr *constantExpr ) { 764 alternatives.push_back( Alternative( constantExpr->clone(), env, Cost::zero ) ); 765 } 766 767 void AlternativeFinder::visit( SizeofExpr *sizeofExpr ) { 768 if ( sizeofExpr->get_isType() ) { 769 alternatives.push_back( Alternative( sizeofExpr->clone(), env, Cost::zero ) ); 770 } else { 771 // find all alternatives for the argument to sizeof 772 AlternativeFinder finder( indexer, env ); 773 finder.find( sizeofExpr->get_expr() ); 774 // find the lowest cost alternative among the alternatives, otherwise ambiguous 775 AltList winners; 776 findMinCost( finder.alternatives.begin(), finder.alternatives.end(), back_inserter( winners ) ); 777 if ( winners.size() != 1 ) { 778 throw SemanticError( "Ambiguous expression in sizeof operand: ", sizeofExpr->get_expr() ); 779 } // if 780 // return the lowest cost alternative for the argument 781 Alternative &choice = winners.front(); 782 alternatives.push_back( Alternative( new SizeofExpr( choice.expr->clone() ), choice.env, Cost::zero ) ); 783 } // if 784 } 785 786 void AlternativeFinder::resolveAttr( DeclarationWithType *funcDecl, FunctionType *function, Type *argType, const TypeEnvironment &env ) { 787 // assume no polymorphism 788 // assume no implicit conversions 789 assert( function->get_parameters().size() == 1 ); 790 PRINT( 791 std::cout << "resolvAttr: funcDecl is "; 792 funcDecl->print( std::cout ); 793 std::cout << " argType is "; 794 argType->print( std::cout ); 795 std::cout << std::endl; 590 796 ) 591 } 592 593 for ( AltList::const_iterator funcOp = funcOpFinder.alternatives.begin(); funcOp != funcOpFinder.alternatives.end(); ++funcOp ) { 594 // check if the type is pointer to function 595 PointerType *pointer; 596 if ( funcOp->expr->get_results().size() == 1 597 && ( pointer = dynamic_cast< PointerType* >( funcOp->expr->get_results().front() ) ) ) { 598 if ( FunctionType *function = dynamic_cast< FunctionType* >( pointer->get_base() ) ) { 599 for ( std::list< AltList >::iterator actualAlt = possibilities.begin(); actualAlt != possibilities.end(); ++actualAlt ) { 600 AltList currentAlt; 601 currentAlt.push_back( *func ); 602 currentAlt.insert( currentAlt.end(), actualAlt->begin(), actualAlt->end() ); 603 makeFunctionAlternatives( *funcOp, function, currentAlt, std::back_inserter( candidates ) ); 604 } 605 } 606 } 607 } 608 } 609 } 610 611 for ( AltList::iterator withFunc = candidates.begin(); withFunc != candidates.end(); ++withFunc ) { 612 Cost cvtCost = computeConversionCost( *withFunc, indexer ); 613 614 PRINT( 615 ApplicationExpr *appExpr = dynamic_cast< ApplicationExpr* >( withFunc->expr ); 616 assert( appExpr ); 617 PointerType *pointer = dynamic_cast< PointerType* >( appExpr->get_function()->get_results().front() ); 618 assert( pointer ); 619 FunctionType *function = dynamic_cast< FunctionType* >( pointer->get_base() ); 620 assert( function ); 621 std::cout << "Case +++++++++++++" << std::endl; 622 std::cout << "formals are:" << std::endl; 623 printAll( function->get_parameters(), std::cout, 8 ); 624 std::cout << "actuals are:" << std::endl; 625 printAll( appExpr->get_args(), std::cout, 8 ); 626 std::cout << "bindings are:" << std::endl; 627 withFunc->env.print( std::cout, 8 ); 628 std::cout << "cost of conversion is:" << cvtCost << std::endl; 629 ) 630 if ( cvtCost != Cost::infinity ) { 631 withFunc->cvtCost = cvtCost; 632 alternatives.push_back( *withFunc ); 633 } 634 } 635 candidates.clear(); 636 candidates.splice( candidates.end(), alternatives ); 637 638 findMinCost( candidates.begin(), candidates.end(), std::back_inserter( alternatives ) ); 639 } 640 641 bool isLvalue( Expression *expr ) { 642 for ( std::list< Type* >::const_iterator i = expr->get_results().begin(); i != expr->get_results().end(); ++i ) { 643 if ( !(*i)->get_isLvalue() ) return false; 644 } 645 return true; 646 } 647 648 void AlternativeFinder::visit( AddressExpr *addressExpr ) { 649 AlternativeFinder finder( indexer, env ); 650 finder.find( addressExpr->get_arg() ); 651 for ( std::list< Alternative >::iterator i = finder.alternatives.begin(); i != finder.alternatives.end(); ++i ) { 652 if ( isLvalue( i->expr ) ) { 653 alternatives.push_back( Alternative( new AddressExpr( i->expr->clone() ), i->env, i->cost ) ); 654 } 655 } 656 } 657 658 void AlternativeFinder::visit( CastExpr *castExpr ) { 659 for ( std::list< Type* >::iterator i = castExpr->get_results().begin(); i != castExpr->get_results().end(); ++i ) { 660 SymTab::validateType( *i, &indexer ); 661 adjustExprType( *i, env, indexer ); 662 } 663 664 AlternativeFinder finder( indexer, env ); 665 finder.findWithAdjustment( castExpr->get_arg() ); 666 667 AltList candidates; 668 for ( std::list< Alternative >::iterator i = finder.alternatives.begin(); i != finder.alternatives.end(); ++i ) { 669 AssertionSet needAssertions, haveAssertions; 670 OpenVarSet openVars; 671 672 // It's possible that a cast can throw away some values in a multiply-valued expression. (An example is a 673 // cast-to-void, which casts from one value to zero.) Figure out the prefix of the subexpression results 674 // that are cast directly. The candidate is invalid if it has fewer results than there are types to cast 675 // to. 676 int discardedValues = (*i).expr->get_results().size() - castExpr->get_results().size(); 677 if ( discardedValues < 0 ) continue; 678 std::list< Type* >::iterator candidate_end = (*i).expr->get_results().begin(); 679 std::advance( candidate_end, castExpr->get_results().size() ); 680 if ( !unifyList( (*i).expr->get_results().begin(), candidate_end, 681 castExpr->get_results().begin(), castExpr->get_results().end(), i->env, needAssertions, haveAssertions, openVars, indexer ) ) continue; 682 Cost thisCost = castCostList( (*i).expr->get_results().begin(), candidate_end, 683 castExpr->get_results().begin(), castExpr->get_results().end(), indexer, i->env ); 684 if ( thisCost != Cost::infinity ) { 685 // count one safe conversion for each value that is thrown away 686 thisCost += Cost( 0, 0, discardedValues ); 687 CastExpr *newExpr = castExpr->clone(); 688 newExpr->set_arg( i->expr->clone() ); 689 candidates.push_back( Alternative( newExpr, i->env, i->cost, thisCost ) ); 690 } 691 } 692 693 // findMinCost selects the alternatives with the lowest "cost" members, but has the side effect of copying the 694 // cvtCost member to the cost member (since the old cost is now irrelevant). Thus, calling findMinCost twice 695 // selects first based on argument cost, then on conversion cost. 696 AltList minArgCost; 697 findMinCost( candidates.begin(), candidates.end(), std::back_inserter( minArgCost ) ); 698 findMinCost( minArgCost.begin(), minArgCost.end(), std::back_inserter( alternatives ) ); 699 } 700 701 void AlternativeFinder::visit( UntypedMemberExpr *memberExpr ) { 702 AlternativeFinder funcFinder( indexer, env ); 703 funcFinder.findWithAdjustment( memberExpr->get_aggregate() ); 704 705 for ( AltList::const_iterator agg = funcFinder.alternatives.begin(); agg != funcFinder.alternatives.end(); ++agg ) { 706 if ( agg->expr->get_results().size() == 1 ) { 707 if ( StructInstType *structInst = dynamic_cast< StructInstType* >( agg->expr->get_results().front() ) ) { 708 addAggMembers( structInst, agg->expr, agg->cost, memberExpr->get_member() ); 709 } else if ( UnionInstType *unionInst = dynamic_cast< UnionInstType* >( agg->expr->get_results().front() ) ) { 710 addAggMembers( unionInst, agg->expr, agg->cost, memberExpr->get_member() ); 711 } 712 } 713 } 714 } 715 716 void AlternativeFinder::visit( MemberExpr *memberExpr ) { 717 alternatives.push_back( Alternative( memberExpr->clone(), env, Cost::zero ) ); 718 } 719 720 void AlternativeFinder::visit( NameExpr *nameExpr ) { 721 std::list< DeclarationWithType* > declList; 722 indexer.lookupId( nameExpr->get_name(), declList ); 723 PRINT( 724 std::cerr << "nameExpr is " << nameExpr->get_name() << std::endl; 725 ) 726 for ( std::list< DeclarationWithType* >::iterator i = declList.begin(); i != declList.end(); ++i ) { 727 VariableExpr newExpr( *i, nameExpr->get_argName() ); 728 alternatives.push_back( Alternative( newExpr.clone(), env, Cost() ) ); 729 PRINT( 730 std::cerr << "decl is "; 731 (*i)->print( std::cerr ); 732 std::cerr << std::endl; 733 std::cerr << "newExpr is "; 734 newExpr.print( std::cerr ); 735 std::cerr << std::endl; 736 ) 737 renameTypes( alternatives.back().expr ); 738 if ( StructInstType *structInst = dynamic_cast< StructInstType* >( (*i)->get_type() ) ) { 739 addAggMembers( structInst, &newExpr, Cost( 0, 0, 1 ), "" ); 740 } else if ( UnionInstType *unionInst = dynamic_cast< UnionInstType* >( (*i)->get_type() ) ) { 741 addAggMembers( unionInst, &newExpr, Cost( 0, 0, 1 ), "" ); 742 } 743 } 744 } 745 746 void AlternativeFinder::visit( VariableExpr *variableExpr ) { 747 alternatives.push_back( Alternative( variableExpr->clone(), env, Cost::zero ) ); 748 } 749 750 void AlternativeFinder::visit( ConstantExpr *constantExpr ) { 751 alternatives.push_back( Alternative( constantExpr->clone(), env, Cost::zero ) ); 752 } 753 754 void AlternativeFinder::visit( SizeofExpr *sizeofExpr ) { 755 if ( sizeofExpr->get_isType() ) { 756 alternatives.push_back( Alternative( sizeofExpr->clone(), env, Cost::zero ) ); 757 } else { 758 // find all alternatives for the argument to sizeof 759 AlternativeFinder finder( indexer, env ); 760 finder.find( sizeofExpr->get_expr() ); 761 // find the lowest cost alternative among the alternatives, otherwise ambiguous 762 AltList winners; 763 findMinCost( finder.alternatives.begin(), finder.alternatives.end(), back_inserter( winners ) ); 764 if ( winners.size() != 1 ) { 765 throw SemanticError( "Ambiguous expression in sizeof operand: ", sizeofExpr->get_expr() ); 766 } 767 // return the lowest cost alternative for the argument 768 Alternative &choice = winners.front(); 769 alternatives.push_back( Alternative( new SizeofExpr( choice.expr->clone() ), choice.env, Cost::zero ) ); 770 } 771 } 772 773 void AlternativeFinder::resolveAttr( DeclarationWithType *funcDecl, FunctionType *function, Type *argType, const TypeEnvironment &env ) { 774 // assume no polymorphism 775 // assume no implicit conversions 776 assert( function->get_parameters().size() == 1 ); 777 PRINT( 778 std::cout << "resolvAttr: funcDecl is "; 779 funcDecl->print( std::cout ); 780 std::cout << " argType is "; 781 argType->print( std::cout ); 782 std::cout << std::endl; 783 ) 784 if ( typesCompatibleIgnoreQualifiers( argType, function->get_parameters().front()->get_type(), indexer, env ) ) { 785 alternatives.push_back( Alternative( new AttrExpr( new VariableExpr( funcDecl ), argType->clone() ), env, Cost::zero ) ); 786 for ( std::list< DeclarationWithType* >::iterator i = function->get_returnVals().begin(); i != function->get_returnVals().end(); ++i ) { 787 alternatives.back().expr->get_results().push_back( (*i)->get_type()->clone() ); 788 } 789 } 790 } 791 792 void AlternativeFinder::visit( AttrExpr *attrExpr ) { 793 // assume no 'pointer-to-attribute' 794 NameExpr *nameExpr = dynamic_cast< NameExpr* >( attrExpr->get_attr() ); 795 assert( nameExpr ); 796 std::list< DeclarationWithType* > attrList; 797 indexer.lookupId( nameExpr->get_name(), attrList ); 798 if ( attrExpr->get_isType() || attrExpr->get_expr() ) { 799 for ( std::list< DeclarationWithType* >::iterator i = attrList.begin(); i != attrList.end(); ++i ) { 800 // check if the type is function 801 if ( FunctionType *function = dynamic_cast< FunctionType* >( (*i)->get_type() ) ) { 802 // assume exactly one parameter 803 if ( function->get_parameters().size() == 1 ) { 804 if ( attrExpr->get_isType() ) { 805 resolveAttr( *i, function, attrExpr->get_type(), env ); 806 } else { 807 AlternativeFinder finder( indexer, env ); 808 finder.find( attrExpr->get_expr() ); 809 for ( AltList::iterator choice = finder.alternatives.begin(); choice != finder.alternatives.end(); ++choice ) { 810 if ( choice->expr->get_results().size() == 1 ) { 811 resolveAttr(*i, function, choice->expr->get_results().front(), choice->env ); 812 } 813 } 814 } 815 } 816 } 817 } 818 } else { 819 for ( std::list< DeclarationWithType* >::iterator i = attrList.begin(); i != attrList.end(); ++i ) { 820 VariableExpr newExpr( *i ); 821 alternatives.push_back( Alternative( newExpr.clone(), env, Cost() ) ); 822 renameTypes( alternatives.back().expr ); 823 } 824 } 825 } 826 827 void AlternativeFinder::visit( LogicalExpr *logicalExpr ) { 828 AlternativeFinder firstFinder( indexer, env ); 829 firstFinder.findWithAdjustment( logicalExpr->get_arg1() ); 830 for ( AltList::const_iterator first = firstFinder.alternatives.begin(); first != firstFinder.alternatives.end(); ++first ) { 831 AlternativeFinder secondFinder( indexer, first->env ); 832 secondFinder.findWithAdjustment( logicalExpr->get_arg2() ); 833 for ( AltList::const_iterator second = secondFinder.alternatives.begin(); second != secondFinder.alternatives.end(); ++second ) { 834 LogicalExpr *newExpr = new LogicalExpr( first->expr->clone(), second->expr->clone(), logicalExpr->get_isAnd() ); 835 alternatives.push_back( Alternative( newExpr, second->env, first->cost + second->cost ) ); 836 } 837 } 838 } 839 840 void AlternativeFinder::visit( ConditionalExpr *conditionalExpr ) { 841 AlternativeFinder firstFinder( indexer, env ); 842 firstFinder.findWithAdjustment( conditionalExpr->get_arg1() ); 843 for ( AltList::const_iterator first = firstFinder.alternatives.begin(); first != firstFinder.alternatives.end(); ++first ) { 844 AlternativeFinder secondFinder( indexer, first->env ); 845 secondFinder.findWithAdjustment( conditionalExpr->get_arg2() ); 846 for ( AltList::const_iterator second = secondFinder.alternatives.begin(); second != secondFinder.alternatives.end(); ++second ) { 847 AlternativeFinder thirdFinder( indexer, second->env ); 848 thirdFinder.findWithAdjustment( conditionalExpr->get_arg3() ); 849 for ( AltList::const_iterator third = thirdFinder.alternatives.begin(); third != thirdFinder.alternatives.end(); ++third ) { 850 OpenVarSet openVars; 851 AssertionSet needAssertions, haveAssertions; 852 Alternative newAlt( 0, third->env, first->cost + second->cost + third->cost ); 853 std::list< Type* > commonTypes; 854 if ( unifyList( second->expr->get_results().begin(), second->expr->get_results().end(), third->expr->get_results().begin(), third->expr->get_results().end(), newAlt.env, needAssertions, haveAssertions, openVars, indexer, commonTypes ) ) { 855 ConditionalExpr *newExpr = new ConditionalExpr( first->expr->clone(), second->expr->clone(), third->expr->clone() ); 856 std::list< Type* >::const_iterator original = second->expr->get_results().begin(); 857 std::list< Type* >::const_iterator commonType = commonTypes.begin(); 858 for ( ; original != second->expr->get_results().end() && commonType != commonTypes.end(); ++original, ++commonType ) { 859 if ( *commonType ) { 860 newExpr->get_results().push_back( *commonType ); 861 } else { 862 newExpr->get_results().push_back( (*original)->clone() ); 863 } 864 } 865 newAlt.expr = newExpr; 866 inferParameters( needAssertions, haveAssertions, newAlt, openVars, back_inserter( alternatives ) ); 867 } 868 } 869 } 870 } 871 } 872 873 void AlternativeFinder::visit( CommaExpr *commaExpr ) { 874 TypeEnvironment newEnv( env ); 875 Expression *newFirstArg = resolveInVoidContext( commaExpr->get_arg1(), indexer, newEnv ); 876 AlternativeFinder secondFinder( indexer, newEnv ); 877 secondFinder.findWithAdjustment( commaExpr->get_arg2() ); 878 for ( AltList::const_iterator alt = secondFinder.alternatives.begin(); alt != secondFinder.alternatives.end(); ++alt ) { 879 alternatives.push_back( Alternative( new CommaExpr( newFirstArg->clone(), alt->expr->clone() ), alt->env, alt->cost ) ); 880 } 881 delete newFirstArg; 882 } 883 884 void AlternativeFinder::visit( TupleExpr *tupleExpr ) { 885 std::list< AlternativeFinder > subExprAlternatives; 886 findSubExprs( tupleExpr->get_exprs().begin(), tupleExpr->get_exprs().end(), back_inserter( subExprAlternatives ) ); 887 std::list< AltList > possibilities; 888 combos( subExprAlternatives.begin(), subExprAlternatives.end(), back_inserter( possibilities ) ); 889 for ( std::list< AltList >::const_iterator i = possibilities.begin(); i != possibilities.end(); ++i ) { 890 TupleExpr *newExpr = new TupleExpr; 891 makeExprList( *i, newExpr->get_exprs() ); 892 for ( std::list< Expression* >::const_iterator resultExpr = newExpr->get_exprs().begin(); resultExpr != newExpr->get_exprs().end(); ++resultExpr ) { 893 for ( std::list< Type* >::const_iterator resultType = (*resultExpr)->get_results().begin(); resultType != (*resultExpr)->get_results().end(); ++resultType ) { 894 newExpr->get_results().push_back( (*resultType)->clone() ); 895 } 896 } 897 898 TypeEnvironment compositeEnv; 899 simpleCombineEnvironments( i->begin(), i->end(), compositeEnv ); 900 alternatives.push_back( Alternative( newExpr, compositeEnv, sumCost( *i ) ) ); 901 } 902 } 797 if ( typesCompatibleIgnoreQualifiers( argType, function->get_parameters().front()->get_type(), indexer, env ) ) { 798 alternatives.push_back( Alternative( new AttrExpr( new VariableExpr( funcDecl ), argType->clone() ), env, Cost::zero ) ); 799 for ( std::list< DeclarationWithType* >::iterator i = function->get_returnVals().begin(); i != function->get_returnVals().end(); ++i ) { 800 alternatives.back().expr->get_results().push_back( (*i)->get_type()->clone() ); 801 } // for 802 } // if 803 } 804 805 void AlternativeFinder::visit( AttrExpr *attrExpr ) { 806 // assume no 'pointer-to-attribute' 807 NameExpr *nameExpr = dynamic_cast< NameExpr* >( attrExpr->get_attr() ); 808 assert( nameExpr ); 809 std::list< DeclarationWithType* > attrList; 810 indexer.lookupId( nameExpr->get_name(), attrList ); 811 if ( attrExpr->get_isType() || attrExpr->get_expr() ) { 812 for ( std::list< DeclarationWithType* >::iterator i = attrList.begin(); i != attrList.end(); ++i ) { 813 // check if the type is function 814 if ( FunctionType *function = dynamic_cast< FunctionType* >( (*i)->get_type() ) ) { 815 // assume exactly one parameter 816 if ( function->get_parameters().size() == 1 ) { 817 if ( attrExpr->get_isType() ) { 818 resolveAttr( *i, function, attrExpr->get_type(), env ); 819 } else { 820 AlternativeFinder finder( indexer, env ); 821 finder.find( attrExpr->get_expr() ); 822 for ( AltList::iterator choice = finder.alternatives.begin(); choice != finder.alternatives.end(); ++choice ) { 823 if ( choice->expr->get_results().size() == 1 ) { 824 resolveAttr(*i, function, choice->expr->get_results().front(), choice->env ); 825 } // fi 826 } // for 827 } // if 828 } // if 829 } // if 830 } // for 831 } else { 832 for ( std::list< DeclarationWithType* >::iterator i = attrList.begin(); i != attrList.end(); ++i ) { 833 VariableExpr newExpr( *i ); 834 alternatives.push_back( Alternative( newExpr.clone(), env, Cost() ) ); 835 renameTypes( alternatives.back().expr ); 836 } // for 837 } // if 838 } 839 840 void AlternativeFinder::visit( LogicalExpr *logicalExpr ) { 841 AlternativeFinder firstFinder( indexer, env ); 842 firstFinder.findWithAdjustment( logicalExpr->get_arg1() ); 843 for ( AltList::const_iterator first = firstFinder.alternatives.begin(); first != firstFinder.alternatives.end(); ++first ) { 844 AlternativeFinder secondFinder( indexer, first->env ); 845 secondFinder.findWithAdjustment( logicalExpr->get_arg2() ); 846 for ( AltList::const_iterator second = secondFinder.alternatives.begin(); second != secondFinder.alternatives.end(); ++second ) { 847 LogicalExpr *newExpr = new LogicalExpr( first->expr->clone(), second->expr->clone(), logicalExpr->get_isAnd() ); 848 alternatives.push_back( Alternative( newExpr, second->env, first->cost + second->cost ) ); 849 } 850 } 851 } 852 853 void AlternativeFinder::visit( ConditionalExpr *conditionalExpr ) { 854 AlternativeFinder firstFinder( indexer, env ); 855 firstFinder.findWithAdjustment( conditionalExpr->get_arg1() ); 856 for ( AltList::const_iterator first = firstFinder.alternatives.begin(); first != firstFinder.alternatives.end(); ++first ) { 857 AlternativeFinder secondFinder( indexer, first->env ); 858 secondFinder.findWithAdjustment( conditionalExpr->get_arg2() ); 859 for ( AltList::const_iterator second = secondFinder.alternatives.begin(); second != secondFinder.alternatives.end(); ++second ) { 860 AlternativeFinder thirdFinder( indexer, second->env ); 861 thirdFinder.findWithAdjustment( conditionalExpr->get_arg3() ); 862 for ( AltList::const_iterator third = thirdFinder.alternatives.begin(); third != thirdFinder.alternatives.end(); ++third ) { 863 OpenVarSet openVars; 864 AssertionSet needAssertions, haveAssertions; 865 Alternative newAlt( 0, third->env, first->cost + second->cost + third->cost ); 866 std::list< Type* > commonTypes; 867 if ( unifyList( second->expr->get_results().begin(), second->expr->get_results().end(), third->expr->get_results().begin(), third->expr->get_results().end(), newAlt.env, needAssertions, haveAssertions, openVars, indexer, commonTypes ) ) { 868 ConditionalExpr *newExpr = new ConditionalExpr( first->expr->clone(), second->expr->clone(), third->expr->clone() ); 869 std::list< Type* >::const_iterator original = second->expr->get_results().begin(); 870 std::list< Type* >::const_iterator commonType = commonTypes.begin(); 871 for ( ; original != second->expr->get_results().end() && commonType != commonTypes.end(); ++original, ++commonType ) { 872 if ( *commonType ) { 873 newExpr->get_results().push_back( *commonType ); 874 } else { 875 newExpr->get_results().push_back( (*original)->clone() ); 876 } // if 877 } // for 878 newAlt.expr = newExpr; 879 inferParameters( needAssertions, haveAssertions, newAlt, openVars, back_inserter( alternatives ) ); 880 } // if 881 } // for 882 } // for 883 } // for 884 } 885 886 void AlternativeFinder::visit( CommaExpr *commaExpr ) { 887 TypeEnvironment newEnv( env ); 888 Expression *newFirstArg = resolveInVoidContext( commaExpr->get_arg1(), indexer, newEnv ); 889 AlternativeFinder secondFinder( indexer, newEnv ); 890 secondFinder.findWithAdjustment( commaExpr->get_arg2() ); 891 for ( AltList::const_iterator alt = secondFinder.alternatives.begin(); alt != secondFinder.alternatives.end(); ++alt ) { 892 alternatives.push_back( Alternative( new CommaExpr( newFirstArg->clone(), alt->expr->clone() ), alt->env, alt->cost ) ); 893 } // for 894 delete newFirstArg; 895 } 896 897 void AlternativeFinder::visit( TupleExpr *tupleExpr ) { 898 std::list< AlternativeFinder > subExprAlternatives; 899 findSubExprs( tupleExpr->get_exprs().begin(), tupleExpr->get_exprs().end(), back_inserter( subExprAlternatives ) ); 900 std::list< AltList > possibilities; 901 combos( subExprAlternatives.begin(), subExprAlternatives.end(), back_inserter( possibilities ) ); 902 for ( std::list< AltList >::const_iterator i = possibilities.begin(); i != possibilities.end(); ++i ) { 903 TupleExpr *newExpr = new TupleExpr; 904 makeExprList( *i, newExpr->get_exprs() ); 905 for ( std::list< Expression* >::const_iterator resultExpr = newExpr->get_exprs().begin(); resultExpr != newExpr->get_exprs().end(); ++resultExpr ) { 906 for ( std::list< Type* >::const_iterator resultType = (*resultExpr)->get_results().begin(); resultType != (*resultExpr)->get_results().end(); ++resultType ) { 907 newExpr->get_results().push_back( (*resultType)->clone() ); 908 } // for 909 } // for 910 911 TypeEnvironment compositeEnv; 912 simpleCombineEnvironments( i->begin(), i->end(), compositeEnv ); 913 alternatives.push_back( Alternative( newExpr, compositeEnv, sumCost( *i ) ) ); 914 } // for 915 } 903 916 } // namespace ResolvExpr 917 918 // Local Variables: // 919 // tab-width: 4 // 920 // mode: c++ // 921 // compile-command: "make install" // 922 // End: // -
translator/ResolvExpr/AlternativeFinder.h
rb87a5ed ra32b204 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 // AlternativeFinder.h -- 8 // 9 // Author : Richard C. Bilson 10 // Created On : Sat May 16 23:56:12 2015 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sat May 16 23:58:43 2015 13 // Update Count : 2 14 // 15 1 16 #ifndef ALTERNATIVEFINDER_H 2 17 #define ALTERNATIVEFINDER_H … … 11 26 12 27 namespace ResolvExpr { 13 class AlternativeFinder : public Visitor { 14 public: 15 AlternativeFinder( const SymTab::Indexer &indexer, const TypeEnvironment &env ); 16 void find( Expression *expr, bool adjust = false ); 17 void findWithAdjustment( Expression *expr ); 18 AltList &get_alternatives() { return alternatives; } 19 20 // make this look like an STL container so that we can apply generic algorithms 21 typedef Alternative value_type; 22 typedef AltList::iterator iterator; 23 typedef AltList::const_iterator const_iterator; 24 AltList::iterator begin() { return alternatives.begin(); } 25 AltList::iterator end() { return alternatives.end(); } 26 AltList::const_iterator begin() const { return alternatives.begin(); } 27 AltList::const_iterator end() const { return alternatives.end(); } 28 29 const SymTab::Indexer &get_indexer() const { return indexer; } 30 const TypeEnvironment &get_environ() const { return env; } 31 private: 32 virtual void visit( ApplicationExpr *applicationExpr ); 33 virtual void visit( UntypedExpr *untypedExpr ); 34 virtual void visit( AddressExpr *addressExpr ); 35 virtual void visit( CastExpr *castExpr ); 36 virtual void visit( UntypedMemberExpr *memberExpr ); 37 virtual void visit( MemberExpr *memberExpr ); 38 virtual void visit( NameExpr *variableExpr ); 39 virtual void visit( VariableExpr *variableExpr ); 40 virtual void visit( ConstantExpr *constantExpr ); 41 virtual void visit( SizeofExpr *sizeofExpr ); 42 virtual void visit( AttrExpr *attrExpr ); 43 virtual void visit( LogicalExpr *logicalExpr ); 44 virtual void visit( ConditionalExpr *conditionalExpr ); 45 virtual void visit( CommaExpr *commaExpr ); 46 virtual void visit( TupleExpr *tupleExpr ); 47 public: // xxx - temporary hack - should make Tuples::TupleAssignment a friend 48 template< typename InputIterator, typename OutputIterator > 49 void findSubExprs( InputIterator begin, InputIterator end, OutputIterator out ); 28 class AlternativeFinder : public Visitor { 29 public: 30 AlternativeFinder( const SymTab::Indexer &indexer, const TypeEnvironment &env ); 31 void find( Expression *expr, bool adjust = false ); 32 void findWithAdjustment( Expression *expr ); 33 AltList &get_alternatives() { return alternatives; } 50 34 51 private: 52 template< typename StructOrUnionType > void addAggMembers( StructOrUnionType *aggInst, Expression *expr, const Cost &newCost, const std::string &name );53 bool instantiateFunction( std::list< DeclarationWithType* >& formals, /*const*/ AltList &actuals, bool isVarArgs, OpenVarSet& openVars, TypeEnvironment &resultEnv, AssertionSet &resultNeed, AssertionSet &resultHave );54 template< typename OutputIterator >55 void makeFunctionAlternatives( const Alternative &func, FunctionType *funcType, AltList &actualAlt, OutputIterator out );56 template< typename OutputIterator >57 void inferParameters( const AssertionSet &need, AssertionSet &have, const Alternative &newAlt, OpenVarSet &openVars, OutputIterator out );58 void resolveAttr( DeclarationWithType *funcDecl, FunctionType *function, Type *argType, const TypeEnvironment &env );35 // make this look like an STL container so that we can apply generic algorithms 36 typedef Alternative value_type; 37 typedef AltList::iterator iterator; 38 typedef AltList::const_iterator const_iterator; 39 AltList::iterator begin() { return alternatives.begin(); } 40 AltList::iterator end() { return alternatives.end(); } 41 AltList::const_iterator begin() const { return alternatives.begin(); } 42 AltList::const_iterator end() const { return alternatives.end(); } 59 43 60 const SymTab::Indexer &indexer; 61 AltList alternatives; 62 const TypeEnvironment &env; 63 }; // AlternativeFinder 44 const SymTab::Indexer &get_indexer() const { return indexer; } 45 const TypeEnvironment &get_environ() const { return env; } 46 private: 47 virtual void visit( ApplicationExpr *applicationExpr ); 48 virtual void visit( UntypedExpr *untypedExpr ); 49 virtual void visit( AddressExpr *addressExpr ); 50 virtual void visit( CastExpr *castExpr ); 51 virtual void visit( UntypedMemberExpr *memberExpr ); 52 virtual void visit( MemberExpr *memberExpr ); 53 virtual void visit( NameExpr *variableExpr ); 54 virtual void visit( VariableExpr *variableExpr ); 55 virtual void visit( ConstantExpr *constantExpr ); 56 virtual void visit( SizeofExpr *sizeofExpr ); 57 virtual void visit( AttrExpr *attrExpr ); 58 virtual void visit( LogicalExpr *logicalExpr ); 59 virtual void visit( ConditionalExpr *conditionalExpr ); 60 virtual void visit( CommaExpr *commaExpr ); 61 virtual void visit( TupleExpr *tupleExpr ); 62 public: // xxx - temporary hack - should make Tuples::TupleAssignment a friend 63 template< typename InputIterator, typename OutputIterator > 64 void findSubExprs( InputIterator begin, InputIterator end, OutputIterator out ); 64 65 65 Expression *resolveInVoidContext( Expression *expr, const SymTab::Indexer &indexer, TypeEnvironment &env ); 66 private: 67 template< typename StructOrUnionType > void addAggMembers( StructOrUnionType *aggInst, Expression *expr, const Cost &newCost, const std::string &name ); 68 bool instantiateFunction( std::list< DeclarationWithType* >& formals, /*const*/ AltList &actuals, bool isVarArgs, OpenVarSet& openVars, TypeEnvironment &resultEnv, AssertionSet &resultNeed, AssertionSet &resultHave ); 69 template< typename OutputIterator > 70 void makeFunctionAlternatives( const Alternative &func, FunctionType *funcType, AltList &actualAlt, OutputIterator out ); 71 template< typename OutputIterator > 72 void inferParameters( const AssertionSet &need, AssertionSet &have, const Alternative &newAlt, OpenVarSet &openVars, OutputIterator out ); 73 void resolveAttr( DeclarationWithType *funcDecl, FunctionType *function, Type *argType, const TypeEnvironment &env ); 74 75 const SymTab::Indexer &indexer; 76 AltList alternatives; 77 const TypeEnvironment &env; 78 }; // AlternativeFinder 79 80 Expression *resolveInVoidContext( Expression *expr, const SymTab::Indexer &indexer, TypeEnvironment &env ); 66 81 } // namespace ResolvExpr 67 82 68 83 #endif // ALTERNATIVEFINDER_H 84 85 // Local Variables: // 86 // tab-width: 4 // 87 // mode: c++ // 88 // compile-command: "make install" // 89 // End: // -
translator/ResolvExpr/AlternativePrinter.cc
rb87a5ed ra32b204 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 // AlternativePrinter.cc -- 8 // 9 // Author : Richard C. Bilson 10 // Created On : Sun May 17 06:53:19 2015 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sun May 17 06:55:05 2015 13 // Update Count : 2 14 // 15 1 16 #include "AlternativePrinter.h" 2 17 #include "AlternativeFinder.h" … … 8 23 9 24 namespace ResolvExpr { 10 25 AlternativePrinter::AlternativePrinter( std::ostream &os ) : SymTab::Indexer( false ), os( os ) {} 11 26 12 13 TypeEnvironment env;14 AlternativeFinder finder( *this, env );15 finder.findWithAdjustment( exprStmt->get_expr() );16 int count = 1;17 os << "There are " << finder.get_alternatives().size() << " alternatives" << std::endl;18 for ( AltList::const_iterator i = finder.get_alternatives().begin(); i != finder.get_alternatives().end(); ++i ) {19 20 21 22 23 } // for24 27 void AlternativePrinter::visit( ExprStmt *exprStmt ) { 28 TypeEnvironment env; 29 AlternativeFinder finder( *this, env ); 30 finder.findWithAdjustment( exprStmt->get_expr() ); 31 int count = 1; 32 os << "There are " << finder.get_alternatives().size() << " alternatives" << std::endl; 33 for ( AltList::const_iterator i = finder.get_alternatives().begin(); i != finder.get_alternatives().end(); ++i ) { 34 os << "Alternative " << count++ << " ==============" << std::endl; 35 printAll( i->expr->get_results(), os ); 36 // i->print( os ); 37 os << std::endl; 38 } // for 39 } // AlternativePrinter::visit 25 40 } // namespace ResolvExpr 41 42 // Local Variables: // 43 // tab-width: 4 // 44 // mode: c++ // 45 // compile-command: "make install" // 46 // End: // -
translator/ResolvExpr/AlternativePrinter.h
rb87a5ed ra32b204 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 // AlternativePrinter.h -- 8 // 9 // Author : Richard C. Bilson 10 // Created On : Sun May 17 06:55:43 2015 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sun May 17 06:57:12 2015 13 // Update Count : 3 14 // 15 1 16 #ifndef ALTERNATIVEPRINTER_H 2 17 #define ALTERNATIVEPRINTER_H … … 8 23 9 24 namespace ResolvExpr { 10 11 12 AlternativePrinter( std::ostream &os );13 virtual void visit(ExprStmt *exprStmt);14 15 std::ostream &os;16 25 class AlternativePrinter : public SymTab::Indexer { 26 public: 27 AlternativePrinter( std::ostream &os ); 28 virtual void visit( ExprStmt *exprStmt ); 29 private: 30 std::ostream &os; 31 }; 17 32 } // namespace ResolvExpr 18 33 19 34 #endif // ALTERNATIVEPRINTER_H 35 36 // Local Variables: // 37 // tab-width: 4 // 38 // mode: c++ // 39 // compile-command: "make install" // 40 // End: // -
translator/ResolvExpr/CastCost.cc
rb87a5ed ra32b204 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 // CastCost.cc -- 8 // 9 // Author : Richard C. Bilson 10 // Created On : Sun May 17 06:57:43 2015 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sun May 17 06:59:10 2015 13 // Update Count : 2 14 // 15 1 16 #include "typeops.h" 2 17 #include "Cost.h" … … 8 23 9 24 namespace ResolvExpr { 10 11 12 CastCost( Type *dest, const SymTab::Indexer &indexer, const TypeEnvironment &env );25 class CastCost : public ConversionCost { 26 public: 27 CastCost( Type *dest, const SymTab::Indexer &indexer, const TypeEnvironment &env ); 13 28 14 virtual void visit( BasicType *basicType );15 virtual void visit( PointerType *pointerType );16 29 virtual void visit( BasicType *basicType ); 30 virtual void visit( PointerType *pointerType ); 31 }; 17 32 18 Cost castCost( Type *src, Type *dest, const SymTab::Indexer &indexer, const TypeEnvironment &env ) { 19 if ( TypeInstType *destAsTypeInst = dynamic_cast< TypeInstType* >( dest ) ) { 20 EqvClass eqvClass; 21 NamedTypeDecl *namedType; 22 if ( env.lookup( destAsTypeInst->get_name(), eqvClass ) ) { 23 return castCost( src, eqvClass.type, indexer, env ); 24 } else if ( ( namedType = indexer.lookupType( destAsTypeInst->get_name() ) ) ) { 25 TypeDecl *type = dynamic_cast< TypeDecl* >( namedType ); 26 // all typedefs should be gone by this point 27 assert( type ); 28 if ( type->get_base() ) { 29 return castCost( src, type->get_base(), indexer, env ) + Cost( 0, 0, 1 ); 33 Cost castCost( Type *src, Type *dest, const SymTab::Indexer &indexer, const TypeEnvironment &env ) { 34 if ( TypeInstType *destAsTypeInst = dynamic_cast< TypeInstType* >( dest ) ) { 35 EqvClass eqvClass; 36 NamedTypeDecl *namedType; 37 if ( env.lookup( destAsTypeInst->get_name(), eqvClass ) ) { 38 return castCost( src, eqvClass.type, indexer, env ); 39 } else if ( ( namedType = indexer.lookupType( destAsTypeInst->get_name() ) ) ) { 40 TypeDecl *type = dynamic_cast< TypeDecl* >( namedType ); 41 // all typedefs should be gone by this point 42 assert( type ); 43 if ( type->get_base() ) { 44 return castCost( src, type->get_base(), indexer, env ) + Cost( 0, 0, 1 ); 45 } // if 46 } // if 30 47 } // if 31 } // if 32 } // if 33 if ( typesCompatibleIgnoreQualifiers( src, dest, indexer, env ) ) { 34 return Cost( 0, 0, 0 ); 35 } else if ( dynamic_cast< VoidType* >( dest ) ) { 36 return Cost( 0, 0, 1 ); 37 } else { 38 CastCost converter( dest, indexer, env ); 39 src->accept( converter ); 40 if ( converter.get_cost() == Cost::infinity ) { 41 return Cost::infinity; 42 } else { 43 return converter.get_cost() + Cost( 0, 0, 0 ); 44 } // if 45 } // if 46 } 48 if ( typesCompatibleIgnoreQualifiers( src, dest, indexer, env ) ) { 49 return Cost( 0, 0, 0 ); 50 } else if ( dynamic_cast< VoidType* >( dest ) ) { 51 return Cost( 0, 0, 1 ); 52 } else { 53 CastCost converter( dest, indexer, env ); 54 src->accept( converter ); 55 if ( converter.get_cost() == Cost::infinity ) { 56 return Cost::infinity; 57 } else { 58 return converter.get_cost() + Cost( 0, 0, 0 ); 59 } // if 60 } // if 61 } 47 62 48 49 : ConversionCost( dest, indexer, env ) {50 63 CastCost::CastCost( Type *dest, const SymTab::Indexer &indexer, const TypeEnvironment &env ) 64 : ConversionCost( dest, indexer, env ) { 65 } 51 66 52 53 if ( dynamic_cast< PointerType* >( dest ) ) {54 55 } else {56 57 } // if58 67 void CastCost::visit( BasicType *basicType ) { 68 if ( dynamic_cast< PointerType* >( dest ) ) { 69 cost = Cost( 1, 0, 0 ); 70 } else { 71 ConversionCost::visit( basicType ); 72 } // if 73 } 59 74 60 void CastCost::visit( PointerType *pointerType ) { 61 if ( PointerType *destAsPtr = dynamic_cast< PointerType* >( dest ) ) { 62 if ( pointerType->get_qualifiers() <= destAsPtr->get_qualifiers() && typesCompatibleIgnoreQualifiers( pointerType->get_base(), destAsPtr->get_base(), indexer, env ) ) { 63 cost = Cost( 0, 0, 1 ); 64 } else if ( BasicType *destAsBasic = dynamic_cast< BasicType* >( dest ) ) { 65 if ( destAsBasic->isInteger() ) { 66 cost = Cost( 1, 0, 0 ); 67 } 68 } else { 69 TypeEnvironment newEnv( env ); 70 newEnv.add( pointerType->get_forall() ); 71 newEnv.add( pointerType->get_base()->get_forall() ); 72 int assignResult = ptrsCastable( pointerType->get_base(), destAsPtr->get_base(), newEnv, indexer ); 73 if ( assignResult > 0 ) { 74 cost = Cost( 0, 0, 1 ); 75 } else if ( assignResult < 0 ) { 76 cost = Cost( 1, 0, 0 ); 75 void CastCost::visit( PointerType *pointerType ) { 76 if ( PointerType *destAsPtr = dynamic_cast< PointerType* >( dest ) ) { 77 if ( pointerType->get_qualifiers() <= destAsPtr->get_qualifiers() && typesCompatibleIgnoreQualifiers( pointerType->get_base(), destAsPtr->get_base(), indexer, env ) ) { 78 cost = Cost( 0, 0, 1 ); 79 } else if ( BasicType *destAsBasic = dynamic_cast< BasicType* >( dest ) ) { 80 if ( destAsBasic->isInteger() ) { 81 cost = Cost( 1, 0, 0 ); 82 } // if 83 } else { 84 TypeEnvironment newEnv( env ); 85 newEnv.add( pointerType->get_forall() ); 86 newEnv.add( pointerType->get_base()->get_forall() ); 87 int assignResult = ptrsCastable( pointerType->get_base(), destAsPtr->get_base(), newEnv, indexer ); 88 if ( assignResult > 0 ) { 89 cost = Cost( 0, 0, 1 ); 90 } else if ( assignResult < 0 ) { 91 cost = Cost( 1, 0, 0 ); 92 } // if 93 } // if 77 94 } // if 78 } // if 79 } // if 80 } 95 } 81 96 } // namespace ResolvExpr 97 98 // Local Variables: // 99 // tab-width: 4 // 100 // mode: c++ // 101 // compile-command: "make install" // 102 // End: // -
translator/ResolvExpr/CommonType.cc
rb87a5ed ra32b204 1 /* 2 * This file is part of the Cforall project 3 * 4 * $Id: CommonType.cc,v 1.6 2005/08/29 20:14:15 rcbilson Exp $ 5 * 6 */ 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 // CommonType.cc -- 8 // 9 // Author : Richard C. Bilson 10 // Created On : Sun May 17 06:59:27 2015 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sun May 17 07:04:50 2015 13 // Update Count : 2 14 // 7 15 8 16 #include "typeops.h" … … 14 22 15 23 namespace ResolvExpr { 16 17 class CommonType : public Visitor 18 { 19 public: 20 CommonType( Type *type2, bool widenFirst, bool widenSecond, const SymTab::Indexer &indexer, TypeEnvironment &env, const OpenVarSet &openVars ); 21 22 Type *get_result() const { return result; } 23 24 private: 25 virtual void visit( VoidType *voidType ); 26 virtual void visit( BasicType *basicType ); 27 virtual void visit( PointerType *pointerType ); 28 virtual void visit( ArrayType *arrayType ); 29 virtual void visit( FunctionType *functionType ); 30 virtual void visit( StructInstType *aggregateUseType ); 31 virtual void visit( UnionInstType *aggregateUseType ); 32 virtual void visit( EnumInstType *aggregateUseType ); 33 virtual void visit( ContextInstType *aggregateUseType ); 34 virtual void visit( TypeInstType *aggregateUseType ); 35 virtual void visit( TupleType *tupleType ); 36 37 template< typename RefType > void handleRefType( RefType *inst, Type *other ); 38 39 Type *result; 40 Type *type2; // inherited 41 bool widenFirst, widenSecond; 42 const SymTab::Indexer &indexer; 43 TypeEnvironment &env; 44 const OpenVarSet &openVars; 45 }; 46 47 Type * 48 commonType( Type *type1, Type *type2, bool widenFirst, bool widenSecond, const SymTab::Indexer &indexer, TypeEnvironment &env, const OpenVarSet &openVars ) 49 { 50 CommonType visitor( type2, widenFirst, widenSecond, indexer, env, openVars ); 51 type1->accept( visitor ); 52 Type *result = visitor.get_result(); 53 if( !result ) { 54 if( widenSecond ) { 55 TypeInstType *inst = dynamic_cast< TypeInstType* >( type2 ); 56 if( inst ) { 57 NamedTypeDecl *nt = indexer.lookupType( inst->get_name() ); 58 if( nt ) { 59 TypeDecl *type = dynamic_cast< TypeDecl* >( nt ); 60 assert( type ); 61 if( type->get_base() ) { 62 Type::Qualifiers tq1 = type1->get_qualifiers(), tq2 = type2->get_qualifiers(); 63 AssertionSet have, need; 64 OpenVarSet newOpen( openVars ); 65 type1->get_qualifiers() = Type::Qualifiers(); 66 type->get_base()->get_qualifiers() = tq1; 67 if( unifyExact( type1, type->get_base(), env, have, need, newOpen, indexer ) ) { 68 result = type1->clone(); 69 result->get_qualifiers() = tq1 + tq2; 70 } 71 type1->get_qualifiers() = tq1; 72 type->get_base()->get_qualifiers() = Type::Qualifiers(); 73 } 74 } 75 } 76 } 77 } 24 class CommonType : public Visitor { 25 public: 26 CommonType( Type *type2, bool widenFirst, bool widenSecond, const SymTab::Indexer &indexer, TypeEnvironment &env, const OpenVarSet &openVars ); 27 Type *get_result() const { return result; } 28 private: 29 virtual void visit( VoidType *voidType ); 30 virtual void visit( BasicType *basicType ); 31 virtual void visit( PointerType *pointerType ); 32 virtual void visit( ArrayType *arrayType ); 33 virtual void visit( FunctionType *functionType ); 34 virtual void visit( StructInstType *aggregateUseType ); 35 virtual void visit( UnionInstType *aggregateUseType ); 36 virtual void visit( EnumInstType *aggregateUseType ); 37 virtual void visit( ContextInstType *aggregateUseType ); 38 virtual void visit( TypeInstType *aggregateUseType ); 39 virtual void visit( TupleType *tupleType ); 40 41 template< typename RefType > void handleRefType( RefType *inst, Type *other ); 42 43 Type *result; 44 Type *type2; // inherited 45 bool widenFirst, widenSecond; 46 const SymTab::Indexer &indexer; 47 TypeEnvironment &env; 48 const OpenVarSet &openVars; 49 }; 50 51 Type *commonType( Type *type1, Type *type2, bool widenFirst, bool widenSecond, const SymTab::Indexer &indexer, TypeEnvironment &env, const OpenVarSet &openVars ) { 52 CommonType visitor( type2, widenFirst, widenSecond, indexer, env, openVars ); 53 type1->accept( visitor ); 54 Type *result = visitor.get_result(); 55 if ( ! result ) { 56 if ( widenSecond ) { 57 TypeInstType *inst = dynamic_cast< TypeInstType* >( type2 ); 58 if ( inst ) { 59 NamedTypeDecl *nt = indexer.lookupType( inst->get_name() ); 60 if ( nt ) { 61 TypeDecl *type = dynamic_cast< TypeDecl* >( nt ); 62 assert( type ); 63 if ( type->get_base() ) { 64 Type::Qualifiers tq1 = type1->get_qualifiers(), tq2 = type2->get_qualifiers(); 65 AssertionSet have, need; 66 OpenVarSet newOpen( openVars ); 67 type1->get_qualifiers() = Type::Qualifiers(); 68 type->get_base()->get_qualifiers() = tq1; 69 if ( unifyExact( type1, type->get_base(), env, have, need, newOpen, indexer ) ) { 70 result = type1->clone(); 71 result->get_qualifiers() = tq1 + tq2; 72 } // if 73 type1->get_qualifiers() = tq1; 74 type->get_base()->get_qualifiers() = Type::Qualifiers(); 75 } // if 76 } // if 77 } // if 78 } // if 79 } // if 78 80 #ifdef DEBUG 79 80 81 82 83 if( result ) {84 85 86 87 88 } 89 81 std::cout << "============= commonType" << std::endl << "type1 is "; 82 type1->print( std::cout ); 83 std::cout << " type2 is "; 84 type2->print( std::cout ); 85 if ( result ) { 86 std::cout << " common type is "; 87 result->print( std::cout ); 88 } else { 89 std::cout << " no common type"; 90 } // if 91 std::cout << std::endl; 90 92 #endif 91 92 }93 94 static const BasicType::Kind combinedType[ BasicType::NUMBER_OF_BASIC_TYPES ][ BasicType::NUMBER_OF_BASIC_TYPES ] =95 {93 return result; 94 } 95 96 static const BasicType::Kind combinedType[ BasicType::NUMBER_OF_BASIC_TYPES ][ BasicType::NUMBER_OF_BASIC_TYPES ] = 97 { 96 98 /* Bool Char SignedChar UnsignedChar ShortSignedInt ShortUnsignedInt SignedInt UnsignedInt LongSignedInt LongUnsignedInt LongLongSignedInt LongLongUnsignedInt Float Double LongDouble FloatComplex DoubleComplex LongDoubleComplex FloatImaginary DoubleImaginary LongDoubleImaginary */ 97 /* Bool */ { BasicType::Bool, BasicType::Char, BasicType::SignedChar, BasicType::UnsignedChar, BasicType::ShortSignedInt, BasicType::ShortUnsignedInt, BasicType::SignedInt, BasicType::UnsignedInt, BasicType::LongSignedInt, BasicType::LongUnsignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 98 /* Char */ { BasicType::Char, BasicType::Char, BasicType::UnsignedChar, BasicType::UnsignedChar, BasicType::ShortSignedInt, BasicType::ShortUnsignedInt, BasicType::SignedInt, BasicType::UnsignedInt, BasicType::LongSignedInt, BasicType::LongUnsignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 99 /* SignedChar */ { BasicType::SignedChar, BasicType::UnsignedChar, BasicType::SignedChar, BasicType::UnsignedChar, BasicType::ShortSignedInt, BasicType::ShortUnsignedInt, BasicType::SignedInt, BasicType::UnsignedInt, BasicType::LongSignedInt, BasicType::LongUnsignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 100 /* UnsignedChar */ { BasicType::UnsignedChar, BasicType::UnsignedChar, BasicType::UnsignedChar, BasicType::UnsignedChar, BasicType::ShortSignedInt, BasicType::ShortUnsignedInt, BasicType::SignedInt, BasicType::UnsignedInt, BasicType::LongSignedInt, BasicType::LongUnsignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 101 /* ShortSignedInt */ { BasicType::ShortSignedInt, BasicType::ShortSignedInt, BasicType::ShortSignedInt, BasicType::ShortSignedInt, BasicType::ShortSignedInt, BasicType::ShortUnsignedInt, BasicType::SignedInt, BasicType::UnsignedInt, BasicType::LongSignedInt, BasicType::LongUnsignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 102 /* ShortUnsignedInt */ { BasicType::ShortUnsignedInt, BasicType::ShortUnsignedInt, BasicType::ShortUnsignedInt, BasicType::ShortUnsignedInt, BasicType::ShortUnsignedInt, BasicType::ShortUnsignedInt, BasicType::SignedInt, BasicType::UnsignedInt, BasicType::LongSignedInt, BasicType::LongUnsignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 103 /* SignedInt */ { BasicType::SignedInt, BasicType::SignedInt, BasicType::SignedInt, BasicType::SignedInt, BasicType::SignedInt, BasicType::SignedInt, BasicType::SignedInt, BasicType::UnsignedInt, BasicType::LongSignedInt, BasicType::LongUnsignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 104 /* UnsignedInt */ { BasicType::UnsignedInt, BasicType::UnsignedInt, BasicType::UnsignedInt, BasicType::UnsignedInt, BasicType::UnsignedInt, BasicType::UnsignedInt, BasicType::UnsignedInt, BasicType::UnsignedInt, BasicType::LongUnsignedInt, BasicType::LongUnsignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 105 /* LongSignedInt */ { BasicType::LongSignedInt, BasicType::LongSignedInt, BasicType::LongSignedInt, BasicType::LongSignedInt, BasicType::LongSignedInt, BasicType::LongSignedInt, BasicType::LongSignedInt, BasicType::LongUnsignedInt, BasicType::LongSignedInt, BasicType::LongUnsignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 106 /* LongUnsignedInt */ { BasicType::LongUnsignedInt, BasicType::LongUnsignedInt, BasicType::LongUnsignedInt, BasicType::LongUnsignedInt, BasicType::LongUnsignedInt, BasicType::LongUnsignedInt, BasicType::LongUnsignedInt, BasicType::LongUnsignedInt, BasicType::LongUnsignedInt, BasicType::LongUnsignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 107 /* LongLongSignedInt */ { BasicType::LongLongSignedInt, BasicType::LongLongSignedInt, BasicType::LongLongSignedInt, BasicType::LongLongSignedInt, BasicType::LongLongSignedInt, BasicType::LongLongSignedInt, BasicType::LongLongSignedInt, BasicType::LongLongSignedInt, BasicType::LongLongSignedInt, BasicType::LongLongSignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 108 /* LongLongUnsignedInt */ { BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 109 /* Float */ { BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 110 /* Double */ { BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::LongDouble, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 111 /* LongDouble */ { BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex }, 112 /* FloatComplex */ { BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 113 /* DoubleComplex */ { BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 114 /* LongDoubleComplex */ { BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex }, 115 /* FloatImaginary */ { BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatImaginary, BasicType::DoubleImaginary, BasicType::LongDoubleImaginary }, 116 /* DoubleImaginary */ { BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::DoubleImaginary, BasicType::DoubleImaginary, BasicType::LongDoubleImaginary }, 117 /* LongDoubleImaginary */ { BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleImaginary, BasicType::LongDoubleImaginary, BasicType::LongDoubleImaginary } 118 }; 119 120 CommonType::CommonType( Type *type2, bool widenFirst, bool widenSecond, const SymTab::Indexer &indexer, TypeEnvironment &env, const OpenVarSet &openVars ) 121 : result( 0 ), type2( type2 ), widenFirst( widenFirst ), widenSecond( widenSecond ), indexer( indexer ), env( env ), openVars( openVars ) 122 { 123 } 124 125 void 126 CommonType::visit( VoidType *voidType ) 127 { 128 } 129 130 void 131 CommonType::visit( BasicType *basicType ) 132 { 133 if( BasicType *otherBasic = dynamic_cast< BasicType* >( type2 ) ) { 134 BasicType::Kind newType = combinedType[ basicType->get_kind() ][ otherBasic->get_kind() ]; 135 if( ( ( newType == basicType->get_kind() && basicType->get_qualifiers() >= otherBasic->get_qualifiers() ) || widenFirst ) && ( ( newType == otherBasic->get_kind() && basicType->get_qualifiers() <= otherBasic->get_qualifiers() ) || widenSecond ) ) { 136 result = new BasicType( basicType->get_qualifiers() + otherBasic->get_qualifiers(), newType ); 137 } 138 } 139 } 140 141 void 142 CommonType::visit( PointerType *pointerType ) 143 { 144 if( PointerType *otherPointer = dynamic_cast< PointerType* >( type2 ) ) { 145 if( widenFirst && dynamic_cast< VoidType* >( otherPointer->get_base() ) ) { 146 result = otherPointer->clone(); 147 result->get_qualifiers() += pointerType->get_qualifiers(); 148 } else if( widenSecond && dynamic_cast< VoidType* >( pointerType->get_base() ) ) { 149 result = pointerType->clone(); 150 result->get_qualifiers() += otherPointer->get_qualifiers(); 151 } else if( ( pointerType->get_base()->get_qualifiers() >= otherPointer->get_base()->get_qualifiers() || widenFirst ) 152 && ( pointerType->get_base()->get_qualifiers() <= otherPointer->get_base()->get_qualifiers() || widenSecond ) ) { 153 Type::Qualifiers tq1 = pointerType->get_base()->get_qualifiers(), tq2 = otherPointer->get_base()->get_qualifiers(); 154 pointerType->get_base()->get_qualifiers() = Type::Qualifiers(); 155 otherPointer->get_base()->get_qualifiers() = Type::Qualifiers(); 156 AssertionSet have, need; 157 OpenVarSet newOpen( openVars ); 158 if( unifyExact( pointerType->get_base(), otherPointer->get_base(), env, have, need, newOpen, indexer ) ) { 159 if( tq1 < tq2 ) { 160 result = pointerType->clone(); 161 } else { 162 result = otherPointer->clone(); 163 } 164 result->get_qualifiers() = tq1 + tq2; 165 } else { 166 /// std::cout << "place for ptr-to-type" << std::endl; 167 } 168 pointerType->get_base()->get_qualifiers() = tq1; 169 otherPointer->get_base()->get_qualifiers() = tq2; 170 } 171 } 172 } 173 174 void 175 CommonType::visit( ArrayType *arrayType ) 176 { 177 } 178 179 void 180 CommonType::visit( FunctionType *functionType ) 181 { 182 } 183 184 template< typename RefType > void 185 CommonType::handleRefType( RefType *inst, Type *other ) 186 { 187 } 188 189 void 190 CommonType::visit( StructInstType *aggregateUseType ) 191 { 192 } 193 194 void 195 CommonType::visit( UnionInstType *aggregateUseType ) 196 { 197 } 198 199 void 200 CommonType::visit( EnumInstType *aggregateUseType ) 201 { 202 } 203 204 void 205 CommonType::visit( ContextInstType *aggregateUseType ) 206 { 207 } 208 209 void 210 CommonType::visit( TypeInstType *inst ) 211 { 212 if( widenFirst ) { 213 NamedTypeDecl *nt = indexer.lookupType( inst->get_name() ); 214 if( nt ) { 215 TypeDecl *type = dynamic_cast< TypeDecl* >( nt ); 216 assert( type ); 217 if( type->get_base() ) { 218 Type::Qualifiers tq1 = inst->get_qualifiers(), tq2 = type2->get_qualifiers(); 219 AssertionSet have, need; 220 OpenVarSet newOpen( openVars ); 221 type2->get_qualifiers() = Type::Qualifiers(); 222 type->get_base()->get_qualifiers() = tq1; 223 if( unifyExact( type->get_base(), type2, env, have, need, newOpen, indexer ) ) { 224 result = type2->clone(); 225 result->get_qualifiers() = tq1 + tq2; 226 } 227 type2->get_qualifiers() = tq2; 228 type->get_base()->get_qualifiers() = Type::Qualifiers(); 229 } 230 } 231 } 232 } 233 234 void 235 CommonType::visit( TupleType *tupleType ) 236 { 237 } 238 99 /* Bool */ { BasicType::Bool, BasicType::Char, BasicType::SignedChar, BasicType::UnsignedChar, BasicType::ShortSignedInt, BasicType::ShortUnsignedInt, BasicType::SignedInt, BasicType::UnsignedInt, BasicType::LongSignedInt, BasicType::LongUnsignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 100 /* Char */ { BasicType::Char, BasicType::Char, BasicType::UnsignedChar, BasicType::UnsignedChar, BasicType::ShortSignedInt, BasicType::ShortUnsignedInt, BasicType::SignedInt, BasicType::UnsignedInt, BasicType::LongSignedInt, BasicType::LongUnsignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 101 /* SignedChar */ { BasicType::SignedChar, BasicType::UnsignedChar, BasicType::SignedChar, BasicType::UnsignedChar, BasicType::ShortSignedInt, BasicType::ShortUnsignedInt, BasicType::SignedInt, BasicType::UnsignedInt, BasicType::LongSignedInt, BasicType::LongUnsignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 102 /* UnsignedChar */ { BasicType::UnsignedChar, BasicType::UnsignedChar, BasicType::UnsignedChar, BasicType::UnsignedChar, BasicType::ShortSignedInt, BasicType::ShortUnsignedInt, BasicType::SignedInt, BasicType::UnsignedInt, BasicType::LongSignedInt, BasicType::LongUnsignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 103 /* ShortSignedInt */ { BasicType::ShortSignedInt, BasicType::ShortSignedInt, BasicType::ShortSignedInt, BasicType::ShortSignedInt, BasicType::ShortSignedInt, BasicType::ShortUnsignedInt, BasicType::SignedInt, BasicType::UnsignedInt, BasicType::LongSignedInt, BasicType::LongUnsignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 104 /* ShortUnsignedInt */ { BasicType::ShortUnsignedInt, BasicType::ShortUnsignedInt, BasicType::ShortUnsignedInt, BasicType::ShortUnsignedInt, BasicType::ShortUnsignedInt, BasicType::ShortUnsignedInt, BasicType::SignedInt, BasicType::UnsignedInt, BasicType::LongSignedInt, BasicType::LongUnsignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 105 /* SignedInt */ { BasicType::SignedInt, BasicType::SignedInt, BasicType::SignedInt, BasicType::SignedInt, BasicType::SignedInt, BasicType::SignedInt, BasicType::SignedInt, BasicType::UnsignedInt, BasicType::LongSignedInt, BasicType::LongUnsignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 106 /* UnsignedInt */ { BasicType::UnsignedInt, BasicType::UnsignedInt, BasicType::UnsignedInt, BasicType::UnsignedInt, BasicType::UnsignedInt, BasicType::UnsignedInt, BasicType::UnsignedInt, BasicType::UnsignedInt, BasicType::LongUnsignedInt, BasicType::LongUnsignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 107 /* LongSignedInt */ { BasicType::LongSignedInt, BasicType::LongSignedInt, BasicType::LongSignedInt, BasicType::LongSignedInt, BasicType::LongSignedInt, BasicType::LongSignedInt, BasicType::LongSignedInt, BasicType::LongUnsignedInt, BasicType::LongSignedInt, BasicType::LongUnsignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 108 /* LongUnsignedInt */ { BasicType::LongUnsignedInt, BasicType::LongUnsignedInt, BasicType::LongUnsignedInt, BasicType::LongUnsignedInt, BasicType::LongUnsignedInt, BasicType::LongUnsignedInt, BasicType::LongUnsignedInt, BasicType::LongUnsignedInt, BasicType::LongUnsignedInt, BasicType::LongUnsignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 109 /* LongLongSignedInt */ { BasicType::LongLongSignedInt, BasicType::LongLongSignedInt, BasicType::LongLongSignedInt, BasicType::LongLongSignedInt, BasicType::LongLongSignedInt, BasicType::LongLongSignedInt, BasicType::LongLongSignedInt, BasicType::LongLongSignedInt, BasicType::LongLongSignedInt, BasicType::LongLongSignedInt, BasicType::LongLongSignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 110 /* LongLongUnsignedInt */ { BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::LongLongUnsignedInt, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 111 /* Float */ { BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Float, BasicType::Double, BasicType::LongDouble, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 112 /* Double */ { BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::Double, BasicType::LongDouble, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 113 /* LongDouble */ { BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDouble, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex }, 114 /* FloatComplex */ { BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 115 /* DoubleComplex */ { BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex }, 116 /* LongDoubleComplex */ { BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex }, 117 /* FloatImaginary */ { BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::FloatImaginary, BasicType::DoubleImaginary, BasicType::LongDoubleImaginary }, 118 /* DoubleImaginary */ { BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::DoubleComplex, BasicType::DoubleComplex, BasicType::LongDoubleComplex, BasicType::DoubleImaginary, BasicType::DoubleImaginary, BasicType::LongDoubleImaginary }, 119 /* LongDoubleImaginary */ { BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleComplex, BasicType::LongDoubleImaginary, BasicType::LongDoubleImaginary, BasicType::LongDoubleImaginary } 120 }; 121 122 CommonType::CommonType( Type *type2, bool widenFirst, bool widenSecond, const SymTab::Indexer &indexer, TypeEnvironment &env, const OpenVarSet &openVars ) 123 : result( 0 ), type2( type2 ), widenFirst( widenFirst ), widenSecond( widenSecond ), indexer( indexer ), env( env ), openVars( openVars ) { 124 } 125 126 void CommonType::visit( VoidType *voidType ) { 127 } 128 129 void CommonType::visit( BasicType *basicType ) { 130 if ( BasicType *otherBasic = dynamic_cast< BasicType* >( type2 ) ) { 131 BasicType::Kind newType = combinedType[ basicType->get_kind() ][ otherBasic->get_kind() ]; 132 if ( ( ( newType == basicType->get_kind() && basicType->get_qualifiers() >= otherBasic->get_qualifiers() ) || widenFirst ) && ( ( newType == otherBasic->get_kind() && basicType->get_qualifiers() <= otherBasic->get_qualifiers() ) || widenSecond ) ) { 133 result = new BasicType( basicType->get_qualifiers() + otherBasic->get_qualifiers(), newType ); 134 } // if 135 } // if 136 } 137 138 void CommonType::visit( PointerType *pointerType ) { 139 if ( PointerType *otherPointer = dynamic_cast< PointerType* >( type2 ) ) { 140 if ( widenFirst && dynamic_cast< VoidType* >( otherPointer->get_base() ) ) { 141 result = otherPointer->clone(); 142 result->get_qualifiers() += pointerType->get_qualifiers(); 143 } else if ( widenSecond && dynamic_cast< VoidType* >( pointerType->get_base() ) ) { 144 result = pointerType->clone(); 145 result->get_qualifiers() += otherPointer->get_qualifiers(); 146 } else if ( ( pointerType->get_base()->get_qualifiers() >= otherPointer->get_base()->get_qualifiers() || widenFirst ) 147 && ( pointerType->get_base()->get_qualifiers() <= otherPointer->get_base()->get_qualifiers() || widenSecond ) ) { 148 Type::Qualifiers tq1 = pointerType->get_base()->get_qualifiers(), tq2 = otherPointer->get_base()->get_qualifiers(); 149 pointerType->get_base()->get_qualifiers() = Type::Qualifiers(); 150 otherPointer->get_base()->get_qualifiers() = Type::Qualifiers(); 151 AssertionSet have, need; 152 OpenVarSet newOpen( openVars ); 153 if ( unifyExact( pointerType->get_base(), otherPointer->get_base(), env, have, need, newOpen, indexer ) ) { 154 if ( tq1 < tq2 ) { 155 result = pointerType->clone(); 156 } else { 157 result = otherPointer->clone(); 158 } // if 159 result->get_qualifiers() = tq1 + tq2; 160 } else { 161 /// std::cout << "place for ptr-to-type" << std::endl; 162 } // if 163 pointerType->get_base()->get_qualifiers() = tq1; 164 otherPointer->get_base()->get_qualifiers() = tq2; 165 } // if 166 } // if 167 } 168 169 void CommonType::visit( ArrayType *arrayType ) { 170 } 171 172 void CommonType::visit( FunctionType *functionType ) { 173 } 174 175 template< typename RefType > void CommonType::handleRefType( RefType *inst, Type *other ) { 176 } 177 178 void CommonType::visit( StructInstType *aggregateUseType ) { 179 } 180 181 void CommonType::visit( UnionInstType *aggregateUseType ) { 182 } 183 184 void CommonType::visit( EnumInstType *aggregateUseType ) { 185 } 186 187 void CommonType::visit( ContextInstType *aggregateUseType ) { 188 } 189 190 void CommonType::visit( TypeInstType *inst ) { 191 if ( widenFirst ) { 192 NamedTypeDecl *nt = indexer.lookupType( inst->get_name() ); 193 if ( nt ) { 194 TypeDecl *type = dynamic_cast< TypeDecl* >( nt ); 195 assert( type ); 196 if ( type->get_base() ) { 197 Type::Qualifiers tq1 = inst->get_qualifiers(), tq2 = type2->get_qualifiers(); 198 AssertionSet have, need; 199 OpenVarSet newOpen( openVars ); 200 type2->get_qualifiers() = Type::Qualifiers(); 201 type->get_base()->get_qualifiers() = tq1; 202 if ( unifyExact( type->get_base(), type2, env, have, need, newOpen, indexer ) ) { 203 result = type2->clone(); 204 result->get_qualifiers() = tq1 + tq2; 205 } // if 206 type2->get_qualifiers() = tq2; 207 type->get_base()->get_qualifiers() = Type::Qualifiers(); 208 } // if 209 } // if 210 } // if 211 } 212 213 void CommonType::visit( TupleType *tupleType ) { 214 } 239 215 } // namespace ResolvExpr 216 217 // Local Variables: // 218 // tab-width: 4 // 219 // mode: c++ // 220 // compile-command: "make install" // 221 // End: // -
translator/ResolvExpr/ConversionCost.cc
rb87a5ed ra32b204 1 /* 2 * This file is part of the Cforall project 3 * 4 * $Id: ConversionCost.cc,v 1.11 2005/08/29 20:14:15 rcbilson Exp $ 5 * 6 */ 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 // ConversionCost.cc -- 8 // 9 // Author : Richard C. Bilson 10 // Created On : Sun May 17 07:06:19 2015 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sun May 17 07:22:19 2015 13 // Update Count : 4 14 // 7 15 8 16 #include "ConversionCost.h" … … 12 20 #include "SymTab/Indexer.h" 13 21 14 15 22 namespace ResolvExpr { 16 17 const Cost Cost::zero = Cost( 0, 0, 0 ); 18 const Cost Cost::infinity = Cost( -1, -1, -1 ); 19 20 Cost 21 conversionCost( Type *src, Type *dest, const SymTab::Indexer &indexer, const TypeEnvironment &env ) 22 { 23 if( TypeInstType *destAsTypeInst = dynamic_cast< TypeInstType* >( dest ) ) { 24 EqvClass eqvClass; 25 NamedTypeDecl *namedType; 23 const Cost Cost::zero = Cost( 0, 0, 0 ); 24 const Cost Cost::infinity = Cost( -1, -1, -1 ); 25 26 Cost conversionCost( Type *src, Type *dest, const SymTab::Indexer &indexer, const TypeEnvironment &env ) { 27 if ( TypeInstType *destAsTypeInst = dynamic_cast< TypeInstType* >( dest ) ) { 28 EqvClass eqvClass; 29 NamedTypeDecl *namedType; 26 30 /// std::cout << "type inst " << destAsTypeInst->get_name(); 27 if( env.lookup( destAsTypeInst->get_name(), eqvClass ) ) {28 29 } else if( ( namedType = indexer.lookupType( destAsTypeInst->get_name() ) ) ) {31 if ( env.lookup( destAsTypeInst->get_name(), eqvClass ) ) { 32 return conversionCost( src, eqvClass.type, indexer, env ); 33 } else if ( ( namedType = indexer.lookupType( destAsTypeInst->get_name() ) ) ) { 30 34 /// std::cout << " found" << std::endl; 31 32 33 34 if( type->get_base() ) {35 36 } 37 } 35 TypeDecl *type = dynamic_cast< TypeDecl* >( namedType ); 36 // all typedefs should be gone by this point 37 assert( type ); 38 if ( type->get_base() ) { 39 return conversionCost( src, type->get_base(), indexer, env ) + Cost( 0, 0, 1 ); 40 } // if 41 } // if 38 42 /// std::cout << " not found" << std::endl; 39 } 43 } // if 40 44 /// std::cout << "src is "; 41 45 /// src->print( std::cout ); … … 44 48 /// std::cout << std::endl << "env is" << std::endl; 45 49 /// env.print( std::cout, 8 ); 46 if( typesCompatibleIgnoreQualifiers( src, dest, indexer, env ) ) {50 if ( typesCompatibleIgnoreQualifiers( src, dest, indexer, env ) ) { 47 51 /// std::cout << "compatible!" << std::endl; 48 return Cost( 0, 0, 0 ); 49 } else if( dynamic_cast< VoidType* >( dest ) ) { 50 return Cost( 0, 0, 1 ); 51 } else { 52 ConversionCost converter( dest, indexer, env ); 53 src->accept( converter ); 54 if( converter.get_cost() == Cost::infinity ) { 55 return Cost::infinity; 56 } else { 57 return converter.get_cost() + Cost( 0, 0, 0 ); 58 } 59 } 60 } 61 62 ConversionCost::ConversionCost( Type *dest, const SymTab::Indexer &indexer, const TypeEnvironment &env ) 63 : dest( dest ), indexer( indexer ), cost( Cost::infinity ), env( env ) 64 { 65 } 52 return Cost( 0, 0, 0 ); 53 } else if ( dynamic_cast< VoidType* >( dest ) ) { 54 return Cost( 0, 0, 1 ); 55 } else { 56 ConversionCost converter( dest, indexer, env ); 57 src->accept( converter ); 58 if ( converter.get_cost() == Cost::infinity ) { 59 return Cost::infinity; 60 } else { 61 return converter.get_cost() + Cost( 0, 0, 0 ); 62 } // if 63 } // if 64 } 65 66 ConversionCost::ConversionCost( Type *dest, const SymTab::Indexer &indexer, const TypeEnvironment &env ) 67 : dest( dest ), indexer( indexer ), cost( Cost::infinity ), env( env ) { 68 } 66 69 67 70 /* 68 Old69 ===70 71 72 73