Changes in src/GenPoly/GenPoly.cc [3e5dd913:d76c588]
- File:
-
- 1 edited
-
src/GenPoly/GenPoly.cc (modified) (9 diffs)
Legend:
- Unmodified
- Added
- Removed
-
src/GenPoly/GenPoly.cc
r3e5dd913 rd76c588 46 46 } 47 47 48 bool hasPolyParams( const std::vector<ast::ptr<ast::Expr>> & params, const ast::TypeSubstitution * env) {49 for (auto ¶m : params) {50 auto paramType = param.strict_as<ast::TypeExpr>();51 if (isPolyType(paramType->type, env)) return true;52 }53 return false;54 }55 56 48 /// Checks a parameter list for polymorphic parameters from tyVars; will substitute according to env if present 57 49 bool hasPolyParams( std::list< Expression* >& params, const TyVarMap &tyVars, const TypeSubstitution *env ) { … … 64 56 } 65 57 66 bool hasPolyParams( const std::vector<ast::ptr<ast::Expr>> & params, const TyVarMap & tyVars, const ast::TypeSubstitution * env) {67 for (auto ¶m : params) {68 auto paramType = param.strict_as<ast::TypeExpr>();69 if (isPolyType(paramType->type, tyVars, env)) return true;70 }71 return false;72 }73 74 58 /// Checks a parameter list for dynamic-layout parameters from tyVars; will substitute according to env if present 75 59 bool hasDynParams( std::list< Expression* >& params, const TyVarMap &tyVars, const TypeSubstitution *env ) { … … 108 92 Type *newType = env->lookup( typeInst->get_name() ); 109 93 if ( newType ) return newType; 110 }111 return type;112 }113 114 const ast::Type * replaceTypeInst(const ast::Type * type, const ast::TypeSubstitution * env) {115 if (!env) return type;116 if (auto typeInst = dynamic_cast<const ast::TypeInstType*> (type)) {117 auto newType = env->lookup(typeInst);118 if (newType) return newType;119 94 } 120 95 return type; … … 136 111 } 137 112 138 const ast::Type * isPolyType(const ast::Type * type, const ast::TypeSubstitution * env) {139 type = replaceTypeInst( type, env );140 141 if ( dynamic_cast< const ast::TypeInstType * >( type ) ) {142 return type;143 } else if ( auto arrayType = dynamic_cast< const ast::ArrayType * >( type ) ) {144 return isPolyType( arrayType->base, env );145 } else if ( auto structType = dynamic_cast< const ast::StructInstType* >( type ) ) {146 if ( hasPolyParams( structType->params, env ) ) return type;147 } else if ( auto unionType = dynamic_cast< const ast::UnionInstType* >( type ) ) {148 if ( hasPolyParams( unionType->params, env ) ) return type;149 }150 return 0;151 }152 153 113 Type *isPolyType( Type *type, const TyVarMap &tyVars, const TypeSubstitution *env ) { 154 114 type = replaceTypeInst( type, env ); … … 166 126 } 167 127 return 0; 168 }169 170 const ast::Type * isPolyType(const ast::Type * type, const TyVarMap & tyVars, const ast::TypeSubstitution * env) {171 type = replaceTypeInst( type, env );172 173 if ( auto typeInst = dynamic_cast< const ast::TypeInstType * >( type ) ) {174 return tyVars.find(typeInst->typeString()) != tyVars.end() ? type : nullptr;175 } else if ( auto arrayType = dynamic_cast< const ast::ArrayType * >( type ) ) {176 return isPolyType( arrayType->base, env );177 } else if ( auto structType = dynamic_cast< const ast::StructInstType* >( type ) ) {178 if ( hasPolyParams( structType->params, env ) ) return type;179 } else if ( auto unionType = dynamic_cast< const ast::UnionInstType* >( type ) ) {180 if ( hasPolyParams( unionType->params, env ) ) return type;181 }182 return nullptr;183 128 } 184 129 … … 504 449 } 505 450 506 namespace {507 // temporary hack to avoid re-implementing anything related to TyVarMap508 // does this work? these two structs have identical definitions.509 inline TypeDecl::Data convData(const ast::TypeDecl::Data & data) {510 return *reinterpret_cast<const TypeDecl::Data *>(&data);511 }512 }513 514 451 bool needsBoxing( Type * param, Type * arg, const TyVarMap &exprTyVars, const TypeSubstitution * env ) { 515 452 // is parameter is not polymorphic, don't need to box … … 522 459 } 523 460 524 bool needsBoxing( const ast::Type * param, const ast::Type * arg, const TyVarMap &exprTyVars, const ast::TypeSubstitution * env) {525 // is parameter is not polymorphic, don't need to box526 if ( ! isPolyType( param, exprTyVars ) ) return false;527 ast::ptr<ast::Type> newType = arg;528 if ( env ) env->apply( newType );529 // if the argument's type is polymorphic, we don't need to box again!530 return ! isPolyType( newType );531 }532 533 461 bool needsBoxing( Type * param, Type * arg, ApplicationExpr * appExpr, const TypeSubstitution * env ) { 534 462 FunctionType * function = getFunctionType( appExpr->function->result ); … … 539 467 } 540 468 541 bool needsBoxing( const ast::Type * param, const ast::Type * arg, const ast::ApplicationExpr * appExpr, const ast::TypeSubstitution * env) {542 const ast::FunctionType * function = getFunctionType(appExpr->func->result);543 assertf( function, "ApplicationExpr has non-function type: %s", toString( appExpr->func->result ).c_str() );544 TyVarMap exprTyVars(TypeDecl::Data{});545 makeTyVarMap(function, exprTyVars);546 return needsBoxing(param, arg, exprTyVars, env);547 548 }549 550 469 void addToTyVarMap( TypeDecl * tyVar, TyVarMap &tyVarMap ) { 551 tyVarMap.insert( tyVar->name, TypeDecl::Data{ tyVar } ); 552 } 553 554 void addToTyVarMap( const ast::TypeInstType * tyVar, TyVarMap & tyVarMap) { 555 tyVarMap.insert(tyVar->typeString(), convData(ast::TypeDecl::Data{tyVar->base})); 470 // xxx - should this actually be insert? 471 tyVarMap[ tyVar->get_name() ] = TypeDecl::Data{ tyVar }; 556 472 } 557 473 … … 563 479 if ( PointerType *pointer = dynamic_cast< PointerType* >( type ) ) { 564 480 makeTyVarMap( pointer->get_base(), tyVarMap ); 565 }566 }567 568 void makeTyVarMap(const ast::Type * type, TyVarMap & tyVarMap) {569 if (auto ptype = dynamic_cast<const ast::FunctionType *>(type)) {570 for (auto & tyVar : ptype->forall) {571 assert (tyVar);572 addToTyVarMap(tyVar, tyVarMap);573 }574 }575 if (auto pointer = dynamic_cast<const ast::PointerType *>(type)) {576 makeTyVarMap(pointer->base, tyVarMap);577 481 } 578 482 }
Note:
See TracChangeset
for help on using the changeset viewer.