Reputation: 11913
I am writing a binding to the girara
library and I have an issue with the statusbar item text: the first character is missing.
Here is a part of my binding:
#[link(name="girara-gtk3")]
extern "C" {
// Statusbar.
pub fn girara_statusbar_item_add(session: *mut girara_session_t,
expand: bool,
fill: bool,
left: bool,
callback: girara_statusbar_event_t)
-> *mut girara_statusbar_item_t;
pub fn girara_statusbar_item_set_text(session: *mut girara_session_t,
item: *mut girara_statusbar_item_t,
text: *const c_char);
}
and here is how I call these functions:
let item = unsafe { girara_statusbar_item_add(session, true, true, true, None) };
assert!(item != 0 as *mut _);
let text = CString::new("girara-left").unwrap().as_ptr();
unsafe { girara_statusbar_item_set_text(session, item, text) };
But instead of showing girara-left
, I only see irara-left
.
Is using CString
a good way to send *const c_char
to a FFI?
Why is the first character missing?
Update
There is something weird hapening here.
If I change the code to:
let text = CString::new("girara-left").unwrap().as_ptr();
let text2 = CString::new("hello World").unwrap();
unsafe { girara_statusbar_item_set_text(session, item, text) };
(where text2
is unused), the text hello World
is shown, which does not make sense. It seems the pointer does not point at the right place.
Upvotes: 0
Views: 370
Reputation: 11913
This issue came by the fact that the CString
was dropped before the pointer was sent to the ffi function (see here).
The solution is to bind the CString
to a variable:
let text = CString::new("girara-left").unwrap();
unsafe { girara_statusbar_item_set_text(session, item, text.as_ptr()) };
Upvotes: 2