Optimize `Lua::create_registry_value` by reusing previously expired registry keys.
This commit is contained in:
parent
6190427f37
commit
18c3255c90
21
src/lua.rs
21
src/lua.rs
|
@ -1721,14 +1721,29 @@ impl Lua {
|
||||||
let _sg = StackGuard::new(self.state);
|
let _sg = StackGuard::new(self.state);
|
||||||
check_stack(self.state, 4)?;
|
check_stack(self.state, 4)?;
|
||||||
|
|
||||||
|
let unref_list = (*self.extra.get()).registry_unref_list.clone();
|
||||||
self.push_value(t)?;
|
self.push_value(t)?;
|
||||||
|
|
||||||
|
// Try to reuse previously allocated RegistryKey
|
||||||
|
let unref_list2 = unref_list.clone();
|
||||||
|
let mut unref_list2 = mlua_expect!(unref_list2.lock(), "unref list poisoned");
|
||||||
|
if let Some(registry_id) = unref_list2.as_mut().and_then(|x| x.pop()) {
|
||||||
|
// It must be safe to replace the value without triggering memory error
|
||||||
|
ffi::lua_rawseti(self.state, ffi::LUA_REGISTRYINDEX, registry_id as Integer);
|
||||||
|
return Ok(RegistryKey {
|
||||||
|
registry_id,
|
||||||
|
unref_list,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
// Allocate a new RegistryKey
|
||||||
let registry_id = protect_lua!(self.state, 1, 0, |state| {
|
let registry_id = protect_lua!(self.state, 1, 0, |state| {
|
||||||
ffi::luaL_ref(state, ffi::LUA_REGISTRYINDEX)
|
ffi::luaL_ref(state, ffi::LUA_REGISTRYINDEX)
|
||||||
})?;
|
})?;
|
||||||
|
|
||||||
Ok(RegistryKey {
|
Ok(RegistryKey {
|
||||||
registry_id,
|
registry_id,
|
||||||
unref_list: (*self.extra.get()).registry_unref_list.clone(),
|
unref_list,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1787,6 +1802,10 @@ impl Lua {
|
||||||
key: &RegistryKey,
|
key: &RegistryKey,
|
||||||
t: T,
|
t: T,
|
||||||
) -> Result<()> {
|
) -> Result<()> {
|
||||||
|
if !self.owns_registry_value(key) {
|
||||||
|
return Err(Error::MismatchedRegistryKey);
|
||||||
|
}
|
||||||
|
|
||||||
let t = t.to_lua(self)?;
|
let t = t.to_lua(self)?;
|
||||||
unsafe {
|
unsafe {
|
||||||
let _sg = StackGuard::new(self.state);
|
let _sg = StackGuard::new(self.state);
|
||||||
|
|
Loading…
Reference in New Issue