ARM C高階學習筆記(九)函式庫

2021-10-04 16:58:08 字數 2499 閱讀 7026

函式庫就是一些事先寫好的函式的集合,給別人復用。

函式是模組化的,因此可以被復用。我們寫好了乙個函式,可以被反覆使用。也可以a寫好了乙個函式然後共享出來,當b有相同的需求時就不需自己寫直接用a寫好的這個函式即可。

早期的函式共享都是以源**的形式進行的。這種方式共享是最徹底的(後來這種原始碼共享的方向就形成了我們現在的開源社群)。但是這種方式有它的缺點,缺點就是無法以商業化形式來發布函式庫。

商業公司需要將自己的有用的函式庫共享給被人(當然是付費的),但是又不能給客戶源**。這時候的解決方案就是以庫(主要有2種:靜態庫和動態庫)的形式來提供。

比較早出現的是靜態鏈結庫。靜態庫其實就是商業公司將自己的函式庫源**經過只編譯不連線形成.o的目標檔案,然後用ar工具將.o檔案歸檔成.a的歸檔檔案(.a的歸檔檔案又叫靜態鏈結庫檔案)。商業公司通過發布.a庫檔案和.h標頭檔案來提供靜態庫給客戶使用;客戶拿到.a和.**件後,通過.h標頭檔案得知庫中的庫函式的原型,然後在自己的.c檔案中直接呼叫這些庫檔案,在連線的時候鏈結器會去.a檔案中拿出被呼叫的那個函式的編譯後的.o二進位制**段鏈結進去形成最終的可執行程式。

動態鏈結庫比靜態鏈結庫出現的晚一些,效率更高一些,是改進型的。現在我們一般都是使用動態庫。靜態庫在使用者鏈結自己的可執行程式時就已經把呼叫的庫中的函式的**段鏈結進最終可執行程式中了,這樣好處是可以執行,壞處是太佔地方了。尤其是有多個應用程式都使用了這個庫函式時,實際上在多個應用程式最後生成的可執行程式中都各自有乙份這個庫函式的**段。當這些應用程式同時在記憶體中執行時,實際上在記憶體中有多個這個庫函式的**段,這完全重複了。而動態鏈結庫本身不將庫函式的**段鏈結入可執行程式,只是做個標記。然後當應用程式在記憶體中執行時,執行時環境發現它呼叫了乙個動態庫中的庫函式時,會去載入這個動態庫到記憶體中,然後以後不管有多少個應用程式去呼叫這個庫中的函式都會跳轉到第一次載入的地方去執行(不會重複載入)。

gcc中編譯鏈結程式預設是使用動態庫的,要想靜態鏈結需要顯式用-static來強制靜態鏈結。

庫函式的使用需要注意3點:第一,包含相應的標頭檔案;第二,呼叫庫函式時注意函式原型;第三,有些庫函式鏈結時需要額外用-l***來指定鏈結;第四,如果是動態庫,要注意-l指定動態庫的位址。

//使用makefile完成以上工作

all:

gcc aston.c -o aston.o -c

ar -rc libaston.a aston.o

/tmp/cchcm1r9.o: in function `main':

test.c:

(.text+

0x5)

: undefined reference to `func1'

test.c:

(.text+

0xa)

: undefined reference to `func2'

collect2: error: ld returned 1 exit status

/usr/bin/ld: cannot find -laston

collect2: error: ld returned 1 exit status

動態鏈結庫的字尾名是.so(對應windows系統中的dll),靜態庫的副檔名是.a

all:

gcc aston.c -o aston.o -c -fpic

gcc -o libaston.so aston.o -shared

第二步:使用自己建立的共享庫。

/tmp/ccbkinbl.o: in function `main':

test.c:

(.text+

0x5)

: undefined reference to `func1'

test.c:

(.text+

0xa)

: undefined reference to `func2'

collect2: error: ld returned 1 exit status

/usr/bin/ld: cannot find -laston

collect2: error: ld returned 1 exit status

.

/test: error while loading shared libraries: libaston.so: cannot open shared object file: no such file or directory

cp libaston.so /usr/lib
export ld_library_path=$ld_library_path:

/mnt/hgfs/win10share/arm_c/

4.6/dynamicfunclib/testlib

在ubuntu中還有個解決方案三,用ldconfig(僅ubuntu中有,所以不推薦使用)

C 學習筆記 字元函式庫cctype

cctype中的字元函式 函式名稱 返回值isalnum 如果引數是字母數字,即字母或數字,該函式返回true isalpht 如果引數是字母,該函式返回true iscntrl 如果引數是控制字元,該函式返回true isdigit 如果引數是數字 0 9 該函式返回true isgraph 如果...

C 學習筆記(一) cctype函式庫整理

函式名稱 返回值isalnum 若引數為字母或數字,函式返回true isalpha 若引數為字母,函式返回true iscntrl 若引數為控制字元,函式返回true isdigit 若引數為數字,函式返回true isgraph 若引數為除空格外字元,函式返回true islower 若引數為小...

Shell學習(7)建立函式庫

建立庫函式 以獲取ip位址為例 1.在乙個資料夾下建立庫檔案mylib1.sh,該函式獲取網絡卡ip位址 bin bash 獲取傳個函式的引數 網絡卡 的ip getip ip funreply ip funreply是乙個陣列變數 注 在命名時,函式名稱第乙個字元使用 下劃線 通常這樣子表示系統函...