2

昨日、GCC でコンパイルされた DLL を Cygwin で使用しているときに、やや厄介なクラッシュが発生しました。基本的に、デバッガーで実行するとすぐに、RtlFreeHeap() が割り当てられていないアドレスを受け取ることによって引き起こされるデバッグ トラップに陥る可能性があります。

これは、Cygwin 上の GCC 3.4 の既知のバグです。この状況は、libstdc++ ライブラリに空の文字列に対する「巧妙な」最適化が含まれているために発生します。詳細は省略しますが (この投稿全体の参照を参照)、別の DLL に「属する」 std::string オブジェクトに対して 1 つの DLL にメモリを割り当てると、1 つのヒープに解放するチャンクを与えることになります。別のヒープ。したがって、RtlFreeHeap() の SIGTRAPです。

DLL の境界を越えて例外がスローされた場合に報告されるその他の問題があります。

これにより、プロジェクトが DLL と STL に基づいているとすぐに、Windows 上の GCC 3.4 は受け入れられないソリューションになります。このオプションを通過するためのオプションがいくつかありますが、その多くは非常に時間がかかり、面倒です。

  • libstdc++にパッチを当てるか、 --enable-fully-dynamic-string構成オプションを使用して再構築できます
  • 代わりに静的ライブラリを使用できるため、リンク時間が長くなります

私が使用している他のツールが原因で、(まだ) 別のコンパイラに切り替えることもできません。一部の GCC 関係者からは、「ほとんど報告されていないので、問題にならない可能性が高い」というコメントが寄せられており、それがさらに私を悩ませています。

これについて何かニュースを持っている人はいますか?GNU Radio bug trackerに関する 1 つのコメントを除いて、これが修正されたという明確な発表を見つけることができません (バグはまだ「割り当て済み」としてマークされています) 。

ありがとう!

4

1 に答える 1

1

あなたが直面している一般的な問題は、C++ が実際にはコンポーネント言語として意図されていないということです。完全なスタンドアロン アプリケーションを作成するために使用するように設計されています。共有ライブラリなどのメカニズムは、ベンダーが独自に作成したものです。次の例を考えてみてください。C++ オブジェクトを返す C++ コンポーネントを作成したとします。C++ コンポーネントは、C++ 呼び出し元によって使用されることをどのように認識していますか? また、呼び出し元が C++ アプリケーションの場合、ライブラリを直接使用しないのはなぜでしょうか?

もちろん、上記の情報は実際には役に立ちません。

代わりに、いくつかのルールに従うように共有ライブラリ/DLL を作成します。

  1. コンポーネントによって作成されたオブジェクトも、同じコンポーネントによって破棄されます。
  2. 作成されたすべてのオブジェクトが破棄されると、コンポーネントを安全にアンロードできます。

これらのルールを確実にするために、コンポーネントに追加の API を作成する必要がある場合がありますが、これらのルールに従うことで、説明されているような問題が発生しないことが保証されます。

于 2009-02-06T21:17:20.357 に答える