gcc编译流程简介

编译过程中隐藏着很多细节,了解那些隐藏的细节可以帮助我们深入的理解产生的大量警告和错误信息,从而可以更精确的编译程序和控制连接。
1.C预处理器 cpp
C预处理器cpp是用来完成宏的求知、条件编译、以及其他一些需要把代码传递到编译器前的工作。通常所见的那些“#”号后面的语句由cpp来进行处理。来看下面一段代码:
#define FOO (5*2)
...
printf("%d\n",FOO*2);
...

经过cpp预处理后,代码变成下面形式:
printf("%d\n",(5*2)*2);
可以看出,cpp完成了以下工作:
解释宏,处理包含文件,处理#if和#ifdef声明,还有其他以#开头的标志。可以在命令行中使用cpp,也可以使用gcc -E调用cpp,通常gcc编译器会自动调用cpp,前面的实例中就是gcc自动调用cpp。

2.GUN连接器 ld
在编写一个大程序时,经常把它分成许多独立的模块,这时需要连接器把所有的模块组合起来,并结合C函数库和初始化代码,产生最后的可执行文件。连接器在产生可执行文件之前,起到重要的作用。
通常情况下,ld被编译器所调用,产生可执行代码,但是如果想更好的控制连接过程,最好手工调用ld。

3.GUN汇编器 as
使用gcc编译程序时,产生汇编代码,as会处理这些汇编代码,从而产生目标文件(二进制文件),而目标文件将生成.o文件、库或者最终的可执行文件。as像前两项一样,通常情况下是gcc调用的,但是想使用汇编语言编写程序,可以手工调用。

4.文件处理器 ar
可以使用ar程序建立静态库,把几个小文件组合成一个大文件。建立静态库时,必须把多个.o文件组合成一个单独的.a文件。

5.库显示 ldd
一个可执行文件可能要使用一些共享函数库,可以使用ldd工具显示它们,ldd是Library Dependency Display的缩写。
命令行如下:
$ldd ./test

猜你喜欢

转载自blog.csdn.net/chenzhengfeng/article/details/81387834