簡體   English   中英

在c語言中鏈接和加載有什么區別

[英]what is the difference between linking and loading in c language

鏈接和加載動態庫是否都在運行時發生? 或者只是在運行時加載庫?

請參閱前面關於靜態鏈接和動態鏈接之間區別的非常好的觀點。 假設您指的是動態鏈接,那么:

加載和(動態)鏈接都是由鏈接器完成的 - 在linux和其他Unix上/lib/ld.so ,這是由/lib/ld.so完成的,這是幾乎所有情況下操作系統啟動的實際程序。 ld.so反過來你的應用程序 - mygameBinary 加載到內存中,然后ld.so從文件mygameBinary讀取它需要的動態鏈接庫列表。

然后,鏈接器ld.so依次將每個庫加載到內存中,例如libc.solibpthread.solibopengl.so ,並查看這些可能需要的其他庫,例如libm.so

加載完成后,開始鏈接 ,查看由一個庫或應用程序導出並由另一個庫或應用程序導入的命名對象或函數的過程。 然后,鏈接器更改各種引用,有時還會更新代碼以更新每個庫中的未鏈接數據指針和函數調用,以指向實際數據或函數所在的位置。 例如, mygameBinaryprintfmygameBinary開始沒有指向任何內容(實際上它只是調用鏈接器),但是在鏈接之后變成了跳轉到libcprintf函數。

完成此鏈接后,通過調用mygameBinary_start函數啟動應用程序,然后調用main ,然后啟動游戲。

以這種方式動態鏈接是必要的,以支持以下內容:

  • 應用程序發布后庫更新,這會更改函數和數據的位置。
  • 在不同版本的OS上運行的單個應用程序
  • 關於庫或應用程序可能在內存中加載的不確定性
  • 通過在多個應用程序之間共享庫使用的物理ram來減小核心的大小。

某些操作系統的細節不同,例如OSX和AIX都將某組庫預先加載到內存中的固定位置。 這意味着它們不需要加載,只需鏈接,這可能更快。

某些操作系統(如OSX,有時還支持Linux)支持預鏈接,這是一個腳本在啟動它們之前在系統上的應用程序上運行並進行鏈接的過程。 啟動它們時,您無需鏈接它們。 這很重要,因為聯需要,當你啟動應用了大量的計算機的時間,和一些應用程序可能會推出多次第二,如gcccppas在應用程序的構建過程,或過濾器腳本索引你的計算機的數據時(OSX Spotlight)。

鏈接是獲取一些較小的可執行文件並將它們作為單個較大的可執行文件連接在一起的過程。

加載是在執行之前將可執行文件加載到內存中。

有兩種類型的鏈接:靜態鏈接和動態鏈接。

靜態鏈接在編譯時發生,因此它在加載程序之前發生。 使用靜態鏈接,程序使用的外部符號(例如函數名稱)將在編譯時解析。

動態鏈接在運行時發生,因此它發生在加載程序之后或加載時。 通過動態鏈接,符號在加載時或在訪問符號時的運行時解析(延遲綁定)。 后者更常見。

兩者都發生在動態庫的運行時。

首先,加載庫以及它們的所有依賴項(以及這些庫的依賴項等)。 然后動態鏈接器解析已加載庫中的符號。 通常這兩個功能都是由同一個軟件實現的; 在Linux上它是ld.so。

靜態庫中的符號在鏈接時解析並包含在可執行文件本身中。 但是,靜態庫可能具有未解析的符號,這些符號在運行時由動態庫滿足。

這里有一個深入的描述如何發生這種情況,名稱如何散列,在運行時解析符號的成本等等, 如何編寫共享庫

file01.c,file02.c - >產生 - > file01.o,file02.o - >這些.o信息被分組並放入一個動態庫,即lib1.a file11.c,file12.c - >產生 - > file11.o,file12.o - >這些.o信息被分組並放入一個動態庫,即lib2.a

現在,我有2個庫最終鏈接在一起以生成可執行文件(如.elf或.mot或.fls)。 將lib1.a和lib2.a中的信息鏈接起來形成單個可執行文件的過程稱為鏈接。

現在,我需要將其加載到內存中以便運行它以查看最終可執行文件的行為。 將最終可執行文件(如.elf或.mot或.fls)加載到內存中以便運行的過程稱為加載。

我希望這將清除鏈接和加載的重要性(但定義不合適:-))。

Windows和Unix系統使用完全不同的動態庫方法。

Windows DLL未鏈接。 因此,您無法跨DLL共享靜態對象。 它就像你的地址空間中的一個單獨的程序。

Unix共享對象在運行時實際上是“鏈接”的,就像同一項目的不同模塊一樣,執行符號解析。

動態鏈接和庫加載都在運行時發生,但動態鏈接在程序執行之前完成,由系統鏈接器完成。 因此,例如,如果缺少必需的庫,則無法執行程序。 另一方面,庫加載是由程序本身通過dlopen / LoadLibrary函數完成的。 在這種情況下,加載過程由應用程序控制,該應用程序可以例如處理錯誤。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM