Skip to content

Wrong Method::invoke implementation #9

@nikvoid

Description

@nikvoid

Method::invoke Implementation works fine only with value types like integers. Using Object in method signature breaks it and causing crashes.

wrapped_mono/src/method.rs

Lines 207 to 215 in fac74e2

pub fn invoke(&self, object: Option<Object>, args: Args) -> Result<Option<Object>, Exception> {
//convert object to invoke on to a pointer.
let obj_ptr = object.map_or(core::ptr::null_mut(), |obj| obj.get_ptr());
let mut expect: *mut MonoException = null_mut();
//convert argument types
let mut args = <Args as InteropSend>::get_mono_rep(args);
let mut params = <<Args as InteropSend>::TargetType as TupleToPtrs>::get_ptrs(
std::ptr::addr_of_mut!(args),
);

Actual problem is in get_ptrs method

wrapped_mono/src/method.rs

Lines 213 to 215 in fac74e2

let mut params = <<Args as InteropSend>::TargetType as TupleToPtrs>::get_ptrs(
std::ptr::addr_of_mut!(args),
);

args is the tuple of pointers and values.

But get_ptrs implementations treat all args members like values, creating pointers to each:

impl<A, B, C> TupleToPtrs for (A, B, C) {
type Res = [*mut c_void; 3];
fn get_ptrs(base_ptr: *mut Self) -> Self::Res {
let a = base_ptr as usize;
let b = a + std::mem::size_of::<A>();
let c = b + std::mem::size_of::<B>();
[a as VoidPtr, b as VoidPtr, c as VoidPtr]
}
}

MonoObject* pointers must be stored by value, not by reference to pointer.

I think this is easy to reproduce using any method that takes Object by pointer value:

let object: Object = /*...*/ ; 
let method: Method<(Object, )> = /*...*/ ;
    
// This works fine
let mut params = [object.get_ptr()];
wrapped_mono::binds::mono_runtime_invoke(method.get_ptr(), 0 as _, params.as_mut_ptr() as _, 0 as _);

// This crashes
method.invoke(None, (object, ));

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions