先了解编译四大步骤
预处理 编译 汇编 链接
下面逐个使用
预编译:宏替换 ,文件引入 ,去除空行,注释,为编译做准备
预编译命令:
gcc -E test.c -o test.i
test.c中内容
#include <stdio.h>
int main(){
printf(“hello world!\n”);
return 0;
}
-E表示gcc在预处理结束后就停止编译了,test.i是预处理后的输出文件
-o指定输出文件
编译:预处理后的代码编译成汇编代码.
编译命令
gcc -S test.i -o test.s
选项-S让gcc在编译结束后停止编译过程
test.s 为编译后生成的汇编代码
汇编: 把编译阶段生成的".s" 文件转成二进制目标代码,也就是机器代码(01序列)
汇编命令:
gcc -c test.s -o test.o
-C让gcc在汇编结束后停止编译过程
test.o为汇编后生成的机器码目标文件
链接
链接就是将多个目标文件以及所需的库文件链接生成可执行目标文件的过程
链接命令 :
gcc test.o -o test
./test
-o是重命名选项,不写-o 时,默认生成a.out文件 这里生成可执行文件test
./test执行后输出
下面介绍静态库和动态库的概念和使用
准备代码
先创建3个文件
tool.h tool.c main.c
在tool.h中
int find_max(int arr[],int n);
在tool.c中
#include "tool.h"
int find_max(int arr[],int n){
int max= arr[0];
int i;
for(i= 0;i<n;i++){
if(arr[i]>max){
max= arr[i];
}
}
return max;
}
在main.c中
#include <stdio.h>
#include "tool.h"
int main(){
int arr[]= {1,3,5,8,2};
int max= find_max(arr,5);
printf("max=%d\n",max);
}
静态库:
静态库就是一些目标文件的集合 以.o结尾,静态库一般以.a结尾,只用于生成可执行文件的阶段
在链接步骤中,链接器从库文件中取代码,复制到可执行文件中.这种库叫静态库
可执行文件中有完整的库代码拷贝,多次使用会有多次冗余拷贝,如果有更新,所有使用他的程序都要重新编译发布
命令:
生成目标文件
gcc -c test.c -o test.o
Ar命令将文打包静态库
ar rcs libtest.a test.o
查看静态库内容 ar t xxx.a
ar t libtest.a
test.o
具体完整操作
{
gcc -c tool.c
ar rcs libtool.a tool.o
gcc -o main main.c -L. -ltool
把main.c 和tool库连接起来
-l 后直接跟要连的库名字
L 表示按照指定路径取寻找库文件 . 表示当前目录找
./main
}
动态库
在链接阶段没有被复制到程序中,在程序运行时有系
统动态加载到内存中
只需要载入一次动态库,不同程序可以得到内存中相同动态库的副本.
命令:
gcc -c test.c
gcc -shared -fPIC -o libtest.so test.o
具体完整代码
{
gcc -c tool.c
gcc -shared -fPIC -o libtool.so tool.o
gcc -o main main.c -L. -ltool
当静态库和动态库同名的时候 gcc优先加载动态库
此时执行./main 发现找不到文件
ldd main 看哪个文件找不到
配置环境变量
LD_LIBRARY_PATH=. ./main
}
补充命令
查看可执行文件依赖哪些库
ldd main
查看文件大小
ls -lh