為什麼有“/lib”和“/lib64”而只有“/bin”?

為什麼有“/lib”和“/lib64”而只有“/bin”?

在我的筆記型電腦中:

$ cat /etc/issue  
Ubuntu 18.04 LTS \n \l

x86庫和有兩個不同的資料夾x86_64

~$ ls -1 /  
bin
lib
lib64
sbin
...

為什麼二進位檔案只存在一個目錄?

PS 我也對 Android 感興趣,但我希望答案應該是相同的。

答案1

首先,為什麼有單獨的/lib/lib64

檔案系統層次結構標準 提到分離/lib/lib64存在是因為:

10.1.在支援多種需要單獨庫的二進位格式的系統上,/lib 目錄可能有一種或多種變體。 (...) 這通常用於支援多種二進位格式但需要同名函式庫的系統上的 64 位元或 32 位元支援。在這種情況下,/lib32 和 /lib64 可能是函式庫目錄,而 /lib 是其中之一的符號連結。

例如,在我的 Slackware 14.2 上, 分別有 32 位元和 64 位元函式庫的目錄,儘管它 /lib不像FHS 程式碼片段所建議的那樣是符號連結:/lib64/lib

$ ls -l /lib/libc.so.6
lrwxrwxrwx 1 root root 12 Aug 11  2016 /lib/libc.so.6 -> libc-2.23.so
$ ls -l /lib64/libc.so.6
lrwxrwxrwx 1 root root 12 Aug 11  2016 /lib64/libc.so.6 -> libc-2.23.so

和中有兩個libc.so.6庫。/lib/lib64

每個動態構建 ELF二進位 包含解釋器的硬編碼路徑,在本例中為 /lib/ld-linux.so.2/lib64/ld-linux-x86-64.so.2

$ file main
main: ELF 32-bit LSB executable, Intel 80386, version 1 (SYSV), dynamically linked, interpreter /lib/ld-linux.so.2, not stripped
$ readelf  -a main  | grep 'Requesting program interpreter'
      [Requesting program interpreter: /lib/ld-linux.so.2]

$ file ./main64
./main64: ELF 64-bit LSB executable, x86-64, version 1 (SYSV), dynamically linked, interpreter /lib64/ld-linux-x86-64.so.2, not stripped
$ readelf  -a main64  | grep 'Requesting program interpreter'
      [Requesting program interpreter: /lib64/ld-linux-x86-64.so.2]

解釋器的工作是載入必要的共享庫。您可以詢問 GNU 解釋器它將加載哪些庫,甚至無需使用LD_TRACE_LOADED_OBJECTS=1ldd包裝器運行二進位:

$ LD_TRACE_LOADED_OBJECTS=1 ./main
        linux-gate.so.1 (0xf77a9000)
        libc.so.6 => /lib/libc.so.6 (0xf760e000)
        /lib/ld-linux.so.2 (0xf77aa000)
$ LD_TRACE_LOADED_OBJECTS=1 ./main64
        linux-vdso.so.1 (0x00007ffd535b3000)
        libc.so.6 => /lib64/libc.so.6 (0x00007f56830b3000)
        /lib64/ld-linux-x86-64.so.2 (0x00007f568347c000)

正如您所看到的,給定的解釋器確切地知道在哪裡查找庫 - 32 位元版本在 中查找庫/lib,64 位元版本在/lib64.

FHS 標準規定如下/bin

/bin 包含系統管理員和使用者都可以使用的命令,但在沒有安裝其他檔案系統時(例如在單一使用者模式下)需要這些命令。它也可能包含由腳本間接使用的命令。

IMO 之所以沒有單獨的文件/bin/bin64是因為如果我們在這兩個目錄中都有同名的文件,我們就無法間接調用其中一個,因為我們必須將/binor/bin64放在第一個目錄中 $PATH

但是,請注意,上面只是約定 - Linux 核心並不真正關心您是否有單獨的/bin/bin64。如果您需要它們,您可以建立它們並相應地設定您的系統。

你還提到了Android - 請注意,除了運行修改後的Linux核心之外,它與Ubuntu等GNU系統無關- 沒有glibc,沒有bash(默認情況下,你當然可以手動編譯和部署它),還有目錄結構是完全不同的。

答案2

原因是 lib/lib64 目錄可能包含恰好具有相同的文件姓名因為這些是與不同程式共享的庫。將它們放在單獨的目錄中可以解決衝突。 (通常......)沒有充分的理由在同一 32/64 位元系統上分發同名的可執行文件,但由於可能存在混合的可執行文件,因此必須提供共享庫。

相關內容