私はBDS 2006 Turbo C++を長い間使用していますが、より大きなプロジェクト ( CAD/CAM、3D gfx エンジン、および天文計算) の一部で例外がスローされることがあります (たとえば、24 時間 365 日のヘビーデューティー使用で 3 ~ 12 か月に 1 回)。 )。広範なデバッグの後、私はこれを見つけました:
//code1:
struct _s { int i; } // any struct
_s *s=new _s[1024]; // dynamic allocation
delete[] s; // free up memory
このコードは通常、テンプレート内に_s
あり、クラスにもなる可能性があるため、delete[]
このコードは適切に機能するはずですが、delete[]
構造体では適切に機能しません (クラスは問題ないように見えます)。例外はスローされず、メモリは解放されますが、何らかの形でメモリ マネージャーの割り当てテーブルが破損し、その後、新しい割り当てが間違っている可能性があります (新しい割り当ては、既に割り当てられている領域または割り当てられていない領域と重複する割り当てを作成する可能性があるため、時折例外が発生します)
_s
空のデストラクタを追加すると、突然すべてが正常に見えることがわかりました
struct _s { int i; ~_s(){}; }
さて、奇妙な部分が来ます。AnsiString
これをプロジェクトに更新した後、クラスにも不適切な再割り当てがあることがわかりました。例えば:
//code2:
int i;
_s *dat=new _s[1024];
AnsiString txt="";
// setting of dat
for (i=0;i<1024;i++) txt+="bla bla bla\r\n";
// usage of dat
delete[] dat;
このコードdat
にはいくつかの有用なデータが含まれており、後でtxt
行を追加して作成された文字列があるため、txt
数回再割り当てする必要があり、dat
データが上書きされることがありますtxt
(重複していなくても、AnsiString
再割り当てに必要な一時txt
が重複していると思いますdat
)
だから私の質問は:
- code1、code2 で何か間違っていますか?
AnsiString
(再) 割り当てエラーを回避する方法はありますか? (でもまだ使ってる)AnsiString
大規模なデバッグの後 (質問 2 を投稿した後) 、問題を引き起こさないことがわかりました。それらは使用中にのみ発生します。本当の問題は、おそらくOpenGLクライアント間の切り替えにあります。ベクター グラフィックスのプレビューを表示する [開く/保存] ダイアログがあります。これらのVCLサブウィンドウでOpenGLの使用を無効にすると、メモリ管理エラーは完全になくなります。私は何が問題なのかはわかりません ( MFC/VCLウィンドウ間の非互換性、またはコンテキストの切り替えで間違いを犯した可能性が高いため、さらに調査します)。懸念されるOpenGLウィンドウは次のとおりです。AnsiString
- メインVCLフォーム +クライアント領域内のOpenGL
Canvas
- メインMFCの[開く/保存] ダイアログの子 + ドッキングされたプレビューVCLフォーム +クライアント領域内のOpenGL
Canvas
PS
new/delete/delete[]
これらのエラーは、割り当てられたサイズではなく、使用回数に依存します- code1 と code2 の両方のエラーが繰り返されます (たとえば、複雑な ini ファイルをロードするパーサーがあり、ini が変更されていない場合、同じ行でエラーが発生します)。
- これらのエラーは、 と テンプレートを内部動的割り当てと組み合わせて使用する大きなプロジェクト (プレーン ソース コード > 1MB) でのみ検出されます
AnsiString
が、より単純なプロジェクトでも発生する可能性がありますが、まれにしか発生しないため、見逃してしまいます。 - 感染したプロジェクトの仕様:
- win32 noinstall スタンドアロン ( Win7sp1 x64を使用しますが、XPsp3 x32では同じように動作します)
- GDIまたはOpenGl/GLSLを使用する場合は測定しません
- デバイス ドライバーDLLを使用するかどうかを測定しません。
- OCXなし、または非標準のVCLコンポーネント
- DirectXなし
- 1 バイト アラインされたコンパイル/リンク
- RTL 、パッケージ、またはフレームワークを使用しない(スタンドアロン)
悪い英語/文法で申し訳ありません...助け/結論/提案をいただければ幸いです。