use crate::Key;
use crate::Value;
use std::ffi::CStr;
use std::ptr;
#[unsafe(no_mangle)]
pub extern "C" fn key_new(name: *const i8, value: *const Value) -> *mut Key {
unsafe {
if name.is_null() || value.is_null() { return ptr::null_mut(); }
let cstr = CStr::from_ptr(name);
let name_str = match cstr.to_str() { Ok(s) => s, Err(_) => return ptr::null_mut() };
Box::into_raw(Box::new(Key::new(name_str, (*value).clone())))
}
}
#[unsafe(no_mangle)]
pub extern "C" fn key_free(key: *mut Key) {
unsafe { if !key.is_null() { let _ = Box::from_raw(key); } }
}
#[unsafe(no_mangle)]
pub extern "C" fn key_serialize(key: *const Key, out_bytes: *mut u8, max_len: usize) -> usize {
unsafe {
if key.is_null() || out_bytes.is_null() { return 0; }
let key = &*key;
match key.serialize() {
Ok(vec) => {
let len = vec.len().min(max_len);
ptr::copy_nonoverlapping(vec.as_ptr(), out_bytes, len);
len
}
Err(_) => 0,
}
}
}
#[unsafe(no_mangle)]
pub extern "C" fn key_deserialize(bytes: *const u8, len: usize) -> *mut Key {
unsafe {
if bytes.is_null() || len == 0 { return ptr::null_mut(); }
let vec = std::slice::from_raw_parts(bytes, len).to_vec();
match Key::deserialize(vec) {
Ok(k) => Box::into_raw(Box::new(k)),
Err(_) => ptr::null_mut(),
}
}
}
#[unsafe(no_mangle)]
pub extern "C" fn key_get_name(key: *const Key) -> *const i8 {
unsafe {
if key.is_null() { return ptr::null(); }
(*key).name.as_ptr() as *const i8
}
}
#[unsafe(no_mangle)]
pub extern "C" fn key_set_value(key: *mut Key, value: *const Value) {
unsafe {
if key.is_null() || value.is_null() { return; }
(*key).set_value((*value).clone());
}
}
#[unsafe(no_mangle)]
pub extern "C" fn key_get_value(key: *const Key) -> *const Value {
unsafe {
if key.is_null() { return ptr::null(); }
&(*key).value
}
}