一、什么叫做庫:
庫:二進制的程序,能被操作系統載入內存中執行
二、Linux下的庫有兩種:靜態庫和共享庫(動態庫),二者的不同點在于代碼載入的時刻不同。
A、靜態庫在程序編譯的時候并會被連接到目標代碼中,程序運行時將不再需要該靜態庫,因此體積較大
B、動態庫在程序編譯的時候并不會被連接到目標代碼中,而是在程序運行時被載入,因此程序運行時還需要動態庫存在,因此目標代碼體積小。
1、靜態庫的制作
A、創建靜態庫的源代碼 fun.c
B、將源代碼編譯成.o文件
gcc -c fun.c -o fun.o
gcc -c -o fun.o fun.c
C、將.o文件生成靜態庫
ar crs libfun.a fun.o(ar是生成靜態庫的命令,crs是選項)
ar crs的諧音是愛人才認識
靜態庫的命名規則:libxxx.a xxx表示庫名
D、編寫測試代碼并編譯(-L 指定路徑 –lfun指定庫)
gcc main.c -o main -lfun -L. 庫在當前目錄
gcc -o main main.c -L. –lfun 一樣的效果
gcc main.c -o main -lfun -L.. 庫在上一級目錄
gcc main.c -o main -lfun -L ../auto_lib/ 庫在上一級目錄的auto_lib路徑下面
E、執行 ./main
2、動態庫的制作
A、編寫庫的源代碼 fun.c
B、將其編譯成.o文件
gcc -fPIC -Wall -c fun.c
C、將.o文件生成動態庫
gcc -shared -fPIC -o libfun.so fun.o
D、編寫測試代碼main.c 并編譯
gcc -o main main.c -L. –lfun
備注:此時執行的話會出現這樣的錯誤提示
原因是動態庫沒有裝載,解決這個問題有3種方法:
<1> 將制作的動態庫放在 /lib或/usr/lib
sudo mv libfun.so /lib/
sudo mv libfun.so /usr/lib/
然后執行./main 結果如下
<2>將制作的動態庫的當前路徑加入庫的配置文件中
配置文件查找當前路徑
進入配置文件 sudo vi /etc/ld.so.conf.d/libc.conf
添加路徑
使配置生效 sudo ldconfig
<3>將路徑加入環境變量中(此方法不靠譜)
查看環境變量中有沒有值
echo $LD_LIBRARY_PATH
在環境變量中加上庫所在的路徑
export LD_LIBRARY_PATH=/home/leo/IO/16073/auto_lib
使配置生效 sudo ldconfig
3、庫的升級(后臺修改庫,升級系統)
<1> 修改庫的源代碼
將其編譯生成.o文件
gcc -fPIC -Wall -c fun.c
將.o文件生成動態庫
gcc -shared -fPIC -o libfun.so fun.o
執行 ./main 看效果
升級成功,以上這些就是靜態庫和動態庫的知識了
附件知識:
● -shared:指定生成動態鏈接庫。
● -static:指定生成靜態鏈接庫。(創建靜態庫我們一般用ar命令,它將很多.o轉換成.a)
● -fPIC:表示編譯為位置獨立的代碼,用于編譯共享庫。目標文件需要創建成位置無關碼,概念上就是在可執行程序裝載它們的時候,它們可以放在可執行程序的內存里的任何地方。
● -L.:表示要連接的庫在當前目錄中。
● -l:指定鏈接時需要的動態庫。編譯器查找動態連接庫時有隱含的命名規則,即在給出的名字前面加上lib,后面加上.so來確定庫的名稱。
● -Wall:生成所有警告信息。
● -ggdb:此選項將盡可能的生成gdb的可以使用的調試信息。
● -g:編譯器在編譯的時候產生調試信息。
● -c:只激活預處理、編譯和匯編,也就是把程序做成目標文件(.o文件)。
● -Wl,options:把參數(options)傳遞給鏈接器ld。如果options中間有逗號,就將options分成多個選項,然后傳遞給鏈接程序。