Skip to content
This repository has been archived by the owner on Jun 5, 2024. It is now read-only.

Commit

Permalink
Get rid of thread handles in favor of simple id-based map
Browse files Browse the repository at this point in the history
  • Loading branch information
filiptibell committed Jan 31, 2024
1 parent 5820858 commit 013537b
Show file tree
Hide file tree
Showing 10 changed files with 153 additions and 179 deletions.
4 changes: 2 additions & 2 deletions examples/callbacks.rs
Original file line number Diff line number Diff line change
Expand Up @@ -26,13 +26,13 @@ pub fn main() -> LuaResult<()> {

// Load the main script into the runtime, and keep track of the thread we spawn
let main = lua.load(MAIN_SCRIPT);
let handle = rt.push_thread_front(main, ())?;
let id = rt.push_thread_front(main, ())?;

// Run until completion
block_on(rt.run());

// We should have gotten the error back from our script
assert!(handle.result(&lua).unwrap().is_err());
assert!(rt.thread_result(id).unwrap().is_err());

Ok(())
}
Expand Down
4 changes: 2 additions & 2 deletions examples/scheduler_ordering.rs
Original file line number Diff line number Diff line change
Expand Up @@ -32,13 +32,13 @@ pub fn main() -> LuaResult<()> {

// Load the main script into the runtime, and keep track of the thread we spawn
let main = lua.load(MAIN_SCRIPT);
let handle = rt.push_thread_front(main, ())?;
let id = rt.push_thread_front(main, ())?;

// Run until completion
block_on(rt.run());

// We should have gotten proper values back from our script
let res = handle.result(&lua).unwrap().unwrap();
let res = rt.thread_result(id).unwrap().unwrap();
let nums = Vec::<usize>::from_lua_multi(res, &lua)?;
assert_eq!(nums, vec![1, 2, 3, 4, 5, 6]);

Expand Down
29 changes: 23 additions & 6 deletions lib/functions.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,10 @@ use mlua::prelude::*;
use crate::{
error_callback::ThreadErrorCallback,
queue::{DeferredThreadQueue, SpawnedThreadQueue},
result_map::ThreadResultMap,
runtime::Runtime,
util::LuaThreadOrFunction,
thread_id::ThreadId,
util::{is_poll_pending, LuaThreadOrFunction, ThreadResult},
};

const ERR_METADATA_NOT_ATTACHED: &str = "\
Expand Down Expand Up @@ -63,24 +65,39 @@ impl<'lua> Functions<'lua> {
.app_data_ref::<ThreadErrorCallback>()
.expect(ERR_METADATA_NOT_ATTACHED)
.clone();
let result_map = lua
.app_data_ref::<ThreadResultMap>()
.expect(ERR_METADATA_NOT_ATTACHED)
.clone();

let spawn_map = result_map.clone();
let spawn = lua.create_function(
move |lua, (tof, args): (LuaThreadOrFunction, LuaMultiValue)| {
let thread = tof.into_thread(lua)?;
if thread.status() == LuaThreadStatus::Resumable {
// NOTE: We need to resume the thread once instantly for correct behavior,
// and only if we get the pending value back we can spawn to async executor
match thread.resume::<_, LuaValue>(args.clone()) {
match thread.resume::<_, LuaMultiValue>(args.clone()) {
Ok(v) => {
if v.as_light_userdata()
.map(|l| l == Lua::poll_pending())
.unwrap_or_default()
{
if v.get(0).map(is_poll_pending).unwrap_or_default() {
spawn_queue.push_item(lua, &thread, args)?;
} else {
// Not pending, store the value
let id = ThreadId::from(&thread);
if spawn_map.is_tracked(id) {
let res = ThreadResult::new(Ok(v), lua);
spawn_map.insert(id, res);
}
}
}
Err(e) => {
error_callback.call(&e);
// Not pending, store the error
let id = ThreadId::from(&thread);
if spawn_map.is_tracked(id) {
let res = ThreadResult::new(Err(e), lua);
spawn_map.insert(id, res);
}
}
};
}
Expand Down
130 changes: 0 additions & 130 deletions lib/handle.rs

This file was deleted.

3 changes: 1 addition & 2 deletions lib/lib.rs
Original file line number Diff line number Diff line change
@@ -1,15 +1,14 @@
mod error_callback;
mod functions;
mod handle;
mod queue;
mod result_map;
mod runtime;
mod status;
mod thread_id;
mod traits;
mod util;

pub use functions::Functions;
pub use handle::Handle;
pub use runtime::Runtime;
pub use status::Status;
pub use thread_id::ThreadId;
Expand Down
21 changes: 4 additions & 17 deletions lib/queue.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ use event_listener::Event;
use futures_lite::{Future, FutureExt};
use mlua::prelude::*;

use crate::{handle::Handle, traits::IntoLuaThread, util::ThreadWithArgs};
use crate::{traits::IntoLuaThread, util::ThreadWithArgs, ThreadId};

/**
Queue for storing [`LuaThread`]s with associated arguments.
Expand All @@ -32,31 +32,18 @@ impl ThreadQueue {
lua: &'lua Lua,
thread: impl IntoLuaThread<'lua>,
args: impl IntoLuaMulti<'lua>,
) -> LuaResult<()> {
) -> LuaResult<ThreadId> {
let thread = thread.into_lua_thread(lua)?;
let args = args.into_lua_multi(lua)?;

tracing::trace!("pushing item to queue with {} args", args.len());
let id = ThreadId::from(&thread);
let stored = ThreadWithArgs::new(lua, thread, args)?;

self.queue.push(stored).into_lua_err()?;
self.event.notify(usize::MAX);

Ok(())
}

pub fn push_item_with_handle<'lua>(
&self,
lua: &'lua Lua,
thread: impl IntoLuaThread<'lua>,
args: impl IntoLuaMulti<'lua>,
) -> LuaResult<Handle> {
let handle = Handle::new(lua, thread, args)?;
let handle_thread = handle.create_thread(lua)?;

self.push_item(lua, handle_thread, ())?;

Ok(handle)
Ok(id)
}

pub fn drain_items<'outer, 'lua>(
Expand Down
41 changes: 41 additions & 0 deletions lib/result_map.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
use std::{
cell::RefCell,
collections::{HashMap, HashSet},
rc::Rc,
};

use crate::{thread_id::ThreadId, util::ThreadResult};

#[derive(Clone)]
pub(crate) struct ThreadResultMap {
tracked: Rc<RefCell<HashSet<ThreadId>>>,
inner: Rc<RefCell<HashMap<ThreadId, ThreadResult>>>,
}

impl ThreadResultMap {
pub fn new() -> Self {
Self {
tracked: Rc::new(RefCell::new(HashSet::new())),
inner: Rc::new(RefCell::new(HashMap::new())),
}
}

pub fn track(&self, id: ThreadId) {
self.tracked.borrow_mut().insert(id);
}

pub fn is_tracked(&self, id: ThreadId) -> bool {
self.tracked.borrow().contains(&id)
}

pub fn insert(&self, id: ThreadId, result: ThreadResult) {
assert!(self.is_tracked(id), "Thread must be tracked");
self.inner.borrow_mut().insert(id, result);
}

pub fn remove(&self, id: ThreadId) -> Option<ThreadResult> {
let res = self.inner.borrow_mut().remove(&id)?;
self.tracked.borrow_mut().remove(&id);
Some(res)
}
}
Loading

0 comments on commit 013537b

Please sign in to comment.