侧边栏壁纸
    • 累计撰写 302 篇文章
    • 累计收到 527 条评论
    C语言编译的四个步骤
    我的学记|刘航宇的博客

    C语言编译的四个步骤

    刘航宇
    2024-03-12 / 0 评论 / 122 阅读 / 正在检测是否收录...

    编译一个C语言程序是一个多阶段的过程。从总体上看,这个过程可以分成四个独立的阶段。预处理、编译、汇编和连接。

    在这篇文章中,我将逐一介绍编译下列C程序的四个阶段。

    /*
     
    * "Hello, World!": A classic.
     
    */
    #include <stdio.h>
     
    int main(void)
     
    {
     
        puts("Hello, World!");
     
        return 0;
     
    }

    预处理

    编译的第一个阶段称为预处理。在这个阶段,以#字符开头的行被预处理器解释为预处理器命令。这些命令形成一种简单的宏语言,有自己的语法和语义。这种语言通过提供内联文件、定义宏和有条件地省略代码的功能,来减少源代码的重复性。
    在解释命令之前,预处理器会做一些初始处理。这包括连接续行(以 \ 结尾的行)和剥离注释。
    要打印预处理阶段的结果,请向gcc传递-E选项。
    gcc -E hello_world.c
    考虑到上面的 "Hello, World!"的例子,预处理器将产生stdio.h头文件的内容和hello_world.c文件的内容,并将其前面的注释剥离出来。

    编译

    编译的第二个阶段被称为编译,令人困惑。在这个阶段,预处理过的代码被翻译成目标处理器架构特有的汇编指令。这些形成了一种中间的人类可读语言。

    这一步骤的存在允许C代码包含内联汇编指令,并允许使用不同的汇编器。

    一些编译器也支持使用集成汇编器,在这种情况下,编译阶段直接生成机器代码,避免了生成中间汇编指令和调用汇编器的开销。

    要保存编译阶段的结果,可以向gcc传递-S选项。
    gcc -S hello_world.c
    这将创建一个名为hello_world.s的文件,包含生成的汇编指令。

    汇编

    在这个阶段,汇编器被用来将汇编指令翻译成目标代码。输出包括目标处理器要运行的实际指令。
    要保存汇编阶段的结果,请向gcc传递-c选项。
    gcc -c hello_world.c
    运行上述命令将创建一个名为hello_world.o的文件,包含程序的目标代码。这个文件的内容是二进制格式,可以用运行命令hexdump或od来检查。

    hexdump hello_world.o
     
    od -c hello_world.o

    Linux中的od(octal dump)命令用于转换输入内容为八进制。

    Hexdump是一个命令行工具,用于以各种方式显示文件的原始内容,包括十六进制,可用于Linux、FreeBDS、OS X和其他平台。Hexdump不是传统Unix系统或GNU命令的一部分。

    链接

    汇编阶段产生的目标代码是由处理器能够理解的机器指令组成的,但程序的某些部分是不符合顺序的或缺失的。为了产生一个可执行的程序,现有的部分必须被重新排列,并把缺失的部分补上。这个过程被称为链接。

    链接器将安排目标代码的各个部分,使某些部分的功能能够成功地调用其他部分的功能。它还将添加包含程序所使用的库函数指令的片段。在 "Hello,world!"程序的例子中,链接器将添加puts函数的对象代码。

    这一阶段的结果是最终的可执行程序。当不使用选项运行时,gcc 将把这个文件命名为 a.out。如果要给文件命名,请向 gcc 传递 -o 选项。

    gcc -o hello_world hello_world.c
    0
    Verilog语言实现读写txt文件方法
    « 上一篇 2024-04-14
    Socket通信-Linux系统中C语言实现TCP/UDP图片和文件传输
    下一篇 » 2024-02-29

    评论 (0)

    取消