- /*
- * ntcreatepagefile.c - create a Windows NT paging file
- *
- * - Compile with
- * $ clang -target x86_64-pc-windows-gnu -Wall -Wextra -DUNICODE=1 -D_UNICODE=1 -I/usr/include -g ntcreatepagefile.c -lntdll -o ntcreatepagefile.exe
- *
- * - Useful commands:
- * # list active pagefiles
- * powershell -Command 'Get-CimInstance Win32_PageFile | Select-Object Name,AllocatedSize'
- */
- #include <windows.h>
- #include <stdio.h>
- #include <stdbool.h>
- typedef LONG NTSTATUS;
- #ifndef NT_SUCCESS
- #define NT_SUCCESS(Status) (((NTSTATUS)(Status)) >= 0)
- #endif
- /* |UNICODE_STRING| compatible with Native API */
- typedef struct _UNICODE_STRING {
- USHORT Length;
- USHORT MaximumLength;
- PWSTR Buffer;
- } UNICODE_STRING, *PUNICODE_STRING;
- /* NtCreatePagingFile from ntdll.dll (user-mode export) */
- __declspec(dllimport)
- NTSTATUS NTAPI NtCreatePagingFile(
- const UNICODE_STRING* PageFileName, /* OM path, e.g. \??\N:\pagefile.sys */
- const LARGE_INTEGER* MinimumSize, /* bytes, multiple of page size */
- const LARGE_INTEGER* MaximumSize, /* bytes, multiple of page size */
- ULONG FlagsOrPriority /* historically ignored; 0 is fine */
- );
- static
- bool EnablePrivilege(const char *privName, BOOL enable)
- {
- HANDLE hTok = NULL;
- if (!OpenProcessToken(GetCurrentProcess(),
- TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY, &hTok)) {
- (int)GetLastError());
- return false;
- }
- LUID luid;
- if (!LookupPrivilegeValueA(NULL, privName, &luid)) {
- "LookupPrivilegeValueA('%s') failed, lasterr=%d\n",
- privName, (int)GetLastError());
- (void)CloseHandle(hTok);
- return false;
- }
- TOKEN_PRIVILEGES tp = {
- .PrivilegeCount = 1,
- .Privileges[0].Luid = luid,
- .Privileges[0].Attributes = (enable ? SE_PRIVILEGE_ENABLED : 0)
- };
- if (!AdjustTokenPrivileges(hTok, FALSE, &tp, sizeof(tp), NULL, NULL)) {
- (int)GetLastError());
- (void)CloseHandle(hTok);
- return false;
- }
- if (GetLastError() == ERROR_NOT_ALL_ASSIGNED) {
- privName);
- (void)CloseHandle(hTok);
- return false;
- }
- (void)CloseHandle(hTok);
- return true;
- }
- static void InitUnicodeString(PUNICODE_STRING u, PCWSTR s)
- {
- u->Buffer = (PWSTR)s;
- u->MaximumLength = u->Length;
- }
- const ULONGLONG MiB = 1024ULL * 1024ULL;
- int main(int ac, char *av[])
- {
- (void)ac; /* unused */
- /* Native path: \??\N:\pagefile.sys (Object Manager alias for DosDevices) */
- const wchar_t *ntPath = L"\\??\\N:\\pagefile.sys";
- HANDLE h = CreateFileW(
- ntPath,
- GENERIC_READ | GENERIC_WRITE,
- FILE_SHARE_READ | FILE_SHARE_WRITE,
- NULL,
- CREATE_ALWAYS,
- FILE_ATTRIBUTE_SYSTEM | FILE_FLAG_WRITE_THROUGH,
- NULL
- );
- if (h == INVALID_HANDLE_VALUE) {
- av[0], (int)GetLastError());
- return EXIT_FAILURE;
- }
- LARGE_INTEGER off = {
- .QuadPart = 512ULL * MiB
- };
- if (!SetFilePointerEx(h, off, NULL, FILE_BEGIN)) {
- av[0], (int)GetLastError());
- (void)CloseHandle(h);
- return EXIT_FAILURE;
- }
- if (!SetEndOfFile(h)) {
- av[0], (int)GetLastError());
- (void)CloseHandle(h);
- return EXIT_FAILURE;
- }
- if (!FlushFileBuffers(h)) {
- av[0], (int)GetLastError());
- (void)CloseHandle(h);
- return EXIT_FAILURE;
- }
- (void)CloseHandle(h);
- /* Set min/max sizes (bytes). Must be multiples of page size. */
- LARGE_INTEGER minSize = { .QuadPart = 512ULL * MiB };
- LARGE_INTEGER maxSize = { .QuadPart = 512ULL * MiB };
- /* Enable SeCreatePagefilePrivilege */
- if (!EnablePrivilege("SeCreatePagefilePrivilege", TRUE)) {
- "%s: Failed to enable SeCreatePagefilePrivilege\n", av[0]);
- return EXIT_FAILURE;
- }
- UNICODE_STRING u;
- InitUnicodeString(&u, ntPath);
- NTSTATUS st = NtCreatePagingFile(&u, &minSize, &maxSize, 0UL);
- /* Revert the privilege */
- EnablePrivilege("SeCreatePagefilePrivilege", FALSE);
- if (!NT_SUCCESS(st)) {
- "%s: NtCreatePagingFile() failed: ntstatus=0x%lx\n",
- av[0], (long)st);
- return EXIT_FAILURE;
- }
- ntPath, minSize.QuadPart, maxSize.QuadPart);
- return EXIT_SUCCESS;
- }
ntcreatepagefile.c - create a Windows NT paging file
Posted by Anonymous on Sat 25th Oct 2025 14:35
raw | new post
Submit a correction or amendment below (click here to make a fresh posting)
After submitting an amendment, you'll be able to view the differences between the old and new posts easily.
nrubsig.kpaste.net RSS