use crate::PicoError;
use std::{ffi, mem};
#[derive(Debug)]
pub struct PicoString {
mem_layout: std::alloc::Layout,
buf: *mut u8,
}
impl PicoString {
pub fn new(size: usize) -> PicoString {
let mem_size: usize = mem::size_of::<std::os::raw::c_char>() * size;
let mem_layout = std::alloc::Layout::from_size_align(mem_size, 16).unwrap();
let buf = unsafe { std::alloc::alloc(mem_layout) };
PicoString { mem_layout, buf }
}
}
impl PicoString {
pub unsafe fn as_ptr(&self) -> *const std::os::raw::c_char {
self.buf as *const std::os::raw::c_char
}
pub unsafe fn as_mut_ptr(&mut self) -> *mut std::os::raw::c_char {
self.buf as *mut std::os::raw::c_char
}
pub fn to_str(&self) -> Result<&str, std::str::Utf8Error> {
let c_str = unsafe { ffi::CStr::from_ptr(self.buf as *const std::os::raw::c_char) };
c_str.to_str()
}
}
impl Drop for PicoString {
fn drop(&mut self) {
unsafe {
std::alloc::dealloc(self.buf, self.mem_layout);
}
}
}
pub fn make_cstring(string: impl AsRef<str>, err_descr: &str) -> Result<ffi::CString, PicoError> {
ffi::CString::new(string.as_ref()).map_err(|err| PicoError {
code: -1,
descr: format!("{}: {}", err_descr, err),
})
}