Changeset cc3528f
- Timestamp:
- May 13, 2016, 2:49:38 PM (7 years ago)
- Branches:
- ADT, aaron-thesis, arm-eh, 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, with_gc
- Children:
- 189243c
- Parents:
- 346a0bf
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
src/GenPoly/Box.cc
r346a0bf rcc3528f 9 9 // Author : Richard C. Bilson 10 10 // Created On : Mon May 18 07:44:20 2015 11 // Last Modified By : Peter A. Buhr12 // Last Modified On : Fri Feb 5 16:45:07201613 // Update Count : 2 8611 // Last Modified By : Rob Schluntz 12 // Last Modified On : Fri May 13 13:59:22 2016 13 // Update Count : 295 14 14 // 15 15 … … 133 133 Value *lookup( Key *key, const std::list< TypeExpr* >& params ) const { 134 134 TypeList typeList( params ); 135 135 136 136 // scan scopes for matches to the key 137 137 for ( typename InnerMap::const_iterator insts = instantiations.find( key ); insts != instantiations.end(); insts = instantiations.findNext( insts, key ) ) { … … 160 160 virtual Declaration *mutate( UnionDecl *unionDecl ); 161 161 }; 162 162 163 163 /// Replaces polymorphic return types with out-parameters, replaces calls to polymorphic functions with adapter calls as needed, and adds appropriate type variables to the function call 164 164 class Pass1 : public PolyMutator { … … 208 208 ResolvExpr::TypeMap< DeclarationWithType > scopedAssignOps; ///< Currently known assignment operators 209 209 ScopedMap< std::string, DeclarationWithType* > adapters; ///< Set of adapter functions in the current scope 210 210 211 211 DeclarationWithType *retval; 212 212 bool useRetval; … … 226 226 virtual Type *mutate( PointerType *pointerType ); 227 227 virtual Type *mutate( FunctionType *funcType ); 228 228 229 229 private: 230 230 void addAdapters( FunctionType *functionType ); … … 297 297 /// Exits the type-variable scope 298 298 void endTypeScope(); 299 299 300 300 ScopedSet< std::string > knownLayouts; ///< Set of generic type layouts known in the current scope, indexed by sizeofName 301 301 ScopedSet< std::string > knownOffsets; ///< Set of non-generic types for which the offset array exists in the current scope, indexed by offsetofName … … 351 351 PolyGenericCalculator polyCalculator; 352 352 Pass3 pass3; 353 353 354 354 layoutBuilder.mutateDeclarationList( translationUnit ); 355 355 mutateTranslationUnit/*All*/( translationUnit, pass1 ); … … 370 370 return functionDecl; 371 371 } 372 372 373 373 /// Get a list of type declarations that will affect a layout function 374 374 std::list< TypeDecl* > takeOtypeOnly( std::list< TypeDecl* > &decls ) { … … 380 380 } 381 381 } 382 382 383 383 return otypeDecls; 384 384 } … … 387 387 void addOtypeParams( FunctionType *layoutFnType, std::list< TypeDecl* > &otypeParams ) { 388 388 BasicType sizeAlignType( Type::Qualifiers(), BasicType::LongUnsignedInt ); 389 389 390 390 for ( std::list< TypeDecl* >::const_iterator param = otypeParams.begin(); param != otypeParams.end(); ++param ) { 391 391 TypeInstType paramType( Type::Qualifiers(), (*param)->get_name(), *param ); … … 444 444 return makeCond( ifCond, ifExpr ); 445 445 } 446 446 447 447 /// adds an expression to a compound statement 448 448 void addExpr( CompoundStmt *stmts, Expression *expr ) { … … 454 454 stmts->get_kids().push_back( stmt ); 455 455 } 456 456 457 457 Declaration *LayoutFunctionBuilder::mutate( StructDecl *structDecl ) { 458 458 // do not generate layout function for "empty" tag structs … … 467 467 BasicType *sizeAlignType = new BasicType( Type::Qualifiers(), BasicType::LongUnsignedInt ); 468 468 PointerType *sizeAlignOutType = new PointerType( Type::Qualifiers(), sizeAlignType ); 469 469 470 470 ObjectDecl *sizeParam = new ObjectDecl( sizeofName( structDecl->get_name() ), DeclarationNode::NoStorageClass, LinkageSpec::Cforall, 0, sizeAlignOutType, 0 ); 471 471 layoutFnType->get_parameters().push_back( sizeParam ); … … 497 497 addStmt( layoutDecl->get_statements(), makeAlignTo( derefVar( sizeParam ), new AlignofExpr( memberType->clone() ) ) ); 498 498 } 499 499 500 500 // place current size in the current offset index 501 501 addExpr( layoutDecl->get_statements(), makeOp( "?=?", makeOp( "?[?]", new VariableExpr( offsetParam ), new ConstantExpr( Constant::from_ulong( n_members ) ) ), … … 505 505 // add member size to current size 506 506 addExpr( layoutDecl->get_statements(), makeOp( "?+=?", derefVar( sizeParam ), new SizeofExpr( memberType->clone() ) ) ); 507 507 508 508 // take max of member alignment and global alignment 509 509 addStmt( layoutDecl->get_statements(), makeAssignMax( derefVar( alignParam ), new AlignofExpr( memberType->clone() ) ) ); … … 515 515 return structDecl; 516 516 } 517 517 518 518 Declaration *LayoutFunctionBuilder::mutate( UnionDecl *unionDecl ) { 519 519 // do not generate layout function for "empty" tag unions 520 520 if ( unionDecl->get_members().empty() ) return unionDecl; 521 521 522 522 // get parameters that can change layout, exiting early if none 523 523 std::list< TypeDecl* > otypeParams = takeOtypeOnly( unionDecl->get_parameters() ); … … 528 528 BasicType *sizeAlignType = new BasicType( Type::Qualifiers(), BasicType::LongUnsignedInt ); 529 529 PointerType *sizeAlignOutType = new PointerType( Type::Qualifiers(), sizeAlignType ); 530 530 531 531 ObjectDecl *sizeParam = new ObjectDecl( sizeofName( unionDecl->get_name() ), DeclarationNode::NoStorageClass, LinkageSpec::Cforall, 0, sizeAlignOutType, 0 ); 532 532 layoutFnType->get_parameters().push_back( sizeParam ); … … 545 545 assert( dwt ); 546 546 Type *memberType = dwt->get_type(); 547 547 548 548 // take max member size and global size 549 549 addStmt( layoutDecl->get_statements(), makeAssignMax( derefVar( sizeParam ), new SizeofExpr( memberType->clone() ) ) ); 550 550 551 551 // take max of member alignment and global alignment 552 552 addStmt( layoutDecl->get_statements(), makeAssignMax( derefVar( alignParam ), new AlignofExpr( memberType->clone() ) ) ); … … 558 558 return unionDecl; 559 559 } 560 560 561 561 ////////////////////////////////////////// Pass1 //////////////////////////////////////////////////// 562 562 … … 619 619 return 0; 620 620 } 621 621 622 622 /// returns T if the given declaration is: (*?=?)(T *, T) for some type T (return not checked, but maybe should be), NULL otherwise 623 623 /// Only picks assignments where neither parameter is cv-qualified … … 631 631 Type *paramType2 = funType->get_parameters().back()->get_type(); 632 632 if ( paramType2->get_qualifiers() != defaultQualifiers ) return 0; 633 633 634 634 if ( PointerType *pointerType = dynamic_cast< PointerType* >( paramType1 ) ) { 635 635 Type *baseType1 = pointerType->get_base(); … … 803 803 passArgTypeVars( appExpr, polyRetType, concRetType, arg, exprTyVars, seenTypes ); 804 804 } 805 805 806 806 // add type information args for presently unseen types in parameter list 807 807 for ( ; fnParm != funcType->get_parameters().end() && fnArg != appExpr->get_args().end(); ++fnParm, ++fnArg ) { … … 882 882 assert( env ); 883 883 Type *concrete = replaceWithConcrete( appExpr, polyType ); 884 // add out-parameter for return value 884 // add out-parameter for return value 885 885 return addRetParam( appExpr, function, concrete, arg ); 886 886 } … … 1035 1035 std::list< DeclarationWithType *>::iterator param = adapterType->get_parameters().begin(); 1036 1036 std::list< DeclarationWithType *>::iterator realParam = adaptee->get_parameters().begin(); 1037 param++; // skip adaptee parameter 1037 param++; // skip adaptee parameter in the adapter type 1038 1038 if ( realType->get_returnVals().empty() ) { 1039 // void return 1039 1040 addAdapterParams( adapteeApp, arg, param, adapterType->get_parameters().end(), realParam, tyVars ); 1040 1041 bodyStmt = new ExprStmt( noLabels, adapteeApp ); 1041 1042 } else if ( isPolyType( adaptee->get_returnVals().front()->get_type(), tyVars ) ) { 1043 // return type T 1042 1044 if ( (*param)->get_name() == "" ) { 1043 1045 (*param)->set_name( "_ret" ); … … 1366 1368 return new VariableExpr( functionObj ); 1367 1369 } 1368 1370 1369 1371 Statement * Pass1::mutate( ReturnStmt *returnStmt ) { 1370 1372 if ( retval && returnStmt->get_expr() ) { … … 1886 1888 } 1887 1889 } 1888 1890 1889 1891 Type *ret = Mutator::mutate( funcType ); 1890 1892 … … 1946 1948 return derefdVar; 1947 1949 } 1948 1950 1949 1951 Expression *PolyGenericCalculator::mutate( MemberExpr *memberExpr ) { 1950 1952 // mutate, exiting early if no longer MemberExpr … … 2066 2068 if ( n_members == 0 ) { 2067 2069 // all empty structs have the same layout - size 1, align 1 2068 makeVar( sizeofName( typeName ), layoutType, new SingleInit( new ConstantExpr( Constant::from_ulong( 1 ) ) ) );2069 makeVar( alignofName( typeName ), layoutType->clone(), new SingleInit( new ConstantExpr( Constant::from_ulong( 1 ) ) ) );2070 makeVar( sizeofName( typeName ), layoutType, new SingleInit( new ConstantExpr( Constant::from_ulong( (unsigned long)1 ) ) ) ); 2071 makeVar( alignofName( typeName ), layoutType->clone(), new SingleInit( new ConstantExpr( Constant::from_ulong( (unsigned long)1 ) ) ) ); 2070 2072 // NOTE zero-length arrays are forbidden in C, so empty structs have no offsetof array 2071 2073 } else { … … 2144 2146 Type *ty = offsetofExpr->get_type(); 2145 2147 if ( ! findGeneric( ty ) ) return offsetofExpr; 2146 2148 2147 2149 if ( StructInstType *structType = dynamic_cast< StructInstType* >( ty ) ) { 2148 2150 // replace offsetof expression by index into offset array
Note: See TracChangeset
for help on using the changeset viewer.