C 为什么';t__属性__((构造函数))是否在静态库中工作?

C 为什么';t__属性__((构造函数))是否在静态库中工作?,c,constructor,attributes,static-libraries,C,Constructor,Attributes,Static Libraries,在以下示例中,程序应打印“foo called”: 但是,如果foo.c被编译到一个静态库中,程序将不打印任何内容 gcc -c main.c gcc -c foo.c as rcs foo.a foo.o gcc -o test foo.a main.o 为什么会发生这种情况?链接器没有在最终程序中包含foo.a中的代码,因为main.o中没有引用它。如果将main.c重写如下,程序将工作: //main.c void foo(); int main() { void (*f)(

在以下示例中,程序应打印“foo called”:

但是,如果foo.c被编译到一个静态库中,程序将不打印任何内容

gcc -c main.c
gcc -c foo.c
as rcs foo.a foo.o
gcc -o test foo.a main.o

为什么会发生这种情况?

链接器没有在最终程序中包含foo.a中的代码,因为main.o中没有引用它。如果将
main.c
重写如下,程序将工作:

//main.c

void foo();

int main()
{
    void (*f)() = foo;
    return 0;
}
此外,在使用静态库进行编译时,gcc(或链接器)的参数顺序非常重要:库必须位于引用它的对象之后

gcc -o test main.o foo.a

如前所述,归档文件中未引用的符号不会进入输出二进制文件,因为默认情况下链接器会丢弃它们

要在链接静态库时覆盖此行为,
--整个存档
/
--不能使用链接器的整个存档
选项,如下所示:

gcc -c main.c
gcc -c foo.c
ar rcs foo.a foo.o
gcc -o test -Wl,--whole-archive foo.a -Wl,--no-whole-archive main.o

这可能会导致二进制文件膨胀,因为链接器会将
foo.a
中的所有符号都包含在输出中,但有时这是合理的。

为什么会进行否决?有什么不正确的吗?不确定(不是我!),但也许有人对你这么快回答自己的问题持异议?嗯,我只是想为一个不明显的问题添加一个有用的网站参考。FAQ表明回答自己的问题是一件好事(其实在第一部分)。
gcc -o test main.o foo.a
gcc -c main.c
gcc -c foo.c
ar rcs foo.a foo.o
gcc -o test -Wl,--whole-archive foo.a -Wl,--no-whole-archive main.o