use convert_case::{Case, Casing}; use once_cell::sync::Lazy; use regex::{Captures, Regex}; static C_PTR_RE: Lazy = Lazy::new(|| Regex::new(r"(const )?([a-zA-Z0-9_]+)\s?\*(.*)").unwrap()); static REST_C_PTR_RE: Lazy = Lazy::new(|| Regex::new(r"(const)?\s?\*").unwrap()); pub fn clean_param_name(param_name: &str) -> String { match param_name { "ref" => "reference", "type" => "ty", "in" => "inside", "box" => "a_box", name => name, } .to_case(Case::Snake) } pub fn fix_type(ty: &str) -> String { let ty = ty.replace("struct", ""); let ty = c_ptr_to_rust_ptr(&ty); ty.replace("void", "std::ffi::c_void") } pub fn c_ptr_to_rust_ptr(c_ptr: &str) -> String { C_PTR_RE .replace(c_ptr, |captures: &Captures| { let const_or_mut = captures.get(1).map_or_else(|| "mut", |_| "const"); let type_name = captures.get(2).unwrap().as_str(); let rest = captures.get(3).unwrap(); let rest_ptr_matches = REST_C_PTR_RE.captures_iter(rest.as_str()); let rest_ptrs = rest_ptr_matches .map(|capts| { let const_or_mut = capts.get(1).map_or_else(|| "mut", |_| "const"); format!("*{const_or_mut} ") }) .collect::>(); format!("{}*{const_or_mut} {type_name}", rest_ptrs.join(" ")) }) .to_string() }