Mengapa sistem Unix / Linux tidak menelusuri direktori sampai mereka menemukan versi yang diperlukan dari perpustakaan yang ditautkan?

17

Saya memiliki executable biner bernama "alpha" yang membutuhkan pustaka tertaut (libz.so.1.2.7) yang ditempatkan di /home/username/myproduct/lib/libz.so.1.2.7

Saya mengekspor hal yang sama ke instance terminal saya sebelum menelurkan binary yang dapat dieksekusi dengan mengeksekusi perintah berikut.

export LD_LIBRARY_PATH=/home/username/myproduct/lib/:$LD_LIBRARY_PATH

Sekarang, ketika saya menelurkan aplikasi lain "bravo" yang membutuhkan pustaka yang sama tetapi dari versi yang berbeda, yaitu (libz.so.1.2.8) yang tersedia /lib/x86_64-linux-gnu/libz.so.1.2.8, sistem melempar kesalahan berikut.

version `ZLIB_1.2.3.3' not found (required by /usr/lib/x86_64-linux-gnu/libxml2.so.2)

Jika saya menghapus LD_LIBRARY_PATH, "bravo" mulai baik-baik saja. Saya mengerti bahwa perilaku di atas karena LD_LIBRARY_PATHlebih diutamakan daripada jalur direktori didefinisikan dalam /etc/ld.so.confsambil mencari perpustakaan terkait dan akibatnya kesalahan di atas terjadi. Saya hanya ingin tahu mengapa pengembang UNIX / LINUX tidak merancang OS untuk mencari perpustakaan yang terhubung di direktori lain sesuai dengan hierarki jika instance perpustakaan pertama adalah versi yang berbeda.

Sederhananya, sistem UNIX / LINUX melintasi seperangkat direktori sampai menemukan perpustakaan yang diperlukan. Tetapi mengapa ia tidak melakukan hal yang sama sampai ia menemukan versi yang diharapkan daripada menerima contoh pertama perpustakaan terlepas dari versinya?

daedalus_hamlet
sumber
Saya tidak yakin, tapi saya kira untuk keamanan. Saya pribadi lebih suka tidak perlu khawatir tentang sym-link di mana saja di komputer saya
Joe
@ Jo. Banyak perpustakaan yang memiliki symlink yang menunjuk ke sana. libz.so.1adalah symlink kelibz.so.1.2.8
Nasir Riley

Jawaban:

28

Tetapi mengapa ia tidak melakukan hal yang sama sampai ia menemukan versi yang diharapkan daripada menerima contoh pertama perpustakaan terlepas dari versinya?

Itu, sejauh yang disadari. zlib.so.1.2.7dan zlib.so.1.2.8keduanya memiliki nama samaran zlib.so.1, jadi biner Anda alphadan bravomereka mengatakan mereka membutuhkannya zlib.so.1. Loader dinamis memuat perpustakaan yang cocok pertama yang ditemukannya; tidak tahu bahwa versi 1.2.8 menyediakan simbol tambahan yang bravodibutuhkan. (Inilah sebabnya mengapa distribusi bersusah payah untuk menentukan informasi dependensi tambahan, seperti zlib1g (>= 1.2.8)untuk bravo.)

Anda mungkin berpikir ini seharusnya mudah untuk diperbaiki, tetapi tidak, paling tidak karena biner dan perpustakaan mendaftar simbol yang mereka butuhkan secara terpisah dari perpustakaan yang mereka butuhkan, sehingga loader tidak dapat memeriksa bahwa perpustakaan yang diberikan menyediakan semua simbol yang dibutuhkan dari itu. Simbol dapat disediakan dalam berbagai cara, dan memperkenalkan tautan antara simbol dan perpustakaan yang menyediakannya dapat merusak biner yang ada. Ada juga kesenangan tambahan dari penempatan simbol untuk mempersulit hal-hal (dan membuat pengembang yang peka terhadap keamanan merobek rambut mereka).

Beberapa perpustakaan menyediakan informasi versi yang akhirnya disimpan .gnu.version_r, dengan tautan ke perpustakaan yang menyediakan, yang akan membantu di sini, tetapi libzbukan salah satunya.

(Diberikan sonames, saya berharap alphabiner Anda bekerja dengan baik zlib.so.1.2.8.)

Stephen Kitt
sumber
Dan orang harus mencatat juga bahwa versi perpustakaan gaya GNU berbeda dari versi semantik (-ish) dengan mana kita paling terbiasa. Karena mereka memiliki nomor "saat ini" yang sama, 1, zlib.so.1.2.8 tidak boleh menyediakan fitur apa pun yang zlib.so.1.2.7 tidak miliki, maka itu seharusnya tidak menjadi masalah (dari perspektif ABI) yang mana ditemukan. Bahwa itu penting harus dianggap cacat.
John Bollinger
4
@ John no, satu-satunya jaminan adalah bahwa perpustakaan dengan soname yang sama kompatibel dengan mundur; perpustakaan yang lebih baru dapat menambahkan fitur, mereka tidak dapat menghapus atau mengubah apa pun dengan cara yang tidak kompatibel ke belakang. Dengan kata lain, biner yang dibangun melawan zlib 1.2.7 akan bekerja dengan itu atau zlib 1 yang lebih baru; tetapi biner yang dibangun melawan zlib 1.2.8 tidak akan selalu berfungsi dengan zlib 1. (Dan versi semantik memungkinkan itu, tetapi penanganan soname bukan versi semantik.)
Stephen Kitt
1
Saya berbicara secara khusus tentang konvensi GNU, seperti yang saya katakan, dan saya kira tentang libtool pada khususnya. Tidak setiap proyek mengikuti konvensi itu, jadi mungkin terlalu kuat untuk menyebut zlib cacat, tetapi di sisi lain, bahkan interpretasi versi semantik dari nomor versi perpustakaan yang terlibat akan sampai pada kesimpulan yang sama. Kompatibilitas ke depan (biner) dalam kasus-kasus semacam itu bukanlah janji yang melekat dalam soname, tetapi itu adalah harapan yang masuk akal dalam kasus ini.
John Bollinger
1
Ya, saya sangat memahami hubungan antara angka CRA dan SOVERSION, yang kembali ke titik awal saya: situasi yang dijelaskan oleh OP tampaknya tidak konsisten dengan penggunaan skema CRA yang benar . Menghindari masalah seperti OP adalah salah satu tujuan utama dari skema itu. Jika zlib menambahkan antarmuka biner baru (versi a), maka nomor C-nya harus ditambah. Bahwa benjolan seperti itu dapat menyebabkan benjolan juga menjadi nomor dua.
John Bollinger
2
@John benar, saya curiga kita dalam perjanjian kekerasan dan bahwa saya salah mengerti maksud Anda. toh zlibtidak digunakan libtool, kecuali di Darwin ar;-).
Stephen Kitt