gcc编译过程简析

今天360面试,问了一道gcc编译的问题,说实话这个问题在之前真看过,不过不知道多就之前了,所以忘记了,只答出了由.xxc直接到目标文件xx.o然后直接到可执行文件了。

正文

gcc的整个编译过程分为四个阶段:预编译,编译,汇编以及链接
这里准备一个test.c文件作为例子进行说明
<pre name="code" class="cpp">#include <stdio.h>

#define HELLO "hello world"
int main(){
    printf("%s\n",HELLO);
    return 0;
}


 
 

预编译: 

将源文件中所有的#开头的内存做处理,宏替换就是在这里完成的。

通过命令gcc -E test.c -o test.i 进行预编译,看一下test.i的主要内容

# 943 "/usr/include/stdio.h" 3 4 

# 2 "test.c" 2


int main(){
  printf("%s\n","hello world");
  return 0;
}

可以看到宏定义被替换了。同时还包含一些stdio.h中的声明

编译

编译就是将test.i编程成汇编代码。通过命令gcc -S test.i -o test.s
 .file "test.c"
  .section  .rodata
.LC0:
  .string "hello world"
  .text
  .globl  main
  .type main, @function
main:
.LFB0:
  .cfi_startproc
  pushl %ebp
  .cfi_def_cfa_offset 8
  .cfi_offset 5, -8
  movl  %esp, %ebp
  .cfi_def_cfa_register 5
  andl  $-16, %esp
  subl  $16, %esp
  movl  $.LC0, (%esp)
  call  puts
  movl  $0, %eax
  leave
  .cfi_restore 5
  .cfi_def_cfa 4, 4
  ret 
  .cfi_endproc
.LFE0:
  .size main, .-main
  .ident  "GCC: (Ubuntu/Linaro 4.7.2-2ubuntu1) 4.7.2"
  .section  .note.GNU-stack,"",@progbits

汇编

汇编的过程就是将test.s汇编代码生成对应的机器码,也就是通常我们所说的目标文件。
通过命令gcc -c test.s -o test.o 

链接

链接就是将目标文件中使用到的符号进行依赖关系处理,找到一些静态库以及动态库,链接的过程极为复杂,记得有一本经典的书讲的很好。
通过ld命令进行链接操作生成最后的可执行文件

参考

http://blog.chinaunix.net/uid-20196318-id-28797.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值