0


0

数回の反復後のBadPtr

C++. Visual Studioでデバッグし、メモリを操作するというより多くの質問があります。

ファイルのリストを分析するプログラムがあり、現在のファイルへのパスは文字列への連結です:「フォルダ」という名前のCStringオブジェクトとファイル名自体(CStringも)。

しかし、144回目の反復の後(数値が重要でないことを確認)、フォルダーが突然BadPtrに変わり、アプリケーションがアクセス違反でクラッシュします。 確認するには、同じディレクトリでCFileFindオブジェクトを作成し、フォルダーと連結する代わりに、finder.GetRoot()と連結します。 同じ話、144回目の反復とクラッシュ。

問題は、この変数のメモリを保護する方法(144回目の反復の前に問題ありません)、または実際にその場所に書き込む関数またはこの問題をデバッグするために何かをトレースする方法です。 サイクル中、フォルダー変数はまったく変更されません。 実際には、いくつかのクラスのプライベートセクション内にあり、サイクルに表示されるすべての関数はこのプライベートセクションにアクセスできません。

コードは次のようになります(いくつかのタイプミスがある可能性がありますが、重要ではないものを切り取ります):

typedef map > metadata;
...
metadata::iterator it=mt.begin();
list< CRect >::iterator it_l;
float i=0;

while(it!=mt.end()){
        if(cur.Load(folder+"\\"+(*it).first+".jpg")){
            it_l=(*it).second.begin();
            i+=1.0;
            while(it_l!=(*it).second.end()){
                cur.buildVector(*it_l);
                cur.printVector(mf,',');
                mf<<",1"<<"\n";
                it_l++;
            }
        }
        it++;
    }

buildVectorは現在のイメージのCRectオブジェクトの機能を収集し、cur.Loadはイメージをロードし、printVectorはベクターをmfという名前のofstreamに出力します。 繰り返しをカウントします。

更新:コードを調べ、cur.Load(…​)以外のすべての行にコメントを付けましたが、584回目の反復でクラッシュしました。 メモリの上書き問題のようです。 Loadのすべての機能を調べました。

    bool Image::Load(CString& path){
     if(!src.IsNull()){
        src.Destroy();
     }
     src.Load(path);
     width=src.GetWidth();
     height=src.GetHeight();
     fillBrightnessMatrix();
     fillGradientMatrices();
     return true;
    }

また、fillBrightnessMatrix()にコメントを付けると、エラーが発生することなくリストの最後まで反復処理が行われることを発見しました。 この関数はメモリで動作する唯一の関数であり、そのコードは次のとおりです。

 void Image::fillBrightnessMatrix(){
    const int nPitch = src.GetPitch();

    const unsigned int nWidth = src.GetWidth();
    const unsigned int nHeight = src.GetHeight();
    BYTE * pxPixel = reinterpret_cast(src.GetBits());


    for(int nY = 0; nY < nHeight; ++nY)
    {
        for(int nX = 0; nX < nWidth; ++nX)
        {
            pxPixel += 3;
            bright[nX][nY]=((*pxPixel+*(pxPixel+1)+*(pxPixel+2))/3.0)/255.0;
        };

        if(nPitch >= 0)
            pxPixel += nPitch - (nWidth*3);
        else
            pxPixel -= ((nWidth*3) + (nPitch*(-1)));
    };
}

brightはコンストラクタに割り当てられ、そのdouble [500] [500]です。 実際、このコードにはメモリリークはありません。何が間違っていますか?

デバッガーは次の行を指します。

bright[nX][nY]=((*pxPixel+*(pxPixel+1)+*(pxPixel+2))/3.0)/255.0;

pxPixelがBadPtrであると言っている>。<いまいましいことを理解していない。

1 Answer


1


私はあなたのコードを見ていませんが、これは誰かが彼らのデータの境界を越えて書いているようなにおいがします。 このようなものをキャッチするには:

  • ループを143回目の反復まで実行します。 (条件付き 143回目にブレークするブレークポイント。)フォルダーを調べて、それが本当に正常であることを確認します。

  • データのアドレスにデータブレークポイントを設定します。 (知りません CString、だからあなたを助けることはできません。)

  • コードを1ステップ実行します。

  • データブレークポイントがヒットしたら、スタックを調べて何がわかるか ハプニング。