1 #if __has_include(<coroutine>)
2
3 #include <coroutine>
4
5 namespace coro = std;
6
7 #elif __has_include(<experimental/coroutine>)
8
9 #include <experimental/coroutine>
10
11 namespace coro = std::experimental;
12
13 #else
14
15 #warning "no installed coroutine headers found, using test-suite local one"
16
17 /* Dummy version to allow tests without an installed header. */
18 # ifndef __TESTSUITE_CORO_H_n4835
19 # define __TESTSUITE_CORO_H_n4835
20
21 // Fragments (with short-cuts) to mimic enough of the library header to
22 // make some progress.
23
24 # if __cpp_impl_coroutine
25
26 namespace std {
27 inline namespace __n4861 {
28
29 // 21.11.1 coroutine traits
30 template<typename _R, typename...> struct coroutine_traits {
31 using promise_type = typename _R::promise_type;
32 };
33
34 // 21.11.2 coroutine handle
35 template <typename Promise = void> struct coroutine_handle;
36
37 template <>
38 struct coroutine_handle<void> {
39 public:
40 // 21.11.2.1 construct/reset
41 constexpr coroutine_handle () noexcept
42 : __fr_ptr (0) {}
43 constexpr coroutine_handle (decltype(nullptr) __h) noexcept
44 : __fr_ptr (__h) {}
45 coroutine_handle &operator= (decltype(nullptr)) noexcept {
46 __fr_ptr = nullptr;
47 return *this;
48 }
49
50 public:
51 // 21.11.2.2 export/import
52 constexpr void *address () const noexcept { return __fr_ptr; }
53 constexpr static coroutine_handle from_address (void *__a) noexcept {
54 coroutine_handle __self;
55 __self.__fr_ptr = __a;
56 return __self;
57 }
58 public:
59 // 21.11.2.3 observers
60 constexpr explicit operator bool () const noexcept {
61 return bool (__fr_ptr);
62 }
63 bool done () const noexcept {
64 return __builtin_coro_done (__fr_ptr);
65 }
66 // 21.11.2.4 resumption
67 void operator () () const { resume (); }
68 void resume () const {
69 __builtin_coro_resume (__fr_ptr);
70 }
71 void destroy () const {
72 __builtin_coro_destroy (__fr_ptr);
73 }
74 protected:
75 void *__fr_ptr;
76 };
77
78 template <class _Promise>
79 struct coroutine_handle : coroutine_handle<> {
80 // 21.11.2.1 construct/reset
81 using coroutine_handle<>::coroutine_handle;
82 static coroutine_handle from_promise(_Promise &p) {
83 coroutine_handle __self;
84 __self.__fr_ptr =
85 __builtin_coro_promise((char *)&p, __alignof(_Promise), true);
86 return __self;
87 }
88 coroutine_handle& operator=(decltype(nullptr)) noexcept {
89 coroutine_handle<>::operator=(nullptr);
90 return *this;
91 }
92 // 21.11.2.2 export/import
93 constexpr static coroutine_handle from_address(void* __a){
94 coroutine_handle __self;
95 __self.__fr_ptr = __a;
96 return __self;
97 }
98 // 21.11.2.5 promise access
99 _Promise& promise() const {
100 void * __t = __builtin_coro_promise(this->__fr_ptr,
101 __alignof(_Promise), false);
102 return *static_cast<_Promise*>(__t);
103 }
104 };
105
106 // n4760 - 21.11.5 trivial awaitables
107
108 struct suspend_always {
109 bool await_ready() { return false; }
110 void await_suspend(coroutine_handle<>) {}
111 void await_resume() {}
112 };
113
114 struct suspend_never {
115 bool await_ready() { return true; }
116 void await_suspend(coroutine_handle<>) {}
117 void await_resume() {}
118 };
119
120 } // namespace __n4861
121 } // namespace std
122
123 namespace coro = std;
124
125 # else
126 # error "coro.h requires support for coroutines, add -fcoroutines"
127 # endif
128 # endif // __TESTSUITE_CORO_H_n4835
129
130 #endif // __has_include(<experimental/coroutine>)
131
132 #include <cstdlib> /* for abort () */
133
134 #include <utility> /* for std::forward */
135
136 #ifndef OUTPUT
137 # define PRINT(X)
138 # define PRINTF (void)
139 #else
140 #include <stdio.h>
141 # define PRINT(X) puts(X)
142 # define PRINTF printf
143 #endif