我聽說導入庫有「存根」,所以可執行文件知道我們想要哪個dll和函數。現在我的問題是:那些存根是什麼?他們看起來怎麼樣?可執行文件如何將指針設置爲DLL中的正確位置?它是如何知道我們是否在談論普通庫或導入庫,因爲它們都是.lib文件?導入庫如何工作?
導入庫如何工作?
回答
MSVC鏈接器不直接鏈接到DLL,它只能鏈接到靜態庫(.lib)。
非常粗略地說,一個導入庫是一個正常的靜態庫,對每個DLL導出的函數都有一個存根函數。
例如,如果一個DLL具有的功能void func1()
和出口func1
,相應的導入庫將包含存根函數void __imp__func1() { __asm { jmp dword ptr func1; } }
在運行時,「跳」將採取func1
地址從導入表。這就是爲什麼需要存根。
申請中的聲明void __declspec(dllimport) func1();
實際上是指__imp__func1()
。
您可以繞過這整個機制,並在運行時撥打LoadLibrary
和GetProcAddress
以獲取地址func1
。它會有同樣的效果。
這取決於您使用的編譯器(鏈接器)和平臺。
I.e.在Windows操作系統上,共享庫通常是.DLL文件,如果要鏈接到它(除了動態加載它並在運行時解析其符號),則需要相應的.LIB文件,即存根庫。
基本上存根庫是重新映射由DLL輸出(與__declspec(dllexport)
)的所有符號中存在的存根和,可以發現,通過使用__declspec(dllimport)
程序內的靜態鏈接符號的靜態庫。
那麼__declspec(dllexport)是來自Windows API的函數,還是Visual Studio中的指令? –
@Daniel Nyman:'__declspec'是一個關鍵字(據我所知,特定於Visual Studio),'dllexport'和'dllimport'是該關鍵字的屬性。更多信息,請訪問:https://msdn.microsoft.com/en-us/library/3y1sfaz2.aspx – roalz
[__declspec](https://msdn.microsoft.com/en-us/library/dabb5z75.aspx)是一個關鍵字,它分配一個Microsoft特定的存儲類屬性。 – IInspectable
- 1. IBM SQL數據庫導入工作不
- 2. 導入庫創建不工作
- 3. 導入的類型庫不再工作
- 4. 靜態庫的導入如何在Java/Spring中工作?
- 5. 在clojure中導入java庫,它是如何工作的?
- 6. 如何導入庫到Android工作室0.4.3
- 7. 如何將JBLAS庫導入到Android工作室
- 8. 如何導入現有的Android庫項目到Eclipse工作
- 9. 如何導入庫?機器人工作室1.4
- 10. 此導入聲明如何工作?
- 11. Objective-C導入過程如何工作?
- 12. Python導入如何正確工作?
- 13. 這個Python導入如何工作?
- 14. 快速包導入如何工作?
- 15. 導入工作不
- 16. 如何導入工作表的列以激活工作簿
- 17. 在python絕對導入不工作,相對導入工作
- 18. 如何將庫導入Intellij?
- 19. 如何導入com.google.api.client庫?
- 20. 如何導入規格庫
- 21. python newbie - 如何導入庫
- 22. 導入Github庫並只與庫一起工作
- 23. 將VHDL軟件包從工作庫以外的庫導入SV
- 24. HBASE備份 - java api如何導出/導入工作?
- 25. 如何導入和導出JBPM 6.5庫
- 26. phpMyAdmin導出如何工作?
- 27. 導入keras.datasets不工作
- 28. Scipy.misc導入不工作
- 29. 導入Gdal不工作
- 30. Adaljs - 導入不工作角
另請參閱https://msdn.microsoft.com/en-us/magazine/bb985992.aspx –
可執行文件不知道這些。它是鏈接器,它會發出適當的代碼。 – IInspectable