Overview
The VirtualAlloc function reserves, commits, or changes the state of a region of pages in the virtual address space of the calling process.
This function is a fundamental part of memory management in Windows. It allows applications to dynamically allocate memory from the operating system, control its access permissions, and manage its state (reserved, committed, or free).
Syntax
LPVOID VirtualAlloc(
LPVOID lpAddress,
SIZE_T dwSize,
DWORD flAllocationType,
DWORD flProtect
);
Parameters
-
lpAddress[in, optional]
The starting address of the region of pages to be allocated. If this parameter isNULL, the system determines where to allocate the region. -
dwSize[in]
The size, in bytes, of the region of pages to be allocated. IflpAddressisNULL, this parameter is ignored and the function allocates a page-aligned block of memory that is at least the size specified bydwSize. -
flAllocationType[in]
The type of memory allocation. This parameter can be one of the following values:MEM_COMMIT: Allocates physical memory for the specified region of pages.MEM_RESERVE: Reserves a range of the process's virtual address space without any (or changing) physical storage for it.MEM_RESET: Indicates that data in the memory range specified bylpAddressanddwSizeis no longer of interest. The pages should not be written to the paging file. In the future, the calling process can read the memory pages, but the content of the memory that has been committed beyond the allocation granularity of the process is zero.MEM_RESET_UNDO: Indicates that the data in the memory range specified bylpAddressanddwSizeis of interest again.MEM_LARGE_PAGES: Allocates memory using large page support.MEM_PHYSICAL: Allocates physical memory.MEM_TOP_DOWN: Allocates memory from the highest available address.
-
flProtect[in]
The protection for the region of pages to be allocated. This parameter can be one of the following values:PAGE_EXECUTEPAGE_EXECUTE_READPAGE_EXECUTE_READWRITEPAGE_EXECUTE_WRITECOPYPAGE_NOACCESSPAGE_READONLYPAGE_READWRITEPAGE_WRITECOPYPAGE_TARGETS_INVALIDPAGE_TARGETS_NO_UPDATE
PAGE_READWRITE | PAGE_NOCACHE.
Return Value
- If the function succeeds, the return value is the base address of the allocated region of pages.
- If the function fails, the return value is
NULL. To get extended error information, callGetLastError.
Remarks
VirtualAlloc is the primary function for managing memory pages. It offers fine-grained control over memory allocation, including:
- Reserving Memory: Using
MEM_RESERVEmarks a range of virtual addresses as reserved for the process. This prevents other memory allocation functions from using this address range. - Committing Memory: Using
MEM_COMMITallocates physical storage for a previously reserved or newly specified region of virtual addresses. The system assigns actual physical pages to this region. - Protecting Memory: The
flProtectparameter specifies how the memory can be accessed (read, write, execute). This is crucial for security and preventing accidental corruption. - Dynamic Allocation: The function allows applications to grow or shrink their memory footprint as needed during runtime.
When you commit memory, the system initializes the memory region to all zeros. If you reserve memory and then commit it later, the content of the pages committed beyond the allocation granularity of the process is zero.
Example: Allocating and Writing to Memory
#include <windows.h>
#include <stdio.h>
int main() {
LPVOID mem_block;
SIZE_T size = 1024; // Allocate 1KB
// Allocate and commit memory with read/write access
mem_block = VirtualAlloc(NULL, size, MEM_COMMIT | MEM_RESERVE, PAGE_READWRITE);
if (mem_block == NULL) {
fprintf(stderr, "VirtualAlloc failed: %lu\n", GetLastError());
return 1;
}
printf("Memory allocated at: %p\n", mem_block);
// Write some data to the allocated memory
const char* message = "Hello, VirtualAlloc!";
memcpy(mem_block, message, strlen(message) + 1);
printf("Data written: %s\n", (char*)mem_block);
// Free the allocated memory
if (VirtualFree(mem_block, 0, MEM_RELEASE) == 0) {
fprintf(stderr, "VirtualFree failed: %lu\n", GetLastError());
return 1;
}
printf("Memory freed.\n");
return 0;
}