35 ABTI_eventual *p_eventual;
37 p_eventual = (ABTI_eventual *)
ABTU_malloc(
sizeof(ABTI_eventual));
38 ABTI_spinlock_clear(&p_eventual->lock);
40 p_eventual->nbytes = nbytes;
41 p_eventual->value = (nbytes == 0) ? NULL :
ABTU_malloc(nbytes);
42 p_eventual->p_head = NULL;
43 p_eventual->p_tail = NULL;
45 *neweventual = ABTI_eventual_get_handle(p_eventual);
65 ABTI_eventual *p_eventual = ABTI_eventual_get_ptr(*eventual);
66 ABTI_CHECK_NULL_EVENTUAL_PTR(p_eventual);
71 ABTI_spinlock_acquire(&p_eventual->lock);
73 if (p_eventual->value)
107 ABTI_local *p_local = ABTI_local_get_local();
108 ABTI_eventual *p_eventual = ABTI_eventual_get_ptr(eventual);
109 ABTI_CHECK_NULL_EVENTUAL_PTR(p_eventual);
111 ABTI_spinlock_acquire(&p_eventual->lock);
113 ABTI_thread *p_current;
116 ABTD_atomic_int32 ext_signal = ABTD_ATOMIC_INT32_STATIC_INITIALIZER(0);
118 if (p_local != NULL) {
119 p_current = p_local->p_thread;
123 p_unit = &p_current->unit_def;
124 p_unit->handle.thread = ABTI_thread_get_handle(p_current);
129 p_unit = (ABTI_unit *)
ABTU_calloc(1,
sizeof(ABTI_unit));
132 ABTI_STATIC_ASSERT(
sizeof(ext_signal) <=
133 sizeof(p_unit->handle.thread));
134 p_unit->handle.thread = (
ABT_thread)&ext_signal;
138 p_unit->p_next = NULL;
139 if (p_eventual->p_head == NULL) {
140 p_eventual->p_head = p_unit;
141 p_eventual->p_tail = p_unit;
143 p_eventual->p_tail->p_next = p_unit;
144 p_eventual->p_tail = p_unit;
148 ABTI_thread_set_blocked(p_current);
150 ABTI_spinlock_release(&p_eventual->lock);
153 ABTI_thread_suspend(&p_local, p_current);
156 ABTI_spinlock_release(&p_eventual->lock);
160 while (!ABTD_atomic_acquire_load_int32(&ext_signal))
165 ABTI_spinlock_release(&p_eventual->lock);
168 *value = p_eventual->value;
196 ABTI_eventual *p_eventual = ABTI_eventual_get_ptr(eventual);
197 ABTI_CHECK_NULL_EVENTUAL_PTR(p_eventual);
200 ABTI_spinlock_acquire(&p_eventual->lock);
203 *value = p_eventual->value;
206 ABTI_spinlock_release(&p_eventual->lock);
238 ABTI_local *p_local = ABTI_local_get_local();
239 ABTI_eventual *p_eventual = ABTI_eventual_get_ptr(eventual);
240 ABTI_CHECK_NULL_EVENTUAL_PTR(p_eventual);
243 ABTI_spinlock_acquire(&p_eventual->lock);
246 if (p_eventual->value)
247 memcpy(p_eventual->value, value, nbytes);
249 if (p_eventual->p_head == NULL) {
250 ABTI_spinlock_release(&p_eventual->lock);
255 ABTI_unit *p_head = p_eventual->p_head;
256 ABTI_unit *p_unit = p_head;
258 ABTI_unit *p_next = p_unit->p_next;
261 p_unit->p_next = NULL;
264 ABTI_thread *p_thread = ABTI_thread_get_ptr(p_unit->handle.thread);
265 ABTI_thread_set_ready(p_local, p_thread);
268 ABTD_atomic_int32 *p_ext_signal =
269 (ABTD_atomic_int32 *)p_unit->handle.thread;
270 ABTD_atomic_release_store_int32(p_ext_signal, 1);
274 if (p_next != NULL) {
281 p_eventual->p_head = NULL;
282 p_eventual->p_tail = NULL;
284 ABTI_spinlock_release(&p_eventual->lock);
309 ABTI_eventual *p_eventual = ABTI_eventual_get_ptr(eventual);
310 ABTI_CHECK_NULL_EVENTUAL_PTR(p_eventual);
312 ABTI_spinlock_acquire(&p_eventual->lock);
314 ABTI_spinlock_release(&p_eventual->lock);
int ABT_eventual_reset(ABT_eventual eventual)
Reset the readiness of the target eventual.
static void * ABTU_malloc(size_t size)
#define ABT_ERR_INV_EVENTUAL
struct ABT_thread_opaque * ABT_thread
#define ABT_EVENTUAL_NULL
#define HANDLE_ERROR_FUNC_WITH_CODE(n)
int ABT_eventual_free(ABT_eventual *eventual)
Free the eventual object.
struct ABT_eventual_opaque * ABT_eventual
int ABT_eventual_wait(ABT_eventual eventual, void **value)
Wait on the eventual.
int ABT_eventual_test(ABT_eventual eventual, void **value, int *is_ready)
Test the readiness of an eventual.
static void ABTU_free(void *ptr)
int ABT_eventual_create(int nbytes, ABT_eventual *neweventual)
Create an eventual.
int ABT_eventual_set(ABT_eventual eventual, void *value, int nbytes)
Signal the eventual.
static void * ABTU_calloc(size_t num, size_t size)