Skip to content

Commit

Permalink
Replace thread save/restore API with switch (#1869)
Browse files Browse the repository at this point in the history
  • Loading branch information
stedolan authored Oct 6, 2023
1 parent d38db7f commit 3d748da
Show file tree
Hide file tree
Showing 2 changed files with 21 additions and 21 deletions.
32 changes: 15 additions & 17 deletions ocaml/otherlibs/systhreads/st_stubs.c
Original file line number Diff line number Diff line change
Expand Up @@ -243,9 +243,7 @@ static void memprof_ctx_iter(th_ctx_action f, void* data)
} while (th != curr_thread);
}

/* Saving and restoring runtime state in curr_thread */

CAMLexport void caml_thread_save_runtime_state(void)
static void thread_save_runtime_state(void)
{
if (Caml_state->in_minor_collection)
caml_fatal_error("Thread switch from inside minor GC");
Expand Down Expand Up @@ -273,12 +271,8 @@ CAMLexport void caml_thread_save_runtime_state(void)
caml_memprof_leave_thread();
}

CAMLexport void caml_thread_restore_runtime_state(void)
static void thread_restore_runtime_state(void)
{
/* Update curr_thread to point to the thread descriptor corresponding
to the thread currently executing */
curr_thread = st_tls_get(thread_descriptor_key);

#ifdef NATIVE_CODE
Caml_state->top_of_stack = curr_thread->top_of_stack;
Caml_state->bottom_of_stack= curr_thread->bottom_of_stack;
Expand All @@ -303,16 +297,24 @@ CAMLexport void caml_thread_restore_runtime_state(void)
caml_memprof_enter_thread(curr_thread->memprof_ctx);
}

CAMLexport void caml_thread_switch_runtime_state(void)
{
caml_thread_t new_thread = st_tls_get(thread_descriptor_key);
if (new_thread == curr_thread) return;
thread_save_runtime_state();
curr_thread = new_thread;
thread_restore_runtime_state();
}

CAMLexport void caml_switch_runtime_locking_scheme(struct caml_locking_scheme* new)
{
struct caml_locking_scheme* old;

caml_thread_save_runtime_state();
old = atomic_exchange(&caml_locking_scheme, new);
/* We hold 'old', but it is no longer the runtime lock */
old->unlock(old->context);
acquire_runtime_lock();
caml_thread_restore_runtime_state();
caml_thread_switch_runtime_state();
}


Expand All @@ -321,9 +323,6 @@ CAMLexport void caml_switch_runtime_locking_scheme(struct caml_locking_scheme* n

static void caml_thread_enter_blocking_section(void)
{
/* Save the current runtime state in the thread descriptor
of the current thread */
caml_thread_save_runtime_state();
/* Tell other threads that the runtime is free */
release_runtime_lock();
}
Expand All @@ -338,7 +337,7 @@ static void caml_thread_leave_blocking_section(void)
#endif
/* Wait until the runtime is free */
acquire_runtime_lock();
caml_thread_restore_runtime_state();
caml_thread_switch_runtime_state();
#ifdef _WIN32
SetLastError(error);
#endif
Expand Down Expand Up @@ -630,7 +629,7 @@ static void caml_thread_stop(void)
changed as the thread was running, so we save it in the
curr_thread data to make sure that the cleanup logic
below uses accurate information. */
caml_thread_save_runtime_state();
thread_save_runtime_state();
/* Tell memprof that this thread is terminating. */
caml_memprof_delete_th_ctx(curr_thread->memprof_ctx);
/* Signal that the thread has terminated */
Expand Down Expand Up @@ -881,7 +880,6 @@ CAMLprim value caml_thread_yield(value unit) /* ML */
*/
caml_raise_async_if_exception(caml_process_pending_signals_exn(),
"signal handler");
caml_thread_save_runtime_state();
/* caml_locking_scheme may have changed in caml_process_pending_signals_exn */
s = atomic_load(&caml_locking_scheme);
s->yield(s->context);
Expand All @@ -890,7 +888,7 @@ CAMLprim value caml_thread_yield(value unit) /* ML */
s->unlock(s->context);
acquire_runtime_lock();
}
caml_thread_restore_runtime_state();
caml_thread_switch_runtime_state();
caml_raise_async_if_exception(caml_process_pending_signals_exn(),
"signal handler");

Expand Down
10 changes: 6 additions & 4 deletions ocaml/otherlibs/systhreads/threads.h
Original file line number Diff line number Diff line change
Expand Up @@ -102,11 +102,13 @@ CAMLextern_libthreads
void caml_switch_runtime_locking_scheme(struct caml_locking_scheme*);

CAMLextern_libthreads
void caml_thread_save_runtime_state(void);

CAMLextern_libthreads
void caml_thread_restore_runtime_state(void);
void caml_thread_switch_runtime_state(void);

/* A prior version of this API used save/restore rather than a single switch.
For compatibility, aliases are defined for the old API.
(These will be removed when the lone user of this API is updated) */
#define caml_thread_save_runtime_state()
#define caml_thread_restore_runtime_state caml_thread_switch_runtime_state

#ifdef __cplusplus
}
Expand Down

0 comments on commit 3d748da

Please sign in to comment.