对于链接器来说,所有的全局符号可分为两种:强符号(Strong symbols),弱符号(Weak symbols)。gcc的attribute中有个__attribute__((weak)),就是用来声明这个符号是弱符号的。gcc手册中这样写道:
对于这个gcc扩展,这里作了一个简洁的介绍。我们来看更通用的情况。;) 一般来说,函数和已初始化的变量是强符号,而未初始化的变量是弱符号。对于它们,下列三条规则适用: 1. 同名的强符号只能有一个。 这三条规则看起来很好理解,其实不然,尤其是当这些弱符号类型和强符号不同时!表面上看起来正确的程序会导致严重的错误!考虑下面这个csapp中的例子: ===a.c=== ===b.c=== 我们把它们一起编译,并且在p2()函数中给x赋值,你会发现,y也改变了! 虽然x被看作是double,但其定义会取a.c中的int x,也就是说,在b.c中会把a.c中的int x当double来用!这当然是错误!之所以会这样,就是因为上面的规则2。避免这种错误的一个方法是,给gcc加上-fno-common选项。 |
|