VirtualAlloc()で20KB分(0x5000)確保した後、4KB毎にVirtualProtect()で保護モードを変更してみるサンプル。 va01.cpp: #code|c|> #include #include void PrintErrorMsg(DWORD err) { LPTSTR lpMsgBuf; FormatMessage(FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS, NULL, err, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), (LPTSTR)&lpMsgBuf, 0, NULL); printf("%s\n", lpMsgBuf); LocalFree(lpMsgBuf); } void DumpMemoryInfo(void *addr) { MEMORY_BASIC_INFORMATION mbi; size_t res_sz = 0; res_sz = VirtualQuery(addr, &mbi, sizeof(mbi)); if (0 == res_sz) { PrintErrorMsg(GetLastError()); fprintf(stderr, "VirtualQuery() failed.\n"); exit(-1); } printf("[MBI at 0x%08X]:\n", addr); printf("\tmbi.BaseAddress = 0x%08X\n", mbi.BaseAddress); printf("\tmbi.AllocationBase = 0x%08X\n", mbi.AllocationBase); printf("\tmbi.AllocationProtect = 0x%08X\n", mbi.AllocationProtect); printf("\tmbi.RegionSize = 0x%08X\n", mbi.RegionSize); printf("\tmbi.State = 0x%08X\n", mbi.State); printf("\tmbi.Protect = 0x%08X\n", mbi.Protect); printf("\tmbi.Type = 0x%08X\n", mbi.Type); } char msg[] = "ABCD"; int main(int argc, char *argv[]) { void *p1 = NULL; DWORD dw1 = 0; size_t init_sz = 0x5000; p1 = VirtualAlloc(NULL, init_sz, MEM_RESERVE | MEM_COMMIT, PAGE_NOACCESS); if (NULL == p1) { PrintErrorMsg(GetLastError()); fprintf(stderr, "VirtualAlloc() failed.\n"); return -1; } printf("p1 = 0x%08X\n", p1); dw1 = (DWORD)p1; DumpMemoryInfo((void*)(dw1 + 123)); DWORD oldp = 0; DWORD start = dw1; if (!VirtualProtect((void*)(start), 0x1000, PAGE_READONLY, &oldp)) { PrintErrorMsg(GetLastError()); fprintf(stderr, "VirtualProtect() failed.\n"); return -1; } printf("------[1]\n"); DumpMemoryInfo((void*)(start)); start += 0x1000; if (!VirtualProtect((void*)(start), 0x1000, PAGE_EXECUTE_READ, &oldp)) { PrintErrorMsg(GetLastError()); fprintf(stderr, "VirtualProtect() failed.\n"); return -1; } printf("------[2]\n"); DumpMemoryInfo((void*)(start)); start += 0x1000; if (!VirtualProtect((void*)(start), 0x1000, PAGE_READWRITE, &oldp)) { PrintErrorMsg(GetLastError()); fprintf(stderr, "VirtualProtect() failed.\n"); return -1; } printf("------[3]\n"); DumpMemoryInfo((void*)(start)); start += 0x1000; if (!VirtualProtect((void*)(start), 0x1000, PAGE_READONLY, &oldp)) { PrintErrorMsg(GetLastError()); fprintf(stderr, "VirtualProtect() failed.\n"); return -1; } printf("------[4]\n"); DumpMemoryInfo((void*)(start)); return 0; } ||< 実行結果: #pre||> p1 = 0x003A0000 [MBI at 0x003A007B]: mbi.BaseAddress = 0x003A0000 mbi.AllocationBase = 0x003A0000 mbi.AllocationProtect = 0x00000004 mbi.RegionSize = 0x00005000 mbi.State = 0x00001000 mbi.Protect = 0x00000004 mbi.Type = 0x00020000 ------[1] [MBI at 0x003A0000]: mbi.BaseAddress = 0x003A0000 mbi.AllocationBase = 0x003A0000 mbi.AllocationProtect = 0x00000004 mbi.RegionSize = 0x00001000 mbi.State = 0x00001000 mbi.Protect = 0x00000002 mbi.Type = 0x00020000 ------[2] [MBI at 0x003A1000]: mbi.BaseAddress = 0x003A1000 mbi.AllocationBase = 0x003A0000 mbi.AllocationProtect = 0x00000004 mbi.RegionSize = 0x00001000 mbi.State = 0x00001000 mbi.Protect = 0x00000020 mbi.Type = 0x00020000 ------[3] [MBI at 0x003A2000]: mbi.BaseAddress = 0x003A2000 mbi.AllocationBase = 0x003A0000 mbi.AllocationProtect = 0x00000004 mbi.RegionSize = 0x00003000 mbi.State = 0x00001000 mbi.Protect = 0x00000004 mbi.Type = 0x00020000 ------[4] [MBI at 0x003A3000]: mbi.BaseAddress = 0x003A3000 mbi.AllocationBase = 0x003A0000 mbi.AllocationProtect = 0x00000004 mbi.RegionSize = 0x00001000 mbi.State = 0x00001000 mbi.Protect = 0x00000002 mbi.Type = 0x00020000 ||< VirtualAlloc()で確保したメモリ中を、0x1000サイズの領域毎にプロテクトモードを変更出来ている。