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

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 人文社科 > 生活经验 >内容正文

生活经验

程序员的自我修养--链接、装载与库笔记:Linux共享库的组织

發布時間:2023/11/27 生活经验 30 豆豆
生活随笔 收集整理的這篇文章主要介紹了 程序员的自我修养--链接、装载与库笔记:Linux共享库的组织 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

共享庫(Shared Library)概念:其實從文件結構上來講,共享庫和共享對象沒什么區別,Linux下的共享庫就是普通的ELF共享對象。由于共享對象可以被各個程序之間共享,所以它也就成為了庫的很好的存在形式,很多庫的開發者都以共享對象的形式讓程序來使用,久而久之,共享對象和共享庫這兩個概念已經很模糊了,所以廣義上我們可以將它們看作是同一個概念。

1. 共享庫版本

共享庫兼容性:共享庫的開發者會不停地更新共享庫的版本,以修正原有的Bug、增加新的功能或改進性能等。由于動態鏈接的靈活性,使得程序本身和程序所依賴的共享庫可以分別獨立開發和更新。但是共享庫版本的更新可能會導致接口的更改或刪除,這可能導致依賴于該共享庫的程序無法正常運行。最簡單的情況下,共享庫的更新可以被分為兩類:(1). 兼容更新:所有的更新只是在原有的共享庫基礎上添加一些內容,所有原有的接口都保持不變;(2). 不兼容更新:共享庫更新改變了原有的接口,使用該共享庫原有接口的程序可能不能運行或運行不正常。

接口這個詞有著很廣泛的含義,在軟件的很多層次上都有所謂的”接口”。但是這里討論的接口是二進制接口,即ABI(Application Binary Interface)共享庫的ABI跟程序語言有著很大的關系,不同的語言對于接口的兼容性要求不同。ABI對于不同的語言來說,主要包括一些諸如函數調用的堆棧結構、符號命名、參數規則、數據結構的內存分布等方面的規則。對于一個C語言編寫的共享庫來說,什么樣的更改會導致ABI變化呢?常見的更改方式,如下表所示:

導致C語言的共享庫ABI改變的行為主要有如下4個:

(1). 導出函數的行為發生改變,也就是說調用這個函數以后產生的結果與以前不一樣,不再滿足舊版本規定的函數行為準則。

(2). 導出函數被刪除。

(3). 導出數據的結構發生變化,比如共享庫定義的結構體變量的結構發生改變:結構成員刪除、順序改變或其它引起結構體內存布局變化的行為(不過通常來講,往結構體的尾部添加成員不會導致不兼容,當然這個結構體必須是共享庫內部分配的,如果是外部分配的,在分配該結構體時必須考慮成員添加的情況)。

(4). 導出函數的接口發生變化,如函數返回值、參數被更改。

如果能夠保證上述4種情況不發生,那么絕大部分情況下,C語言的共享庫將會保持ABI兼容。注意,僅僅是絕大部分情況,要破壞一個共享庫的ABI十分容易,要保持ABI的兼容卻十分困難。很多因素會導致ABI的不兼容,比如不同版本的編譯器、操作系統和硬件平臺等,使得ABI兼容尤為困難。使用不同版本的編譯器或系統庫可能會導致結構體的成員對齊方式不一致,從而導致了ABI的變化。這種ABI不兼容導致的問題可能非常微妙,表面上看可能無關緊要,但是一旦發生故障,相關的Bug非常難以定位,這也是共享庫很大的一個問題。

對于C++來說,ABI問題就更為嚴重了。由于C++非常復雜,它支持諸如模板等一些高級特性,這些特性對于ABI兼容來說簡直就是災難。因為C++標準對于C++的ABI沒有做出規定,所以不同的編譯器甚至同一個編譯器的不同版本對于C++的一些特性的實現都有著各自的方案,而且相互不兼容,比如虛函數表、模板實例化、多重繼承等。對于Linux來說,如果你要開發一個導出接口為C++的共享庫,需要注意以下事項,以防止ABI不兼容(完全遵循以下準則還是不能保證ABI完全兼容):(1).不要在接口類中使用虛函數,萬不得已要使用虛函數時,不要隨意刪除、添加或在子類中添加新的實現函數,這種會導致類的虛函數表結構發生變化;(2).不要改變類中任何成員變量的位置和類型;(3).不要刪除非內嵌的public或protected成員函數;(4).不要將非內嵌的成員函數改變成內嵌成員函數;(5).不要改變成員函數的訪問權限;(6).不要在接口中使用模板;(7).最重要的是,不要改變接口的任何部分或干脆不要使用C++作為共享庫接口。

共享庫版本命名:有幾種辦法可用于解決共享庫的兼容性問題,有效辦法之一就是使用共享庫版本的方法。Linux有一套規則來命名系統中的每一個共享庫,它規定共享庫的文件名規則必須如下:libname.so.x.y.z

最前面使用前綴”lib”、中間是庫的名字和后綴”.so”,最后面跟著的是三個數字組成的版本號。”x”表示主版本號(Major Version Number),”y”表示次版本號(Minor Version Number),”z”表示發布版本號(Release Version Number)。三個版本號的含義不一樣。主版本號表示庫的重大升級,不同主版本號的庫之間是不兼容的,依賴于舊的主版本號的程序需要改動相應的部分,并且重新編譯,才可以在新版的共享庫中運行;或者系統必須保留舊版的共享庫,使得那些依賴于舊版共享庫的程序能夠正常運行。次版本號表示庫的增量升級,即增加一些新的接口符號,且保持原來的符號不變。在主版本號相同的情況下,高的次版本號的庫向后兼容低的次版本號的庫。一個依賴于舊的次版本號共享庫的程序,可以在新的次版本號共享庫中運行,因為新版中保留了原來所有的接口,并且不改變它們的定義和含義。發布版本號表示庫的一些錯誤的修正、性能的改進等,并不添加任何新的接口,也不對接口進行更改。相同主版本號、次版本號的共享庫,不同的發布版本號之間完全兼容,依賴于某個發布版本號的程序可以在任何一個其它發布版本號中正常運行,而無需做任何修改。當然現在Linux中也存在不少不遵循上述規定的”頑固分子”,比如最基本的C語言庫Glibc就不使用這種規則。

SO-NAME:對于Solaris和Linux,普遍采用一種叫做SO-NAME的命名機制來記錄共享庫的依賴關系。每個共享庫都有一個對應的”SO-NAME”,這個SO-NAME即共享庫的文件名去掉次版本號和發布版本號,保留主版本號。很明顯,”SO-NAME”規定了共享庫的接口,”SO-NAME”的兩個相同共享庫,次版本號大的兼容次版本號小的。Linux系統中,系統會為每個共享庫在它所在的目錄創建一個跟”SO-NAME”相同的并且指向它的軟鏈接(Symbol Link)。比如系統中有存在一個共享庫”/lib/libfoo.so.2.6.1”,那么Linux中的共享庫管理程序就會為它產生一個軟鏈接”/lib/libfoo.so.2”指向它。由于歷史原因,動態鏈接器和C語言庫的共享對象文件名規則不按Linux標準的共享庫命名方法。

那么以”SO-NAME”為名字建立軟鏈接有什么用處呢?實際上這個軟鏈接會指向目錄中主版本號相同、次版本號和發布版本號最新的共享庫。這樣保證了所有的以SO-NAME為名的軟鏈接都指向系統中最新版的共享庫。建立以SO-NAME為名字的軟鏈接目的是,使得所有依賴某個共享庫的模塊,在編譯、鏈接和運行時,都使用共享庫的SO-NAME,而不使用詳細的版本號。當共享庫進行升級的時候,如果只是進行增量升級,即保持主版本號不變,只改變次版本號或發布版本號,那么我們可以直接將新版的共享庫替換掉舊版,并且修改SO-NAME的軟鏈接指向新版本共享庫,即可實現升級;當共享庫的主版本號升級時,系統中就會存在多個SO-NAME,由于這些SO-NAME并不相同,所以已有的程序并不會受影響。總之,SO-NAME表示一個庫的接口,接口不向后兼容,SO-NAME就發生變化,這是基本的原則。Linux中提供了一個工具叫做”ldconfig”,當系統中安裝或更新一個共享庫時,就需要運行這個工具,它會遍歷所有的默認共享庫目錄,比如/lib、/usr/lib等,然后更新所有的軟鏈接,使它們指向最新版的共享庫;如果安裝了新的共享庫,那么ldconfig會為其創建相應的軟鏈接

鏈接名:當我們在編譯器里面使用共享庫的時候(比如使用GCC的”-l”參數鏈接某個共享庫),我們使用了更為簡潔的方式,比如需要鏈接一個libXXX.so.2.6.1的共享庫,只需要在編譯器命令行里面指定-lXXX即可,可省略所有其它部分。編譯器會根據當前環境,在系統中的相關路徑(往往由-L參數指定)查找最新版本的”XXX”庫。這個”XXX”又被稱為共享庫的鏈接名(Link Name)。不同類型的庫可能會有同樣的鏈接名,比如C語言運行庫有靜態版本(libc.a)和動態版本(libc.so.x.y.z)的區別,如果在鏈接時使用參數”-lc”,那么鏈接器會根據輸出文件的情況(動態/靜態)來選擇適合版本的庫。比如ld使用”-static”參數時,”-lc”會查找libc.a;如果使用”-Bdynamic”(這也是默認情況),它會查找最新版本的libc.so.x.y.z。

2. 符號版本

基于符號的版本機制(Symbol Versioning):基本思路是讓每個導出和導入的符號都有一個相關聯的版本號,它的實際做法類似于名稱修飾的方法。與以往簡單地將某個共享庫的版本號重新命名不同(比如將libfoo.so.1.2升級到libfoo.so.1.3),當我們將libfoo.so.1.2升級至1.3時,仍然保持libfoo.so.1這個SO-NAME,但是給在1.3這個新版中添加的那些全局符號打上一個標記,比如”VERS_1.3”。那么,如果一個共享庫每一次次版本號升級,我們都能給那些在新的次版本號中添加的全局符號打上相應的標記,就可以清楚地看到共享庫中的每個符號都擁有相應的標簽,比如”VERS_1.1”、”VERS_1.2”、”VERS_1.3”、”VERS_1.4”。

Linux中的符號版本:Linux系統下共享庫的符號版本機制并沒有被廣泛應用,主要使用共享庫符號版本機制的是Glibc軟件包中所提供的20多個共享庫。這些共享庫比較有效地利用了符號版本機制來表示符號的版本演化及利用范圍機制來屏蔽一些不希望暴露給共享庫使用者的符號。

GCC對Solaris符號版本機制的擴展:GCC在Solaris系統中的符號版本機制的基礎上還提供了兩個擴展。第一個擴展是,除了可以在符號版本腳本中指定符號的版本之外,GCC還允許使用一個叫做”.symver”的匯編宏指令來指定符號的版本,這個匯編宏指令可以被用在GAS匯編中,也可以在GCC的C/C++源代碼中以嵌入匯編指令的模式使用。第二個擴展是GCC允許多個版本的同一個符號存在于一個共享庫中,也就是說,在鏈接層面提供了某種形式的符號重載機制。Linux下的符號版本機制允許同一個名稱的符號存在多個版本。當某個符號在新的共享庫版本中接口被更改或符號的含義被改變,那么共享庫可以保留原來的版本符號。

3. 共享庫系統路徑

目前大多數包括Linux在內的開源操作系統都遵守一個叫做FHS(File Hierarchy Standard)的標準,這個標準規定了一個系統中的系統文件應該如何存放,包括各個目錄的結構、組織和作用,這有利于促進各個開源操作系統之間的兼容性。FHS規定,一個系統中主要有兩個存放共享庫的位置,它們分別為

(1). /lib:這個位置主要存放系統最關鍵和基礎的共享庫,比如動態鏈接器、C語言運行庫、數學庫等,這些庫主要是那些/bin和/sbin下的程序所需要用到的庫,還有系統啟動時需要的庫;

(2). /usr/lib:這個目錄下主要保存的是一些非系統運行時所需要的關鍵性的共享庫,主要是一些開發時用到的共享庫,這些共享庫一般不會被用戶的程序或shell腳本直接用到。這個目錄下面還包含了開發時可能會用到的靜態庫、目標文件等;

(3). /usr/local/lib:這個目錄用來放置一些跟操作系統本身并不十分相關的庫,主要是一些第三方的應用程序的庫。GNU的標準推薦第三方的程序應該默認將庫安裝到/usr/local/lib下。

所以總體來看,/lib和/usr/lib是一些很常用的、成熟的,一般是系統本身所需要的庫;而/usr/local/lib是非系統所需的第三方程序的共享庫。

4. 共享庫查找過程

在Linux系統中,動態鏈接器是/lib/ld-linux.so.X(X是版本號),程序所依賴的共享對象全部由動態鏈接器負責裝載和初始化。任何一個動態鏈接的模塊所依賴的模塊路徑保存在”.dynamic”段里面,由DT_NEED類型的項表示。動態鏈接器對于模塊的查找有一定的規則:如果DT_NEED里面保存的是絕對路徑,那么動態鏈接器就按照這個路徑去查找;如果DT_NEED里面保存的是相對路徑,那么動態鏈接器會在/lib、/usr/lib和由/etc/ld.so.conf配置文件指定的目錄中查找共享庫。為了程序的可移植行和兼容性,共享庫的路徑往往是相對的。ld.so.conf是一個文本配置文件,它可能包含其它的配置文件,這些配置文件中存放著目錄信息。

如果動態鏈接器在每次查找共享庫時都去遍歷這些目錄,那將會非常耗費時。所以Linux系統中都有一個叫做ldconfig的程序,這個程序的作用是為共享庫目錄下的各個共享庫創建、刪除或更新相應的SO-NAME(即相應的符號鏈接),這樣每個共享庫的SO-NAME就能夠指向正確的共享庫文件;并且這個程序還會將這些SO-NAME收集起來,集中存放到/etc/ld.so.cache文件里面,并建立一個SO-NAME的緩存。當動態鏈接器要查找共享庫時,它可以直接從/etc/ld.so.cache里面查找。而/etc/ld.so.cache的結構是經過特殊設計的,非常適合查找,所以這個設計大大加快了共享庫的查找過程。如果動態鏈接器在/etc/ld.so.cache里面沒有找到所需要的共享庫,那么它還會遍歷/lib和/usr/lib這兩個目錄,如果還是沒有找到,就宣告失敗。

所以理論上講,如果我們在系統指定的共享庫目錄下添加、刪除或更新任何一個共享庫,或者我們更改了/etc/ld.so.conf的配置,都應該運行ldconfig這個程序,以便調整SO-NAME和/etc/ld.so.cache。很多軟件包的安裝程序在往系統里面安裝共享庫以后都會調用ldconfig

5. 環境變量

LD_LIBRARY_PATH:Linux系統提供了很多方法來改變動態鏈接器裝載共享庫路徑的方法,通過使用這些方法,我們可以滿足一些特殊的需求,比如共享庫的調試和測試、應用程序級別的虛擬等。改變共享庫查找路徑最簡單的方法是使用LD_LIBRARY_PATH環境變量,這個方法可以臨時改變某個應用程序的共享庫查找路徑,而不會影響系統中的其它程序Linux系統中,LD_LIBRARY_PATH是一個由若干個路徑組成的環境變量,每個路徑之間由冒號分割。默認情況下,LD_LIBRARY_PATH為空。如果我們為某個進程設置了LD_LIBRARY_PATH,那么進程在啟動時,動態鏈接器在查找共享庫時,會首先查找由LD_LIBRARY_PATH指定的目錄。這個環境變量可以很方便地讓我們測試新的共享庫或使用非標準的共享庫。

Linux中還有一種方法可以實現與LD_LIBRARY_PATH類似的功能,那就是直接運行動態鏈接器來啟動程序。

有了LD_LIBRARY_PATH之后,再來總結動態鏈接器查找共享庫的順序。動態鏈接器會按照下列順序依次裝載或查找共享對象(目標文件):(1).由環境變量LD_LIBRARY_PATH指定的路徑;(2).由路徑緩存文件/etc/ld.so.cache指定的路徑;(3).默認共享庫目錄,先/usr/lib,然后/lib。

LD_PRELOAD:這個文件中我們可以指定預先裝載的一些共享庫或目標文件。在LD_PRELOAD里面指定的文件會在動態鏈接器按照固定規則搜索共享庫之前裝載,它比LD_LIBRARY_PATH里面所指定的目錄中的共享庫還要優先。無論程序是否依賴于它們,LD_PRELOAD里面指定的共享庫或目標文件都會被裝載。由于全局符號介入這個機制的存在,LD_PRELOAD里面指定的共享庫或目標文件中的全局符號就會覆蓋后面加載的同名全局符號,這使得我們可以很方便地做到改寫標準C庫中的某個或某幾個函數而不影響其它函數,對于程序的調試或測試非常有用。與LD_LIBRARY_PATH一樣,正常情況下應該盡量避免使用LD_PRELOAD。系統配置文件中有一個文件是/etc/ld.so.preload,它的作用于LD_PRELOAD一樣。這個文件里面記錄的共享庫或目標文件的效果跟LD_PRELOAD里面指定的一樣,也會被提前裝載。

LD_DEBUG:這個變量可以打開動態鏈接器的調試功能,當我們設置這個變量時,動態鏈接器會在運行時打印出各種有用的信息,對于我們開發和調試共享庫有很大的幫助。如執行Program1,程序代碼見https://blog.csdn.net/fengbingchun/article/details/101120761,執行結果如下圖所示:

LD_DEBUG設置值的作用

(1). “files”:動態鏈接器打印整個裝載過程,顯示程序依賴于哪個共享庫并且按照什么步驟裝載和初始化,共享庫裝載時的地址等。

(2). “bindings”:顯示動態鏈接的符號綁定過程。

(3). “libs”:顯示共享庫的查找過程。

(4). “versions”:顯示符號的版本依賴關系。

(5). “reloc”:顯示重定位過程。

(6). “symbols”:顯示符號表查找過程。

(7). “statistics”:顯示動態鏈接過程中的各種統計信息。

(8). “all”:顯示以上所有信息。

(9). “help”:顯示上面的各種可選值的幫助信息。

6. 共享庫的創建和安裝

共享庫的創建創建共享庫的過程跟創建一般的共享對象的過程基本一致,最關鍵的是使用GCC的兩個參數,即”-shared”和”-fPIC”。”-shared”表示輸出結果是共享庫類型的;”-fPIC”表示使用地址無關代碼(Position Independent Code)技術來生產輸出文件。另外還有一個參數是”-Wl”,這個參數可以將指定的參數傳遞給鏈接器,比如當我們使用”-Wl,-soname,my_soname”時,GCC會將”-soname my_soname”傳遞給鏈接器,用來指定輸出共享庫的SO-NAME。如果我們不使用-soname來指定共享庫的SO-NAME,那么該共享庫默認就沒有SO-NAME,即使用ldconfig更新SO-NAME的軟鏈接時,對該共享庫也沒有效果。

幾個值得注意的事項:(1).不要把輸出共享庫中的符號和調試信息去掉,也不要使用GCC的”-fomit-frame-pointer”選項,這樣做雖然不會導致共享庫停止運行,但是會影響調試共享庫,給后面的工作帶來很多麻煩。(2).在開發過程中,你可能要測試新的共享庫,但是又不希望影響現有的程序正常運行,可以用LD_LIBRARY_PATH指定共享庫的查找路徑。還有一種方法是使用鏈接器的”-rpath”選項(或者GCC的-Wl,-rpath),這種方法可以指定鏈接產生的目標程序的共享庫查找路徑。(3).默認情況下,鏈接器在產生可執行文件時,只會將那些鏈接時被其它共享模塊引用到的符號放到動態符號表,這樣可以減少動態符號表的大小。也就是說,在共享模塊中反向引用主模塊中的符號時,只有那些在鏈接時被共享模塊引用到的符號才會被導出。有一種情況是,當程序使用dlopen()動態加載某個共享模塊,而該共享模塊需反向引用主模塊的符號時,有可能主模塊的某些符號因為在鏈接時沒有被其它共享模塊引用而沒有被放到動態符號表里面,導致了反向引用失敗。ld鏈接器提供了一個”-export-dynamic”的參數,這個參數表示鏈接器在生產可執行文件時,將所有全局符號導出到動態符號表,以防止出現上述問題。我們也可以在GCC中使用”-Wl,-export-dynamic”將該參數傳遞給鏈接器。

清除符號信息:正常情況下編譯出來的共享庫或可執行文件里面帶有符號信息和調試信息,這些信息在調試時非常有用,但是對于最終發布的版本來說,這些符號信息用處并不大,并且使得文件尺寸變大。我們可以使用一個叫”strip”的工具清除掉共享庫或可執行文件的所有符號和調試信息(“strip”是binutils的一部分):$ strip libfoo.so

去除符號和調試信息以后的文件往往比之前要小很多。除了使用”strip”工具,我們還可以使用ld的”-s”和”-S”參數,使得鏈接器生成輸出文件時就不產生符號信息。”-s”和”-S”的區別是:”-S”消除調試符號信息,而”-s”消除所有符號信息。我們也可以在GCC中通過”-Wl,-s”和”-Wl,-S”給ld傳遞這兩個參數。

?共享庫的安裝:最簡單的辦法就是將共享庫復制到某個標準的共享庫目錄,如/lib、/usr/lib等,然后運行ldconfig即可。不過上述方法往往需要系統的root權限,如果沒有,則無法往/lib、/usr/lib等目錄添加文件,也無法運行ldconfig程序。也可以通過建立相應的SO-NAME軟鏈接方法,并告訴編譯器和程序如何查找該共享庫等,以便于編譯器和程序都能夠正常運行。建立SO-NAME的辦法也是使用ldconfig,只不過需要指定共享庫所在的目錄。在編譯程序時,也需要指定共享庫的位置,GCC提供了兩個參數”-L”和”-l”,分別用于指定共享庫搜索目錄和共享庫。也可以使用”-rpath”參數。

共享庫構造和析構函數:很多時候你希望共享庫在被裝載時能夠進行一些初始化工作,比如打開文件、網絡連接等,使得共享庫里面的函數接口能夠正常工作。GCC提供了一種共享庫的構造函數,只要在函數聲明時加上”__attribute__((constructor))”的屬性,即指定該函數為共享庫構造函數,擁有這種屬性的函數會在共享庫加載時被執行,即在程序的main函數之前執行。如果我們使用dlopen()打開共享庫,共享庫構造函數會在dlopen()返回之前執行。與共享庫構造函數相對應的是析構函數,我們可以使用在函數聲明時加上”__attribute__((destructor))”的屬性,這種函數會在main()函數執行完畢之后執行(或者是程序調用exit()時執行)。如果共享庫是在運行時加載的,那么我們使用dlclose()來卸載共享庫時,析構函數將會在dlclose()返回之前執行。值得注意的是,如果我們使用了這種析構或構造函數,那么必須使用系統默認的標準運行庫和啟動文件,即不可以使用GCC的”-nostartfiles”或”-nostdlib”這兩個參數。因為這些構造和析構函數是在系統默認的標準運行庫或啟動文件里面被運行的,如果沒有這些輔助構造,它們可能不會被運行。另外還有一個問題是,如果我們有多個構造函數,那么默認情況下,它們被執行的順序是沒有規定的。如果我們希望構造和析構函數能夠按照一定的順序執行,GCC為我們提供了一個參數叫做優先級,我們可以指定某個構造或析構函數的優先級。對于構造函數來說,屬性中優先級數字越小的函數將會在優先級大的函數之前運行;而對于析構函數來講,則剛好相反。這種安排有利于構造函數和析構函數能夠匹配,比如某一對構造函數和析構函數分別用來申請和釋放某個資源,那么它們可以擁有一樣的優先級。這樣做的結果往往是先申請的資源后釋放,符合資源釋放的一般規則。

共享庫腳本:前面所提到的共享庫都是動態鏈接的ELF共享對象文件(.so),事實上,共享庫還可以是符合一定格式的鏈接腳本文件。通過這種腳本文件,我們可以把幾個現有的共享庫通過一定的方式組合起來,從用戶的角度看就是一個新的共享庫。這里的腳本與LD的腳本從語法和命令上來講沒什么區別,它們的作用也相似,即將一個或多個輸入文件以一定的格式經過變換以后形成一個輸出文件。我們也可以將這種共享庫腳本叫做動態鏈接腳本,因為這個鏈接過程是動態完成的,也就是運行時完成的。

GitHub:https://github.com/fengbingchun/Messy_Test

總結

以上是生活随笔為你收集整理的程序员的自我修养--链接、装载与库笔记:Linux共享库的组织的全部內容,希望文章能夠幫你解決所遇到的問題。

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