// Protected-process smoke test. // Verifies that kernel-owned processes remain queryable but cannot be terminated. #include #include #include #define MAX_PROCESSES 16u // Prints one NUL-terminated string to the console. static void print(const char* text) { SYS_WRITE_CONSOLE_REQUEST request = { SysSvFromCstr(text) }; (void)SysWriteConsole(&request); } // Prints one unsigned integer to the console. static void print_u32(uint32_t value) { char buffer[16]; size_t length = 0; if (value == 0) { print("0"); return; } while (value && length < sizeof(buffer)) { buffer[length++] = (char)('0' + (value % 10u)); value /= 10u; } while (length) { char digit = buffer[--length]; SYS_WRITE_CONSOLE_REQUEST request = { SysSvFromParts(&digit, 1) }; (void)SysWriteConsole(&request); } } // Terminates the current test process. static void exit_now(int32_t code) { while (true) (void)SysExitProcess(code); } // Fails the test with one status value. static void fail_status(const char* operation, uint32_t status) { print("process_protection_smoke: "); print(operation); print(" status="); print_u32(status); print("\n"); exit_now(1); } // Verifies one protected process remains alive after a kill attempt. static void verify_protected_process(const SYS_PROCESS_INFO* process) { uint32_t handle = 0; uint32_t status = SysOpenProcess(process->ProcessId, &handle); if (status != NTLSTATUS_SUCCESS) fail_status("open protected process", status); status = SysKillProcess(handle, (int32_t)NTLSTATUS_PROCESS_KILLED); if (status != NTLSTATUS_ACCESS_DENIED) { SysCloseHandle(handle); fail_status("kill protected process", status); } status = SysWaitSingle(handle, SYS_WAIT_FLAG_NONE, 0); SysCloseHandle(handle); if (status != NTLSTATUS_TIMEOUT) fail_status("protected process remained signaled", status); } // Runs the protected-process contract checks. void main(void) { print("process_protection_smoke: start\n"); SYS_PROCESS_INFO processes[MAX_PROCESSES]; size_t count = 0; uint32_t status = SysGetProcessList(processes, MAX_PROCESSES, &count); if (status != NTLSTATUS_SUCCESS) fail_status("query process list", status); int sawIdle = 0; int sawSystem = 0; size_t limit = count < MAX_PROCESSES ? count : MAX_PROCESSES; for (size_t i = 0; i < limit; i++) { const SYS_PROCESS_INFO* process = &processes[i]; if (!(process->Flags & (SYS_PROCESS_FLAG_IDLE | SYS_PROCESS_FLAG_SYSTEM))) continue; if (!(process->Flags & SYS_PROCESS_FLAG_TERMINATION_PROTECTED)) fail_status("missing protected flag", process->ProcessId); verify_protected_process(process); if (process->Flags & SYS_PROCESS_FLAG_IDLE) sawIdle = 1; if (process->Flags & SYS_PROCESS_FLAG_SYSTEM) sawSystem = 1; } if (!sawIdle || !sawSystem) fail_status("missing kernel process", (uint32_t)((sawIdle ? 1u : 0u) | (sawSystem ? 2u : 0u))); print("process_protection_smoke: PASS\n"); exit_now(0); }