Address #820 - ev/cancel to work on already scheduled fibers.

This commit is contained in:
bakpakin 2021-09-28 15:41:41 -05:00
parent 504411eade
commit 924fe97fc3
3 changed files with 12 additions and 9 deletions

View File

@ -18,8 +18,14 @@
@rem Set compile and link options here @rem Set compile and link options here
@setlocal @setlocal
@rem Example use asan
@rem set JANET_COMPILE=cl /nologo /Isrc\include /Isrc\conf /c /O2 /W3 /D_CRT_SECURE_NO_WARNINGS /MD /fsanitize=address /Zi
@rem set JANET_LINK=link /nologo clang_rt.asan_dynamic-x86_64.lib clang_rt.asan_dynamic_runtime_thunk-x86_64.lib
@set JANET_COMPILE=cl /nologo /Isrc\include /Isrc\conf /c /O2 /W3 /D_CRT_SECURE_NO_WARNINGS /MD @set JANET_COMPILE=cl /nologo /Isrc\include /Isrc\conf /c /O2 /W3 /D_CRT_SECURE_NO_WARNINGS /MD
@set JANET_LINK=link /nologo @set JANET_LINK=link /nologo
@set JANET_LINK_STATIC=lib /nologo @set JANET_LINK_STATIC=lib /nologo
@rem Add janet build tag @rem Add janet build tag
@ -81,7 +87,7 @@ exit /b 1
@echo command prompt. @echo command prompt.
exit /b 0 exit /b 0
@rem Clean build artifacts @rem Clean build artifacts
:CLEAN :CLEAN
del *.exe *.lib *.exp del *.exe *.lib *.exp
rd /s /q build rd /s /q build

View File

@ -75,6 +75,7 @@ typedef struct {
JanetFiber *fiber; JanetFiber *fiber;
Janet value; Janet value;
JanetSignal sig; JanetSignal sig;
uint32_t expected_sched_id; /* If the fiber has been rescheduled this loop, don't run first scheduling. */
} JanetTask; } JanetTask;
/* Wrap return value by pairing it with the callback used to handle it /* Wrap return value by pairing it with the callback used to handle it
@ -447,10 +448,7 @@ const JanetAbstractType janet_stream_type = {
/* Register a fiber to resume with value */ /* Register a fiber to resume with value */
void janet_schedule_signal(JanetFiber *fiber, Janet value, JanetSignal sig) { void janet_schedule_signal(JanetFiber *fiber, Janet value, JanetSignal sig) {
if (fiber->flags & JANET_FIBER_FLAG_SCHEDULED) return; JanetTask t = { fiber, value, sig, ++fiber->sched_id };
fiber->flags |= JANET_FIBER_FLAG_SCHEDULED;
fiber->sched_id++;
JanetTask t = { fiber, value, sig };
janet_q_push(&janet_vm.spawn, &t, sizeof(t)); janet_q_push(&janet_vm.spawn, &t, sizeof(t));
} }
@ -1206,9 +1204,9 @@ JanetFiber *janet_loop1(void) {
/* Run scheduled fibers */ /* Run scheduled fibers */
while (janet_vm.spawn.head != janet_vm.spawn.tail) { while (janet_vm.spawn.head != janet_vm.spawn.tail) {
JanetTask task = {NULL, janet_wrap_nil(), JANET_SIGNAL_OK}; JanetTask task = {NULL, janet_wrap_nil(), JANET_SIGNAL_OK, 0};
janet_q_pop(&janet_vm.spawn, &task, sizeof(task)); janet_q_pop(&janet_vm.spawn, &task, sizeof(task));
task.fiber->flags &= ~JANET_FIBER_FLAG_SCHEDULED; if (task.expected_sched_id != task.fiber->sched_id) continue;
Janet res; Janet res;
JanetSignal sig = janet_continue_signal(task.fiber, task.value, &res, task.sig); JanetSignal sig = janet_continue_signal(task.fiber, task.value, &res, task.sig);
void *sv = task.fiber->supervisor_channel; void *sv = task.fiber->supervisor_channel;
@ -2903,7 +2901,7 @@ JANET_CORE_FN(cfun_ev_deadline,
JANET_CORE_FN(cfun_ev_cancel, JANET_CORE_FN(cfun_ev_cancel,
"(ev/cancel fiber err)", "(ev/cancel fiber err)",
"Cancel a suspended fiber in the event loop. Differs from cancel in that it returns the canceled fiber immediately") { "Cancel a suspended fiber in the event loop. Differs from cancel in that it returns the canceled fiber immediately.") {
janet_fixarity(argc, 2); janet_fixarity(argc, 2);
JanetFiber *fiber = janet_getfiber(argv, 0); JanetFiber *fiber = janet_getfiber(argv, 0);
Janet err = argv[1]; Janet err = argv[1];

View File

@ -47,7 +47,6 @@
#define JANET_FIBER_MASK_USER 0x3FF0 #define JANET_FIBER_MASK_USER 0x3FF0
#define JANET_FIBER_STATUS_MASK 0x3F0000 #define JANET_FIBER_STATUS_MASK 0x3F0000
#define JANET_FIBER_FLAG_SCHEDULED 0x800000
#define JANET_FIBER_RESUME_SIGNAL 0x400000 #define JANET_FIBER_RESUME_SIGNAL 0x400000
#define JANET_FIBER_STATUS_OFFSET 16 #define JANET_FIBER_STATUS_OFFSET 16