You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
alexis 3fb16dc637 utask_fixup_stack_len: round down, not up
Closes #3
4 months ago
inc utask_fixup_stack_len: round down, not up 4 months ago
src Define stack by bottom and size 4 months ago
README.md Add a readme 4 months ago
meson.build Initial import of task from xutil 4 months ago

README.md

utask

utask (micro-task) is an extremely lightweight cooperative multitasking library. µTasks are simply executed round-robin until each one yields.

By using compiler extensions in the form of synchronization builtins and carefully constructed clobber lists, utask gets an absolutely minimal context switch. Instead of saving and restoring all registers every time (on some architectures this is a lot — a RISC-V with floating point has 63 registers!), utask simply invalidates all registers before the context switch. This tells the compiler that after the switch, it is responsible for recomputing the contents of any registers that had active allocations. This is much faster, because chances are, you do not have all 63 registers in use at once.

Supported architectures

  • RISC-V

API example

static void task1_f(uintptr_t arg);
static void task2_f(uintptr_t arg);

utask_decl_stack(task1_s, 1024);
utask_decl_stack(task2_s, 1024);

utask_t task1 = {
	.func = task1_f,
	.stack = task1_s,
	.stack_size = sizeof(task1_s),
	.name = "task1",
	UTASK_INIT
};

utask_t task2 = {
	.func = task2_f,
	.stack = task2_s,
	.stack_size = sizeof(task2_s),
	.name = "task2",
	UTASK_INIT
};

int main()
{
	utask_add(&task2, 0);
	utask_add(&task1, 0);
	utask_run();
}

static void task1_f(uintptr_t arg)
{
	printf("Hello, ");
	utask_yield();
}

static void task2_f(uintptr_t arg)
{
	printf("world!\n");
	utask_yield();
}

Copying

This code may not be used by anybody for any purpose. Be gay, do crime.