目录
一、gcc/g++:编译器
功能:
将C/C++高级语言代码翻译成机器可识别的代码
1.1编译过程:
预处理,编译,汇编,链接
1.预处理(进行宏替换):
宏定义展开,头文件展开、条件编译等,同时将代码中的注释删除==
实例:gcc –E hello.c –o hello.i
选项“-E”,该选项的作用是让 gcc 在预处理结束后停止编译过程。
选项“-o”是指目标文件,“.i”文件为已经过预处理的C原始程序。
2.编译(生成汇编):
这个阶段,gcc会检查代码的规范性、是否有语法错误等,以确定代码的实际要做的工作,在检查无误后,把代码翻译成汇编语言。
用户可以使用“-S”选项来进行查看,该选项只进行编译而不进行汇编,生成汇编代码。
实例:gcc –S hello.i –o hello.s
3.汇编(生成机器可识别代码):
汇编阶段是把编译阶段生成的“.s”文件转成目标文件。
读者在此可使用选项“-c”就可看到汇编代码已转化为“.o”的二进制目标代码了。
实例:gcc –c hello.s –o hello.o
4.链接(生成可执行文件或者库文件):
C语言写的程序是需要依赖各种库的,所以编译之后还需要把库链接到最终的可执行程序中去。
实例:gcc hello.o –o hello
1.2函数库:
库文件:已经汇编完成的公共代码
链接:将库中的代码拿到要生成的可执行程序中
Linux有俩种库:1.静态库(libXXX.a)2.动态库(libXXX.so)
静态链接:链接静态库,将库中的代码直接全部拷贝到可执行程序中;好处:程序运行时,不需要依赖库文件的存在;缺点:占用资源多
动态链接:链接动态库,只是记录库中的接口符号位置信息;好处:资源占用冗余较小;缺点:程序运行时需要动态库存在。
默认是动态链接,找的库.so. 加上-static时变成静态链接,找的库.a.
所以用户在链接的时候如果出现了链接错误,请先确认是否存在对应的库。
一步编译:gcc hello.c -o hello
二、gdb:调试器
Linux默认生成的可执行程序时动态链接且以release方式发布的。
1.使用
1.要使用gdb调试,必须在源代码生成二进制程序的时候, 加上 -g 选项
2.gdb调试程序,需要将程序信息,加载到gdb中,进入gdb:
gdb ./hello
r或者run ——运行程序
start ——开始逐步调试
n或者next ——下一步,遇到函数直接得到函数运行结果,并不跟踪进入函数
s或者step ——下一步,遇到函数跟踪进入函数
p 变量名 ——查看变量数据
l或者list 行号 ——查看指定行(默认当前调试行)附近代码(上下5行)
until 行号 ——直接运行到指定行
b(break) 行号 ——向当前调试文件的指定行添加断点
b 函数名 ——向指定函数开头添加断点
b 文件名:行号 ——向指定文件指定行添加断点
watch 变量名 ——变量监控,给变量添加断点,当变量内容发生改变,停止
i(info) b(breakpoints) ——查看所有断点信息
d(delete) 序列号 ——删除指定断点,默认删除所有
c(continue) ——继续运行(代码的块级划分,进而确认错误)
f(finish)——运行完当前函数,逐个检测每个函数是否正常(定位)
set var i=xx——设置变量为特定值
bt(breaktrace) ——查看函数调用栈信息
q(quit) ——退出gdb
三、make/Makefile:项目自动化构建工
Makefile:定义编译规则的普通文件
make:是一个解释程序,解释执行Makefile中定义的编译规则
执行make命令,这时候make程序会在当亲目录下寻找Makefile文件,解释其中的编译规则
make命令找到Makefile文件,并生成可执行程序。
编写规则:
目标对象:依赖对象
规则命令(前面有一个tab键)
执行规则:
通过目标对象与依赖对象最后一次修改时间,判断目标对象是否需要重新生成。
make在Makefile中只找第一个目标对象,为了生成这个目标对象,而执行命令,完成之后直接退出(后边的对象都不再生成)。
make在Makefile中找到第一个对象,这时候如果这个对象的依赖不存在,则在后续编译规则中,寻找是否可以生成这个依赖对象,当所有的依赖对象生成完毕后,最终生成目标对象。
项目清理:
工程是需要被清理的
像clean这种,没有被第一个目标文件直接或间接关联,那么它后面所定义的命令将不会被自动执行,
不过,我们可以显示要make执行。即命令——“make clean”,以此来清除所有的目标文件,以便重编译。
但是一般我们这种clean的目标文件,我们将它设置为伪目标,用 .PHONY 修饰,伪目标的特性是,总是被执行的.
.PHONY:后面常跟伪目标,总是被执行的
预定义变量:
$@ ——要生成所有的目标文件
$^ ——所有的依赖对象
$< ——依赖对象中的第一个