linux--动态库静态库 、软硬链接

动态库与静态库概念

在之前我们学习程序编译的时候,源文件在经过预处理、汇编、编译后生成目标文件,最后一步链接,就是对 之前的声明去实现,合并目标文件、库文件,合并符号表/符号表的重定位,最终生成可执行程序。

其中的库文件是什么呢?
库通俗的说就是把一些常用的公用函数的目标文件打包在一起制作成的函数库,提供相应函数的接口。而且库是一些大佬们写好的现成的,成熟的,可以高效复用的代码,我们只需要了解接口与功能,便可以方便使用。

函数库分为静态库和动态库两种。

windows动态库后缀:     .dll
windows静态库后缀:    .lib

linux静态库后缀:.a
linux动态库后缀:.so
linux库前缀都是:lib

静态库(.a)程序在编译链接的时候把直接库的代码链接到可执行文件中。程序运行的时候将不再需要静态库。
(共享)动态库(.so)程序在运行的时候才去链接动态库的代码,多个程序共享使用库的代码。
由于静态链接是直接把库文件代码直接复制链接到可执行文件中,一旦链接完成生成可执行程序,如果直接删除静态库,代码还是依旧可以执行。而动态库却不可以这样,因为动态链接(dynamic linking):一个与动态库链接的可执行文件仅仅包含它用到的函数入口地址的一个表,而不是外部函数所在目标文件的整个机器码在可执行文件开始运行以前,外部函数的机器码由操作系统从磁盘上的该动态库中复制到内存中。所以动态库生成的可执行程序是一直依赖动态库的,一旦删除动态库,可执行程序便无法执行。
并且动态库可以在多个程序间共享,所以动态链接使得可执行文件更小,节省了磁盘空间。操作系统采用虚拟内存机制允许物理内存中的一份动态库被要用到该库的所有进程共用(所以动态库也叫共享库),节省了内存和磁盘空间。

linux静态库

在这里插入图片描述
测试代码

[lingfei@localhost 3-15]$ ls
add.c  add.h  main.c
[lingfei@localhost 3-15]$ gcc -c add.c -o add.o   //要先编译成.o目标文件
[lingfei@localhost 3-15]$ ls
add.c  add.h  add.o  main.c
[lingfei@localhost 3-15]$ ar -rc libmylib.a add.o  //生成静态库 
[lingfei@localhost 3-15]$ ls
add.c  add.h  add.o  libmylib.a  main.c
 
[lingfei@localhost 3-15]$ ar -tv libmylib.a       //查看静态库里的目录列表
rw-rw-r-- 1000/1000   1240 Mar 15 22:02 2020 add.o
 
[lingfei@localhost 3-15]$ gcc main.c -o main -L. -lmylib  //使用静态库 去掉前后缀
[lingfei@localhost 3-15]$ ls
add.c  add.h  add.o  libmylib.a  main  main.c

[lingfei@localhost 3-15]$ ar -tv libmylib.a       //查看静态库里的目录列表
		t:列出静态库中的文件
		v:verbose 详细信息
[lingfei@localhost 3-15]$ gcc main.c -o main -L. -lmylib  //使用静态库
	-L 指定库路径
	-L.在当前目录下寻找
	-l 指定库名
测试目标文件生成后,静态库删掉,程序照样可以运行。

库搜索路径
	从左到右搜索-L指定的目录。
	由环境变量指定的目录 (LIBRARY_PATH)
	由系统指定的目录
		/usr/lib
		/usr/local/lib

linux动态库

在这里插入图片描述

[lingfei@localhost 3-15]$ gcc -c add.c -o add.o
[lingfei@localhost 3-15]$ gcc -shared -o libmylib.so add.o  //生成动态库
[lingfei@localhost 3-15]$ ls
add.c  add.h  add.o  libmylib.a  libmylib.so  main.c
[lingfei@localhost 3-15]$ gcc main.c -o main -L. -lmylib   //使用动态库 去掉前后缀
[lingfei@localhost 3-15]$ ls
add.c  add.h  add.o  libmylib.a  libmylib.so  main  main.c
[lingfei@localhost 3-15]$ ./main

命令 :  ldd [可执行程序名]      	
	作用 可查看程序所依赖的库文件 

在这里插入图片描述

软硬链接

先了解文件系统中inode节点
inode:索引节点,inode 是 UNIX 操作系统中的一种数据结构,其本质是结构体,它包含了与文件系统中各个文件相关的一些重要信息,它用来存放档案及目录的基本信息,包含时间、档名、使用者及群组等。
inode 表包含一份清单,其中列出了对应文件系统的所有 inode 编号。当用户搜索或者访问一个文件时,UNIX 系统通过 inode 表查找正确的 inode 编号。在找到 inode 编号之后,相关的命令才可以访问该 inode ,并对其进行适当的更改。

理解硬链接

创建硬连接

ln [源文件]  [要创建的硬连接文件] 

特征:
1.硬链接,以文件副本的形式存在,但不占用实际空间。
2.不能给目录创建硬链接
3.硬链接只有在同一个文件系统中才能创建
性质:
系统不为它分配独立的inode和文件。所以,硬链接文件与原始文件其实是同一个文件,相当于源文件的引用(c++的引用的含义)。我们每添加一个硬链接,该文件的inode链接数就会增加1;而且只有当该文件的inode连接数为0时,才算彻底将它删除。所以,由于硬链接实际上是原文件的inode的引用,因此即便原始文件被删除,依然可以通过硬链接文件来访问。

在这里插入图片描述
查看inode链接文件数
在这里插入图片描述
我们看到,真正找到磁盘上文件的并不是文件名,而是inode。 其实在linux中可以让多个文件名对应于同一个inode,上图中链接数为2,
我们在删除文件时干了两件事情:
1.在目录中将对应的记录删除,
2.将硬连接数-1,如果为0,则将对应的磁盘释放。

理解软链接

性质:
上面的硬链接是通过inode引用另外一个文件,而软链接是通过名字引用另外一个文件。软链接就相当于windows上的给文件创建的快捷方式。其实软链接仅仅包含所链接文件的路径名,因此能链接目录文件,也可以跨越文件系统进行链接。但是,当原始文件被删除后,链接文件也将失效。

ln -s [源文件][要创建的软链接文件]

特征:
1.有自己的inode节点;
2.软链接以路径的形式存在。类似于Windows操作系统中的快捷方式
3.可以跨文件系统
4.可以对目录进行链接 类似于Windows操作系统中的快捷方式

在这里插入图片描述

发布了55 篇原创文章 · 获赞 152 · 访问量 3万+

猜你喜欢

转载自blog.csdn.net/qq_44785014/article/details/104885703