私たちの計算クラスターは、古いカーネル(2.6.18)と、もちろん古いライブラリとバイナリを備えた、非常に古いバージョンのCentOSを実行します。すべてを更新するには、すべてのノードで多くの作業が必要になるため、これはオプションではありません。
C++11
を必要とするプログラムをコンパイルして使用しようとしています。そのため、gcc
(またはclang
)の新しいバージョンを使用しています。私はシステムをいじりたくないので、ローカルディレクトリツリーの非rootユーザーとしてこれを実行したいと思います。
問題は、gcc
には、マシンに存在するものよりも新しいglibc
が必要であることです。したがって、おそらく here で説明されているように、ローカルのlib/
ツリーでglibc
の別の新しいバージョンを維持する必要があります。
私が失われた場所は、ローカルライブラリのパスをすべての必要なバイナリ、つまりgcc
、g++
などに「ハードコード」する方法ですか。 LD_LIBRARY_PATHをローカルのlib/
ツリーに設定すると、すべてのシステムバイナリ(ELF file OS ABI invalid
)が機能しなくなります。これは、新しいlibm.so
/libc.so
を使用したくないためです。編集済み。
まとめると、古いシステムと並行して、新しいローカルの開発スタック(glibc
、gcc
などを含む)をrootとしていじらずに維持する適切な方法は何ですか?
副次的な質問として:LD_LIBRARY_PATHの設定は、glibc
を分離する場合、SE全体で解決策として投稿されます。私にとって、システムバイナリ(ls
など)を実行しようとすると、上記のエラーが発生します。どうして?私は何か間違ったことをしましたか、これは意図された動作ですか?
基本的に3つのオプションがあります。
ライブラリを囲むラッパーを使用すると、LD_LIBRARY_PATH
適切に実行してから、目的のライブラリを実行します。
#!/bin/sh
export LD_LIBRARY_PATH="path/goes/here"
exec "$@"
とのリンク -rpath
(-Wl,rpath
)は、ダイナミックリンカーの検索パスをバイナリに追加します( SO answer も参照してください-ラッパーについても言及しています)。
これを読むのは好きではありません:更新yourクラスター(「your」に重点を置いていることに注意してください)。それはいつか行われなければならないので、なぜ今日ではないでしょう。 「オプションではない」は、ほとんどの場合少し強いです。他のユーザーもおそらく同じ問題を抱えています。
問題のある古いバイナリについて-バイナリには、優先される動的リンカーが埋め込まれています。そして、古いダイナミックリンカは新しいABIを理解しません。次のようにバイナリを呼び出してみてください:path/to/your/ld-linux-<Arch>.so binary
。
GCCのビルド:GCCのビルド環境でいつでもCFLAGS
をエクスポートしてみることができますが、確実に伝搬されます。さまざまなディストリビューションのビルドスクリプトを使用すると、いくつかの手掛かりが得られる場合があります(たとえば、openSUSEの場合は 。specファイル の1880行目を見てください)。