1
#include <iostream>

using namespace std;

struct A
{
    int a, b;
};

struct B
{
    int a;
};

int main()
{
    A * pa = (A *)malloc(sizeof(B));
    int c = 5;
    pa -> a = 3;
    cout << pa -> a << endl;
    pa -> b = 0;
    cout << pa -> b << endl;
    cout << c << endl;
    return 0;
}

このコードを VC++ 2012 で実行しました。エラー メッセージは生成されません。

pa -> b はメモリーブロックのアウトバウンドにアクセスすると思います。ヒープの破損が発生するはずです! しかし、実際には、デバッグ モードとリリース モードの両方で何も起こりませんでした。

しかし、 int c は A * pa の直後に続くためです。メモリ内では、pa -> b は int c にアクセスすると思います。

プログラムの出力は次のとおりです。 3 4 5

誰でもこれを説明できますか?


「free(pa);」を追加すると メインの最後に: +デバッグ モードでは、HEAP CORRUPTION ERROR が発生します。+リリースモードでは、まだ何も起こりません。

4

2 に答える 2

1

未定義の動作とは、何でも起こり得ることを意味します。特に、診断は必要ありません。

このタイプのバグを見つける実用的な方法の 1 つは、Valgrindのようなツールを使用することです。

$ valgrind ./a.out
a=3
==37240== Invalid write of size 4
==37240==    at 0x100000E1D: main (test.c:22)
==37240==  Address 0x10001b184 is 0 bytes after a block of size 4 alloc'd
==37240==    at 0x5237: malloc (in /usr/local/Cellar/valgrind/3.8.1/lib/valgrind/vgpreload_memcheck-amd64-darwin.so)
==37240==    by 0x100000DD2: main (test.c:19)
==37240== 
==37240== Invalid read of size 4
==37240==    at 0x100000E28: main (test.c:23)
==37240==  Address 0x10001b184 is 0 bytes after a block of size 4 alloc'd
==37240==    at 0x5237: malloc (in /usr/local/Cellar/valgrind/3.8.1/lib/valgrind/vgpreload_memcheck-amd64-darwin.so)
==37240==    by 0x100000DD2: main (test.c:19)
==37240== 

Windows 用の同様のツールがあります。Windowsに代わる適切な Valgrind はありますか?

于 2013-04-12T09:06:03.100 に答える