Skip to content

Commit

Permalink
Add offset option in cast method (lune-org#243)
Browse files Browse the repository at this point in the history
  • Loading branch information
qwreey committed Nov 2, 2024
1 parent 37b5557 commit 4cc2698
Show file tree
Hide file tree
Showing 3 changed files with 29 additions and 8 deletions.
8 changes: 7 additions & 1 deletion crates/lune-std-ffi/src/c/type_info.rs
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,8 @@ pub trait CTypeCast {
into_ctype: &LuaAnyUserData,
_from: &Ref<dyn FfiData>,
_into: &Ref<dyn FfiData>,
_from_offset: isize,
_into_offset: isize,
) -> LuaResult<()> {
// Show error if have no cast implement
Err(Self::cast_failed_with(self, from_ctype, into_ctype))
Expand Down Expand Up @@ -114,17 +116,21 @@ where
methods.add_function(
"cast",
|_,
(from_type, into_type, from, into): (
(from_type, into_type, from, into, from_offset, into_offset): (
LuaAnyUserData,
LuaAnyUserData,
LuaAnyUserData,
LuaAnyUserData,
Option<isize>,
Option<isize>,
)| {
from_type.borrow::<Self>()?.cast(
&from_type,
&into_type,
&from.get_ffi_data()?,
&into.get_ffi_data()?,
from_offset.unwrap_or(0),
into_offset.unwrap_or(0),
)
},
);
Expand Down
10 changes: 6 additions & 4 deletions crates/lune-std-ffi/src/c/types/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ pub mod u64;
pub mod u8;
pub mod usize;

// create CType userdata and export
// CType userdata export
macro_rules! create_ctypes {
($lua:ident, $(( $name:expr, $rust_type:ty, $libffi_type:expr ),)* ) => {
Ok(vec![$((
Expand Down Expand Up @@ -82,9 +82,9 @@ pub fn export_fixed_types(lua: &Lua) -> LuaResult<Vec<(&'static str, LuaAnyUserD

// Implement type-casting for numeric ctypes
macro_rules! define_cast_num {
($from_rust_type:ident, $self:ident, $from_ctype:ident, $into_ctype:ident, $from:ident, $into:ident, $($into_rust_type:ty)*) => {
($from_rust_type:ident, $self:ident, $from_ctype:ident, $into_ctype:ident, $from:ident, $into:ident, $fromOffset:ident, $intoOffset:ident, $($into_rust_type:ty)*) => {
$( if $into_ctype.is::<CTypeInfo<$into_rust_type>>() {
num_cast::<$from_rust_type, $into_rust_type>($from, $into)
num_cast::<$from_rust_type, $into_rust_type>($from, $into, $fromOffset, $intoOffset)
} else )* {
Err($self.cast_failed_with($from_ctype, $into_ctype))
}
Expand Down Expand Up @@ -113,9 +113,11 @@ where
into_info: &LuaAnyUserData,
from: &Ref<dyn FfiData>,
into: &Ref<dyn FfiData>,
from_offset: isize,
into_offset: isize,
) -> LuaResult<()> {
define_cast_num!(
From, self, from_info, into_info, from, into,
From, self, from_info, into_info, from, into, from_offset, into_offset,
u8 u16 u32 u64 u128 i8 i16 i32 i64 i128 f32 f64 usize isize
)
}
Expand Down
19 changes: 16 additions & 3 deletions crates/lune-std-ffi/src/ffi/cast.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,13 +6,26 @@ use num::cast::AsPrimitive;
use super::FfiData;

#[inline]
pub fn num_cast<From, Into>(from: &Ref<dyn FfiData>, into: &Ref<dyn FfiData>) -> LuaResult<()>
pub fn num_cast<From, Into>(
from: &Ref<dyn FfiData>,
into: &Ref<dyn FfiData>,
from_offset: isize,
into_offset: isize,
) -> LuaResult<()>
where
From: AsPrimitive<Into>,
Into: 'static + Copy,
{
let from_ptr = unsafe { from.get_inner_pointer().cast::<From>() };
let into_ptr = unsafe { into.get_inner_pointer().cast::<Into>() };
let from_ptr = unsafe {
from.get_inner_pointer()
.byte_offset(from_offset)
.cast::<From>()
};
let into_ptr = unsafe {
into.get_inner_pointer()
.byte_offset(into_offset)
.cast::<Into>()
};

unsafe {
*into_ptr = (*from_ptr).as_();
Expand Down

0 comments on commit 4cc2698

Please sign in to comment.