gcc编译动态库静态库及Makefile知识汇总;

本文介绍了Linux环境下gcc编译动态库和静态库的步骤,包括预处理、编译、汇编和链接四个阶段。讨论了静态链接与动态链接的优缺点,并详细阐述了静态库(libxxx.a)和动态库(libxxx.so)的创建过程。此外,还讲解了Makefile的基本使用,以及make工具如何根据依赖关系自动编译文件,帮助提高开发效率。
摘要由CSDN通过智能技术生成

gcc编译过程

我们在Linux下使用vim命令写的.c文件,想要这个文件编译、运行的话就要使用"gcc [选项] 文件名" 这个格式的命令来操作,具体有四个步骤。通过下面的图片来简单介绍:
在这里插入图片描述
生成可执行程序过程为成四个步骤:

1、由.c文件到.i文件,这个过程叫预处理
2、由.i文件到.s文件,这个过程叫编译
3、由.s文件到.o文件,这个过程叫汇编
4、由.o文件到可执行文件,这个过程叫链接

1、预处理:

预处理是读取c源程序,对其中的伪指令和特殊符号进行“替代”处理;经过此处理,生成一个没有宏定义、没有条件编译指令、没有特殊符号的输出文件。这个文件的含义同没有经过预处理的源文件是相同的,仍然是C文件,但内容有所不同。伪指令主要包括以下三个方面:
(1)宏定义指令,如#define NAME TokenString, #undef以及编译器内建的一些宏,如_DATE_,FILE, LINE, TIME,_FUNCTION_等。
(2)条件编译指令,如#ifdef, #ifndef, #else, #elif, #endif等。
(3)头文件包含指令,如#include “FileName”或者#include 等。

预处理的过程主要包括以下过程:
将所有的#define删除,并且展开所有的宏定义
处理所有的条件预编译指令,比如#if 、#ifdef、#elif、#else、#endif等
处理#include预编译指令,将被包含的文件插入到该预编译指令的位置。
删除所有注释“//”和“ /
/”
添加行号和文件标识,以便编译时产生调试用的行号及编译错误警告行号。
保留所有的#pragma编译器指令,因为编译器需要使用它们

2、编译

编译程序所要做的工作就是通过词法分析和语法分析,在确认所有的指令都符合语法规则之后,将其翻译成等价的中间代码表示或汇编代码

3、汇编
汇编过程实际上把汇编语言代码翻译成目标机器指令的过程。对于被翻译系统处理的每一个c语言源程序,都将最终经过一处理而得到相应的目标文件。

4、链接
汇编程序生成的目标文件并不能立即就被执行,其中可能还有许多没有解决的问题。例如,在某个源文件中的函数可能引用了另一个源文件中定义的某个符号(如变量或者函数调用等);在程序中可能调用了某个库文件的函数,等等,所有的这些问题,都需要经过链接才能得以解决,链接程序的主要工作就是将有关的目标文件彼此相连接,也即将在一个文件中引用的符号同该符号在另外一个文件中的定义连接起来,使得所有的这些目标文件成为一个能够被操作系统装入执行的统一整体,也就是可执行程序,根据开发人员指定的库函数的链接方式的不同,链接处理可分为两种:①静态链接 ②动态链接。

动态链接:动态链接使用动态链接库进行链接,生成的程序在执行的时候需要加载所需的动态库才能运行。 动态链接生成的程序体积较小,但是必须依赖所需的动态库,否则无法执行。

静态链接:静态链接使用静态库进行链接,生成的程序包含程序运行所需要的全部库,可以直接运行,不过静态链接生成的程序体积较大。

对于可执行文件中的函数调用,可分别采用动态链接或静态链接的方法。使用动态链接能够使最终的可执行文件比较短小,并且当共享对象被多个进程使用时能节约一些内存,因为在内存中只需要保存一份此共享对象的代码。但并不是使用动态链接就一定比使用静态链接要优越,在某些情况下动态链接可能带来一些性能上的损害。

在Linux下可以使用gcc --help 来查看详细内容

gcc的常用选项

选项 说明
-E 只进行预处理,不编译(简单的宏替代,伪指令的处理)
-S 只编译,不汇编
-c 只编译、汇编,不链接
-g 编译生成可执行文件包含gdb调试信息,可被gsb调试
-o 指定编译生成可执行文件名
-I(i大写) 指定include包含文件的搜索目录
-L 指定链接所需库(动态库或静态库)所在路径
-l(L小写) 指定所需链接库名
-ansi ANSI标准
-std=c99 c99标准
-werror 不区分警告和错误,遇到任何警告都停止编译
-wall 开启大部分警告提示
–static 静态编译
-static 静态链接
-O0 关闭所有优化选项
-O1 第一级别优化,使用此选项可使可执行文件更小、运行更快,并不会增加太多编译时间,简写为-O
-O2 第二级别优化,采用了几乎所有的优化技术,使用此选项会延长编译时间
-O3 第三级别优化,在-O2的基础上增加了产生inline函数、使用寄存器等优化技术
-Os 此选项类似-O2,作用是优化所占用的空间,但不会进行性能优化,常用生成最终版本

静态库,动态库并制作;

库是什么呢?本质上来说,库时一种可执行代码的二进制形式,可以被操作系统载
入内存执行。我们通常将一些通用函数写成函数库,所以库是别人写好的,现有的,成熟的,可以复用的代码,你可以使用但要必须得遵守许可协议。在我们现实开发过程中,不可能每一份代码都从头编写,当我们拥有库时,我们就可以直接将我们所需要的文件链接到我们的程序中。可以为我们节省大量的时间,提高开发效率。Linux下库分为两种,静态库和动态库。这两种库相
同点是两种库都是由.o文件生成的

1, 静态库
静态库文件名的命名方式是“libxxx.a”,库名前加”lib”,windows和linux下都是后缀用”.a”,“xxx”为静态库名,windows下的静态库名也叫libxxx.a;
链接时间: 静态库的代码是在编译过程中被载入程序中。
链接方式:静态库的链接是将整个函数库的所有数据都整合进了目标代码。这样做优点是在编译后的执行程序不在需要外部的函数库支持,因为所使用的函数都已经被编进去了。缺点是,如果所使用的静态库发生更新改变,你的程序必须重新编译。
1.1制作静态库
首先,我们需要有三个文件,分别为 function.c、fuction.h、test.c .

//这个是我们自己写的一个对strchr()函数的实现,然后就要在test.c文件里调用它
#include <stdio.h>
#include<string.h>
char *my_strchr(
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值