0

これで、問題なくビルドして実行できるアプリケーションができました。リンク先の20以上の静的および動的ライブラリの束でいくつかのコンパイラ設定をいじり始めましたが、特定の時点で開始時にアプリが一貫してクラッシュします。

ビルド システムの mod を元に戻しましたが、アプリは再び問題なく動作します。(ただし、実際に行った変更をメモするのを忘れていました...)

純粋に問題として、私はまだ悪いバイナリ (デバッグ モードでビルド) のコピーを持っているので、物事を台無しにするために正確に行ったことをリバース エンジニアリングしてみたいと思います。:-)

デバッガーをアタッチすると.so、関数呼び出しを介して、メイン アプリがコールバックとして使用するための関数ポインターをメイン アプリに渡していることがわかります。

呼び出し元のフレーム ( 内.so) では、関数ポインターは 1 つの値を持ちます。(メイン アプリの) 呼び出し先のフレームでは、関数ポインターは魔法のように異なる値を持ちます。

メイン アプリが格納された関数ポインターを呼び出そうとすると、プログラムが segfault (マッパー エラー) でクラッシュします。関数ポインターには、おそらく間違っている 2 番目の値がまだあるようです。

これを区別する方法について何か提案はありますか?


更新:詳細はリクエストに応じて。

クラッシュは次の場所にあります。

 0xfffffffffffeac58 ???????? ()
 0x000000000063a040 app_exec_callbacks()
 0xfffffd7ffea14514 dynlib_stuff ()
 0x000000000063a15e other_app_stuff () 
 0x00000000004d10a3 app_stuff ()
 0x0000000000499f20 main ()

これに先立って、関数はへの呼び出しを介してアプリにdynlib_do_setup()関数ポインタ (の) を渡します。dynlib_callback_handler()app_register_callback()

デバッガーを使用するとdynlib_do_setup()、関数内でポインターの値が0xfffffd7ffea13fa0. パラメーターの関数本体内でapp_register_callback()突然の値を持つ0xfffffffffffeac58

したがって、 のガベージ値は0xfffffffffffeac58アプリのコールバック テーブルに格納されます。驚くことではありませんが、上記のスタック トレースでわかるように、そのコールバック アドレスが呼び出されるとアプリがクラッシュします。

繰り返しますが、純粋に教育的関心の問題として、この魔法の腐敗はどのように/なぜ起こるのでしょうか? ビルドシステムの変更を元に戻すと、これが突然修正されたのはなぜですか?

ありがとうございました

4

2 に答える 2

0

答えが見つかりました:

特定の最適化フラグの組み合わせの結果としてのコンパイラのバグ。既知ですが、過去3年間は修正されていません。:(

于 2012-08-13T17:37:27.073 に答える
0

何が起こっているのかをすでに理解していたようです。おそらく、リンク中に (おそらく再配置に関連して?) 何か奇妙なことが起こり、main() が関数ポインターの正しいアドレスを持たなくなった可能性があります。

于 2012-07-25T15:35:17.997 に答える