linux下檢視動態庫中的符號
阿新 • • 發佈:2019-01-10
功能
列出.o .a .so中的符號資訊,包括諸如符號的值,符號型別及符號名稱等。所謂符號,通常指定義出的函式,全域性變數等等。
使用
nm [option(s)] [file(s)]
有用的options:
- -A 在每個符號資訊的前面列印所在物件檔名稱;
- -C 輸出demangle過了的符號名稱;
- -D 列印動態符號;
- -l 使用物件檔案中的除錯資訊打印出所在原始檔及行號;
- -n 按照地址/符號值來排序;
- -u 打印出那些未定義的符號;
常見的符號型別:
- A 該符號的值在今後的連結中將不再改變;
- B 該符號放在BSS段中,通常是那些未初始化的全域性變數;
- D 該符號放在普通的資料段中,通常是那些已經初始化的全域性變數;
- T 該符號放在程式碼段中,通常是那些全域性非靜態函式;
- U 該符號未定義過,需要自其他物件檔案中連結進來;
- W 未明確指定的弱連結符號;同連結的其他物件檔案中有它的定義就用上,否則就用一個系統特別指定的預設值。
注意幾點:
- -C 總是適用於c++編譯出來的物件檔案。還記得c++中有過載麼?為了區分過載函式,c++編譯器會將函式返回值/引數等資訊附加到函式名稱中去形成一個mangle過的符號,那用這個選項列出符號的時候,做一個逆操作,輸出那些原始的、我們可理解的符號名稱。
- 使用 -l 時,必須保證你的物件檔案中帶有符號調式資訊,這一般要求你在編譯的時候指定一個 -g 選項,見 Linux:Gcc。
- 使用nm前,最好先用
舉例
更詳細的內容見man page。這裡舉例說明:
- nm -u hello.o
- 顯示hello.o 中的未定義符號,需要和其他物件檔案進行連結.
- nm -A /usr/lib/* 2>/dev/null | grep "T memset"
在 /usr/lib/ 目錄下找出哪個庫檔案定義了memset函式.