x86 Solaris 10 で OpenSSL 0.9.8 が Core dumped

相当まいった。
/usr/sfw/libにも/usr/local/libにも存在する状況で、/path/to/some/other/dir/openssl にまた別なバージョンを、しかもLD無視してリンクするように(rpathだよ)小細工するようなOpenSSLを作ってたから、本当に気づくのが遅かった。
悪いのは俺じゃなかった。

さて、OpenSSL 0.9.8以降を、x86 Solaris 10でコンパイルすると、出来上がったバイナリは以下のようになる。

# /path/to/openssl/bin/openssl
Segmentation Fault (core dumped)

こうなる原因が俺かと思ったらそうじゃなくて、OpenSSLのソースに同梱されている PROBLEMS ファイルに書いてあった。

- There is a subtle Solaris x86-specific gcc run-time environment bug, which
  "falls between" OpenSSL [0.9.8 and later], Solaris ld and GCC. The bug
  manifests itself as Segmentation Fault upon early application start-up.
  The problem can be worked around by patching the environment according to
  http://www.openssl.org/~appro/values.c.

以下俺訳(無保証。正しくは原文を。)
--------
Solaris x86gccランタイム環境に微妙なバグがあってOpenSSLの0.9.8以降とSolarisのldとgccの間でおこる。アプリケーションの起動時にセグメンテーションフォルトになっちゃうんだよね。↓のパッチでなおるよ。ワークアラウンドだぜ。
http://www.openssl.org/~appro/values.c
--------
んで、このパッチ?にしてはCファイルじゃん?あれれ?
中身を見たら

# This is Solaris x86 specific GCC run-time environment patch, which
# makes it possible to reliably deploy .init snippets. Trouble is that
# Solaris linker erroneously pads .init segment with zeros [instead of
# nops], which is bound to SEGV early upon program start-up. This bug
# was recognized by GCC team [it is mentioned in source code], but
# workaround apparently and obviously erroneously slipped away in some
# newer GCC release. This patch compensates for this mishap by dropping
# modified values-X*.o into GCC installation tree. Object modules in
# question are normally provided by Sun and linked prior crtbegin.o.
# Modified versions are additionally crafted with custom .init segment,
# which does some magic:-)

こんなコメントが書いてある。
また俺訳。
--------
これはSolaris x86版のGCCランタイム環境向けパッチだよ。たぶんちゃんとした . init の断片の配布版。 (.initって何?俺は知らん)。Solarisのリンカが nops じゃなくてゼロで . init セグメントに追加するもんだから、プログラムの起動時にSEGV(俺注: Segmentation Violationな)が出ちゃうんだよ。GCCチームも知ってる話(ソースに書いてあるんだよね)なんだけど、ワークアラウンドが新しいGCCのリリースからさらっと漏れてんだよ!
だから、このパッチはGCCのインストールツリーにvalues-X*.oがないことで起きるおかしな話を補間します。このあたりのオブジェクトモジュールは普通Sunから提供されて、crtbegin.oにリンクするんだよね。この修正版は追加でカスタムな . initセグメントを作りこむよ。これって魔法?
--------

というわけで、長くなったのでここまで。続きはあとで書く。

      • -

というわけで、あとでの今日は9/22なんだけど、面倒だからこのエントリはここまで!!!

# ksh -f values.c gcc

こんだけやってコンパイルしたら終了だからさ。64bitで動かしてたら

# ksh -f values.c gcc -m64

これもな。以上!!