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

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

静态链接库、动态链接库和动态加载库

發布時間:2025/3/21 编程问答 28 豆豆
生活随笔 收集整理的這篇文章主要介紹了 静态链接库、动态链接库和动态加载库 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

前言

靜態庫是obj文件的一個集合(目標文件中通常僅解析了文件內部的變量和函數,對于引用的函數和變量還沒有解析,這需要將其他已經編寫好的目標文件引用進來,將沒有解析的函數和變量進行解析,通常引用的目標是),通常靜態庫以".a"為后綴,名字格式一般為libxxx.a靜態庫由程序ar生成

實例程序如下:

Main.c

#include <stdio.h>

extern void print_hello();

int

main(void)

{

????print_hello();

}

Print_hello.c

#include <stdio.h>

void

print_hello()

{

????printf("hello\n");

}

?

  • 生成靜態鏈接庫

    創建靜態庫的步驟:

  • 生成目標文件(使用命令gcc –c file.c)
  • 使用工具ar對目標文件進行歸檔。(使用的命令如下)
  • 生成靜態鏈接庫,或者將一個obj文件加入到已經存在的靜態庫的命令格式為:

    ar –rcs 庫文件obj_1 obj_2 …

    使用上面的實例程序print_hello.c創建靜態鏈接庫:

  • 使用靜態鏈接庫

    使用方式一:

    使用方式二:

    注意,在方法二中"-L./"不可少,否則出現如下錯誤:

    這是因為上面的命令在系統默認的路徑下查找hello函數庫,而我們并沒有將libhello.a庫放在系統默認搜索路徑下,所以需要顯示指定庫函數的路徑為當前目錄。

    另外還需注意,在使用-l選項時,-o選項的目標名稱要在-l鏈接的庫名稱之前,否則gcc會認為-l是生成的目標而出錯。

    下面兩個圖分別是頭文件和庫文件的默認搜索路徑:

  • 動態鏈接庫

    前言

    動態鏈接庫是程序運行時加載的庫,當動態鏈接庫正確安裝后,所有的 程序都可以使用動態庫來運行程序。動態鏈接庫是目標文件的集合,目標文件在動態鏈接庫中的組織方式是按照特殊方式形成的。庫中函數和變量的地址是相對地址,不是絕對地址,其真實地址在調用動態庫的程序加載時形成。

    ????動態鏈接庫的名稱有別名(soname)、真名(realname)和鏈接名(linker name):

    ????別名:libxxx.so,這種形式的庫名正是執行編譯命令時編譯器要搜索的名字。

    ????真名:動態鏈接庫的真實名稱,一般總是在別名的基礎上加上一個小版本號、發布版本等構成。

    ????鏈接名:程序鏈接時使用的庫的名字。

  • 生成動態鏈接庫

    生成動態鏈接庫的命令很簡單,使用-fPIC選項或者-fpic選項。-fPIC和-fpic選項的作用是使得gcc生成的代碼是位置無關的,例如下面的命令將print_hello.c編譯生成動態鏈接庫:

    其中-shared選項告訴編譯器生成一個動態鏈接庫;-soname,libhello.so表示生成動態庫的別名是libhello.so;-o libhello.so.1選項擇表示生成名字為libhello.so.1的實際動態鏈接庫文件。

    生成動態鏈接庫之后一個很重要的問題就是安裝,一般情況下將生成的動態鏈接庫復制到系統默認的動態鏈接庫的搜索路徑下,通常有/lib,/usr/lib,/usr/local/lib,放到其中任何一個目錄下都可以。

  • 動態鏈接庫的配置

    動態鏈接庫并不是可以隨意地使用,要在運行的 程序中使用動態鏈接庫,需要指定系統的動態鏈接庫搜索的路徑,讓系統找到運行所需要的動態鏈接庫才可以。

    系統中的配置文件/etc/ld.so.conf是動態鏈接庫的搜索路徑配置文件。這這個文件內,存放著可被Linux共享的動態鏈接庫所在目錄的名字系統目錄/lib,/usr/lib除外,這兩個目錄默認就是動態鏈接庫的搜索路徑),多個目錄名間以空白字符(空格、換行等)或冒號或逗號分割。查看系統中的動態鏈接庫配置文件的內容:

    Linux的配置文件將目錄ld.so.conf.d/中的配置文件包含了進來。

  • 動態鏈接庫管理命令

    為了讓新增加的動態鏈接庫能夠被系統共享,需要運行動態鏈接庫的 管理命令ldconfig。ldconfig命令的作用是在系統的默認搜索路徑和動態鏈接庫配置文件中所列出的目錄里搜索動態鏈接庫,創建動態鏈接庫裝入程序需要的鏈接和緩存文件。搜索完畢后,將結果寫入緩存文件/etc/ld.so.cache中,文件中保存的是已經排好序的動態鏈接庫名字列表。

    ldconfig命令的用法如下:

  • 使用動態鏈接庫

  • 把當前工作目錄(libhello.so.1所在的目錄)加入動態鏈接庫的搜索路徑配置文件/etc/ld.so.conf中

    執行ldconfig命令刷新緩存文件/etc/ld.so.cache:

    我們會發現,執行ldconfig命令后,當前目錄下生成了一個新的文件libhello.so(這是-soname,libhello.so選項導致的,如果沒有該選項,那么ldconfig執行后不會生成新文件libhello.so。),使用ls命令會發現此文件是libhello.so.1的鏈接文件:

    在編譯程序時,使用動態鏈接庫和靜態鏈接庫是一致的,使用"-lxxx"的方式:

    編譯后執行時出現如下錯誤:

    其主要原因是使用了SELINUX。將其狀態設置為disabled即可,方法如下:
    打開/etc/selinux/config,將selinux=enforcing或permissive改成disabled。然后存盤退出,重啟系統。

    再次執行,結果如下:

    運行時,還可能出現這樣的錯誤:test: error while loading shared libraries: libxxx.so:cannot open shared object file: No such file or directory,這是由于程序運行時沒有找到動態鏈接庫造成的。程序編譯時鏈接動態鏈接庫和運行時使用動態鏈接庫的概念是不同的,在運行時,程序鏈接的動態鏈接庫需要在系統目錄下才行。有幾種辦法可以解決此種問題:

  • 將動態鏈接庫的目錄放到程序搜索路徑中,可以將庫的路徑添加到環境變量LD_LIBRARY_PATH中實現:
  • 使用ld-Linux.so.2來加載程序,命令格式為:
  • /lib/ ld-Linux.so.2 –library-path 路徑 程序名

    加載test程序的命令為:

    不過貌似并不是所有系統上都有ld-Linux.so.2。

    注意,如果系統的搜索路徑下同時存在靜態鏈接庫和動態鏈接庫,默認情況下會鏈接動態鏈接庫。如果需要強制鏈接靜態鏈接庫,需要加上"-satic"選項。

    動態加載庫

    前言

    ????動態加載庫和一般的動態鏈接庫所不同的是,一般動態鏈接庫在程序啟動時就要尋找動態庫,找到庫函數;而動態加載庫可以用程序的方法來控制什么時候加載。動態加載庫主要有函數dlopen()、dlerror()、dlsym()和dlclose()來控制動態庫的使用。函數原型如下:

  • 打開動態庫dlopen()

    函數dlopen()按照用戶指定的方式打開動態鏈接庫,其中參數filename為動態鏈接庫的文件名,flag為打開方式,一般為RTLD_LASY,函數的返回值為庫的指針。

    例如,下面的代碼使用dlopen打開當前目錄下的動態庫libhello.so:

    void *phandle = dlopen("./libhello.so", RTLD_LAZY);

  • 獲得函數指針dlsym()

    使用動態鏈接庫的目的是調用其中的函數,完成特定的功能。函數dlsym()可以獲得動態鏈接庫中指定函數的指針,然后可以使用這個函數指針進行操作。其中參數handle為dlopen()打開動態庫后返回的句柄,參數symbol為函數的名稱,返回值為函數指針。

  • 使用動態加載庫實例

    #include <stdio.h>

    #include <dlfcn.h>

    ?

    int

    main(void)

    {

    ????void (*printhello)(void);

    ????void *phandle = NULL;

    ????char *perr = NULL;

    ????phandle = dlopen("./libhello.so", RTLD_LAZY);

    ????if(!phandle)

    ????{

    ????????printf("Failed load library!\n");

    ????}

    ????perr = dlerror();

    ????if(perr != NULL)

    ????{

    ????????printf("%s\n", perr);

    ????????return(0);

    ????}

    ?

    ????printhello = dlsym(phandle, "print_hello");

    ????perr = dlerror();

    ????if(perr != NULL)

    ????{

    ????????printf("%s\n", perr);

    ????????return(0);

    ????}????

    ?

    ????(*printhello)();

    ?

    ????dlclose(phandle);

    ????return(0);

    }

    編譯運行:

    注意,想要使用dlfcn.h中的函數,編譯時必須加上選項-ldl

  • 小發現:

      有沒有注意到,我們并沒有使用用到include <hello.h>(假設我們為print_hello.c寫了一個hello.h的頭文件)。其實,只要編譯命令中加入選項-lhello,hello.h頭文件包含不包含都沒有問題。為了驗證這個問題,使用http://www.cnblogs.com/nufangrensheng/p/3518411.html中的程序清單11-1這個實例進行了測試:

      在http://www.cnblogs.com/nufangrensheng/p/3518411.html程序清單11-1編譯過程中,曾遇到undefined reference to ‘pthread_create’這樣的錯誤,原因在于沒有在編譯命令中加入-lpthread選項。

      如果我們加入了-lpthread選項,此時嘗試著把程序中的#include <pthread.h>去掉,重新編譯你會發現同樣也是可以的。

      總結:如果使用的是標準庫中的函數,則只需將頭文件包含進來。如果使用的函數所在的庫不是標準庫(例如我們自己編寫的庫或標準以外擴展的庫),則在編譯時必須加入-lxxx選項,而頭文件則可以包含也可以不包含,包含進來顯得規范而已。

    總結

    以上是生活随笔為你收集整理的静态链接库、动态链接库和动态加载库的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。

    主站蜘蛛池模板: 亚洲暴爽 | 美女被爆操网站 | 国产精品国色综合久久 | 成人免费毛片东京热 | www.桃色 | 亚洲区国产区 | 国产一区二区日韩 | 蜜桃精品成人影片 | 91看片在线 | a级大片免费看 | 免费精品国产 | 波多野结衣网站 | 我会温柔一点的日剧 | 在线免费看mv的网站入口 | 美丽的姑娘在线观看免费 | 亚洲国产精品毛片av不卡在线 | 精品黄色在线观看 | 巨大乳の揉んで乳榨り奶水 | 免费观看日批视频 | 久久这里只有精品23 | www免费视频 | xxx黄色片 | 美女视频久久 | 色乱码一区二区三区 | 国产成人短视频 | 理论片中文字幕 | 国产欧美一区二区三区沐欲 | 国产裸体无遮挡 | 日韩久久精品一区二区 | 国产熟妇搡bbbb搡bbbb搡 | 国产chinese男男网站大全 | 大尺度激情吻胸视频 | 中文字幕永久在线播放 | www亚洲一区 | 农村脱精光一级 | 日韩一区二 | 亚洲激情欧美 | 一品道av| 国产精选毛片 | av片在线观看 | 污片免费在线观看 | 男女羞羞动态图 | 成人精品三级av在线看 | 伊人网站在线观看 | 99涩涩| 日本道在线观看 | 日本少妇激情舌吻 | 欧美成人精品欧美一级乱黄 | 欧美精品99久久 | 拔萝卜91 | 亚洲第一视频 | 日韩人妻精品一区二区 | 国产精品尤物视频 | 人人九九| 欧美精品韩国精品 | 日韩人成| 韩国三级做爰视频 | 欧美va亚洲va | www.猫咪av | 不许穿内裤随时挨c调教h苏绵 | 麻豆激情网 | 成人亚洲玉足脚交系列 | 激情综合五月婷婷 | 欧美亚洲图片小说 | 色先锋在线 | 精品久久一区 | 日韩精品一区在线观看 | 国产精品一级 | 免费一级肉体全黄毛片 | 蜜臀久久99精品久久久久久 | 久久综合久久鬼色 | 爱情岛论坛av | 婷婷色在线播放 | 亚洲AV无码国产精品播放在线 | 久久狠狠高潮亚洲精品 | 婷婷爱爱 | 狠狠成人 | 爆乳2把你榨干哦ova在线观看 | 久久午夜精品视频 | 久热在线 | 国产传媒一级片 | 在线视频污 | 福利亚洲 | 四虎最新站名点击进入 | 久久久久久久久一区 | 日本另类视频 | 香蕉中文网 | 毛片一区二区三区 | 爱爱免费视频网站 | 好吊色一区二区三区 | 嫩草国产 | 九九九九九九精品 | 6680新视觉电影免费观看 | 亚洲一卡二卡 | 精品国产无码一区二区 | 欧美成在线视频 | 中文字幕一区二区免费 | 欧美成年人视频 | 欧美激情网址 |