2010-02-11 119 views
6

我在這方面需要一點澄清。我覺得條款Static library & Dynamic Library是不正確的。靜態庫和動態庫:混亂

  • lib1.o + lib2.o + lib3.o - >「LinkerOutputFile」(可執行文件或庫)。
  • 如果此「LinkerOutputFile」包含所有文件lib1.o,lib2.o,lib3.o的代碼,則其表示「LinkerOutputFile」已鏈接「LinkerOutputFile」(可執行文件或庫)。 (或)

  • 如果 「LinkerOutputFile」 只包含引用其他&信息到lib1.o,lib2.o,lib3.o不包含這些LIB * .o文件的代碼。然後它說「LinkerOutputFile」動態鏈接。

這是如何使lib * .o文件成爲靜態庫還是動態庫?它們只是庫文件。

還是說,「LinkerOutputFile」是一個庫而不是可執行文件,然後取決於它的靜態鏈接或動態鏈接其被稱爲靜態庫或動態庫。對或錯?

我知道我錯了,因爲,我知道,

在大多數Unix式的平臺 擴展是

  • .A靜態庫(檔案)和
  • .so共享庫。

在Windows上:

  • .DLL表示共享庫
  • 的.lib表示靜態或導入庫。

但無法弄清楚我錯在哪裏。還請告訴我Static library & Dynamic Library內部不同。

此外,這是從ABI規格:

本章描述對象文件 格式,稱爲ELF(可執行和 鏈接格式)。有三種主要的目標文件類型: 。

再定位文件保存代碼和數據 適合與其他對象 文件鏈接到創建可執行或 共享對象文件。

一個可執行文件擁有一個程序 適合執行;文件 指定exec(BA_OS)如何創建 程序的過程映像。

共享對象文件保存代碼和數據 適於兩個 上下文進行鏈接。首先,鏈接編輯器[請參閱 ld(BA_OS)]處理共享對象 文件與其他可重定位和共享的 對象文件,以創建另一個對象 文件。其次,動態鏈接器 將其與可執行文件 和其他共享對象組合以創建過程映像。

「共享對象文件」是用於說動態庫(具有* .so擴展名)的其他詞。但是「靜態庫」呢?這甚至沒有提到它。

「可重定位」&「靜態庫」&「導入庫」是否有區別?請以內部結構說明我。

+0

請注意,用於靜態和動態鏈接的'.o'文件不同(請參閱'-static'選項的gcc參考)。您的問題的答案在這裏:http://stackoverflow.com/questions/1210787/relation-between-object-file-and-shared-object-file/1210857#1210857 – 2010-10-02 13:18:09

+0

可能重複的[靜態和共享庫之間的差異?](http://stackoverflow.com/questions/2649334/difference-between-static-and-shared-libraries) – 2012-04-06 05:31:09

回答

0

比方說,我有我的應用StaticLib.lib鏈接,然後從我的兩個應用StaticLib.lib所有代碼都將在同一個可執行文件。這意味着StaticLib.h 包含其中的函數實現。

現在,如果我鏈接應用DynamicLib.lib,然後我應用將使用DynamicLib.dll實現的功能就意味着DynamicLib.lib constains引用,是這樣的:

  • OpenWAV位於偏移量1處DynamicLib.dll
  • CloseWAV位於偏移量2處在DynamicLib.dll

名稱動態意味着它可以被任何應用程序被加載,而不是真的用DynamicLib.lib聯,但調用LoadLibrary(),並導入由DLL導出函數手。

關於Relocatable,在這一刻我不熟悉這個詞。

我說的是Windows程序員,所以我不會在Linux上真正發生什麼,但從名稱SO(Shared Objects)來看,它們與DLL一樣。

希望我的回答很有幫助!

10

.o文件不是任何類庫文件。它們是對象文件。

.a/.lib文件在構建時鏈接。在事實之後它們不能被替換。這使得它們是靜態的。

.so/.dll文件在運行時鏈接。在執行開始之前可以隨時更換它們。這使他們充滿活力。

搬遷是指在存儲器中放置一個二進制文件;來自靜態庫的代碼與二進制文件集成,因此不能獨立重新定位。

4

靜態庫包含複製到可執行文件中的代碼。庫中未被程序引用的代碼被刪除。只有靜態庫的程序在運行時沒有任何依賴關係。

動態庫在運行時鏈接 - 引用動態庫的程序將在啓動(或按需)時加載並鏈接庫。

可重新定位的庫是動態庫的另一個詞。當您與動態庫鏈接時,將根據庫在內存中的加載位置來計算其中包含的函數的地址。它們是「可重定位的」,因爲包含的功能的地址不是在鏈接時確定的。 (在靜態庫中,地址是在鏈接時計算的。)

目標文件(.o)包含已編譯的代碼,但不包含所有函數的最終地址。鏈接是鏈接器遍歷所有目標文件並計算每個被調用函數的正確地址的過程。