| [5b11c25] | 1 | #include <fstream.hfa> | 
|---|
|  | 2 | #include <kernel.hfa> | 
|---|
|  | 3 | #include <stdlib.hfa> | 
|---|
|  | 4 | #include <thread.hfa> | 
|---|
|  | 5 | #include <monitor.hfa> | 
|---|
|  | 6 | #include <time.hfa> | 
|---|
|  | 7 |  | 
|---|
|  | 8 | #define __kick_rate 150000ul | 
|---|
|  | 9 | #include "long_tests.hfa" | 
|---|
|  | 10 |  | 
|---|
|  | 11 | #ifndef PREEMPTION_RATE | 
|---|
|  | 12 | #define PREEMPTION_RATE 10`ms | 
|---|
|  | 13 | #endif | 
|---|
|  | 14 |  | 
|---|
|  | 15 | Duration default_preemption() { | 
|---|
|  | 16 | return PREEMPTION_RATE; | 
|---|
|  | 17 | } | 
|---|
|  | 18 |  | 
|---|
|  | 19 | #ifdef TEST_LONG | 
|---|
|  | 20 | static const unsigned long N = 600_000ul; | 
|---|
|  | 21 | #else | 
|---|
|  | 22 | static const unsigned long N = 1_000ul; | 
|---|
|  | 23 | #endif | 
|---|
|  | 24 |  | 
|---|
|  | 25 | monitor Printer {}; | 
|---|
|  | 26 | #if !defined(TEST_FOREVER) | 
|---|
|  | 27 | static inline void print(Printer & mutex this, const char * const text ) { | 
|---|
|  | 28 | sout | text; | 
|---|
|  | 29 | } | 
|---|
|  | 30 | #else | 
|---|
|  | 31 | static inline void print(Printer & this, const char * const text ) {} | 
|---|
|  | 32 | #endif | 
|---|
|  | 33 | Printer printer; | 
|---|
|  | 34 |  | 
|---|
|  | 35 | coroutine Coroutine {}; | 
|---|
|  | 36 |  | 
|---|
|  | 37 | volatile bool done = false; | 
|---|
|  | 38 | Coroutine * volatile the_cor = 0p; | 
|---|
|  | 39 |  | 
|---|
|  | 40 | void store(Coroutine * volatile * target, Coroutine * value) { | 
|---|
|  | 41 | long long int val = value; | 
|---|
|  | 42 | volatile long long int * ptr = target; | 
|---|
|  | 43 | __atomic_store(ptr, &val, __ATOMIC_SEQ_CST); | 
|---|
|  | 44 | } | 
|---|
|  | 45 |  | 
|---|
|  | 46 | Coroutine * exchange(Coroutine * volatile * target) { | 
|---|
|  | 47 | long long int ret; | 
|---|
|  | 48 | volatile long long int * ptr = target; | 
|---|
|  | 49 | long long int val = 0; | 
|---|
|  | 50 | ret = __atomic_exchange_n(ptr, &val, __ATOMIC_SEQ_CST); | 
|---|
|  | 51 | assert(ret == 0 || *ptr == 0); | 
|---|
|  | 52 | return (Coroutine *)ret; | 
|---|
|  | 53 | } | 
|---|
|  | 54 |  | 
|---|
|  | 55 | void main(Coroutine& this) { | 
|---|
|  | 56 | for(int i = 0; TEST(i < N); i++) { | 
|---|
|  | 57 |  | 
|---|
|  | 58 | print(printer, "Coroutine 1"); | 
|---|
|  | 59 | void publish() { | 
|---|
|  | 60 | assert(!the_cor); | 
|---|
|  | 61 | store( &the_cor, &this ); | 
|---|
|  | 62 | } | 
|---|
|  | 63 | suspend_then(publish); | 
|---|
|  | 64 | print(printer, "Coroutine 2"); | 
|---|
|  | 65 | KICK_WATCHDOG; | 
|---|
|  | 66 | yield(); | 
|---|
|  | 67 | } | 
|---|
|  | 68 | done = true; | 
|---|
|  | 69 | } | 
|---|
|  | 70 |  | 
|---|
|  | 71 | thread Thread {}; | 
|---|
|  | 72 | void main(Thread & this) { | 
|---|
|  | 73 | Coroutine * mine = 0p; | 
|---|
|  | 74 | while(!done) { | 
|---|
|  | 75 | yield(); | 
|---|
|  | 76 |  | 
|---|
|  | 77 | mine = exchange( &the_cor ); | 
|---|
|  | 78 | if(!mine) continue; | 
|---|
|  | 79 |  | 
|---|
|  | 80 | print(printer, "Thread 1"); | 
|---|
|  | 81 | resume(*mine); | 
|---|
|  | 82 | print(printer, "Thread 2"); | 
|---|
|  | 83 | } | 
|---|
|  | 84 | } | 
|---|
|  | 85 |  | 
|---|
|  | 86 |  | 
|---|
|  | 87 | int main(int argc, char* argv[]) { | 
|---|
|  | 88 | processor p[2]; | 
|---|
|  | 89 | Coroutine c; | 
|---|
|  | 90 | the_cor = &c; | 
|---|
|  | 91 | { | 
|---|
|  | 92 | Thread t[2]; | 
|---|
|  | 93 | } | 
|---|
|  | 94 | } | 
|---|