您的位置:首页 > 大数据 > 人工智能

RT-Thread源码学习第三篇,$Sub$$main与$Super$$main扩展main函数

2019-02-06 12:39 309 查看

MDK5的__main函数是自动生成的,且无法修改源码。同时,MDK5提供了一对符号$Sub$$和$Super$$来扩展函数。这一对符号作用在连接器,当连接器连接到func时,如果发现存在$Sub$$func函数,会先连接$Sub$$func函数,一直到出现$Super$$func为止,$Super$$func是func函数的新的入口。

Keil官网给的例子:

extern void ExtraFunc(void); extern void $Super$$foo(void):
/* this function is called instead of the original foo() */
void $Sub$$foo(void)
{
ExtraFunc();    /* does some extra setup work */
$Super$$foo();  /* calls the original foo() function */
/* To avoid calling the original foo() function
* omit the $Super$$foo(); function call.
*/
}

$Sub$$和$Super$$符号可以在不修改原程序的情况下添加新功能,rtt就使用了这对符号来扩展main函数。

做一个简单的例子来测试一下这种扩展:

int i = 0;

void $Super$$main(void);
void $Sub$$main(void)
{
i++;
$Super$$main();
}

int main(void)
{
i++;
while(1)
{

}
}

看反汇编(assembly mode),原来跳转到main函数变成了跳转到$Sub$$main函数:

__rt_entry_main:
0x08000172 F000F867  BL.W     $Sub$$main (0x08000244)
0x08000176 F000F84F  BL.W     exit (0x08000218)

 $Sub$$main函数:

$Sub$$main:
0x08000244 B510      PUSH     {r4,lr}
0x08000246 4804      LDR      r0,[pc,#16]  ; @0x08000258
0x08000248 6800      LDR      r0,[r0,#0x00]
0x0800024A 1C40      ADDS     r0,r0,#1
0x0800024C 4902      LDR      r1,[pc,#8]  ; @0x08000258
0x0800024E 6008      STR      r0,[r1,#0x00]
0x08000250 F000F8A8  BL.W     main (0x080003A4)
0x08000254 BD10      POP      {r4,pc}
0x08000256 0000      DCW      0x0000
0x08000258 0000      DCW      0x0000
0x0800025A 2000      DCW      0x2000

这样做,可以保持启动代码不变,而同时实现对main函数的扩展。rtt的调度器就是这样做的。

(adsbygoogle = window.adsbygoogle || []).push({});
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  MDK RT-Thread