释放的内存不会导致页面错误

Freed memory not causing page fault

在尝试为进程保留和提交虚拟内存时,我分配了 64K 字节的内存 VirtualAllocmemcpy 将测试字符串放入其中,printf 将其放入就像一个字符串,用 VirtualFreeMEM_RELEASE 标志释放内存,然后再次 printf 。由于某种原因,没有触发页面错误。这是为什么?

#include <stdio.h>
#include <windows.h>

INT main(DWORD argc, LPSTR argv[]) {
    SYSTEM_INFO info;
    DWORD dwPageSize;
    DWORD dwMemSize;
    LPVOID lpvMem;

    GetSystemInfo(&info);
    dwPageSize = info.dwPageSize;
    dwMemSize = 16 * dwPageSize;

    lpvMem = VirtualAlloc((LPVOID) 0x00F00000, dwMemSize, MEM_COMMIT | MEM_RESERVE, PAGE_READWRITE);
    if (!lpvMem) {
        printf("Error allocating virtual memory\n");
        return 1;
    }

    printf("lpvMem = 0x%08X\n", (UINT32) (UINT64) lpvMem);

    if (!memcpy(lpvMem, "I love foxes \(^o^)/", 21)) {
        printf("Error copying memory (error code 0x%08X)\n", GetLastError());
        return 1;
    }

    printf("Before free: %s\n", (LPCSTR) lpvMem);
    VirtualFree(lpvMem, dwMemSize, MEM_RELEASE);
    printf("After free:  %s\n", (LPCSTR) lpvMem);

    fflush(stdout);

    return 0;
}

输出:

lpvPagedMemory = 0x00F00000
Before free: I love foxes \(^o^)/
After free:  I love foxes \(^o^)/

这一行:

VirtualFree(lpvMem, dwMemSize, MEM_RELEASE);

是一个错误。您没有检查什么 VirtualFree() returns,文档说:

dwSize [in]
...
If the dwFreeType parameter is MEM_RELEASE, this parameter must be 0 (zero). The function frees the entire region that is reserved in the initial allocation call to VirtualAlloc.

所以你需要改用这个:

VirtualFree(lpvMem, 0, MEM_RELEASE);

关于页面错误 - 它可以(并且必须)仅在 成功 调用 VirtualFree().

之后发生