如何从 ADA 调用在 ROM(或地址)中实现的 "C" 函数?

How to call a "C" function that is implemented in a ROM (or at an address) from ADA?

我有一个关于在 ROM 中调用 "C" 函数的方法的问题,正在寻找一种不涉及 link 时间更改的方法。

比如我们知道"C"函数:

int my_func(int a); 

位于地址 0xFFFF_AAAA;

所以我们尝试:

type ROM_my_func is access function (a : Interfaces.C.int) return Interfaces.C.int;

pragma Convention (C, ROM_my_func);

ADA_my_func : ROM_my_func := 16#FFFF_AAAA#;

我无法解决的错误是 ADA_my_func 的赋值,不确定是否存在类型转换,并尝试使用 System.Address_To_Access_Conversions也没有成功。

任何指向示例的指针and/or帮助将不胜感激。

如果您使用的是现代 GNAT 和 Ada2012,您可以说

function My_Func (A : Interfaces.C.Int) return Interfaces.C.Int
with
  Import,
  Convention => C,
  Address => System'To_Address (16#ffff_aaaa#);

注意System’To_Address是GNAT-specific;你可以使用 System.Storage_Elements.To_Address.

我运行一个程序在GDB下使用这个得到

(gdb) run
Starting program: /Users/simon/tmp/so/asker 

Program received signal SIGSEGV, Segmentation fault.
0x00000000ffffaaaa in ?? ()

所以这显然是正确的。

如果不使用 Ada2012 方面,您可以编写

function My_Func (A : Interfaces.C.Int) return Interfaces.C.Int;
pragma Import (C, My_Func);
for My_Func'Address use System'To_Address (16#ffff_aaaa#);