makeを使用したコンパイル:ライブラリへのリンク

makeを使用したコンパイル:ライブラリへのリンク

私はアプリケーション用のPHPをコンパイルするためにmakeを使用しています。問題は、ldd phpを実行するときに次のようなものがあることです。

libk5crypto.so.3 => /usr/lib/x86_64-linux-gnu/libk5crypto.so.3 (0x00007f5b4e661000)

ただし、libk5crypto.so.3 は libk5crypto.so.3.1 を指す記号です。

私のPHPがlibk5crypto.so.3.1を直接指すようにしたいと思います。

可能ですか?

編集:私が直接コンパイルしたPHPサーバーを含むWebアプリケーションがあります。私はそれを/ etcにインストールしたくないので、私のアプリケーションにインストールするだけです。

私のアプリケーションには、php、fop、mapserverなどを保存するserverというフォルダがあります。

私のPHPフォルダには、すべての依存関係を持つlibフォルダがあります(ldd bin / php)。

アプリケーションをインストールするときは、/etc/ld.so.conf ファイルを変更して PHP サーバーの lib ディレクトリを追加し、ldconfig を実行します。

時々、これらのライブラリは/usr/lib/x86_64-linux-gnuにすでに存在し、PHPはそのフォルダのライブラリの代わりにそのライブラリを使用します。これはほとんど問題ではありませんが、時には/usr/libに同じメジャーバージョンですが、マイナーバージョンが低いライブラリがあります。 PHPは/usr/libからそれを取得しようとしますが、PHPが最新の依存関係にコンパイルされたため、エラーが発生します。

このため、libk5crypto.so.3.1を直接指したいと思います。

アプリケーションを更新するときにPHPを削除し、新しいライブラリをすべて含む最新のPHPを挿入しました。

もう一つのことは、PHPに与えられたディレクトリでライブラリを見つけるように指示しましたが、問題は、コンパイル時にライブラリがどこにあるのかわからないということです。

JigglyNagaの編集者:PHPをコンパイルし、imapやその他の拡張機能をコンパイルします。問題はPHPと拡張にあります。だから、imapの編集が短くなり、皆さんにお知らせします。

root@ubuntu16:~/compilPHP/php-7.2.2/ext/imap# make
/bin/bash /root/compilPHP/php-7.2.2/ext/imap/libtool --mode=compile cc  -I. -I/root/compilPHP/php-7.2.2/ext/imap -DPHP_ATOM_INC -I/root/compilPHP/php-7.2.2/ext/imap/include -I/root/compilPHP/php-7.2.2/ext/imap/main -I/root/compilPHP/php-7.2.2/ext/imap -I/php/include/php -I/php/include/php/main -I/php/include/php/TSRM -I/php/include/php/Zend -I/php/include/php/ext -I/php/include/php/ext/date/lib -I/usr/include/c-client  -DHAVE_CONFIG_H  -g -O2   -c /root/compilPHP/php-7.2.2/ext/imap/php_imap.c -o php_imap.lo
mkdir .libs
cc -I. -I/root/compilPHP/php-7.2.2/ext/imap -DPHP_ATOM_INC -I/root/compilPHP/php-7.2.2/ext/imap/include -I/root/compilPHP/php-7.2.2/ext/imap/main -I/root/compilPHP/php-7.2.2/ext/imap -I/php/include/php -I/php/include/php/main -I/php/include/php/TSRM -I/php/include/php/Zend -I/php/include/php/ext -I/php/include/php/ext/date/lib -I/usr/include/c-client -DHAVE_CONFIG_H -g -O2 -c /root/compilPHP/php-7.2.2/ext/imap/php_imap.c  -fPIC -DPIC -o .libs/php_imap.o
/bin/bash /root/compilPHP/php-7.2.2/ext/imap/libtool --mode=link cc -DPHP_ATOM_INC -I/root/compilPHP/php-7.2.2/ext/imap/include -I/root/compilPHP/php-7.2.2/ext/imap/main -I/root/compilPHP/php-7.2.2/ext/imap -I/php/include/php -I/php/include/php/main -I/php/include/php/TSRM -I/php/include/php/Zend -I/php/include/php/ext -I/php/include/php/ext/date/lib -I/usr/include/c-client  -DHAVE_CONFIG_H  -g -O2   -o imap.la -export-dynamic -avoid-version -prefer-pic -module -rpath /root/compilPHP/php-7.2.2/ext/imap/modules  php_imap.lo -Wl,-rpath,/usr/lib/x86_64-linux-gnu/mit-krb5 -L/usr/lib/x86_64-linux-gnu/mit-krb5 -lc-client -lcrypt -lpam -lgssapi_krb5 -lkrb5 -lk5crypto -lcom_err -lssl -lcrypto
cc -shared  .libs/php_imap.o  -L/usr/lib/x86_64-linux-gnu/mit-krb5 -lc-client -lcrypt -lpam -lgssapi_krb5 -lkrb5 -lk5crypto -lcom_err -lssl -lcrypto  -Wl,-rpath -Wl,/usr/lib/x86_64-linux-gnu/mit-krb5 -Wl,-soname -Wl,imap.so -o .libs/imap.so
creating imap.la
(cd .libs && rm -f imap.la && ln -s ../imap.la imap.la)
/bin/bash /root/compilPHP/php-7.2.2/ext/imap/libtool --mode=install cp ./imap.la /root/compilPHP/php-7.2.2/ext/imap/modules
cp ./.libs/imap.so /root/compilPHP/php-7.2.2/ext/imap/modules/imap.so
cp ./.libs/imap.lai /root/compilPHP/php-7.2.2/ext/imap/modules/imap.la
PATH="$PATH:/sbin" ldconfig -n /root/compilPHP/php-7.2.2/ext/imap/modules

最終編集:うまくいきます。作成前にrpathを変更しました。エクスポート LDFLAGS='-Wl,-rpath,\$${ORIGIN}/../lib' すべての回答に心から感謝します。

答え1

これが可能かどうかはよくわかりませんが、そうしてはいけません。とても悪い考えです。

ライブラリSONAME(libfoo.so.X エントリ) はライブラリで定義されています。フルパスがPHPバイナリにあると思うかもしれませんが、SONAMEだけではそうではありません。これが出力にldd表示される理由ですlibk5crypto.so.3 => /usr/lib/x86_64-linux-gnu/libk5crypto.so.3:name libk5crypto.so.3このシステムでは/usr/lib/x86_64-linux-gnuこのディレクトリのファイルで解決されます。

libk5crypto.so.3ファイルが常にこの場所にあるという保証はありません。パスの一部は、完全なx86_64-linux-gnuマルチアーキテクチャ(Red Hatなど)ではなく、デュアルアーキテクチャのみをサポートするDebianまたはその派生ディストリビューションのいずれかを実行していることを完全に示しています/usr/lib64。これはランタイムダイナミックリンカによって異なり、その設定を使用して(通常)デバッグできるldd場所を見つけることができます。libk5crypto.so.3/etc/ld.so.conf

SONAME非常に特別な意味を持っています。技術全体の詳細に興味があれば、Ulrich Drepperの素晴らしい本を心からお勧めします。文書このトピックに関する限り、そうでない場合は.so.3ファイル名の一部がエンコードされていることを理解する必要があります。互換性APIの一部です。アイデアは、libk5crypto何らかの理由でアップデートするとシステムがインストールされることです。新しいたとえば、libk5crypto.so.3.2シンボリックリンクを移動し、最後に古いライブラリを削除します。つまり、ライブラリが存在する限りABIと互換性、これに対してコンパイルされたすべてのプログラムは、ライブラリが更新されるという理由だけで再コンパイルする必要はありません。

ただし、ライブラリのフルネームをバイナリにエンコードすると、これらの利点は完全になくなり、ライブラリをアップグレードするたびに再コンパイルする必要があります。あなたはほとんど確かにこれをしたくありません。

すべてを言うと、質問は次のとおりです。XYの問題。正確に何を達成しようとしていますか?

答え2

他の答えはまだそれ自体で存在するかもしれませんが、あなたの質問(説明後)が異なるので、これを別の答えとして追加してください。これがシステムだけでなくアプリケーションに付属のライブラリに関するものであれば、状況は比較できません。問題を解決するために必要な作業はほぼ完了しましたが、まだ完了していません。 :-)

問題に対する回避策はLD_LIBRARY_PATH、、rpath変更されたライブラリ転送、複数のコンパイルなど、いくつかあります。それぞれに利点と問題があるので説明します。

  • LD_LIBRARY_PATH

    このパスに従うと、プログラムを実行する前に環境変数を設定できます。バイナリの周りにラッパースクリプトを使用する必要があるかもしれません。つまり、/path/to/my/php直接実行するのではなく、最初に設定して実行するシェルスクリプトを実行する必要があります。LD_LIBRARY_PATH/path/to/my/php

    このアプローチの欠点は、わずかに脆弱であることです。

    • LD_LIBRARY_PATHライブラリ検索パスの前に追加されますが、置き換えられません。つまり、問題のライブラリがシステム全体にインストールされているが、何らかの理由で提供されたライブラリをロードできない場合、動的リンカーはシステム提供のライブラリに依存します。
    • シェルスクリプトを呼び出す必要があるという要件は、追加の分岐/実行呼び出しが必要であることを意味し、これが問題を引き起こす可能性があります。これはシェルスクリプトでコマンドを使用してある程度緩和することができますがexec(スクリプトがphpバイナリに置き換えられ、phpプログラムが親プログラムの正しいサブルーチンになるように)まだ汚れています。

    一方、リポジトリの場所にある程度の柔軟性があります(たとえば、システム提供のライブラリが場合によっては十分であれば、ディレクトリから削除してもかまいませんLD_LIBRARY_PATH)。

  • rpath

    ここでのアイデアは、gcc -Wl,-rpath,'/path/to/library'ライブラリを見つける場所をコンパイラに正確に伝えることです。これはコンパイル時にプログラムにハードコードされており、動的リンカーはシステム提供のバージョンをrpath含むユーザーが提供するライブラリの外部バージョンを絶対に無視します。これにより、上記の混乱を避けることができますが、LD_LIBRARY_PATHファイルシステム内のアイテムを移動する必要がある場合は、すべてを再コンパイルする必要があるという欠点があります。

    これはまた、ユーザーが何かが別々にインストールされることを期待している場合は幸運ではないことを意味します。彼らはそれを好きではないかもしれません。

どちらの方法もld.soマニュアルページに文書化されています。

  • 変更されたライブラリの配送

    ここでのアイデアは、に接続しようとするのではなく、libk5crypto.so.3に接続しようとすることですlibmycorp-k5crypto.so.3。この場合、動的リンカーはシステムが提供するものを得る可能性はまったくありませんlibk5crypto.so.3。ここでの利点は、一度インストールすると非常にシンプルでエレガントです。欠点は、人々が変更を適用したかどうか疑問に思うかもしれません(そしてパッチを要求した場合)、それを得るためにビルドシステムをlibk5crypto詳しく調べる必要があるということです。libk5crypto.so実際にlibmycorp-k5crypto.soライブラリを作成します。長期的に見ても良くないかもしれませんので、この道を行く前に注意してください。

  • 複数回コンパイル

    システム全体で提供されるライブラリを提供する代わりにできるサポートされている各ディストリビューションでアプリケーションをコンパイルしてライブラリを提供するのではなく、各ディストリビューションのパッケージを提供するだけです。絵packagecloud.ioこれをより簡単にします。システムには指定された名前のライブラリが1つしかないため、選択できるライブラリは1つだけで、誤ったライブラリを選択することは不可能です。欠点は、テストする必要がある項目の範囲が大きいため、リリース時により多くの作業を行う必要があることです(そして良いテストスイートをお勧めします)。

    このアプローチの利点は、他の方法よりも少ない量を提供するため、サポートする必要が少なく、サポートされなくなった以前のバージョンをlibk5crypto.so使用するディストリビューションユーザーに最初に更新する必要があることを知らせることができることです。

関連情報