在链接脚本中,经常有这样的代码:
会话{
.
.=align(4);
. Rodata:{*(.Rodata ) }
.=align(4);
. data:{*(.data ) }
.=align(4);
. got : { *(.got
.=align(4);
__bss_start=.
. BSS:{*(.BSS ) }
_end=.
}其中__bss_start,_end表示BSS段的开始、结束地址。
如果希望此空间为零,则可以直接在1 .程序集代码中引用__bss_start,_end。 例如,以下情况:
ldr r0,=__bss_start
ldr r1,=_end )。
2.在C代码中,我们不能直接引用它们,要这样做:
void clean_bss(void ){
extern int __bss_start,_end;
int *p=__bss_start;
for (; p _end; p )
*p=0;
}
你可能会怀疑。 __bss_start,_end不是表示某个值吗? 为什么在c代码中使用地址符号?
理由:第一,在c代码中,这样的语句:
int foo=1000; 会发生两件事
代码中留出4字节的空间,存储数值1000
在c语言的symbole talbe (符号表)中,有一个名为foo的项,其中包含该4字节空间的地址。
我们执行foo=1时,首先在符号表中找到与foo对应的地址,并将数值1填写到与该地址对应的内存中;
我们执行int *a=foo时,将符号表中foo的地址直接写入a。
二,在链接脚本中,假设
_ _ BSS _ start=1000 _ _ BSS _ start不仅仅是变量,它只是一个值,不需要在内存中留出空间进行保存。在c语言中,符号表中有一个名为__bss_start的项目。 该项目的值(地址值)为1000。
请注意,这1000没有实际存在的内存。
三所以:在C语言中,要去使用链接脚本中定义的值时,应该这样做:
extern int __bss_start;int val=__bss_start; 使用地址符号获取符号表中的值。 请注意,此值是在链接脚本中定义的值,不表示变量的地址。
————————————————
这是CSDN博客“bbdbz”的原始文章,符合CC 4.0 BY-SA版权协议。 请附上原文来源的链接和本声明。
原文链接: https://blog.csdn.net/this way _ DIY/article/details/101016296