diff options
| author | Stefan Monnier | 2022-02-12 15:25:53 -0500 |
|---|---|---|
| committer | Stefan Monnier | 2022-02-12 15:25:53 -0500 |
| commit | b8460fcb8c320ea6d7449f37f07502d10eb74cd5 (patch) | |
| tree | 49eed9555d20693eb01321881204dd9bc45176d1 /src/thread.c | |
| parent | 89bb5a5f357e911aeb0b9f14e8b2f7c5a5fbabf7 (diff) | |
| download | emacs-b8460fcb8c320ea6d7449f37f07502d10eb74cd5.tar.gz emacs-b8460fcb8c320ea6d7449f37f07502d10eb74cd5.zip | |
Rewrite thread context switch code (bug#48990)
Make the context switch code handle buffer-local variables more
correctly by reusing the code originally written for `backtrace-eval`.
This has the side benefit of making the `saved_value` field unused.
* src/lisp.h (enum specbind_tag): Remove `saved_value` field.
(rebind_for_thread_switch, unbind_for_thread_switch): Delete decls.
(specpdl_unrewind): Declare function.
* src/eval.c (specpdl_saved_value): Delete function.
(specbind): Delete the code related to `saved_value`, and consolidate
common code between the different branches.
(rebind_for_thread_switch, -unbind_for_thread_switch): Move to `thread.c`.
(specpdl_unrewind): New function, extracted from `backtrace_eval_unrewind`.
Use `SET_INTERNAL_THREAD_SWITCH`. Skip the buffer & excursion unwinds
depending on new arg `vars_only`.
(backtrace_eval_unrewind): Use it.
(mark_specpdl): Don't mark `saved_value`.
* src/thread.c (rebind_for_thread_switch, unbind_for_thread_switch):
Move from `eval.c` and rewrite using `specpdl_unrewind`.
* test/src/thread-tests.el (threads-test-bug48990): New test.
* test/Makefile.in (test_template): Add a + as suggested by make:
"warning: jobserver unavailable: using -j1. Add '+' to parent make rule".
Diffstat (limited to 'src/thread.c')
| -rw-r--r-- | src/thread.c | 16 |
1 files changed, 16 insertions, 0 deletions
diff --git a/src/thread.c b/src/thread.c index 8a6a2de18be..4c98d590b7a 100644 --- a/src/thread.c +++ b/src/thread.c | |||
| @@ -83,6 +83,22 @@ release_global_lock (void) | |||
| 83 | sys_mutex_unlock (&global_lock); | 83 | sys_mutex_unlock (&global_lock); |
| 84 | } | 84 | } |
| 85 | 85 | ||
| 86 | static void | ||
| 87 | rebind_for_thread_switch (void) | ||
| 88 | { | ||
| 89 | ptrdiff_t distance | ||
| 90 | = current_thread->m_specpdl_ptr - current_thread->m_specpdl; | ||
| 91 | specpdl_unrewind (specpdl_ptr, -distance, true); | ||
| 92 | } | ||
| 93 | |||
| 94 | static void | ||
| 95 | unbind_for_thread_switch (struct thread_state *thr) | ||
| 96 | { | ||
| 97 | ptrdiff_t distance = thr->m_specpdl_ptr - thr->m_specpdl; | ||
| 98 | specpdl_unrewind (thr->m_specpdl_ptr, distance, true); | ||
| 99 | } | ||
| 100 | |||
| 101 | |||
| 86 | /* You must call this after acquiring the global lock. | 102 | /* You must call this after acquiring the global lock. |
| 87 | acquire_global_lock does it for you. */ | 103 | acquire_global_lock does it for you. */ |
| 88 | static void | 104 | static void |