Files
nt-lite/code/public/ntlite/syscall.h
T

1235 lines
41 KiB
C

// Public NTLite syscall ABI declarations shared between kernel, drivers, and user mode.
#pragma once
#include <stddef.h>
#include <stdint.h>
#include <stdbool.h>
#include <intrin.h>
#include <ntlite/string_view.h>
#include <ntlite/dirent.h>
#include <ntlite/file_stat.h>
#include <ntlite/input.h>
#include <ntlite/time.h>
#include <ntlite/display.h>
#include <ntlite/status.h>
// User process/thread environment.
// GS base points at SYS_TEB. GS:[0] is the process PEB pointer.
#define SYS_PEB_MAGIC 0x30424550u // "PEB0"
#define SYS_TEB_MAGIC 0x30424554u // "TEB0"
#define SYS_ENV_VERSION 1u
#define SYS_CWD_MAX 520u
#define SYS_PATH_MAX 1024u
#ifndef SYS_USER_ENV_TYPES_DEFINED
#define SYS_USER_ENV_TYPES_DEFINED 1
typedef struct SYS_PEB {
uint32_t Magic;
uint32_t Version;
uint32_t ProcessId;
SYS_STRING_VIEW ImagePath;
SYS_STRING_VIEW CommandLine;
SYS_STRING_VIEW CurrentDirectory;
} SYS_PEB;
typedef struct SYS_TEB {
SYS_PEB* Peb;
void* StackBase;
void* StackLimit;
struct SYS_TEB* Self;
uint32_t ThreadId;
uint32_t Magic;
// The kernel leaves this NULL so personalities can attach per-thread state.
void* SubsystemData;
} SYS_TEB;
#endif // SYS_USER_ENV_TYPES_DEFINED
// Returns the current thread's process environment block.
static inline SYS_PEB* SysGetPeb(void) {
return (SYS_PEB*)(uintptr_t)__readgsqword(0);
}
// Returns the kernel-maintained current-directory cache from the PEB.
static inline SYS_STRING_VIEW SysGetCurrentDirectoryView(void) {
SYS_PEB* peb = SysGetPeb();
if (!peb || peb->Magic != SYS_PEB_MAGIC || peb->Version != SYS_ENV_VERSION)
return SysSvFromParts("", 0);
return peb->CurrentDirectory;
}
// Returns the current thread environment block.
static inline SYS_TEB* SysGetTeb(void) {
return (SYS_TEB*)(uintptr_t)__readgsqword(offsetof(SYS_TEB, Self));
}
// APC and async I/O ABI.
typedef struct SYS_IO_STATUS_BLOCK {
volatile uint32_t Status;
volatile uint64_t Information;
} SYS_IO_STATUS_BLOCK;
typedef void (*SYS_USER_APC_ROUTINE)(void* normalContext,
SYS_IO_STATUS_BLOCK* iosb,
uint64_t information);
typedef struct SYS_FILE_IO_REQUEST {
uint32_t FileHandle;
uint32_t Flags;
void* Buffer;
size_t Size;
size_t* TransferredOut;
} SYS_FILE_IO_REQUEST;
static inline SYS_FILE_IO_REQUEST SysMakeFileIoRequest(uint32_t fileHandle,
const void* buffer,
size_t size,
size_t* transferredOut) {
SYS_FILE_IO_REQUEST request;
request.FileHandle = fileHandle;
request.Flags = 0;
request.Buffer = (void*)(uintptr_t)buffer;
request.Size = size;
request.TransferredOut = transferredOut;
return request;
}
typedef struct SYS_ASYNC_FILE_REQUEST {
uint32_t FileHandle;
uint32_t EventHandle; // optional; 0 means no event signal
uint32_t Flags;
uint64_t Offset; // explicit byte offset; does not touch file pointer
void* Buffer;
size_t Size;
SYS_IO_STATUS_BLOCK* Iosb; // required; initialized to STATUS_PENDING
SYS_USER_APC_ROUTINE ApcRoutine; // optional; requires SysSetUserApcDispatcher
void* ApcContext;
uint32_t* RequestHandleOut; // optional; receives cancel/query handle
} SYS_ASYNC_FILE_REQUEST;
// User APC frames are kernel-issued control records, not resume contexts.
// User mode may read the routine and arguments, but SysApcReturn only accepts
// the active frame token and restores the kernel-owned saved return state.
typedef struct SYS_USER_APC_FRAME {
uint64_t Magic;
uint64_t ReturnToken;
uint64_t Routine;
uint64_t NormalContext;
uint64_t SystemArgument1;
uint64_t SystemArgument2;
} SYS_USER_APC_FRAME;
#define SYS_USER_APC_FRAME_MAGIC 0x3143504152455355ULL
void SysUserApcDispatcher(void);
// Trap-frame query ABI.
typedef struct SYS_TRAP_FRAME_INFO {
uint32_t Size;
uint32_t Kind;
uint32_t Vector;
uint32_t PreviousMode;
uint64_t Rip;
uint64_t Cs;
uint64_t Rflags;
uint64_t Rsp;
uint64_t Ss;
uint64_t Rax;
uint64_t Rcx;
uint64_t Rdx;
uint64_t R8;
uint64_t R9;
uint64_t R10;
uint64_t R11;
} SYS_TRAP_FRAME_INFO;
// String-view based syscall request structures.
typedef struct SYS_CREATE_PROCESS_REQUEST {
SYS_STRING_VIEW Path;
SYS_STRING_VIEW CommandLine;
uint32_t* HandleOut;
} SYS_CREATE_PROCESS_REQUEST;
typedef struct SYS_PATH_HANDLE_REQUEST {
SYS_STRING_VIEW Path;
uint32_t* HandleOut;
} SYS_PATH_HANDLE_REQUEST;
#define SYS_FILE_ACCESS_READ 0x00000001u
#define SYS_FILE_ACCESS_WRITE 0x00000002u
#define SYS_FILE_ACCESS_APPEND 0x00000004u
#define SYS_FILE_ACCESS_QUERY 0x00000008u
#define SYS_FILE_ACCESS_LOCK 0x00000010u
#define SYS_FILE_OPEN_EXISTING 1u
#define SYS_FILE_CREATE_NEW 2u
#define SYS_FILE_CREATE_ALWAYS 3u
#define SYS_FILE_OPEN_ALWAYS 4u
#define SYS_FILE_TRUNCATE_EXISTING 5u
#define SYS_FILE_FLAG_NONE 0x00000000u
typedef struct SYS_OPEN_FILE_REQUEST {
SYS_STRING_VIEW Path;
uint32_t Access;
uint32_t Disposition;
uint32_t Flags;
uint32_t* HandleOut;
} SYS_OPEN_FILE_REQUEST;
// Builds a flags-based file-open request.
static inline SYS_OPEN_FILE_REQUEST SysMakeOpenFileRequest(SYS_STRING_VIEW path,
uint32_t access,
uint32_t disposition,
uint32_t flags,
uint32_t* handleOut) {
SYS_OPEN_FILE_REQUEST request;
request.Path = path;
request.Access = access;
request.Disposition = disposition;
request.Flags = flags;
request.HandleOut = handleOut;
return request;
}
typedef struct SYS_PATH_REQUEST {
SYS_STRING_VIEW Path;
} SYS_PATH_REQUEST;
#define SYS_REAL_PATH_FLAG_NONE 0x00000000u
// SysRealPath returns a canonical native path of the form "N:/path". It uses
// the kernel-owned process CWD for relative input, collapses '.', '..', and
// repeated separators, and clamps parent traversal at the volume root. The
// current filesystem model has no symlinks, so resolution is lexical and does
// not require the final path to exist. RequiredSizeOut receives the byte count
// including the terminating NUL; a NULL buffer with size zero only queries it.
typedef struct SYS_REAL_PATH_REQUEST {
uint32_t Size;
uint32_t Flags;
SYS_STRING_VIEW Path;
char* Buffer;
size_t BufferSize;
size_t* RequiredSizeOut;
} SYS_REAL_PATH_REQUEST;
typedef struct SYS_STAT_FILE_REQUEST {
SYS_STRING_VIEW Path;
SYS_FILE_STAT* StatOut;
} SYS_STAT_FILE_REQUEST;
typedef struct SYS_RENAME_FILE_REQUEST {
SYS_STRING_VIEW OldPath;
SYS_STRING_VIEW NewPath;
} SYS_RENAME_FILE_REQUEST;
#define SYS_FILE_LOCK_SHARED 1u
#define SYS_FILE_LOCK_EXCLUSIVE 2u
#define SYS_FILE_LOCK_FLAG_NONE 0x00000000u
#define SYS_FILE_LOCK_TO_EOF UINT64_MAX
// File locks are advisory, process-owned byte-range locks keyed by filesystem
// identity. A zero timeout is an immediate try and returns STATUS_WOULD_BLOCK
// on conflict. A finite timeout returns STATUS_TIMEOUT only when its deadline
// expires. SYS_WAIT_TIMEOUT_INFINITE waits without a deadline. Length must be
// nonzero; SYS_FILE_LOCK_TO_EOF locks from Offset through end-of-file growth.
// Unlock removes this process's overlapping locks for the file identity.
typedef struct SYS_LOCK_FILE_REQUEST {
uint32_t Size;
uint32_t FileHandle;
uint32_t Mode;
uint32_t Flags;
uint64_t Offset;
uint64_t Length;
uint64_t TimeoutMilliseconds;
} SYS_LOCK_FILE_REQUEST;
typedef struct SYS_UNLOCK_FILE_REQUEST {
uint32_t Size;
uint32_t FileHandle;
uint32_t Flags;
uint64_t Offset;
uint64_t Length;
} SYS_UNLOCK_FILE_REQUEST;
typedef struct SYS_WRITE_CONSOLE_REQUEST {
SYS_STRING_VIEW Text;
} SYS_WRITE_CONSOLE_REQUEST;
typedef struct SYS_PRINT_DEBUG_REQUEST {
SYS_STRING_VIEW Text;
} SYS_PRINT_DEBUG_REQUEST;
typedef struct SYS_PUBLISH_QUEUE_REQUEST {
SYS_STRING_VIEW Name;
uint32_t QueueHandle;
} SYS_PUBLISH_QUEUE_REQUEST;
typedef struct SYS_OPEN_NAMED_QUEUE_REQUEST {
SYS_STRING_VIEW Name;
uint32_t* HandleOut;
} SYS_OPEN_NAMED_QUEUE_REQUEST;
typedef struct SYS_NAMED_QUEUE_OWNER_REQUEST {
SYS_STRING_VIEW Name;
uint32_t* ProcessHandleOut;
} SYS_NAMED_QUEUE_OWNER_REQUEST;
#define SYS_QUEUE_FLAG_NONE 0x00000000u
#define SYS_QUEUE_MESSAGE_SIZE 56u
// Queue send and receive requests use wait-style timeouts. A zero timeout is
// an immediate try operation and returns STATUS_WOULD_BLOCK if the queue cannot
// make progress without waiting. SYS_WAIT_TIMEOUT_INFINITE requests a blocking
// wait without a deadline. Message pointers reference SYS_QUEUE_MESSAGE_SIZE
// bytes owned by the caller for the duration of the syscall. The common IPC
// pattern is a small control record with one pointer-sized payload token: the
// shared address-space model means that token does not need translation when
// both endpoints agree on the object lifetime. Queues order the token; they do
// not copy storage behind it.
typedef struct SYS_QUEUE_SEND_REQUEST {
uint32_t Size;
uint32_t QueueHandle;
uint32_t Flags;
uint64_t TimeoutMilliseconds;
const void* Message;
} SYS_QUEUE_SEND_REQUEST;
typedef struct SYS_QUEUE_RECV_REQUEST {
uint32_t Size;
uint32_t QueueHandle;
uint32_t Flags;
uint64_t TimeoutMilliseconds;
void* MessageOut;
} SYS_QUEUE_RECV_REQUEST;
#define SYS_WAIT_FLAG_NONE 0x00000000u
#define SYS_WAIT_FLAG_ALERTABLE 0x00000001u
#define SYS_WAIT_TIMEOUT_INFINITE UINT64_MAX
// SysWaitMany copies handles through a fixed kernel stack buffer. This public
// ABI/resource limit is intentionally small to keep wait setup bounded.
#define SYS_WAIT_MANY_MAX_HANDLES 32u
typedef struct SYS_WAIT_MANY_REQUEST {
uint32_t Size;
uint32_t Flags;
const uint32_t* Handles;
uint32_t Count;
uint32_t* SignaledIndexOut;
uint64_t TimeoutMilliseconds;
} SYS_WAIT_MANY_REQUEST;
typedef struct SYS_CREATE_THREAD_REQUEST {
uintptr_t Entry;
uintptr_t Argument;
uint32_t Priority;
uint32_t Flags;
uint32_t* ThreadHandleOut;
uint32_t* ThreadIdOut;
} SYS_CREATE_THREAD_REQUEST;
void SysExitProcess(int32_t exitCode);
void SysExitThread(int32_t exitCode);
uint32_t SysCreateProcess(const SYS_CREATE_PROCESS_REQUEST* request);
uint32_t SysWaitSingle(uint32_t handle, uint32_t flags, uint64_t timeoutMilliseconds);
uint32_t SysWaitMany(const SYS_WAIT_MANY_REQUEST* request);
// SysOpenInputQueue returns a readable and waitable handle to the default
// keyboard input queue. The handle does not create a second event stream;
// SysReadInputEvent, SysPeekInputEvent, SysReadKey, and SysReadKeyboardChar
// consume the same queue. SysWaitSingle succeeds for this handle when a
// keyboard input event can be read.
uint32_t SysOpenInputQueue(uint32_t flags, uint32_t* handleOut);
static inline uint32_t SysWait(uint32_t handle, uint32_t flags) {
return SysWaitSingle(handle, flags, SYS_WAIT_TIMEOUT_INFINITE);
}
uint32_t SysGetProcessExitCode(uint32_t handle, int32_t* exitCodeOut);
uint32_t SysOpenProcess(uint32_t pid, uint32_t* handleOut);
// Protected kernel processes remain openable for query and wait operations,
// but SysKillProcess returns STATUS_ACCESS_DENIED for them.
uint32_t SysKillProcess(uint32_t processHandle, int32_t exitCode);
#define SYS_PROCESS_NAME_MAX 64u
#define SYS_PROCESS_CWD_MAX 128u
#define SYS_PROCESS_STATE_RUNNING 0u
#define SYS_PROCESS_STATE_TERMINATING 1u
#define SYS_PROCESS_STATE_EXITED 2u
#define SYS_PROCESS_FLAG_SYSTEM 0x00000001u
#define SYS_PROCESS_FLAG_CURRENT 0x00000002u
#define SYS_PROCESS_FLAG_TERMINATING 0x00000004u
#define SYS_PROCESS_FLAG_EXITED 0x00000008u
#define SYS_PROCESS_FLAG_IDLE 0x00000010u
#define SYS_PROCESS_FLAG_TERMINATION_PROTECTED 0x00000020u
#define SYS_THREAD_STATE_READY 0u
#define SYS_THREAD_STATE_RUNNING 1u
#define SYS_THREAD_STATE_WAITING 2u
#define SYS_THREAD_STATE_DEAD 3u
#define SYS_THREAD_FLAG_CURRENT 0x00000001u
#define SYS_THREAD_FLAG_IDLE 0x00000002u
#define SYS_THREAD_FLAG_KERNEL 0x00000004u
#define SYS_THREAD_FLAG_QUEUED 0x00000008u
#define SYS_THREAD_FLAG_ALERTABLE_WAIT 0x00000010u
#define SYS_THREAD_FLAG_KERNEL_APC_PENDING 0x00000020u
#define SYS_THREAD_FLAG_USER_APC_PENDING 0x00000040u
#define SYS_THREAD_WAIT_NONE 0u
#define SYS_THREAD_WAIT_PROCESS 1u
#define SYS_THREAD_WAIT_THREAD 2u
#define SYS_THREAD_WAIT_MUTEX 3u
#define SYS_THREAD_WAIT_SEMAPHORE 4u
#define SYS_THREAD_WAIT_EVENT 5u
#define SYS_THREAD_WAIT_QUEUE 6u
#define SYS_THREAD_WAIT_FILE 7u
#define SYS_THREAD_WAIT_DIR 8u
#define SYS_THREAD_WAIT_ASYNC_IO 9u
#define SYS_THREAD_WAIT_SOCKET 10u
#define SYS_THREAD_WAIT_DEVICE 11u
#define SYS_THREAD_WAIT_DRIVER 12u
#define SYS_THREAD_WAIT_USB_DEVICE 13u
#define SYS_THREAD_WAIT_USB_PIPE 14u
#define SYS_THREAD_WAIT_FILE_MAPPING 15u
#define SYS_THREAD_WAIT_SURFACE 16u
#define SYS_THREAD_WAIT_TIMER 17u
#define SYS_THREAD_WAIT_UNKNOWN 0xffffffffu
typedef struct SYS_THREAD_INFO {
uint32_t Size;
uint32_t ProcessId;
uint32_t ThreadId;
uint32_t State;
uint32_t Priority;
uint32_t Flags;
uint32_t RunningCpu;
uint32_t LastCpu;
uint32_t QuantumRemaining;
uint32_t QuantumTicks;
uint32_t CpuBurstTicks;
uint32_t LastRunTicks;
uint32_t WaitObjectType;
uint32_t WaitStatus;
uint32_t KernelApcDisable;
} SYS_THREAD_INFO;
typedef struct SYS_PROCESS_INFO {
uint32_t Size;
uint32_t ProcessId;
uint32_t State;
uint32_t Flags;
uint32_t ThreadCount;
uint32_t HandleCount;
// ModuleCount is the number of DLL-like process modules recorded by the loader.
// The main executable image is reported separately through ImageBase/ImageSize.
uint32_t ModuleCount;
uint32_t CurrentDrive;
int32_t ExitCode;
uintptr_t ImageBase;
size_t ImageSize;
uintptr_t PebBase;
size_t VadCount;
size_t UserReservedBytes;
size_t UserCommittedBytes;
char Name[SYS_PROCESS_NAME_MAX];
char CurrentDirectory[SYS_PROCESS_CWD_MAX];
} SYS_PROCESS_INFO;
uint32_t SysGetProcessList(SYS_PROCESS_INFO* processesOut, size_t maxCount, size_t* countOut);
uint32_t SysGetProcessPid(uint32_t handle, uint32_t* pidOut);
uint32_t SysGetThreadList(uint32_t pid, SYS_THREAD_INFO* threadsOut, size_t maxCount, size_t* countOut);
#define SYS_MODULE_NAME_MAX 64u
#define SYS_MODULE_INFO_VERSION 1u
#define SYS_LOAD_MODULE_FLAG_NONE 0u
#define SYS_MODULE_FLAG_PUBLIC_REF 0x00000001u
#define SYS_MODULE_FLAG_IMPORT_PINNED 0x00000002u
#define SYS_MODULE_FLAG_UNLOADABLE 0x00000004u
typedef struct SYS_MODULE_INFO {
uint32_t Size;
uint32_t Version;
uint32_t Flags;
uint32_t Reserved;
uintptr_t Base;
size_t ImageSize;
uintptr_t EntryPoint;
uint32_t PublicRefCount;
uint32_t ImportRefCount;
uint32_t TotalRefCount;
uint32_t Reserved2;
char Name[SYS_MODULE_NAME_MAX];
} SYS_MODULE_INFO;
typedef struct SYS_LOAD_MODULE_REQUEST {
uint32_t Size;
uint32_t Flags;
SYS_STRING_VIEW Path;
uint32_t* ModuleHandleOut;
SYS_MODULE_INFO* InfoOut;
} SYS_LOAD_MODULE_REQUEST;
typedef struct SYS_GET_MODULE_EXPORT_REQUEST {
uint32_t Size;
uint32_t ModuleHandle;
SYS_STRING_VIEW Name;
uintptr_t* AddressOut;
} SYS_GET_MODULE_EXPORT_REQUEST;
uint32_t SysLoadModule(const SYS_LOAD_MODULE_REQUEST* request);
uint32_t SysUnloadModule(uint32_t moduleHandle);
uint32_t SysGetModuleInfo(uint32_t moduleHandle, SYS_MODULE_INFO* infoOut);
uint32_t SysGetModuleExport(const SYS_GET_MODULE_EXPORT_REQUEST* request);
uint32_t SysGetModuleList(SYS_MODULE_INFO* modulesOut, size_t maxCount, size_t* countOut);
uint32_t SysCreateThread(const SYS_CREATE_THREAD_REQUEST* request);
uint32_t SysGetCurrentTid(void);
uint32_t SysGetCurrentPid(void);
uint32_t SysSetThreadPriority(uint32_t priority);
uint32_t SysYield(void);
#define SYS_TIMER_FLAG_NONE 0u
// Timer deadlines are relative millisecond delays. A zero due time makes the
// timer signaled immediately; a zero period makes it one-shot. Setting an
// already-set timer replaces the previous deadline and clears stale signal
// state before applying the new schedule.
typedef struct SYS_SET_TIMER_REQUEST {
uint32_t Size;
uint32_t TimerHandle;
uint32_t Flags;
uint64_t DueTimeMilliseconds;
uint64_t PeriodMilliseconds;
} SYS_SET_TIMER_REQUEST;
uint32_t SysCreateTimer(uint32_t* handleOut);
uint32_t SysSetTimer(const SYS_SET_TIMER_REQUEST* request);
uint32_t SysCancelTimer(uint32_t timerHandle);
// SysSleep blocks the current thread through the same timer backend used by
// waitable timer handles. A zero-length sleep yields the processor.
uint32_t SysSleep(uint64_t ms);
uint32_t SysSetUserApcDispatcher(void* dispatcher);
// Returns from the active user APC dispatcher. The frame pointer must identify
// the kernel-issued frame for the current delivery; it is not a general resume
// or context-switch syscall.
uint32_t SysApcReturn(const SYS_USER_APC_FRAME* frame);
// Virtual memory and handles.
typedef enum SYS_VM_PROTECTION {
SYS_VM_NOACCESS = 0,
SYS_VM_READ = 1,
SYS_VM_READWRITE = 2,
SYS_VM_EXECUTE = 3,
SYS_VM_EXECUTE_READ = 4,
SYS_VM_EXECUTE_READWRITE = 5,
} SYS_VM_PROTECTION;
#define SYS_VM_FLAG_NONE 0u
#define SYS_VM_FLAG_FIXED 1u
typedef struct SYS_VM_REGION_INFO {
void* Base;
size_t PageCount;
uint32_t Protect;
uint32_t Flags;
uint32_t Type;
uint32_t OwnerPid;
} SYS_VM_REGION_INFO;
uint32_t SysAllocVm(void* preferredBase, size_t pageCount, uint32_t protect, uint32_t flags, void** baseOut);
uint32_t SysFreeVm(void* base);
uint32_t SysProtectVm(void* base, size_t pageCount, uint32_t protect, uint32_t* oldProtectOut);
uint32_t SysQueryVm(void* address, SYS_VM_REGION_INFO* out);
#define SYS_MAP_ACCESS_READ 0x00000001u
#define SYS_MAP_ACCESS_WRITE 0x00000002u
#define SYS_MAP_ACCESS_COPY 0x00000004u
#define SYS_MAP_ACCESS_EXECUTE 0x00000008u
#define SYS_MAP_FLAG_NONE 0x00000000u
uint32_t SysCreateFileMapping(uint32_t fileHandle, uint32_t protect, uint32_t flags,
uint64_t maximumSize, uint32_t* mappingHandleOut);
uint32_t SysMapFile(uint32_t mappingHandle, uint64_t offset, size_t size,
uint32_t access, uint32_t flags, void** baseOut);
uint32_t SysCloseHandle(uint32_t handle);
#define SYS_HANDLE_RIGHT_READ 0x00000001u
#define SYS_HANDLE_RIGHT_WRITE 0x00000002u
#define SYS_HANDLE_RIGHT_WAIT 0x00000004u
#define SYS_HANDLE_RIGHT_SIGNAL 0x00000008u
#define SYS_HANDLE_RIGHT_DUPLICATE 0x00000010u
#define SYS_HANDLE_RIGHT_QUERY 0x00000020u
#define SYS_HANDLE_RIGHT_TERMINATE 0x00000040u
#define SYS_HANDLE_RIGHT_LOCK 0x00000080u
#define SYS_HANDLE_RIGHT_ALL 0x000000FFu
#define SYS_DUPLICATE_HANDLE_FLAG_NONE 0x00000000u
#define SYS_DUPLICATE_HANDLE_FLAG_SAME_RIGHTS 0x00000001u
typedef struct SYS_DUPLICATE_HANDLE_REQUEST {
uint32_t SourceHandle;
uint32_t TargetProcessHandle;
uint32_t DesiredRights;
uint32_t Flags;
uint32_t* TargetHandleOut;
} SYS_DUPLICATE_HANDLE_REQUEST;
uint32_t SysDuplicateHandle(const SYS_DUPLICATE_HANDLE_REQUEST* request);
uint32_t SysCreateMutex(uint32_t* handleOut);
uint32_t SysTryAcquireMutex(uint32_t handle);
uint32_t SysReleaseMutex(uint32_t handle);
uint32_t SysCreateSem(int32_t initial, int32_t max, uint32_t* handleOut);
uint32_t SysTryWaitSem(uint32_t handle);
uint32_t SysSignalSem(uint32_t handle);
uint32_t SysCreateEvent(uint32_t type, uint32_t initialState, uint32_t* handleOut);
uint32_t SysSignalEvent(uint32_t handle);
uint32_t SysClearEvent(uint32_t handle);
uint32_t SysCreateQueue(uint32_t* handleOut);
uint32_t SysSendQueue(const SYS_QUEUE_SEND_REQUEST* request);
uint32_t SysRecvQueue(const SYS_QUEUE_RECV_REQUEST* request);
uint32_t SysPublishQueue(const SYS_PUBLISH_QUEUE_REQUEST* request);
uint32_t SysOpenNamedQueue(const SYS_OPEN_NAMED_QUEUE_REQUEST* request);
uint32_t SysOpenNamedQueueOwnerProcess(const SYS_NAMED_QUEUE_OWNER_REQUEST* request);
uint32_t SysOpenFile(const SYS_OPEN_FILE_REQUEST* request);
uint32_t SysReadFile(const SYS_FILE_IO_REQUEST* request);
uint32_t SysWriteFile(const SYS_FILE_IO_REQUEST* request);
uint32_t SysReadFileAsync(const SYS_ASYNC_FILE_REQUEST* request);
uint32_t SysWriteFileAsync(const SYS_ASYNC_FILE_REQUEST* request);
uint32_t SysCancelIo(uint32_t asyncRequestHandle);
uint32_t SysSeekFile(uint32_t handle, uint64_t offset);
uint32_t SysGetFilePos(uint32_t handle, uint64_t* positionOut);
uint32_t SysGetFileSize(uint32_t handle, uint64_t* sizeOut);
uint32_t SysGetFileStat(uint32_t handle, SYS_FILE_STAT* statOut);
uint32_t SysStatFile(const SYS_STAT_FILE_REQUEST* request);
uint32_t SysTruncateFile(uint32_t handle, uint64_t newSize);
uint32_t SysFlushFile(uint32_t handle);
uint32_t SysDeleteFile(const SYS_PATH_REQUEST* request);
uint32_t SysRenameFile(const SYS_RENAME_FILE_REQUEST* request);
uint32_t SysLockFile(const SYS_LOCK_FILE_REQUEST* request);
uint32_t SysUnlockFile(const SYS_UNLOCK_FILE_REQUEST* request);
uint32_t SysOpenDir(const SYS_PATH_HANDLE_REQUEST* request);
uint32_t SysReadDir(uint32_t handle, SYS_DIR_ENTRY* entryOut);
uint32_t SysCreateDir(const SYS_PATH_REQUEST* request);
uint32_t SysRemoveDir(const SYS_PATH_REQUEST* request);
uint32_t SysSetCwd(const SYS_PATH_REQUEST* request);
uint32_t SysRealPath(const SYS_REAL_PATH_REQUEST* request);
// Console and graphics.
typedef struct SYS_CONSOLE_INFO {
uint32_t Columns;
uint32_t Rows;
uint32_t CursorX;
uint32_t CursorY;
uint16_t Attribute;
} SYS_CONSOLE_INFO;
uint32_t SysWriteConsole(const SYS_WRITE_CONSOLE_REQUEST* request);
uint32_t SysGetConsoleInfo(SYS_CONSOLE_INFO* infoOut);
uint32_t SysSetConsoleCursor(int x, int y);
uint32_t SysFillConsoleCharacter(char c, int x, int y, size_t length, size_t* writtenOut);
uint32_t SysFillConsoleAttribute(uint16_t attr, int x, int y, size_t length, size_t* writtenOut);
uint32_t SysPutScreenChar(char c, int x, int y, uint32_t fg, uint32_t bg);
uint32_t SysCreateSurface(uint32_t width, uint32_t height, uint32_t format, uint32_t flags, uint32_t* handleOut);
uint32_t SysMapSurface(uint32_t surfaceHandle, void** baseOut, uint32_t* pitchBytesOut);
uint32_t SysQuerySurface(uint32_t surfaceHandle, SYS_SURFACE_DESC* descOut);
uint32_t SysPresentSurface(uint32_t surfaceHandle, const DISPLAY_RECT* rects, uint32_t rectCount);
uint32_t SysClearScreen(uint32_t color);
uint32_t SysGetScreenSize(int* widthOut, int* heightOut);
uint32_t SysQueryDisplayInfo(SYS_DISPLAY_INFO* infoOut);
// Input.
#define SYS_INPUT_QUEUE_FLAG_NONE 0x00000000u
#define SYS_INPUT_EVENT_FLAG_NONE 0x00000000u
// A zero QueueHandle means the default keyboard input queue. A
// nonzero QueueHandle must be a handle returned by SysOpenInputQueue. A zero
// timeout is an immediate try and returns STATUS_WOULD_BLOCK when the queue is
// empty. A finite timeout returns STATUS_TIMEOUT only when its deadline expires.
typedef struct SYS_INPUT_EVENT_REQUEST {
uint32_t Size;
uint32_t QueueHandle;
uint32_t Flags;
uint64_t TimeoutMilliseconds;
INPUT_KEY_RECORD* RecordOut;
} SYS_INPUT_EVENT_REQUEST;
uint32_t SysPollKeyboard(INPUT_KEY* keyOut);
uint32_t SysIsKeyDown(INPUT_KEY key, bool* downOut);
uint32_t SysReadKeyboardChar(char* charOut);
uint32_t SysReadKey(INPUT_KEY* keyOut);
uint32_t SysGetKeyModifiers(void);
uint32_t SysReadInputEvent(const SYS_INPUT_EVENT_REQUEST* request);
uint32_t SysPeekInputEvent(const SYS_INPUT_EVENT_REQUEST* request);
uint32_t SysPeekMouse(INPUT_MOUSE_EVENT* eventOut);
uint32_t SysReadMouse(INPUT_MOUSE_EVENT* eventOut);
uint32_t SysGetMousePos(int* xOut, int* yOut);
// Native sockets.
#define SYS_AF_INET 2u
#define SYS_AF_INET6 10u
#define SYS_SOCK_STREAM 1u
#define SYS_SOCK_DGRAM 2u
#define SYS_SOCK_RAW 3u
#define SYS_IPPROTO_ICMP 1u
#define SYS_IPPROTO_TCP 6u
#define SYS_IPPROTO_UDP 17u
#define SYS_IPPROTO_ICMPV6 58u
#define SYS_RESOLVE_HOST_NAME_MAX 255u
#define SYS_SOCKET_OPT_RECV_TIMEOUT_MS 1u
#define SYS_SOCKET_OPT_SEND_TIMEOUT_MS 2u
#define SYS_SOCKET_OPT_NONBLOCKING 3u
#define SYS_POLL_READ 0x0001u
#define SYS_POLL_WRITE 0x0002u
#define SYS_POLL_ERROR 0x0004u
#define SYS_POLL_HANGUP 0x0008u
#define SYS_POLL_INVALID 0x0010u
#define SYS_POLL_TIMEOUT_INFINITE 0xFFFFFFFFu
#define SYS_SHUTDOWN_READ 0u
#define SYS_SHUTDOWN_WRITE 1u
#define SYS_SHUTDOWN_BOTH 2u
#define SYS_SOCKET_ADDRESS_SIZE 28u
// Socket addresses are tagged native records. For IPv4, Address[0..3]
// contains the address bytes. For IPv6, all 16 address bytes are used and
// ScopeId carries the zone index for scoped addresses. Port is host byte order.
typedef struct SYS_SOCKET_ADDRESS {
uint16_t Family;
uint16_t Size;
uint16_t Port;
uint8_t Address[16];
uint32_t ScopeId;
} SYS_SOCKET_ADDRESS;
typedef struct SYS_SOCKET_SEND_TO_REQUEST {
const void* Buffer;
size_t Length;
uint32_t Flags;
const SYS_SOCKET_ADDRESS* RemoteAddress;
size_t RemoteAddressSize;
size_t* SentOut;
} SYS_SOCKET_SEND_TO_REQUEST;
typedef struct SYS_SOCKET_RECV_FROM_REQUEST {
void* Buffer;
size_t Length;
uint32_t Flags;
SYS_SOCKET_ADDRESS* RemoteAddressOut;
size_t* RemoteAddressSizeInOut;
size_t* ReceivedOut;
} SYS_SOCKET_RECV_FROM_REQUEST;
typedef struct SYS_RESOLVE_HOST_REQUEST {
SYS_STRING_VIEW Name;
uint32_t Family;
uint32_t Flags;
SYS_SOCKET_ADDRESS* AddressOut;
size_t* AddressSizeInOut;
} SYS_RESOLVE_HOST_REQUEST;
typedef struct SYS_SOCKET_OPTION_REQUEST {
uint32_t Option;
void* Value;
size_t ValueSize;
size_t* ActualSizeOut;
} SYS_SOCKET_OPTION_REQUEST;
typedef struct SYS_POLLFD {
uint32_t Handle;
uint32_t Events;
uint32_t ReturnedEvents;
} SYS_POLLFD;
#define SYS_ASYNC_SOCKET_FLAG_NONE 0x00000000u
#define SYS_ASYNC_SOCKET_OP_BIND 1u
#define SYS_ASYNC_SOCKET_OP_LISTEN 2u
#define SYS_ASYNC_SOCKET_OP_ACCEPT 3u
#define SYS_ASYNC_SOCKET_OP_CONNECT 4u
#define SYS_ASYNC_SOCKET_OP_SEND 5u
#define SYS_ASYNC_SOCKET_OP_RECV 6u
#define SYS_ASYNC_SOCKET_OP_SEND_TO 7u
#define SYS_ASYNC_SOCKET_OP_RECV_FROM 8u
#define SYS_ASYNC_SOCKET_OP_SHUTDOWN 9u
#define SYS_ASYNC_SOCKET_OP_SET_OPT 10u
#define SYS_ASYNC_SOCKET_OP_GET_OPT 11u
#define SYS_ASYNC_SOCKET_OP_POLL 12u
// Async socket requests return operation-specific byte counts through Iosb.
// Information is the byte count for send/receive, the accepted handle for
// accept, returned poll events for poll, and the actual option byte count for
// get-option. RequestHandleOut receives a waitable/cancellable async I/O handle
// when the request is queued. A zero handle means the operation failed before
// queueing.
typedef struct SYS_ASYNC_SOCKET_REQUEST {
uint32_t Size;
uint32_t SocketHandle;
uint32_t EventHandle;
uint32_t Operation;
uint32_t Flags;
uint32_t SocketFlags;
uint32_t Backlog;
uint32_t ShutdownHow;
uint32_t Option;
uint32_t PollEvents;
void* Buffer;
size_t Length;
const SYS_SOCKET_ADDRESS* Address;
size_t AddressSize;
SYS_SOCKET_ADDRESS* AddressOut;
size_t* AddressSizeInOut;
void* OptionValue;
size_t OptionValueSize;
size_t* OptionActualSizeOut;
uint32_t* HandleOut;
uint32_t* PollReturnedEventsOut;
SYS_IO_STATUS_BLOCK* Iosb;
SYS_USER_APC_ROUTINE ApcRoutine;
void* ApcContext;
uint32_t* RequestHandleOut;
} SYS_ASYNC_SOCKET_REQUEST;
uint32_t SysCreateSocket(uint32_t domain, uint32_t type, uint32_t protocol, uint32_t* handleOut);
uint32_t SysBindSocket(uint32_t socket, const SYS_SOCKET_ADDRESS* address, size_t addressSize);
uint32_t SysListenSocket(uint32_t socket, uint32_t backlog);
uint32_t SysAcceptSocket(uint32_t socket, SYS_SOCKET_ADDRESS* remoteAddressOut, size_t* remoteAddressSizeInOut, uint32_t* acceptedHandleOut);
uint32_t SysConnectSocket(uint32_t socket, const SYS_SOCKET_ADDRESS* address, size_t addressSize);
uint32_t SysSendSocket(uint32_t socket, const void* buffer, size_t length, uint32_t flags, size_t* sentOut);
uint32_t SysRecvSocket(uint32_t socket, void* buffer, size_t length, uint32_t flags, size_t* receivedOut);
uint32_t SysShutdownSocket(uint32_t socket, uint32_t how);
uint32_t SysSendToSocket(uint32_t socket, const SYS_SOCKET_SEND_TO_REQUEST* request);
uint32_t SysRecvFromSocket(uint32_t socket, const SYS_SOCKET_RECV_FROM_REQUEST* request);
uint32_t SysResolveHost(const SYS_RESOLVE_HOST_REQUEST* request);
uint32_t SysSetSocketOption(uint32_t socket, const SYS_SOCKET_OPTION_REQUEST* request);
uint32_t SysGetSocketOption(uint32_t socket, const SYS_SOCKET_OPTION_REQUEST* request);
uint32_t SysPoll(SYS_POLLFD* fds, size_t count, uint32_t timeoutMs, size_t* readyOut);
uint32_t SysSocketIoAsync(const SYS_ASYNC_SOCKET_REQUEST* request);
typedef struct SYS_MEMORY_STATUS {
uint64_t FreePhysicalBytes;
uint64_t KernelPoolBytes;
uint64_t UserHeapBytes;
uint64_t ReclaimablePhysicalBytes;
uint64_t AvailablePhysicalBytes;
uint64_t PinnedPhysicalBytes;
uint64_t NonEvictablePhysicalBytes;
uint64_t UserPhysicalBytes;
uint64_t PageTablePhysicalBytes;
} SYS_MEMORY_STATUS;
#define SYS_KERNEL_STATS_SCHEDULER 1u
#define SYS_KERNEL_STATS_PMM 2u
#define SYS_KERNEL_STATS_CPU 3u
#define SYS_KERNEL_STATS_PFN 4u
#define SYS_KERNEL_STATS_PTE 5u
#define SYS_KERNEL_STATS_VAD 6u
#define SYS_KERNEL_STATS_SWAP 7u
#define SYS_KERNEL_STATS_FILE_CACHE 8u
#define SYS_KERNEL_STATS_SURFACE 9u
#define SYS_KERNEL_STATS_FILESYSTEM 10u
#define SYS_KERNEL_STATS_DISK 11u
#define SYS_KERNEL_STATS_NET_IRP 12u
// Public stats payloads start with Size and Version. Size is the byte count
// returned for that payload, including any trailing records. Version describes
// the field layout for fixed fields in the named payload.
#define SYS_STATS_VERSION 1u
typedef struct SYS_SCHEDULER_STATS {
uint32_t Size;
uint32_t Version;
uint64_t Ticks;
uint64_t ContextSwitches;
uint64_t KeepCurrentDecisions;
uint64_t IdleSelections;
uint64_t Demotions;
uint64_t AgingPromotions;
uint64_t QuantumExpirations;
uint64_t PriorityPreemptions;
uint64_t VoluntaryBlocks;
uint64_t CpuBurstDemotions;
uint64_t SmtSiblingDeferrals;
uint64_t SmtPrimaryPokes;
} SYS_SCHEDULER_STATS;
typedef struct SYS_PMM_STATS {
uint32_t Size;
uint32_t Version;
uint64_t TotalFrames;
uint64_t FreeFrames;
uint64_t UsedFrames;
uint64_t LargestFreeRun;
uint64_t FreeRunCount;
uint64_t FreeRunHistogram[8];
} SYS_PMM_STATS;
#define SYS_CPU_THREAD_FLAG_IDLE 0x00000001u
typedef struct SYS_CPU_STAT {
uint32_t CpuIndex;
uint32_t LapicId;
uint32_t Flags;
uint32_t CurrentTid;
uint32_t CurrentThreadFlags;
uint64_t SchedulerTicks;
uint64_t ContextSwitches;
} SYS_CPU_STAT;
// CPU stats use trailing SYS_CPU_STAT records after the fixed header.
typedef struct SYS_CPU_STATS {
uint32_t Size;
uint32_t Version;
uint32_t HeaderSize;
uint32_t CpuCount;
uint32_t RecordSize;
uint32_t RecordCount;
} SYS_CPU_STATS;
#define SYS_CPU_STATS_RECORDS(stats) ((SYS_CPU_STAT*)((uint8_t*)(stats) + sizeof(SYS_CPU_STATS)))
#define SYS_CPU_STATS_CONST_RECORDS(stats) ((const SYS_CPU_STAT*)((const uint8_t*)(stats) + sizeof(SYS_CPU_STATS)))
typedef struct SYS_PFN_STATS {
uint32_t Size;
uint32_t Version;
uint64_t TotalFrames;
uint64_t FreeFrames;
uint64_t UsedFrames;
uint64_t ReservedFrames;
uint64_t ZeroedFrames;
uint64_t ActiveFrames;
uint64_t StandbyFrames;
uint64_t ModifiedFrames;
uint64_t PinnedFrames;
uint64_t EvictableFrames;
uint64_t NonEvictableFrames;
uint64_t ReclaimableFrames;
uint64_t AvailableFrames;
uint64_t MappedFrames;
uint64_t KernelFrames;
uint64_t PageTableFrames;
uint64_t UserFrames;
uint64_t CleanFileCacheFrames;
uint64_t ActiveCleanFileCacheFrames;
uint64_t StandbyCleanFileCacheFrames;
uint64_t ImageFrames;
uint64_t ActiveImageFrames;
uint64_t StandbyImageFrames;
uint64_t MappedFileFrames;
uint64_t AnonymousFrames;
uint64_t CowFrames;
uint64_t SurfaceFrames;
uint64_t DriverFrames;
uint64_t DmaFrames;
uint64_t BootloaderFrames;
uint64_t PfnDatabaseFrames;
uint64_t MmioFrames;
uint64_t AllocationCount;
uint64_t FreeCount;
uint64_t RetainCount;
uint64_t ReleaseCount;
uint64_t PinCount;
uint64_t UnpinCount;
uint64_t FailedAllocations;
uint64_t FailedContiguousAllocations;
uint64_t FailedInvalidRange;
uint64_t FailedEmptyRange;
uint64_t FailedReserveDenied;
uint64_t FailedNoFrame;
uint64_t FailedContiguousInvalidRequest;
uint64_t FailedContiguousReserveDenied;
uint64_t FailedContiguousNoRun;
uint64_t ReclaimAttempts;
uint64_t ReclaimPagesRequested;
uint64_t ReclaimPagesSucceeded;
uint64_t ReclaimPagesFailed;
uint64_t ReclaimReentrantSkips;
} SYS_PFN_STATS;
typedef struct SYS_VAD_STATS {
uint32_t Size;
uint32_t Version;
uint64_t ResolveFaultCalls;
uint64_t ResolvedFaults;
uint64_t FailedFaults;
uint64_t ProtectionFaults;
uint64_t NoVadFaults;
uint64_t UncommittedFaults;
uint64_t NoAccessFaults;
uint64_t DemandZeroPages;
uint64_t ZeroPageMaps;
uint64_t ZeroPageCowSplits;
uint64_t CowFaults;
uint64_t CowPagesCopied;
uint64_t CowViewsCreated;
uint64_t CowPagesShared;
uint64_t EnsureResidentCalls;
uint64_t EnsureResidentPages;
uint64_t AlreadyResidentPages;
uint64_t FileBackedFaults;
uint64_t FileBackedReads;
uint64_t FileBackedReadFailures;
uint64_t FileBackedDiscards;
uint64_t FileBackedSharedWritableFaults;
uint64_t FileBackedDirtyFaults;
uint64_t FileBackedDirtySyncs;
uint64_t ImageBackedFaults;
uint64_t ImageBackedZeroFaults;
uint64_t ImageBackedPrivateFaults;
uint64_t ImageFixupPrivateCalls;
uint64_t ImageFixupPrivatePages;
uint64_t SwapPageOuts;
uint64_t SwapPageIns;
} SYS_VAD_STATS;
typedef struct SYS_FILE_CACHE_STATS {
uint32_t Size;
uint32_t Version;
uint64_t Lookups;
uint64_t Hits;
uint64_t Misses;
uint64_t Loads;
uint64_t LoadFailures;
uint64_t RaceDiscards;
uint64_t InflightWaits;
uint64_t Invalidations;
uint64_t DirtyPages;
uint64_t MaxDirtyPages;
uint64_t DirtyMarks;
uint64_t WritebackRequests;
uint64_t WritebackPages;
uint64_t WritebackBytes;
uint64_t WritebackFailures;
uint64_t FlushFileCalls;
uint64_t FlushFileFailures;
uint64_t MappedDirtySyncs;
uint64_t MappedDirtyPages;
uint64_t Drops;
uint64_t DropFailures;
uint64_t StandbyTransitions;
uint64_t StandbyHits;
uint64_t ReadAheadRequests;
uint64_t ReadAheadPagesRequested;
uint64_t ReadAheadPagesQueued;
uint64_t ReadAheadPagesLoaded;
uint64_t ReadAheadPagesSkipped;
uint64_t ReadAheadFailures;
uint64_t ReadAheadPagesThrottled;
uint64_t MaxReadAheadPagesPerRequest;
uint64_t BatchReads;
uint64_t BatchPagesRequested;
uint64_t BatchPagesLoaded;
uint64_t MaxBatchPagesRequested;
uint64_t MaxBatchPagesLoaded;
uint64_t ResidentPages;
uint64_t ActivePages;
uint64_t StandbyPages;
uint64_t MaxResidentPages;
} SYS_FILE_CACHE_STATS;
// Filesystem stats are generic VFS/driver telemetry. Drivers should map
// private metadata work onto these counters instead of exposing filesystem-
// specific cache names through the public ABI.
typedef struct SYS_FILESYSTEM_STATS {
uint32_t Size;
uint32_t Version;
uint64_t PathLookups;
uint64_t PathCacheHits;
uint64_t PathCacheMisses;
uint64_t PathCacheStores;
uint64_t PathCacheInvalidations;
uint64_t PathCacheGeneration;
uint64_t DirectorySearches;
uint64_t DirectoryBlocksRead;
uint64_t DirectoryEntriesScanned;
uint64_t DataReadRuns;
uint64_t DataReadSectors;
uint64_t DataReadRunMerges;
uint64_t MaxDataReadSpanSectors;
} SYS_FILESYSTEM_STATS;
typedef struct SYS_DISK_STATS {
uint32_t Size;
uint32_t Version;
uint64_t RegisteredDisks;
uint64_t ReadRequests;
uint64_t ReadSectors;
uint64_t WriteRequests;
uint64_t WriteSectors;
uint64_t MaxReadSectors;
uint64_t MaxWriteSectors;
uint64_t ReadaheadHits;
uint64_t ReadaheadMisses;
uint64_t ReadaheadStores;
uint64_t ReadaheadInvalidations;
uint64_t ReadaheadBytesServed;
uint64_t ReadaheadSectorsLoaded;
uint64_t ReadaheadSequentialDetections;
uint64_t ReadaheadSuppressed;
uint64_t ReadaheadAllocFailures;
uint64_t ReadaheadReadFailures;
uint64_t MaxReadaheadSectors;
} SYS_DISK_STATS;
#define SYS_NET_IRP_OPERATION_COUNT 16u
#define SYS_NET_IRP_OP_INVALID 0u
#define SYS_NET_IRP_OP_CREATE 1u
#define SYS_NET_IRP_OP_CLOSE 2u
#define SYS_NET_IRP_OP_BIND 3u
#define SYS_NET_IRP_OP_LISTEN 4u
#define SYS_NET_IRP_OP_ACCEPT 5u
#define SYS_NET_IRP_OP_CONNECT 6u
#define SYS_NET_IRP_OP_SEND 7u
#define SYS_NET_IRP_OP_RECEIVE 8u
#define SYS_NET_IRP_OP_SEND_TO 9u
#define SYS_NET_IRP_OP_RECEIVE_FROM 10u
#define SYS_NET_IRP_OP_SHUTDOWN 11u
#define SYS_NET_IRP_OP_SET_OPTION 12u
#define SYS_NET_IRP_OP_GET_OPTION 13u
#define SYS_NET_IRP_OP_POLL 14u
#define SYS_NET_IRP_OP_RESOLVE_HOST 15u
typedef struct SYS_NET_IRP_STATS {
uint32_t Size;
uint32_t Version;
uint64_t Submitted;
uint64_t Completed;
uint64_t CompletedSynchronously;
uint64_t CompletedAsynchronously;
uint64_t Pending;
uint64_t CancelRequested;
uint64_t Cancelled;
uint64_t WouldBlock;
uint64_t Timeout;
uint64_t Failed;
uint64_t ByOperation[SYS_NET_IRP_OPERATION_COUNT];
} SYS_NET_IRP_STATS;
typedef struct SYS_SWAP_STATS {
uint32_t Size;
uint32_t Version;
uint64_t Enabled;
uint64_t TotalSlots;
uint64_t UsedSlots;
uint64_t FreeSlots;
uint64_t HighWaterSlots;
uint64_t PageOuts;
uint64_t PageIns;
uint64_t PageOutFailures;
uint64_t PageInFailures;
uint64_t SlotAllocations;
uint64_t SlotFrees;
uint64_t SlotAllocationFailures;
} SYS_SWAP_STATS;
#define SYS_PTE_QUERY_GENERIC 0u
#define SYS_PTE_QUERY_USER_PROBE 1u
#define SYS_PTE_QUERY_HEAP 2u
#define SYS_PTE_QUERY_VAD 3u
#define SYS_PTE_QUERY_DEBUG 4u
#define SYS_PTE_QUERY_SELF_TEST 5u
#define SYS_PTE_QUERY_PURPOSE_COUNT 6u
typedef struct SYS_PTE_STATS {
uint32_t Size;
uint32_t Version;
uint64_t MapCalls;
uint64_t MapFailures;
uint64_t UnmapCalls;
uint64_t UnmapFailures;
uint64_t ProtectCalls;
uint64_t ProtectFailures;
uint64_t QueryCalls;
uint64_t QueryFailures;
uint64_t QueryByPurpose[SYS_PTE_QUERY_PURPOSE_COUNT];
uint64_t QueryFailuresByPurpose[SYS_PTE_QUERY_PURPOSE_COUNT];
uint64_t TranslateCalls;
uint64_t LocalFlushes;
uint64_t GlobalFlushes;
uint64_t ShootdownRequests;
uint64_t ShootdownTargetCpus;
uint64_t ShootdownSkippedNoTargets;
uint64_t ShootdownAcks;
uint64_t ShootdownTimeouts;
uint64_t NewMappingNoFlushes;
uint64_t ReplacedMappingFlushes;
uint64_t PageTablePagesAllocated;
uint64_t CurrentLeafMappings;
} SYS_PTE_STATS;
#define SYS_CPU_FLAG_PRESENT 0x00000001u
#define SYS_CPU_FLAG_STARTED 0x00000002u
#define SYS_CPU_FLAG_PARKED 0x00000004u
#define SYS_CPU_FLAG_ONLINE 0x00000008u
#define SYS_CPU_FLAG_BSP 0x00000010u
#define SYS_CPU_FLAG_PRIMARY 0x00000020u
// Time and diagnostics.
// SysGetTick returns monotonic ticks since boot. The tick unit is defined by
// SysGetTickFrequency and is not a wall-clock timestamp.
uint64_t SysGetTick(void);
// SysGetTickFrequency returns the number of SysGetTick ticks per second.
uint32_t SysGetTickFrequency(uint64_t* frequencyOut);
// Converts a tick delta to milliseconds using the supplied tick frequency.
static inline uint64_t SysTicksToMilliseconds(uint64_t ticks, uint64_t frequency) {
if (!frequency) return 0;
return (ticks / frequency) * 1000ull + ((ticks % frequency) * 1000ull) / frequency;
}
// Converts a tick delta to microseconds using the supplied tick frequency.
static inline uint64_t SysTicksToMicroseconds(uint64_t ticks, uint64_t frequency) {
if (!frequency) return 0;
return (ticks / frequency) * 1000000ull + ((ticks % frequency) * 1000000ull) / frequency;
}
uint32_t SysPrintDebug(const SYS_PRINT_DEBUG_REQUEST* request);
uint32_t SysQueryTrapFrame(SYS_TRAP_FRAME_INFO* info);
uint32_t SysGetMemoryStatus(SYS_MEMORY_STATUS* statusOut);
uint32_t SysQueryKernelStats(uint32_t classId, void* buffer, size_t bufferSize, size_t* requiredSizeOut);
uint32_t SysGetSystemTime(SYS_SYSTEM_TIME* timeOut);