- Timestamp:
- Mar 14, 2017, 11:14:53 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:
- 026bb82
- Parents:
- c54b0b4
- Location:
- src
- Files:
-
- 3 edited
Legend:
- Unmodified
- Added
- Removed
-
src/Concurrency/Keywords.cc
rc54b0b4 r64adb03 1 // -*- Mode: CPP -*- 2 // 3 // Cforall Version 1.0.0 Copyright (C) 2016 University of Waterloo 4 // 5 // The contents of this file are covered under the licence agreement in the 6 // file "LICENCE" distributed with Cforall. 7 // 8 // Keywords.cc -- 9 // 10 // Author : Thierry Delisle 11 // Created On : Mon Mar 13 12:41:22 2017 12 // Last Modified By : 13 // Last Modified On : 14 // Update Count : 0 15 // 16 17 #include "Concurrency/Keywords.h" 18 19 #include "SynTree/Declaration.h" 20 #include "SynTree/Expression.h" 21 #include "SynTree/Initializer.h" 22 #include "SynTree/Mutator.h" 23 #include "SynTree/Statement.h" 24 #include "SynTree/Type.h" 25 #include "SynTree/Visitor.h" 26 27 namespace Concurrency { 28 29 namespace { 30 const std::list<Label> noLabels; 31 DeclarationNode::StorageClasses noStorage; 32 Type::Qualifiers noQualifiers; 33 } 34 35 //============================================================================================= 36 // Visitors declaration 37 //============================================================================================= 38 39 //----------------------------------------------------------------------------- 40 //Handles thread type declarations : 41 // thread Mythread { struct MyThread { 42 // int data; int data; 43 // a_struct_t more_data; a_struct_t more_data; 44 // => thread_desc __thrd_d; 45 // }; }; 46 // static inline thread_desc * get_thread( MyThread * this ) { return &this->__thrd_d; } 47 // void main( MyThread * this ); 48 // 49 class ThreadKeyword final : public Mutator { 50 public: 51 52 static void implement( std::list< Declaration * > & translationUnit ) {} 53 }; 54 55 //----------------------------------------------------------------------------- 56 //Handles coroutine type declarations : 57 // coroutine MyCoroutine { struct MyCoroutine { 58 // int data; int data; 59 // a_struct_t more_data; a_struct_t more_data; 60 // => coroutine_desc __cor_d; 61 // }; }; 62 // static inline coroutine_desc * get_coroutine( MyCoroutine * this ) { return &this->__cor_d; } 63 // void main( MyCoroutine * this ); 64 // 65 class CoroutineKeyword final : public Mutator { 66 public: 67 68 static void implement( std::list< Declaration * > & translationUnit ) {} 69 }; 70 71 //----------------------------------------------------------------------------- 72 //Handles monitor type declarations : 73 // monitor MyMonitor { struct MyMonitor { 74 // int data; int data; 75 // a_struct_t more_data; a_struct_t more_data; 76 // => monitor_desc __mon_d; 77 // }; }; 78 // static inline monitor_desc * get_coroutine( MyMonitor * this ) { return &this->__cor_d; } 79 // void main( MyMonitor * this ); 80 // 81 class MonitorKeyword final : public Mutator { 82 public: 83 84 static void implement( std::list< Declaration * > & translationUnit ) {} 85 }; 86 87 //----------------------------------------------------------------------------- 88 //Handles mutex routines definitions : 89 // void foo( A * mutex a, B * mutex b, int i ) { void foo( A * a, B * b, int i ) { 90 // monitor_desc * __monitors[] = { a, b }; 91 // monitor_guard_t __guard = { __monitors, 2 }; 92 // /*Some code*/ => /*Some code*/ 93 // } } 94 // 95 class MutexKeyword final : public Visitor { 96 public: 97 98 using Visitor::visit; 99 virtual void visit( FunctionDecl *functionDecl ) override final; 100 101 std::list<DeclarationWithType*> findMutexArgs( FunctionDecl* ); 102 void validate( DeclarationWithType * ); 103 void addStatments( CompoundStmt *, const std::list<DeclarationWithType * > &); 104 105 static void implement( std::list< Declaration * > & translationUnit ) { 106 MutexKeyword impl; 107 acceptAll( translationUnit, impl ); 108 } 109 }; 110 111 //============================================================================================= 112 // General entry routine 113 //============================================================================================= 114 void applyKeywords( std::list< Declaration * > & translationUnit ) { 115 ThreadKeyword ::implement( translationUnit ); 116 CoroutineKeyword ::implement( translationUnit ); 117 MonitorKeyword ::implement( translationUnit ); 118 MutexKeyword ::implement( translationUnit ); 119 } 120 121 //============================================================================================= 122 // Mutex keyword implementation 123 //============================================================================================= 124 void MutexKeyword::visit(FunctionDecl* decl) { 125 std::list<DeclarationWithType*> mutexArgs = findMutexArgs( decl ); 126 if( mutexArgs.empty() ) return; 127 128 for(auto arg : mutexArgs) { 129 validate( arg ); 130 } 131 132 CompoundStmt* body = decl->get_statements(); 133 if( ! body ) return; 134 135 addStatments( body, mutexArgs ); 136 } 137 138 std::list<DeclarationWithType*> MutexKeyword::findMutexArgs( FunctionDecl* decl ) { 139 std::list<DeclarationWithType*> mutexArgs; 140 141 for( auto arg : decl->get_functionType()->get_parameters()) { 142 //Find mutex arguments 143 Type* ty = arg->get_type(); 144 if( ! ty->get_qualifiers().isMutex ) continue; 145 146 //Append it to the list 147 mutexArgs.push_back( arg ); 148 } 149 150 return mutexArgs; 151 } 152 153 void MutexKeyword::validate( DeclarationWithType * arg ) { 154 Type* ty = arg->get_type(); 155 156 //Makes sure it's not a copy 157 PointerType* pty = dynamic_cast< PointerType * >( ty ); 158 if( ! pty ) throw SemanticError( "Mutex argument must be of pointer/reference type ", arg ); 159 160 //Make sure the we are pointing directly to a type 161 Type* base = pty->get_base(); 162 if( dynamic_cast< PointerType * >( base ) ) throw SemanticError( "Mutex argument have exactly one level of indirection ", arg ); 163 164 //Make sure that typed isn't mutex 165 if( ! base->get_qualifiers().isMutex ) throw SemanticError( "mutex keyword may only appear once per argument ", arg ); 166 } 167 168 void MutexKeyword::addStatments( CompoundStmt * body, const std::list<DeclarationWithType * > & args ) { 169 //in reverse order : 170 // monitor_guard_t __guard = { __monitors, # }; 171 body->push_front( 172 new DeclStmt( noLabels, new ObjectDecl( 173 "__guard", 174 noStorage, 175 LinkageSpec::Cforall, 176 nullptr, 177 new StructInstType( 178 noQualifiers, 179 "monitor_guard_t" 180 ), 181 new ListInit( 182 { 183 new SingleInit( new NameExpr( "__monitors" ) ), 184 new SingleInit( new ConstantExpr( Constant::from_ulong( args.size() ) ) ) 185 } 186 ) 187 )) 188 ); 189 190 //monitor_desc * __monitors[] = { a, b }; 191 body->push_front( 192 new DeclStmt( noLabels, new ObjectDecl( 193 "__monitors", 194 noStorage, 195 LinkageSpec::Cforall, 196 nullptr, 197 new ArrayType( 198 noQualifiers, 199 new PointerType( 200 noQualifiers, 201 new StructInstType( 202 noQualifiers, 203 "monitor_desc" 204 ) 205 ), 206 new ConstantExpr( Constant::from_ulong( args.size() ) ), 207 false, 208 false 209 ), 210 new ListInit( 211 map_range < std::list<Initializer*> > ( args, [](DeclarationWithType * var ){ 212 return new SingleInit( new VariableExpr( var ) ); 213 }) 214 ) 215 )) 216 ); 217 } 218 }; -
src/Concurrency/Keywords.h
rc54b0b4 r64adb03 1 // -*- Mode: CPP -*- 2 // 3 // Cforall Version 1.0.0 Copyright (C) 2016 University of Waterloo 4 // 5 // The contents of this file are covered under the licence agreement in the 6 // file "LICENCE" distributed with Cforall. 7 // 8 // Keywords.h -- 9 // 10 // Author : Thierry Delisle 11 // Created On : Fri Mar 10 15:16:42 2017 12 // Last Modified By : 13 // Last Modified On : 14 // Update Count : 0 15 // 16 17 #ifndef KEYWORDS_H 18 #define KEYWORDS_H 19 20 #include <list> 21 22 #include "SynTree/Declaration.h" 23 24 namespace Concurrency { 25 void applyKeywords( std::list< Declaration * > & translationUnit ); 26 }; 27 28 #endif //KEYWORDS_H -
src/main.cc
rc54b0b4 r64adb03 32 32 #include "GenPoly/CopyParams.h" 33 33 #include "GenPoly/InstantiateGeneric.h" 34 #include "Concurrency/Keywords.h" 34 35 #include "CodeGen/Generate.h" 35 36 #include "CodeGen/FixNames.h" … … 236 237 OPTPRINT( "mutate" ) 237 238 ControlStruct::mutate( translationUnit ); 239 OPTPRINT( "Concurrency" ) 240 Concurrency::applyKeywords( translationUnit ); 238 241 OPTPRINT( "fixNames" ) 239 242 CodeGen::fixNames( translationUnit );
Note: See TracChangeset
for help on using the changeset viewer.