C function parameters, pointers and unsafe


#1

I have C function which gets pointer as parameter, builds object and doesn’t copy memory pointed by pointer, just use this pointer. Rust uses Vec or Vec and calls .as_ptr(). C function must be in block unsafe. It is impossible to change C function, need to change Rust calling. How to prevent from free Vec until exists object making by C function?
Real example: CreateWindowExW get wchar* parameter from Rust and is needed Vec<16> to be live all time until window will be destroyed. With window is associated structure with field string, but method converting it to wchar* uses local Vec.


#2

You need to make sure you do something like this


let data: vec[0; 16] = [0; 16];
unsafe {
  my_c_call(data.ptr());
}

If you construct the vec on the same line as you take out the ptr the point may point to freed/stale memory.

This is a quite common problem when using CString as if you do

unsafe {
  my_c_call(CString::new("foo").as_ptr());
}

This will actually point to freed memory so the way to solve this is to store it in a local variable first.


#3

It sounds like you want to create a &[u16], not a Vec here (see slice::from_raw_parts). That way you are guaranteed with lifetimes, and won’t have the issue where Rust is deallocating somethign it doesn’t own (because it actually belongs to your Windows object).

Shameless plug - I’m not sure if it’s relevant, but me and a couple others have been working on an FFI guide for Rust. It may be helpful for doing this kind of stuff, if you check it out and it doesn’t explain something, let us know in the issue tracker.