use std::rc::Rc;
use super::StateHandleLease;
use crate::thread_state;
struct StateOwnerFrame;
impl Drop for StateOwnerFrame {
fn drop(&mut self) {
thread_state::runtimes(|state| state.state_owners.borrow_mut().pop());
}
}
pub(crate) fn collecting_states<T>(build: impl FnOnce() -> T) -> (T, Vec<Rc<StateHandleLease>>) {
thread_state::runtimes(push_state_owner);
let frame = StateOwnerFrame;
let value = build();
let states = thread_state::runtimes(take_owned_states);
drop(frame);
(value, states)
}
fn push_state_owner(state: &thread_state::RuntimeThreadState) {
state.state_owners.borrow_mut().push(Vec::new());
}
fn take_owned_states(state: &thread_state::RuntimeThreadState) -> Vec<Rc<StateHandleLease>> {
state
.state_owners
.borrow_mut()
.last_mut()
.map(std::mem::take)
.unwrap_or_default()
}
pub(super) fn hand_to_current_owner(lease: &Rc<StateHandleLease>) -> bool {
thread_state::runtimes(|state| match state.state_owners.borrow_mut().last_mut() {
Some(owner) => {
owner.push(Rc::clone(lease));
true
}
None => false,
})
}