Ruby string to rust and back again
我正在尝试将 Ruby 中的字符串传递给 rust 可执行文件,对其进行操作并将被操作的字符串传回。
到目前为止,我可以将字符串传入并返回,但我不知道如何将其转换为 rust 字符串,对其进行操作,然后将其传递回 ruby??。这是我到目前为止所拥有的:
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
|
// lib. rs
use std::ffi::CStr;
#[no_mangle]
pub extern fn return_string(test_str: &CStr) -> &CStr {
// working funciton
test_str
}
#[no_mangle]
pub extern fn manipulate_and_return_string(mystr: &CStr) -> &CStr {
// mystr type == &std::ffi::c_str::CStr
// println!(“{:?}”, mystr); => std::ffi::c_str::CStr` cannot be formatted using `:?`
let cstr = mystr.to_bytes_with_nul();
// println!(“{:?}”, mystr); => []
// cstr type == &[u8]
let ptr = cstr.as_ptr();
// ptr type == *const u8
// println!(“{:?}”, mystr); => 0x7fd898edb520
let str_slice: &str = std::str::from_utf8(cstr).unwrap();
// str type == &str
// println!(“{:?}”, mystr); =>””
let str_buf: String = str_slice.to_owned();
// str_bug == collections::string::String
// println!(“{:?}”, mystr); =>””
}
|
1 2 3 4 5 6 7 8 9 10
|
# rust.rb
require ‘ffi’
module Rust
extend FFI::Library
ffi_lib ‘./bin/libembed.dylib’
attach_function :return_string, [:string], :string
attach_function :manipulate_and_return_string, [:string], :string
end
|
- 快速评论:这有两个直接的问题。首先,CStr 不是 FFI 安全类型,不应该这样使用。您应该使用 *const libc::c_char。其次,答案完全取决于谁拥有结果字符串。 Ruby 管理它吗?如果是这样,怎么做?它需要分配在哪个堆上? Rust 还拥有它吗?如果是这样,您如何提供清理功能?我所能推荐的就是找出如何在 C 中做到这一点,然后在 Rust 中这样做。
-
另请查看 stackoverflow.com/q/30510764/155423,因为它涵盖了所有重要部分。在这一点上使其适应 Ruby 很容易。
-
clalance.blogspot.ca/2011/01/… 会有帮助,github.com/ruby/ruby/blob/trunk/doc/extension.rdoc 也会有帮助
感谢 Steve Klabnik、shepmaster 和 DK 的一些指导,我想出了如何在 Rust 中编写外部字符串 concat 函数并在 Ruby 中使用它。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23
|
// lib. rs
#![feature(libc)]
#![feature(cstr_to_str)]
#![feature(cstr_memory)]
extern crate libc;
use std::ffi:: {CStr,CString };
#[no_mangle]
pub extern fn concat(s1: *const libc::c_char, s2: *const libc::c_char) -> *const libc::c_char {
let s1_cstr = unsafe { CStr::from_ptr(s1) }; // &std::ffi::c_str::CStr
let s2_cstr = unsafe { CStr::from_ptr(s2) }; // &std::ffi::c_str::CStr
let s1_and_str = s1_cstr.to_str().unwrap(); // &str
let s2_and_str = s2_cstr.to_str().unwrap(); // &str
let mut s1_string = s1_and_str.to_string(); // collections::string::String
s1_string.push_str(s2_and_str);
// s1_string + s2_and_str); // same thing
let concated_string = CString::new(s1_string).unwrap(); // std::ffi::c_str::CString
concated_string.into_ptr() // const i8
}
|
1 2 3 4 5 6 7 8 9
|
# rust.rb
require ‘ffi’
module Rust
extend FFI::Library
ffi_lib ‘./bin/libembed.dylib’
attach_function :concat, [:string, :string], :string
end
|
1 2 3
|
#calling the function in Ruby
Rust.concat(‘This is a ‘, ‘cohesive sentence’) # => ‘This is a cohesive sentence’
|
来源:https://www.codenong.com/31021453/
微信公众号
手机浏览(小程序)
Warning: get_headers(): SSL operation failed with code 1. OpenSSL Error messages:
error:14090086:SSL routines:ssl3_get_server_certificate:certificate verify failed in
/mydata/web/wwwshanhubei/web/wp-content/themes/shanhuke/single.php on line
57
Warning: get_headers(): Failed to enable crypto in
/mydata/web/wwwshanhubei/web/wp-content/themes/shanhuke/single.php on line
57
Warning: get_headers(https://static.shanhubei.com/qrcode/qrcode_viewid_9804.jpg): failed to open stream: operation failed in
/mydata/web/wwwshanhubei/web/wp-content/themes/shanhuke/single.php on line
57