Changeset 4f748c5 for src/GenPoly
- Timestamp:
- Nov 2, 2017, 11:45:10 AM (8 years ago)
- Branches:
- ADT, aaron-thesis, arm-eh, ast-experimental, cleanup-dtors, deferred_resn, demangler, enum, forall-pointer-decay, jacob/cs343-translation, jenkins-sandbox, master, new-ast, new-ast-unique-expr, new-env, no_list, persistent-indexer, pthread-emulation, qualifiedEnum, resolv-new, with_gc
- Children:
- 6de43b6
- Parents:
- b1e68d03 (diff), fde89cf6 (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the(diff)links above to see all the changes relative to each parent. - Location:
- src/GenPoly
- Files:
-
- 4 edited
-
Box.cc (modified) (6 diffs)
-
InstantiateGeneric.cc (modified) (1 diff)
-
ScrubTyVars.cc (modified) (1 diff)
-
Specialize.cc (modified) (6 diffs)
Legend:
- Unmodified
- Added
- Removed
-
src/GenPoly/Box.cc
rb1e68d03 r4f748c5 734 734 Type * newType = param->clone(); 735 735 if ( env ) env->apply( newType ); 736 ObjectDecl *newObj = new ObjectDecl( tempNamer.newName(), Type::StorageClasses(), LinkageSpec::C, 0, newType, 0);736 ObjectDecl *newObj = ObjectDecl::newObject( tempNamer.newName(), newType, nullptr ); 737 737 newObj->get_type()->get_qualifiers() = Type::Qualifiers(); // TODO: is this right??? 738 738 stmtsToAddBefore.push_back( new DeclStmt( noLabels, newObj ) ); … … 745 745 } 746 746 747 // find instances of polymorphic type parameters 748 struct PolyFinder { 749 const TyVarMap * tyVars = nullptr; 750 bool found = false; 751 752 void previsit( TypeInstType * t ) { 753 if ( isPolyType( t, *tyVars ) ) { 754 found = true; 755 } 756 } 757 }; 758 759 // true if there is an instance of a polymorphic type parameter in t 760 bool hasPolymorphism( Type * t, const TyVarMap &tyVars ) { 761 PassVisitor<PolyFinder> finder; 762 finder.pass.tyVars = &tyVars; 763 maybeAccept( t, finder ); 764 return finder.pass.found; 765 } 766 747 767 /// cast parameters to polymorphic functions so that types are replaced with 748 768 /// void * if they are type parameters in the formal type. 749 769 /// this gets rid of warnings from gcc. 750 770 void addCast( Expression *&actual, Type *formal, const TyVarMap &tyVars ) { 751 if ( getFunctionType( formal ) ) { 771 // type contains polymorphism, but isn't exactly a polytype, in which case it 772 // has some real actual type (e.g. unsigned int) and casting to void * is wrong 773 if ( hasPolymorphism( formal, tyVars ) && ! isPolyType( formal, tyVars ) ) { 752 774 Type * newType = formal->clone(); 753 775 newType = ScrubTyVars::scrub( newType, tyVars ); … … 757 779 758 780 void Pass1::boxParams( ApplicationExpr *appExpr, FunctionType *function, std::list< Expression *>::iterator &arg, const TyVarMap &exprTyVars ) { 759 for ( std::list< DeclarationWithType *>::const_iterator param = function->get_parameters().begin(); param != function-> get_parameters().end(); ++param, ++arg ) {760 assertf( arg != appExpr-> get_args().end(), "boxParams: missing argument for param %s to %s in %s", toString( *param ).c_str(), toString( function ).c_str(), toString( appExpr ).c_str() );781 for ( std::list< DeclarationWithType *>::const_iterator param = function->get_parameters().begin(); param != function->parameters.end(); ++param, ++arg ) { 782 assertf( arg != appExpr->args.end(), "boxParams: missing argument for param %s to %s in %s", toString( *param ).c_str(), toString( function ).c_str(), toString( appExpr ).c_str() ); 761 783 addCast( *arg, (*param)->get_type(), exprTyVars ); 762 784 boxParam( (*param)->get_type(), *arg, exprTyVars ); … … 767 789 std::list< Expression *>::iterator cur = arg; 768 790 for ( Type::ForallList::iterator tyVar = functionType->get_forall().begin(); tyVar != functionType->get_forall().end(); ++tyVar ) { 769 for ( std::list< DeclarationWithType *>::iterator assert = (*tyVar)-> get_assertions().begin(); assert != (*tyVar)->get_assertions().end(); ++assert ) {791 for ( std::list< DeclarationWithType *>::iterator assert = (*tyVar)->assertions.begin(); assert != (*tyVar)->assertions.end(); ++assert ) { 770 792 InferredParams::const_iterator inferParam = appExpr->get_inferParams().find( (*assert)->get_uniqueId() ); 771 if ( inferParam == appExpr->get_inferParams().end() ) { 772 std::cerr << "looking for assertion: " << (*assert) << std::endl << appExpr << std::endl; 773 } 774 assertf( inferParam != appExpr->get_inferParams().end(), "NOTE: Explicit casts of polymorphic functions to compatible monomorphic functions are currently unsupported" ); 793 assertf( inferParam != appExpr->get_inferParams().end(), "addInferredParams missing inferred parameter: %s in: %s", toString( *assert ).c_str(), toString( appExpr ).c_str() ); 775 794 Expression *newExpr = inferParam->second.expr->clone(); 776 795 addCast( newExpr, (*assert)->get_type(), tyVars ); … … 782 801 783 802 void makeRetParm( FunctionType *funcType ) { 784 DeclarationWithType *retParm = funcType-> get_returnVals().front();803 DeclarationWithType *retParm = funcType->returnVals.front(); 785 804 786 805 // make a new parameter that is a pointer to the type of the old return value … … 795 814 // actually make the adapter type 796 815 FunctionType *adapter = adaptee->clone(); 797 // if ( ! adapter->get_returnVals().empty() && isPolyType( adapter->get_returnVals().front()->get_type(), tyVars ) ) {798 816 if ( isDynRet( adapter, tyVars ) ) { 799 817 makeRetParm( adapter ); -
src/GenPoly/InstantiateGeneric.cc
rb1e68d03 r4f748c5 238 238 assertf( false, "Ttype parameters are not currently allowed as parameters to generic types." ); 239 239 break; 240 case TypeDecl::Any:241 assertf( false, " otype parameters handled by baseParam->isComplete()." );240 default: 241 assertf( false, "Unhandled type parameter kind" ); 242 242 break; 243 243 } -
src/GenPoly/ScrubTyVars.cc
rb1e68d03 r4f748c5 40 40 if ( tyVar != tyVars->end() ) { 41 41 switch ( tyVar->second.kind ) { 42 case TypeDecl::Any:43 42 case TypeDecl::Dtype: 44 43 case TypeDecl::Ttype: -
src/GenPoly/Specialize.cc
rb1e68d03 r4f748c5 45 45 struct Specialize final : public WithTypeSubstitution, public WithStmtsToAdd, public WithVisitorRef<Specialize> { 46 46 Expression * postmutate( ApplicationExpr *applicationExpr ); 47 Expression * postmutate( AddressExpr *castExpr );48 47 Expression * postmutate( CastExpr *castExpr ); 49 48 50 49 void handleExplicitParams( ApplicationExpr *appExpr ); 51 50 Expression * createThunkFunction( FunctionType *funType, Expression *actual, InferredParams *inferParams ); 52 Expression * doSpecialization( Type *formalType, Expression *actual, InferredParams *inferParams = nullptr);51 Expression * doSpecialization( Type *formalType, Expression *actual, InferredParams *inferParams ); 53 52 54 53 std::string paramPrefix = "_p"; … … 67 66 if ( ! boundType ) continue; 68 67 if ( TypeInstType *typeInst = dynamic_cast< TypeInstType* >( boundType ) ) { 68 // bound to another type variable 69 69 if ( closedVars.find( typeInst->get_name() ) == closedVars.end() ) { 70 // bound to a closed variable => must specialize 70 71 return true; 71 72 } // if 72 73 } else { 74 // variable is bound to a concrete type => must specialize 73 75 return true; 74 76 } // if 75 77 } // for 78 // none of the type variables are bound 76 79 return false; 77 80 } else { 81 // no env 78 82 return false; 79 83 } // if … … 131 135 if ( functionParameterSize( fftype ) != functionParameterSize( aftype ) ) return false; 132 136 // tuple-parameter sizes are the same, but actual parameter sizes differ - must tuple specialize 133 if ( fftype-> get_parameters().size() != aftype->get_parameters().size() ) return true;137 if ( fftype->parameters.size() != aftype->parameters.size() ) return true; 134 138 // total parameter size can be the same, while individual parameters can have different structure 135 for ( auto params : group_iterate( fftype-> get_parameters(), aftype->get_parameters()) ) {139 for ( auto params : group_iterate( fftype->parameters, aftype->parameters ) ) { 136 140 DeclarationWithType * formal = std::get<0>(params); 137 141 DeclarationWithType * actual = std::get<1>(params); … … 150 154 if ( needsSpecialization( formalType, actual->get_result(), env ) ) { 151 155 if ( FunctionType *funType = getFunctionType( formalType ) ) { 152 ApplicationExpr *appExpr; 153 VariableExpr *varExpr; 154 if ( ( appExpr = dynamic_cast<ApplicationExpr*>( actual ) ) ) { 156 if ( ApplicationExpr * appExpr = dynamic_cast<ApplicationExpr*>( actual ) ) { 155 157 return createThunkFunction( funType, appExpr->get_function(), inferParams ); 156 } else if ( ( varExpr = dynamic_cast<VariableExpr*>( actual )) ) {158 } else if ( VariableExpr * varExpr = dynamic_cast<VariableExpr*>( actual ) ) { 157 159 return createThunkFunction( funType, varExpr, inferParams ); 158 160 } else { … … 323 325 } 324 326 325 Expression * Specialize::postmutate( AddressExpr *addrExpr ) {326 assert( addrExpr->result );327 addrExpr->set_arg( doSpecialization( addrExpr->result, addrExpr->arg ) );328 return addrExpr;329 }330 331 327 Expression * Specialize::postmutate( CastExpr *castExpr ) { 332 328 if ( castExpr->result->isVoid() ) { … … 334 330 return castExpr; 335 331 } 336 Expression *specialized = doSpecialization( castExpr->result, castExpr->arg );332 Expression *specialized = doSpecialization( castExpr->result, castExpr->arg, &castExpr->inferParams ); 337 333 if ( specialized != castExpr->arg ) { 338 334 // assume here that the specialization incorporates the cast
Note:
See TracChangeset
for help on using the changeset viewer.