在x86_64系统上,当返回值小于等于16字节时,通过寄存器RAX和RDX传递,当返回值大于16字节时,通过第一个sret参数传递。然而,Rust 似乎并不遵循这个规则。
在 C 程序示例中:
struct test_struct {
int a;
int b;
int c;
};
struct test_struct foo() {
struct test_struct a = {1,2,3};
return a;
}
llvm ir中这个函数如下:
define dso_local { i64, i32 } @foo()
我们可以看到返回值是通过寄存器传递的。
在 Rust 程序示例中:
pub struct test_struct {
a: i32,
b: i32,
c: i32,
}
pub fn foo() -> test_struct {
let data = test_struct {
a: 0,
b: 1,
c: 2,
};
data
}
llvm ir中这个函数如下:
define void @_ZN7example3foo17hd5941535b576c335E(ptr sret(%test_struct) %0) unnamed_addr
我们可以看到,可以通过第一个sret参数来传递返回值。 那么 Rust 使用什么 ABI 来传递结构
Rust ABI 未指定,不应依赖。
如果您想使用 C ABI,请将函数指定为
extern "C" fn ...
。确保涉及的所有结构也是 #[repr(C)]
。