ARGOBOTS
abtd_ucontext.h
Go to the documentation of this file.
1 /* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil ; -*- */
2 /*
3  * See COPYRIGHT in top-level directory.
4  */
5 
6 #ifndef ABTD_UCONTEXT_H_INCLUDED
7 #define ABTD_UCONTEXT_H_INCLUDED
8 
9 static void ABTD_ucontext_wrapper(int arg1, int arg2)
10 {
11  ABTD_thread_context *p_self;
12 #if SIZEOF_VOID_P == 8
13  p_self = (ABTD_thread_context *)(((uintptr_t)((uint32_t)arg1) << 32) |
14  ((uintptr_t)((uint32_t)arg2)));
15 #elif SIZEOF_VOID_P == 4
16  p_self = (ABTD_thread_context *)((uintptr_t)arg1);
17 #else
18 #error "Unknown pointer size."
19 #endif
20  p_self->f_uctx_thread(p_self->p_uctx_arg);
21  /* ABTD_thread_context_jump or take must be called at the end of
22  * f_uctx_thread, */
23  ABTI_ASSERT(0);
24 }
25 
26 static inline void ABTD_thread_context_make(ABTD_thread_context *p_ctx,
27  void *sp, size_t size,
28  void (*thread_func)(void *))
29 {
30  getcontext(&p_ctx->uctx);
31  p_ctx->p_ctx = &p_ctx->uctx;
32 
33  /* uc_link is not used. */
34  p_ctx->uctx.uc_link = NULL;
35  p_ctx->uctx.uc_stack.ss_sp = (void *)(((char *)sp) - size);
36  p_ctx->uctx.uc_stack.ss_size = size;
37  p_ctx->f_uctx_thread = thread_func;
38 
39 #if SIZEOF_VOID_P == 8
40  int arg_upper = (int)(((uintptr_t)p_ctx) >> 32);
41  int arg_lower = (int)(((uintptr_t)p_ctx) >> 0);
42  makecontext(&p_ctx->uctx, (void (*)())ABTD_ucontext_wrapper, 2, arg_upper,
43  arg_lower);
44 #elif SIZEOF_VOID_P == 4
45  int arg = (int)((uintptr_t)p_ctx);
46  makecontext(&p_ctx->uctx, (void (*)())ABTD_ucontext_wrapper, 1, arg);
47 #else
48 #error "Unknown pointer size."
49 #endif
50 }
51 
52 static inline void ABTD_thread_context_jump(ABTD_thread_context *p_old,
53  ABTD_thread_context *p_new,
54  void *arg)
55 {
56  p_new->p_uctx_arg = arg;
57  swapcontext(&p_old->uctx, &p_new->uctx);
58 }
59 
60 static inline void ABTD_thread_context_take(ABTD_thread_context *p_old,
61  ABTD_thread_context *p_new,
62  void *arg)
63 {
64  p_new->p_uctx_arg = arg;
65  setcontext(&p_new->uctx);
66  /* Unreachable. */
67 }
68 
69 #if ABT_CONFIG_THREAD_TYPE == ABT_THREAD_TYPE_DYNAMIC_PROMOTION
70 #error "ABTD_thread_context_make_and_call is not implemented."
71 #endif
72 
73 #endif /* ABTD_UCONTEXT_H_INCLUDED */