Idea: stack unwinding without panic

Let's say we have a function fn foo() -> ! { .. }, common examples are libc::abort and libc::exit. AFAIK there is no way right now to force stack unwinding before calling such function. For example, it may be usefull if we want to flush data from things like BufWriter before manually terminating thread (e.g. by using pthread_exit).

This functionality probably can not be implemented in third-party libraries, so we need a language support for it. A hypothetical function can look like this:

/// Unwinds stack and when done executes the callback.
fn unwind_stack(f: impl FnOnce() -> !) -> !;

One limitation is that this function should unwind stack only for the current thread. Trying to automatically clean-up other threads is a huge can of worms, probably without a good cross-platform solution which would fit Rust. But users may keep an object on stack with a Drop implementation which will try to gracefully join child threads, e.g. by sending a STOP message and maybe even kill them using pthread_kill if they misbehave.

What do you think about this idea?

Is the implication that this will unwind the entire stack of the thread up to the "top"? I don't think that's a safe assumption, especially because Rust might not own the "top" of the stack.

1 Like

Well, I think there's a way: throw a value that aborts in drop:

struct HotPotato;

impl Drop for HotPotato {
    fn drop(&mut self) {
        std::process::abort()
    }
}

fn main() {
    std::panic::resume_unwind(Box::new(HotPotato));
}
8 Likes