sammhicks / nostd_async

An asyncronous runtime for a single-threaded no_std environment
MIT License
17 stars 2 forks source link

Soundness issues #4

Open Dirbaio opened 8 months ago

Dirbaio commented 8 months ago
sammhicks commented 1 month ago

As of 9ff2b37f559a99f84c484edc6c9d258b43119fa6, Miri no longer complains.

Dirbaio commented 1 month ago

the other issues still stand though!

it's fundamentally unsound to allocate tasks in the stack and make wakers point directly to the tasks.

sammhicks commented 1 month ago

@Dirbaio I think I have a solution, currently sitting in pinned_tasks. Both futures_util::pin_mut! and core::pin::pin! take ownership of the task, ensuring that they cannot be core::mem::forgeted.

Dirbaio commented 1 month ago

That doesn't fix the 1st issue "Wakers contain a pointer to stack-allocated tasks, and nothing prevents the task from being deallocated while there still are wakers pointing to it.".

Wakers are 'static. Once you get a waker pointing to a task, you can store it literally anywhere, forever. If the task is pinned then you're guaranteed its Drop will run, but there's no way to make Drop "recall" all the wakers pointing to the task that could be stored anywhere across the whole program.

It's possible to do if you add indirection to the wakers. Like, store a "task ID" in wakers, executor contains an id->pointer map so you can mark the id as "stale" on task drop to "deactivate" all the wakers. This adds complexity and hurts perf tho.

I've looked at this hard over the years and my conclusion is the only two good designs are either to alloc+refcount tasks (what most std executors do) or statically allocate tasks so they live forever (what embassy-executor and RTIC do). There's no way to stack-allocate tasks with good perf.

sammhicks commented 1 month ago

Yes, Wakers are the unsolvable issue.

I'd originally written this crate way back in 2020 when as far as I could see there wasn't really a way of doing async on bare metal. Since then both embassy and RTIC have flourished, and if fact I use embassy for my personal projects. As such, I think it's time to deprecate and retire nostd_async.

Do you by any chance know how I might do this?

Possibilities include: