I'm debugging an issue on OS X that only occurs when the application is started from the dock. It does not happen when the app is started from the command line. What is the difference between the two scenarios? The code I'm working with is a c++ based bundled plug-in being loaded in a third party app. I've attached to the process with GDB in both scenarios and the only difference I can see is that a couple of extra dylibs are loaded in the process when running from the command line and that the base address of my library is slightly different in the two scenarios. I've tried changing my linkage to -prebind and/or -bind_at_load to no avail.
4 に答える
重要な違いの 1 つは、最初の作業ディレクトリがケースごとに異なることです。アプリケーションは、作業ディレクトリについていかなる想定もすべきではありません。仮に想定した場合、興味深い方法で壊れます。
Dock アイコンから起動されたアプリケーションは、使用しているシェルで設定されている可能性がある同じ環境変数を取得しません。環境から何かを拾うことに頼っている場合は、別のアプローチを探す必要があります。PATH、HOME、LOGNAME などのいくつかの環境変数を取得します。ただし、HOSTTYPE、LANG、OSTYPE などを探している場合、それらは存在しません。
同様の状況で、アプリ バンドルから実行するとクラッシュします。1 つの可能性は、既に割り当てを解除したメモリを使用しているということです。free()
たとえば、またはの後にポインタまたはクラスのフィールドを使用しますdelete
。
アプリ バンドルはfree/delete
、割り当て解除されたメモリをゼロにする/変更する別の実装と動的にリンクされているようです。
この種のバグは、他のプラットフォーム/コンパイラ (例: Linux/gcc、Windows/Visual Studio、コマンド ラインからの macOS/clang) を使用すると表示されず、プログラムがアプリ バンドル (Finder/dock からの macOS/clang) から実行された場合にのみ表示されます。 )。
この場合、私の問題は、共有ライブラリがロードされる順序の違いによって引き起こされました。アプリケーションが使用するサードパーティ ライブラリの 1 つは、拡張ライブラリをグローバル名前空間にロードします。同じライブラリの別のバージョンとのシンボルの競合がありました。拡張機能ライブラリがグローバル プールに読み込まれる順序は、アプリがドキュメントから起動されたか、コマンド ラインから起動されたかによって異なります。