日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 运维知识 > linux >内容正文

linux

Linux 之三 静态库及动态库的编写和使用

發(fā)布時間:2024/10/14 linux 73 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Linux 之三 静态库及动态库的编写和使用 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

??最近在整理舊電腦時,發(fā)現(xiàn)了一些剛?cè)胄袝r的學習記錄,以及最早使用新浪博客 http://blog.sina.com.cn/zcshou 寫的一些文章。最近要重拾 Linux,所以把這些 Word 文檔重新排版轉(zhuǎn)到此博客上,一來復習一下,二來在 CSDN 上作個存檔!

至于新浪博客上的文章就留那里吧!話說新浪博客是不是塊倒閉了?還有一點,如果沒記錯,文章里使用的是 CentOS。

??注意,這些文章里的內(nèi)容多數(shù)可能來自網(wǎng)絡(當初學習時翻看了各種網(wǎng)絡資料)但應該不是原版抄襲(作為一名工科生,不動手實踐怎么能行!)。如果您發(fā)現(xiàn)其中內(nèi)容有侵權,請私信我,我將立刻處理!

ELF 文件規(guī)范

??ELF(Executable and Linking Format)是一個二進制文件規(guī)范。用于定義不同類型的對象文件(Object files)中都放了什么東西、以及都以什么樣的格式去放這些東西。

??現(xiàn)在流行的二進制可執(zhí)行文件格式 (Executable File Format),主要是 Windows 下的 PE(Portable Executable)和 Linux 的 ELF(Executable and Linking Format)可執(zhí)行和鏈接格式)。他們都是 COFF(Common Object File Format)的變種。ARM 體系中采用的也是 ELF 文件格式。

??COFF 是在 Unix System V Release 3 時由 UNIX 系統(tǒng)實驗室(UNIX System Laboratories, USL)首先提出并且使用的文件規(guī)范,后來微軟公司基于 COFF 格式,制定了 PE 格式標準,并將其用于當時的 Windows NT 系統(tǒng)。在 System V Release 4 時,UNIX 系統(tǒng)實驗室在 COFF 的基礎上,開發(fā)和發(fā)布了 ELF 格式,作為應用程序二進制接口 (Application Binary Interface,ABI)。

??此后,工具接口標準委員會(Tool Interface Standard Committee,TISC)選擇了正在發(fā)展中的 ELF 標準作為工作在 32 位 INTEL 體系上不同操作系統(tǒng)之間可移植的二進制文件格式。可以從這里 找到詳細的標準文檔。如下圖:

TISC 共出過兩個版本(v1.1和 v1.2)的標準文檔。兩個版本內(nèi)容上差不多,但 v1.2 版本重新組織了原本在 v1.1 版本中的內(nèi)容。可讀性更高。兩個版本的目錄如下所示:

在 ELF 文件規(guī)范中,把系統(tǒng)中采用 ELF 格式的文件(規(guī)范中稱為對象文件(Object File))歸類為以下三種:

  • 可重定位文件(Relocatable File ): 這類文件包含代碼和數(shù)據(jù),可用來連接成可執(zhí)行文件或共享對象文件(Object File),靜態(tài)鏈接庫歸為此類,對應于 Linux 中的 .o ;Windows 的 .obj.
  • 可執(zhí)行文件(Executable File ): 這類文件包含了可以直接執(zhí)行的程序,它的代表就是 ELF 可執(zhí)行文件。Linux 下,他們一般沒有擴展名,比如 /bin/bash;Windows 下的 .exe
  • 共享對象文件(Object File)(Shared Object File ): 這種文件包含代碼和數(shù)據(jù),鏈接器可以使用這種文件跟其他可重定位文件的共享對象文件(Object File)鏈接,產(chǎn)生新的對象文件(Object File)。對應于Linux 中的 .so,Windows 中的 DLL
    另外是動態(tài)鏈接器可以將幾個這種共享對象文件(Object File)與可執(zhí)行文件結(jié)合,作為進程鏡像文件來運行。

??在 Linux 系統(tǒng)中,還有一類文件,被稱為核心轉(zhuǎn)儲文件(Core Dump File) ,當進程意外終止,系統(tǒng)可以將該進程地址空間的內(nèi)容及終止時的一些信息轉(zhuǎn)存到核心轉(zhuǎn)儲文件。 對應 Linux 下的 core dump。

庫文件

??為了避免一些重復性的工作并且便于編程,開發(fā)人員定義了一系列的標準函數(shù)以供調(diào)用,這些函數(shù)都放在相應的庫中,而我們在進行開發(fā)時直接使用這些標準函數(shù)。

??庫文件就是在系統(tǒng)層面對于 ELF 各種文件的稱呼。從本質(zhì)上來說就是一種可執(zhí)行代碼的二進制格式,可以被載入內(nèi)存中執(zhí)行。庫分靜態(tài)庫和動態(tài)庫兩種。

靜態(tài)庫

??在編譯目標程序時,所使用的靜態(tài)庫中的函數(shù)的所有數(shù)據(jù)都會被整合進目標代碼中,編譯出的目標程序的執(zhí)行程序不需要外部的函數(shù)庫支持。linux 中靜態(tài)庫文件的擴展名一般為 .a,a 就是 archive 的縮寫。其編寫步驟很簡單:

  • 編寫函數(shù)代碼
  • 編譯生成各目標文件
  • 用 ar 文件對目標文件歸檔,生成靜態(tài)庫文件。注意:歸檔文件名必須以 lib 打頭。
  • 使用要點:
  • 在 gcc 的 -I 參數(shù)后加上靜態(tài)庫頭文件的路徑
  • 在 gcc 的 -L 參數(shù)后加上庫文件所在目錄
  • 在 gcc 的 -l 參數(shù)后加上庫文件名,但是要去掉 lib 和 .a 擴展名。比如庫文件名是 libtest.a,那么參數(shù)就是 -ltest
  • 靜態(tài)庫必須按照 lib[name].a 的規(guī)則命名
  • 編寫最簡單的靜態(tài)庫文件

  • 編寫如下兩個文件,注意放在同一目錄中
    • myalib.h 文件的內(nèi)容void test();
    • myalib.c 文件的內(nèi)容#inlcude <stdio.h> void test() {printf("test\n"); }
  • 制作庫文件
  • 生成目標文件。執(zhí)行命令 gcc -c myalib.c,其中:-c 表示只編譯,不鏈接 myalib.c,執(zhí)行完后會生成一個 myalib.o 文件
  • 用 ar 命令歸檔。格式為 ar -rc <生成的檔案文件名> <.o文件名列表>。歸檔文件名一定要以 lib 打頭及 .a 結(jié)尾。ar -rc libtest.a myalib.o,執(zhí)行完后會生成一個 libtest.a 文件
  • 使用庫文件
  • 編寫一個測試程序 main.c,內(nèi)容為 //main.c 測試靜態(tài)庫調(diào)用的程序#include "myalib.h" //要把函數(shù)的頭文件包含進來,否則編譯時會報錯int main(int argc,char* argv[]){test();return 0; }
  • 編譯目標文件。注意要把靜態(tài)庫頭文件的路徑加到 -I 參數(shù)里面。gcc -I ~ -o main.o -c main.c。其中:-o 表示輸出文件 mian.o,-c 表示只編譯 main.c 不進行鏈接。現(xiàn)在生成了一個 main.o 文件。注意:~ 表示庫文件在當前目錄下,根據(jù)自己目錄修改。
  • 生成可執(zhí)行文件。注意要把靜態(tài)庫文件的路徑加到 -L 參數(shù)里面,把庫文件名(去掉打頭的 lib 和結(jié)尾的 .a )加到 -l 參數(shù)后面。執(zhí)行命令 gcc -o main -L~ main.o -ltest 后會生成一個名為 main 的可執(zhí)行文件 注意:~ 表示庫文件在當前目錄下,根據(jù)自己目錄修改。另外,注意 -l 參數(shù)好象應該加到輸入文件名的后面,否則會報錯。
  • 執(zhí)行可執(zhí)行文件 ./main 查看效果, 如下:

    說明執(zhí)行成功。
  • 動態(tài)庫

    ??動態(tài)庫也有的稱為共享庫。在編譯目標程序的時候,其使用的動態(tài)函數(shù)庫不會被編譯進目標程序中,編譯生成的目標程序執(zhí)行到相關函數(shù)時必須要調(diào)用所使用的動態(tài)庫中的對應函數(shù)。在 linux 中,動態(tài)庫一般以 .so 結(jié)尾,so 就是 shared object 的縮寫。其基本生成步驟為:

  • 編寫函數(shù)代碼
  • 編譯生成動態(tài)庫文件,要加上 -shared 和 -fpic 選項 ,動態(tài)庫文件名以 lib 開頭, 以 .so 結(jié)尾。
  • 使用方式分為兩種: 隱式調(diào)用和顯示調(diào)用
    • 隱式調(diào)用:類似于靜態(tài)庫的使用,但需修改動態(tài)鏈接庫的配置文件 /etc/ld.so.conf;
    • 顯示調(diào)用:則是在主程序里使用 dlopen、dlsym、dlerror、dlclose 等系統(tǒng)函數(shù)。
  • 編寫最簡單的動態(tài)庫文件

  • 編寫如下兩個文件,注意放在同一目錄中
  • myalib.h 文件的內(nèi)容void test();
  • myalib.c 文件的內(nèi)容#inlcude <stdio.h> void test() {printf("test\n"); }
  • 使用命令:gcc -fpic -shared -o libtest.so myalib.c 編譯生成動態(tài)庫,庫文件名以 lib 開頭, 以 .so 結(jié)尾。此時就生成一個 libtest.so 文件
  • 隱式調(diào)用

    ??隱式調(diào)用的含義是代碼里不出現(xiàn)庫文件名,使用方式和調(diào)用靜態(tài)庫的代碼是類似的。下面我們以一個示例來說明一下。

  • 編寫測試文件//main.c 測試動態(tài)庫隱式調(diào)用的程序 #include "myalib.h" // 要把函數(shù)的頭文件包含進來,否則編譯時會報錯 int main(int argc,char* argv[]) {test();return 0; }
  • 使用命令:gcc -I ~ -o main.o -c main.c 編譯測試程序,與靜態(tài)庫類似,要把頭文件的路徑加到 -I 參數(shù)里面。現(xiàn)在生成了一個 main.o 文件
  • 使用命令:gcc -o main -L~ main.o -ltest 連接生成測試程序。此時會生成了一個 main 文件
  • 執(zhí)行測試程序 ./main。不出意外的話,應該會報錯。這是由于 linux 查找動態(tài)庫的方式導致的。此時,可以使用命令:LD_LIBRARY_PATH=. ./mian 來運行。
  • 顯式調(diào)用

    ??顯式調(diào)用的含義是代碼出現(xiàn)庫文件名,用戶需要自己去打開和管理庫文件。注意以下兩點:

  • 需要包含 dlfcn.h 系統(tǒng)頭文件
  • 用 dlopen 函數(shù)打開庫文件,并指定打開方式。
  • 下面以示例來說明一下:

  • 編寫測試文件#include <dlfcn.h> //用于動態(tài)庫管理的系統(tǒng)頭文件 #include "myalib.h" //要把函數(shù)的頭文件包含進來,否則編譯時會報錯 int main(int argc,char *argv[]) {//聲明對應的函數(shù)的函數(shù)指針void(pTest)();//加載動態(tài)庫void pdlHandle = dlopen("libtest.so", RTLD_LAZY);//錯誤處理if (pdlHandle == NULL){printf("Failed load library\n");return -1;}char pszErr = dlerror();if (pszErr != NULL){printf("%s\n", pszErr);return -1;}//獲取函數(shù)的地址pTest = dlsym(pdlHandle, "test");pszErr = dlerror();if (pszErr != NULL){printf("%s\n", pszErr);dlclose(pdlHandle);return -1;}//實現(xiàn)函數(shù)調(diào)用(pTest)();//程序結(jié)束時關閉動態(tài)庫dlclose(pdlHandle);return 0; }
  • 使用命令 gcc -o main -ldl main.c 編譯測試文件。使用 -ldl 選項指明生成的對象模塊需要使用共享庫。執(zhí)行完后就生成了一個 main 文件.
  • 執(zhí)行測試程序。執(zhí)行 ./main
  • 參考

    ??這篇文章中的內(nèi)容,應該參考了一篇百度博客。現(xiàn)在百度博客關閉了,無從查找作者。如果有知道的請私信我,謝謝!

    總結(jié)

    以上是生活随笔為你收集整理的Linux 之三 静态库及动态库的编写和使用的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。

    主站蜘蛛池模板: av资源吧首页 | 免费观看日本 | 一区二区三区欧美日韩 | 中文字幕高清 | 51成人网 | 欧美片 | 久久影院午夜 | 国产精品一区二区性色av | 性――交――性――乱a | 伊人久久精品视频 | 男人狂揉女人下部视频 | 免费看黄色三级三级 | 亚洲av日韩精品久久久久久久 | 国产精品成人一区二区网站软件 | 精品一区二区久久久久久按摩 | 91国产在线播放 | 欧美视频在线免费 | 久久视频在线观看免费 | 91av视频网站 | 一区二区色| 99人妻碰碰碰久久久久禁片 | 免费在线观看一区二区三区 | 免费婷婷| 亚洲成年 | 天天躁夜夜躁av天天爽 | 黄色免费播放 | 欧美国产免费 | 先锋影音制服丝袜 | 在线免费观看一区二区 | 入禽太深免费视频 | 色一情一乱一伦一区二区三区 | 91大片免费看 | 男女视频免费观看 | 超碰人操 | 色姑娘综合网 | 91网在线观看 | 咪咪色影院 | 中文久久字幕 | 久久午夜网站 | 亚洲黄片一区二区 | 一级片毛片 | 国产xxxx18| 欧美成人午夜影院 | 第一宅男av导航入口 | 国产精品网站在线观看 | 国产女无套免费视频 | 亚洲免费在线观看视频 | 波多野结衣中文一区 | 日韩视频免费观看高清完整版 | 先锋av资源网站 | 超碰日韩| 欧美视频网址 | 性欧美在线视频 | 亚洲a毛片| 日韩乱码人妻无码系列中文字幕 | 痴汉电车在线播放 | 国产免费aa | 波多野结衣成人在线 | 久久久久久婷婷 | 一级成人黄色片 | 日韩综合在线视频 | 樱花草涩涩www在线播放 | 欧美九九九 | 成人免费看毛片 | 久久久精品人妻一区二区三区四 | 欧美成人吸奶水做爰 | 午夜视频 | 边打电话边做 | 亚洲午夜一区二区 | 免费成人黄色av | 无套内谢的新婚少妇国语播放 | 国产日本亚洲 | 青青久久久| 91视频免费看 | 欧美36p| 亚洲最大成人综合网 | 欧美日韩一级片在线观看 | 日韩黄色片 | 91麻豆免费视频 | 精品视频一区二区 | 国产成人三级在线 | 秋霞影院午夜丰满少妇在线视频 | 中国毛片网站 | 草草久久久无码国产专区 | 国产精品九色 | 国产农村妇女毛片精品久久麻豆 | av夜夜| 国产麻豆免费观看 | 瑟瑟视频在线 | 好吊色视频一区二区三区 | 中日毛片| www.九色.com| 亚洲草逼 | 亚洲v日韩v综合v精品v | 国产午夜免费视频 | 国产精品综合视频 | 欧美黄色特级片 | 国产精品老熟女一区二区 | 色婷婷狠狠爱 |