我正在编写一些代码,这些代码已经在我的Rust项目中被组装.我和一位同事正在讨论呼叫约定,我一直很难找到明确的资源.
据我所知,Rust调用约定是未定义的.所以,当调用到汇编中时,我应该使用C调用约定来获得已知的内容.
我在三个职能部门之间工作:
unsafe extern "C" fn f(a) -> b
是一个只从Rust调用的裸函数.它完全是汇编的,假设参数和返回值是像C一样完成的(在堆栈上并放入% eax).
因为它被标记为C并从Rust调用,编译器将确保无论在哪里调用它,都将使用C调用约定.
unsafe extern "C" fn g()
也是一个赤裸裸的功能.它从来没有被称为Rust.只有有时f
返回这个函数(即f
的ret
将弹出g
的地址).
虽然这不是一个真正的C函数(我知道它是从f
调用的,并立即使用寄存器而不是f
个左值),它总是会回调到rust函数.本质上,所有这些都是将参数推到堆栈上,然后将call
推到h
(通过使用sym h
).
unsafe fn h
是这里的最后一个功能.它只在内联程序集中从g
经由sym
调用.
因此,h
应该期望用C约定调用,但可以用Rust约定返回(实际上h
永远不会返回).
我的问题是:
使用我的C函数g中的call
和sym h
是否提醒Rust编译器在h
中始终使用C调用约定?
我之前已经将h
标记为extern "C"
,尽管它是纯铁 rust 代码.在我看来,这将确保编译器尊重h
‘S参数是C风格的.但是,代码似乎是双向工作的.我不希望在future Rust决定以不同的方式(并且不正确地)将调用优化为h
时,这一点会改变.