Thanks a lot, deeply appreciate your support ![]()
Now the working code became like this:
The c file:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
void c_free_string(const char *str){
free(str);
}
char *concat(const char *str1, const char *str2)
{
char *res;
const char del[] = ", ";
res = malloc(strlen(str1) + strlen(str2) + strlen(del) + 1);
if (!res) {
fprintf(stderr, "malloc() failed: insufficient memory!\n");
return EXIT_FAILURE;
}
strcpy(res, str1);
strcat(res, del);
strcat(res, str2);
printf("Result: '%s'\n", res);
return res;
}
The Rust file:
use std::ffi::{CStr, CString};
use std::os::raw::c_char;
use std::ops::Deref;
use std::fmt;
extern "C" {
fn concat(str1: *const c_char, str2: *const c_char) -> *mut c_char;
fn c_free_string(str: *mut c_char);
}
pub struct Concat(*mut c_char);
impl fmt::Debug for Concat {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
CStr::fmt(self, f)
}
}
impl Drop for Concat {
fn drop(&mut self) {
unsafe { c_free_string(self.0) }
}
}
impl Deref for Concat {
type Target = CStr;
fn deref(&self) -> &CStr {
unsafe { CStr::from_ptr(self.0) }
}
}
fn concat_cstr(str1: &CStr, str2: &CStr) -> Concat {
let concated = unsafe { concat(str1.as_ptr(), str2.as_ptr()) };
Concat(concated)
}
fn main() {
let str1 = CString::new("First").unwrap();
let str2 = CString::new("Second").unwrap();
let concated_string = concat_cstr(str1.as_c_str(), str2.as_c_str());
println!("{:?}", concated_string.to_str());
}