指向ROM中的功能

时间:2012-01-19 00:03:21

标签: c embedded

我正在使用微控制器。在调试时,必须调用一个在ROM中硬编码的函数。技术参考说明了如何执行此操作:

# define Device_cal (void(*)(void))0x3D7C80

并且调用过程如下所示:

(*Device_cal)()

我无法理解这里发生了什么,所以我的问题是: 它是如何工作的?

5 个答案:

答案 0 :(得分:7)

void (*) (void)是一种类型。它是一个指向函数的指针,该函数不带参数并返回void

(void(*)(void)) 0x3D7C800x3D7C80整数强制转换为此函数指针。

(*Device_cal)()调用该函数。

(Device_cal)()会完全一样。

*Device_calDevice_cal周围的括号是必需的,否则对整数的强制转换不会有更高的优先级。

答案 1 :(得分:3)

#define会导致(*Device_cal)()在编译前立即展开:

(*(void(*)(void))0x3D7C80)()

void(*)(void)是函数指针的声明,它采用void并返回void类型。 (*())表示表达式(0x3D7C80)中下一个标记的强制转换。因此,这要求将位置0x3D7C80处的数据视为一个函数。最后的()调用没有参数的函数。

答案 2 :(得分:2)

好吧,你“定义”一个指向函数的指针,然后调用它。 void(*)(void)表示指向函数的指针,它不带参数,并返回void。 如果您将0x3D7C80强制转换为该类型并调用它,则基本上会调用其地址为0x3D7C80的函数。

答案 3 :(得分:2)

这不是一个答案(已经令人满意地完成),但有些建议:

我建议使用以下方法:

typedef void (*tVOID_ROMFUNCTION_VOID)( void ) ;

tVOID_ROMFUNCTION_VOID Device_cal = (tVOID_ROMFUNCTION_VOID)0x3D7C80 ;

Device_cal() ;

这样,您可以在初始化时创建任意数量的全局函数指针,而调用看起来像普通的静态链接函数。并且您可以避免同时混淆预处理器宏voodoo。

通过创建具有不同签名的不同函数指针类型,编译器也可以为您执行一些参数类型检查。

答案 4 :(得分:0)

粘贴符号,在其中创建一个指向固定内存位置的函数的临时(未命名)指针,然后通过解除引用来调用它。