私が遭遇した問題は、単純化された FreeGLUT C++ アプリケーション内でのスレッド化のおそらく誤用によって発生します。
をエレガントに終了するglutMainLoop()
ことはできないので、私はいくつかの作業を行うことに依存していますが、これはプログラムの機能glutLeaveMainLoop()
に制御を戻すものではありません。GL 呼び出しの前に、ヒープ上に作成されたオブジェクト インスタンスへの関数にmain
設定されるグローバル ポインターがあります。コールバックmain
を使用しないと、このインスタンスでオペレーターを呼び出す人はいませんが、呼び出しの後にそのような操作を配置しました(無益であるため、コメントしました)。atexit
delete
glutMainLoop
これが私がやっていることの疑似コードです(フィルタリングするには長すぎるため、実際のコードは投稿しません):
CWorld* g_world;
AtExit()
{
delete g_world;
}
void main()
{
atexit(AtExit);
// create an instance of an object that creates a thread in its constructor
// via the new operator and joins this thread in its destructor
// calling the delete operator on that pointer to the thread instance
CWidget thisObjectCreatesATinyThread;
g_world = new CWorld();
...
glutMainLoop();
// delete g_world;
}
メイン関数には、コンストラクターで作成されたスレッドを介して何らかの作業を行うウィジェット インスタンスも含まれていることに注意してください。このスレッドはそのデストラクタに結合され、メモリは を介して割り当て解除されますdelete
。
間違った動作: コールバックを設定しないと、オブジェクトatexit
のデストラクタが呼び出されないため、リソース リークが発生します。CWorld
このコールバックを設定すると、関数が 1 回しか呼び出されないdelete
にもかかわらず、何らかの理由でオペレーターが 2 回呼び出されます。AtExit
この奇妙な動作の原因を探す場所はどこですか?
CWidget のインスタンス化を無効にしても、依然として独特の動作が得られます。