Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 3 additions & 3 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

10 changes: 7 additions & 3 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -9,9 +9,9 @@ exclude = [

[workspace.dependencies]
# local
luars = { path = "crates/luars", version = "0.24.0" }
luars-derive = { path = "crates/luars-derive", version = "0.10.1" }
luars_debugger = { path = "crates/luars_debugger", version = "0.24.0" }
luars = { path = "crates/luars", version = "0.25.0" }
luars-derive = { path = "crates/luars-derive", version = "0.11.0" }
luars_debugger = { path = "crates/luars_debugger", version = "0.25.0" }

wasm-bindgen = "0.2"
ahash = "0.8"
Expand All @@ -23,3 +23,7 @@ serde_json = "1.0"

[workspace.lints.rust]
unused_qualifications = "deny"

[profile.release]
opt-level = 3
debug = true
2 changes: 1 addition & 1 deletion crates/luars-derive/Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
[package]
name = "luars-derive"
version = "0.10.1"
version = "0.11.0"
edition = "2024"
authors = ["CppCXY"]
description = "A procedural macro crate for luars, providing derive macros for Lua userdata types"
Expand Down
2 changes: 1 addition & 1 deletion crates/luars/Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
[package]
name = "luars"
version = "0.24.0"
version = "0.25.0"
edition = "2024"
authors = ["CppCXY"]
description = "A library for lua 5.5 runtime implementation in Rust"
Expand Down
26 changes: 18 additions & 8 deletions crates/luars/src/gc/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -396,7 +396,16 @@ impl GC {
l.remove_dead_string(str_ptr);
}

#[inline]
fn prepare_object_for_release(obj: &mut GcObjectOwner) {
if let Some(thread) = obj.as_thread_mut() {
thread.release();
}
}

fn release_or_detach_object(obj: GcObjectOwner) {
let mut obj = obj;
Self::prepare_object_for_release(&mut obj);
if obj.header().is_shared() {
std::mem::forget(obj);
} else {
Expand Down Expand Up @@ -626,7 +635,8 @@ impl GC {

/// Release a GC object by dropping it.
#[inline]
fn release_object(&mut self, obj: GcObjectOwner) {
fn release_object(mut obj: GcObjectOwner) {
Self::prepare_object_for_release(&mut obj);
drop(obj);
}

Expand Down Expand Up @@ -2503,7 +2513,7 @@ impl GC {

let obj = self.allgc.remove(gc_ptr);
self.total_bytes -= obj.size() as isize;
drop(obj);
Self::release_object(obj);
}
} else {
// 存活对象:重置为当前白色 + G_NEW
Expand Down Expand Up @@ -2548,7 +2558,7 @@ impl GC {

let obj = self.survival.remove(gc_ptr);
self.total_bytes -= obj.size() as isize;
drop(obj);
Self::release_object(obj);
}
} else {
// 存活对象:重置为当前白色 + G_NEW,移回 allgc
Expand Down Expand Up @@ -2593,7 +2603,7 @@ impl GC {

let obj = self.old.remove(gc_ptr);
self.total_bytes -= obj.size() as isize;
drop(obj);
Self::release_object(obj);
}
} else {
// 存活对象:重置为当前白色 + G_NEW,移回 allgc
Expand Down Expand Up @@ -2692,7 +2702,7 @@ impl GC {
Self::remove_dead_string_from_intern(l, gc_ptr.as_string_ptr());
}
self.total_bytes -= gc_owner.size() as isize;
self.release_object(gc_owner);
Self::release_object(gc_owner);
continue;
}

Expand Down Expand Up @@ -2912,7 +2922,7 @@ impl GC {
GC::remove_dead_string_from_intern(l, gc_ptr.as_string_ptr());
}
*total_bytes -= gc_owner.size() as isize;
drop(gc_owner);
Self::release_object(gc_owner);
}
} else {
gc_owner.header_mut().set_age(G_OLD);
Expand Down Expand Up @@ -3576,7 +3586,7 @@ impl GC {
#[cfg(debug_assertions)]
Self::validate_not_on_stack(&gc_owner, &stack_ptrs, &self.old);
self.total_bytes -= gc_owner.size() as isize;
self.release_object(gc_owner);
Self::release_object(gc_owner);
}
} else {
// BUG FIX: Match C Lua 5.5's sweepgen age-dependent logic.
Expand Down Expand Up @@ -3640,7 +3650,7 @@ impl GC {
#[cfg(debug_assertions)]
Self::validate_not_on_stack(&gc_owner, &stack_ptrs, &self.old);
self.total_bytes -= gc_owner.size() as isize;
self.release_object(gc_owner);
Self::release_object(gc_owner);
}
} else {
let size = gc_owner.size() as isize;
Expand Down
12 changes: 10 additions & 2 deletions crates/luars/src/gc/object_allocator.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,12 +3,12 @@ use crate::lua_value::UpvalueStore;
use crate::lua_value::{
CClosureFunction, LuaProto, LuaUpvalue, LuaUserdata, RClosureFunction, RustCallback,
};
use crate::lua_vm::{CFunction, LuaState};
use crate::lua_vm::{CFunction, CallInfo, LuaState};
use crate::{
LuaRawFunction, LuaRawTable, LuaResult, LuaValue,
gc::{
GC, GcCClosure, GcFunction, GcObjectOwner, GcProto, GcRClosure, GcString, GcTable,
GcThread, GcUpvalue, GcUserdata, PagedPool, ProtoPtr, StringPtr, TableAllocHandle,
GcThread, GcUpvalue, GcUserdata, PagedPool, Pooled, ProtoPtr, StringPtr, TableAllocHandle,
UpvaluePtr,
},
};
Expand All @@ -25,6 +25,7 @@ pub struct ObjectAllocator {
upvalue_pool: PagedPool<GcUpvalue>,
userdata_pool: PagedPool<GcUserdata>,
proto_pool: PagedPool<GcProto>,
call_info_pool: PagedPool<CallInfo>,
table_allocator: TableAllocHandle,
}

Expand All @@ -46,10 +47,16 @@ impl ObjectAllocator {
upvalue_pool: PagedPool::new(64),
userdata_pool: PagedPool::new(16),
proto_pool: PagedPool::new(16),
call_info_pool: PagedPool::new(64),
table_allocator: TableAllocHandle::default(),
}
}

#[inline(always)]
pub fn alloc_call_info(&mut self, value: CallInfo) -> Pooled<CallInfo> {
self.call_info_pool.alloc(value)
}

/// Create or intern a string (Lua-style with proper hash collision handling)
///
#[inline]
Expand Down Expand Up @@ -279,6 +286,7 @@ impl ObjectAllocator {
self.upvalue_pool.release_empty_pages();
self.userdata_pool.release_empty_pages();
self.proto_pool.release_empty_pages();
self.call_info_pool.release_empty_pages();
self.userdata_pool.release_empty_pages();
}
}
2 changes: 1 addition & 1 deletion crates/luars/src/lua_api/lua_state.rs
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ fn stack_api_base(state: &LuaState) -> usize {
if state.call_depth() == 0 {
0
} else {
state.call_stack[state.call_depth() - 1].base
state.current_frame().map(|frame| frame.base).unwrap_or(0)
}
}

Expand Down
43 changes: 43 additions & 0 deletions crates/luars/src/lua_vm/call_info.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@

use crate::gc::UpvaluePtr;
use crate::lua_value::LuaProto;
use std::ops::{Deref, DerefMut};
use std::ptr::NonNull;

/// Call status flags (equivalent to Lua's CIST_* flags)
pub mod call_status {
Expand Down Expand Up @@ -132,6 +134,47 @@ pub struct CallInfo {
pub aux_i32: i32,
}

#[derive(Clone, Copy)]
pub struct CallInfoPtr(NonNull<CallInfo>);

impl CallInfoPtr {
#[inline(always)]
pub fn from_mut(value: &mut CallInfo) -> Self {
Self(NonNull::from(value))
}

#[inline(always)]
pub fn as_ptr(self) -> *mut CallInfo {
self.0.as_ptr()
}

#[inline(always)]
pub unsafe fn as_ref<'a>(self) -> &'a CallInfo {
unsafe { self.0.as_ref() }
}

#[inline(always)]
pub unsafe fn as_mut<'a>(self) -> &'a mut CallInfo {
unsafe { &mut *self.0.as_ptr() }
}
}

impl Deref for CallInfoPtr {
type Target = CallInfo;

#[inline(always)]
fn deref(&self) -> &Self::Target {
unsafe { self.0.as_ref() }
}
}

impl DerefMut for CallInfoPtr {
#[inline(always)]
fn deref_mut(&mut self) -> &mut Self::Target {
unsafe { &mut *self.0.as_ptr() }
}
}

impl CallInfo {
/// Create a new call frame for a Lua function
pub fn new_lua(base: usize, nparams: usize) -> Self {
Expand Down
Loading
Loading