|
Serene Runtime 1.0.0-dev
C runtime for the Serene programming language
|
#include "serene/rt/fiber.h"#include <inttypes.h>#include <stdio.h>#include <string.h>#include "serene/rt/context.h"#include "serene/rt/engine.h"#include "serene/utils.h"Go to the source code of this file.
Functions | |
| void | srn_fiber_switch (srn_fiber_t *from, srn_fiber_t *to) |
| Compiled without AddressSanitizer instrumentation, in stack-use-after-return mode ASan would place from/to on a fake stack that __sanitizer_start_switch_fiber releases before srn_fiber_swap reads them. | |
| void | srn_fiber_switch_final (srn_fiber_t *to) |
| Like srn_fiber_switch, but for a fiber that has finished and must not be resumed, control transfers to to and never comes back. | |
| void | srn_fiber_on_entry (srn_fiber_t *from) |
| Call as the first action inside a fresh fiber's entry. | |
| void | srn_fiber_on_reap (srn_fiber_t *fiber) |
| Call when a finished fiber is reaped, after it has switched away for the last time. | |
| void | srn_fiber_init_thread (srn_fiber_t *f) |
| Represent the calling OS thread as the running fiber ("#0"), so the scheduler or a test can switch away from it and back. | |
| static void | srn_fiber_launcher (void *fiber_ptr) |
| srn_fiber_t * | srn_fiber_make (srn_context_t *ctx, srn_scheduler_t *sched, const char *name, srn_fiber_entry_t entry, void *arg, size_t stack_size) |
| Create a fiber that will run entry(ctx, arg), registered with sched but NOT scheduled. | |
| srn_fiber_t * | srn_fiber_spawn (srn_context_t *ctx, srn_fiber_entry_t entry, void *arg) |
| Make and schedule a fiber with every default, the engine's scheduler, the configured stack size, and an autogenerated name. | |
| srn_fiber_t * | srn_fiber_spawn_copy (srn_context_t *ctx, srn_fiber_entry_t entry, const void *arg, size_t size) |
| srn_fiber_spawn with size bytes of *arg copied into ctx first, so the fiber owns its argument and the caller's stack frame can die freely. | |
| void srn_fiber_init_thread | ( | srn_fiber_t * | f | ) |
Represent the calling OS thread as the running fiber ("#0"), so the scheduler or a test can switch away from it and back.
The thread's stack bounds are not queried here (there is no portable way). Under the sanitizer they are recorded by the first fiber's srn_fiber_on_entry. The saved context is written by the first switch away.
Definition at line 154 of file fiber.c.
|
static |
Definition at line 184 of file fiber.c.
|
nodiscard |
Create a fiber that will run entry(ctx, arg), registered with sched but NOT scheduled.
The fiber stays NEW until srn_fiber_schedule starts it, so a caller can build several fibers and wire them up before any of them runs. Registration at creation means the scheduler reaps every fiber at shutdown, scheduled or not.
name is a debug label copied into the fiber, truncated to SRN_FIBER_NAME_MAX - 1 bytes, or nullptr for an autogenerated unique one. A stack_size of 0 selects the configured per fiber default.
Definition at line 201 of file fiber.c.
| void srn_fiber_on_entry | ( | srn_fiber_t * | from | ) |
Call as the first action inside a fresh fiber's entry.
from is the fiber that started this one (the scheduler, or the bootstrap thread fiber). It completes the switch for AddressSanitizer and, since from's stack bounds only become discoverable here, records them into from so a later switch back is tracked. from may be null. A no-op when the sanitizer is not in use.
Definition at line 111 of file fiber.c.
| void srn_fiber_on_reap | ( | srn_fiber_t * | fiber | ) |
Call when a finished fiber is reaped, after it has switched away for the last time.
Releases the fiber's ThreadSanitizer handle. A no-op when the sanitizer is not in use.
Definition at line 133 of file fiber.c.
| srn_fiber_t * srn_fiber_spawn | ( | srn_context_t * | ctx, |
| srn_fiber_entry_t | entry, | ||
| void * | arg ) |
Make and schedule a fiber with every default, the engine's scheduler, the configured stack size, and an autogenerated name.
The caller keeps ownership of arg and must keep it alive until the fiber is done with it, srn_fiber_spawn_copy lifts that burden.
Definition at line 247 of file fiber.c.
| srn_fiber_t * srn_fiber_spawn_copy | ( | srn_context_t * | ctx, |
| srn_fiber_entry_t | entry, | ||
| const void * | arg, | ||
| size_t | size ) |
srn_fiber_spawn with size bytes of *arg copied into ctx first, so the fiber owns its argument and the caller's stack frame can die freely.
The copy lives until the context is released, like the fiber itself.
Definition at line 255 of file fiber.c.
| void srn_fiber_switch | ( | srn_fiber_t * | from, |
| srn_fiber_t * | to ) |
Compiled without AddressSanitizer instrumentation, in stack-use-after-return mode ASan would place from/to on a fake stack that __sanitizer_start_switch_fiber releases before srn_fiber_swap reads them.
Switch from from to to, both live fibers, telling AddressSanitizer about the stack change.
Not instrumented by either sanitizer, the stack swaps mid-function, which confuses ASan's fake stack and TSan's shadow stack. The explicit annotations keep each sanitizer's fiber tracking correct across the swap instead.
Definition at line 66 of file fiber.c.
| void srn_fiber_switch_final | ( | srn_fiber_t * | to | ) |
Like srn_fiber_switch, but for a fiber that has finished and must not be resumed, control transfers to to and never comes back.
The fiber's entry function therefore ends at this call – any code after it is unreachable, which is why this is [[noreturn]]. Nothing is freed here. The spent fiber's stack is left frozen and reclaimed later by its owner (the scheduler reaps a finished fiber and frees its stack via srn_fiber_stack_free).
Definition at line 88 of file fiber.c.