编译链接过程

比如源代码是 hello.c

  1. #include <stdio.h>
  2. int main()
  3. {
  4. printf("hello world");
  5. return 0;
  6. }

平时我们开发都是直接使用 ide,实际上ide 帮我们完成了两部分工作
image.png
也就是我们从编写源代码到真正的执行实际分成了下面四个步骤:
image.png
整体编译运行的流程图:
image.png
每个阶段具体完成的事情:
image.png

静态链接

地址重定位

  1. // add.c
  2. #include <stdio.h>
  3. int main()
  4. {
  5. int a = 0;
  6. int b = 0;
  7. //int c = 0; 如果打开这个注释,add 函数的支持就会改变
  8. add(a, b);
  9. return 0;
  10. }
  11. int add(int a, int b)
  12. {
  13. return a + b;
  14. }

假设有上面这个add.c 程序,在main 函数中调用了 add 函数,main 函数肯定是要知道 add 函数的地址是在哪里的才可以执行add函数的代码,若现在将 add(a,b) 这行代码的前面一行注释打开,那么add函数的地址肯定就改变了,重新将add地址给到main函数的过程就是重定位

链接器

因为现在都是分模块化开发,所处需要链接器将所有模块组合起来整个程序才能正常工作
image.png
链接的过程就是经库文件和我们程序编译后的目标文件组合起来形成可执行文件
image.png

  • 常见的库就是运行时库,它是支持程序运行的基本函数的集合
  • 库其实就是一组目标文件的包,也就是一些最常用的代码编译成目标文件打包存放

可以参考《程序员的自我修养-链接、装载与库》对于链接的描述 (2.4 节)

image.png