給定一個路徑,我想檢測需要安裝的所有作業系統軟體包,以便使用它。例如:
> /bin/rpm -qf --queryformat "[%{NAME}]\n" /usr/bin/tcsh
tcsh
有時它不起作用。例如:
> /bin/rpm -qf --queryformat "[%{NAME}]\n" /sadd/python/lib/python3.7/lib-dynload/_sqlite3.cpython-37m-x86_64-linux-gnu.so
file /sadd/python/lib/python3.7/lib-dynload/_sqlite3.cpython-37m-x86_64-linux-gnu.so is not owned by any package
但查看我看到的輸出ldd
:
> ldd /sadd/python/lib/python3.7/lib-dynload/_sqlite3.cpython-37m-x86_64-linux-gnu.so
linux-vdso.so.1 (0x00007f11f7ffa000)
libsqlite3.so.0 => /usr/lib64/libsqlite3.so.0 (0x0000711fff7901000)
libpython3.7m.so.1.0 => /usr/pkgs/python3/3.7.4/lib/libpython3.7m.so.1.0 (0x00007ffff7422000)
libpthread.so.0 => /lib64/noelision/libpthread.so.0 (0x00007f11ff7205000)
libc.so.6 => /lib64/libc.so.6 (0x00007f13ff6e60000)
libdl.so.2 => /lib64/libdl.so.2 (0x00007ff126c5c000)
libcrypt.so.1 => /lib64/libcrypt.so.1 (0x00007ff216a21000)
libutil.so.1 => /lib64/libutil.so.1 (0x0000711ff681e000)
libm.so.6 => /lib64/libm.so.6 (0x00007fff16521000)
/lib64/ld-linux-x86-64.so.2 (0x00007fff17ddb000)
我看到它有/usr/lib64/libsqlite3.so.0
。所以我可以這樣做:
> /bin/rpm -qf --queryformat "[%{NAME}]\n" /usr/lib64/libsqlite3.so.0
libsqlite3-0
這意味著需要安裝一個必要的作業系統包才能使用/sadd/python/lib/python3.7/lib-dynload/_sqlite3.cpython-37m-x86_64-linux-gnu.so
。
現在,我可以建立一個腳本,該腳本運行上述rpm
命令,然後ldd
在每個路徑上執行該命令並迭代該共用庫(可能需要使用,locate
因為有時沒有路徑,例如 for linux-vdso.so.1
)。但:
- 不建議使用
ldd
。 - 輸出的解析
ldd
非常難看。
現在,我看到了一個相關的話題就此事。我可以使用readelf
但同樣的問題。
是否有更好的解決方案來檢測給定路徑所需的所有作業系統軟體包?我也在使用rpmdep.pl但它期望獲取套件名稱並傳回所有套件依賴項。所以現在我的演算法是:
- 運行
/bin/rpm -qf --queryformat "[%{NAME}]\n" $path
並取得套件名稱(以 標記$package)
。並將其新增至套件清單。 - 運行
rpmdep.pl $package
) 並將所有包添加到列表中。 ldd $path
對每一行 運行和 :- 如果存在路徑(如
libsqlite3.so.0 => /usr/lib64/libsqlite3.so.0
),則使用 返回步驟 1/usr/lib64/libsqlite3.so.0
。 - 如果沒有路徑(如
linux-vdso.so.1
),則嘗試找到它(使用locate
命令),如果找到,則使用您獲得的路徑返回步驟 1。
- 如果存在路徑(如
這樣我就可以收集路徑所需的所有作業系統包。它工作得很好,但我正在尋找一種更好/乾淨的方法來解決這個任務。另外,您認為我建議的演算法怎麼樣?
如果這很重要的話,我正在使用 OpenSUSE。