Changeset 4a3386b4 for src/libcfa/concurrency/coroutines
- Timestamp:
- Jan 19, 2017, 2:56:51 PM (9 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:
- 8f49a54
- Parents:
- 765aa76 (diff), c2416d5 (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. - File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
src/libcfa/concurrency/coroutines
r765aa76 r4a3386b4 1 // - *- Mode: CFA - *- 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 // coroutines -- 9 // 10 // Author : Thierry Delisle 11 // Created On : Mon Nov 28 12:27:26 2016 12 // Last Modified By : Thierry Delisle 13 // Last Modified On : Mon Nov 28 12:27:26 2016 14 // Update Count : 0 15 // 16 17 #ifndef COROUTINES_H 18 #define COROUTINES_H 19 20 #include "assert" 21 #include "invoke.h" 22 23 //----------------------------------------------------------------------------- 24 // Coroutine trait 25 // Anything that implements this trait can be resumed. 26 // Anything that is resumed is a coroutine. 27 trait is_coroutine(dtype T) { 28 void main(T * this); 29 coroutine * get_coroutine(T * this); 30 }; 31 32 #define DECL_COROUTINE(X) static inline coroutine* get_coroutine(X* this) { return &this->c; } void main(X* this); 33 34 //----------------------------------------------------------------------------- 35 // Ctors and dtors 36 void ?{}(coStack_t * this); 37 void ?{}(coroutine * this); 38 void ^?{}(coStack_t * this); 39 void ^?{}(coroutine * this); 40 41 //----------------------------------------------------------------------------- 42 // Public coroutine API 43 static inline void suspend(); 44 45 forall(dtype T | is_coroutine(T)) 46 static inline void resume(T * cor); 47 48 forall(dtype T | is_coroutine(T)) 49 void prime(T * cor); 50 51 //----------------------------------------------------------------------------- 52 // PRIVATE exposed because of inline 53 54 // Start coroutine routines 55 extern "C" { 56 forall(dtype T | is_coroutine(T)) 57 void CtxInvokeCoroutine(T * this); 58 59 forall(dtype T | is_coroutine(T)) 60 void CtxStart(T * this, void ( *invoke)(T *)); 61 } 62 63 // Get current coroutine 64 extern coroutine * current_coroutine; //PRIVATE, never use directly 65 static inline coroutine * this_coroutine(void) { 66 return current_coroutine; 67 } 68 69 // Private wrappers for context switch and stack creation 70 extern void corCxtSw(coroutine * src, coroutine * dst); 71 extern void create_stack( coStack_t * this, unsigned int storageSize ); 72 73 // Suspend implementation inlined for performance 74 static inline void suspend() { 75 coroutine * src = this_coroutine(); // optimization 76 77 assertf( src->last != 0, 78 "Attempt to suspend coroutine %.256s (%p) that has never been resumed.\n" 79 "Possible cause is a suspend executed in a member called by a coroutine user rather than by the coroutine main.", 80 src->name, src ); 81 assertf( src->last->notHalted, 82 "Attempt by coroutine %.256s (%p) to suspend back to terminated coroutine %.256s (%p).\n" 83 "Possible cause is terminated coroutine's main routine has already returned.", 84 src->name, src, src->last->name, src->last ); 85 86 corCxtSw( src, src->last ); 87 } 88 89 // Resume implementation inlined for performance 90 forall(dtype T | is_coroutine(T)) 91 static inline void resume(T * cor) { 92 coroutine * src = this_coroutine(); // optimization 93 coroutine * dst = get_coroutine(cor); 94 95 if( unlikely(!dst->stack.base) ) { 96 create_stack(&dst->stack, dst->stack.size); 97 CtxStart(cor, CtxInvokeCoroutine); 98 } 99 100 // not resuming self ? 101 if ( src != dst ) { 102 assertf( dst->notHalted , 103 "Attempt by coroutine %.256s (%p) to resume terminated coroutine %.256s (%p).\n" 104 "Possible cause is terminated coroutine's main routine has already returned.", 105 src->name, src, dst->name, dst ); 106 107 // set last resumer 108 dst->last = src; 109 } // if 110 111 // always done for performance testing 112 corCxtSw( src, dst ); 113 } 114 115 #endif //COROUTINES_H 116 117 // Local Variables: // 118 // mode: c // 119 // tab-width: 4 // 120 // End: //
Note:
See TracChangeset
for help on using the changeset viewer.