-
Notifications
You must be signed in to change notification settings - Fork 3
/
macros.rs
97 lines (79 loc) · 2.06 KB
/
macros.rs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
/// string to c-string
/// required to be converted back to rust string after use
/// to avoid memory leaking
macro_rules! strc_noctx {
($e:expr) => {
std::ffi::CString::new($e).expect("CString::new failed").into_raw()
};
}
macro_rules! str_fromraw {
($e:expr) => {
std::ffi::CString::from_raw($e as *mut std::os::raw::c_char)
};
}
// createates a raw c-string
// and deallocates it in the deconstructor
pub struct StrcCtx{
pub ptr: *mut c_char,
}
impl StrcCtx {
pub fn new(s: &str) -> StrcCtx{
StrcCtx{
ptr: strc_noctx!(s),
}
}
}
impl Drop for StrcCtx{
fn drop(&mut self) {
unsafe{
let _ = str_fromraw!(self.ptr);
}
}
}
/// string to c-string
/// using ontext
macro_rules! strc {
($e:expr) => {
crate::macros::StrcCtx::new($e).ptr
};
}
/// c-string to string
macro_rules! cstr {
($e:expr) => {
if $e == std::ptr::null_mut() {
""
}else{
std::ffi::CStr::from_ptr($e).to_str().unwrap_or("")
}
};
}
macro_rules! cstring {
($e:expr) => {
if $e == std::ptr::null_mut() {
"".to_string()
}else{
unsafe { std::ffi::CStr::from_ptr($e).to_str().unwrap().to_string() }
}
};
}
macro_rules! to_bool {
($e:expr) => {
if $e == -1 { false } else { true }
};
}
use std::os::raw::c_char;
use std::ffi::CString;
// Converts a string into a raw pointer, calls the context then
// after execution, back into a rust string so it can be disposed
pub unsafe fn strc_context1(s: &str, context: fn(raw_str: *mut std::os::raw::c_char)){
let raw_str = strc_noctx!(s);
context(raw_str);
let _ = CString::from_raw(raw_str);
}
pub unsafe fn strc_context2(s1: &str, s2: &str, context: fn(raw_str1: *mut c_char, raw_str2: *mut c_char)){
let raw_str1 = strc_noctx!(s1);
let raw_str2 = strc_noctx!(s2);
context(raw_str1, raw_str2);
let _ = CString::from_raw(raw_str1);
let _ = CString::from_raw(raw_str2);
}