add ntfs.sys standalone driver target, change default usb vhd layout formatting to ntfs, implement Fat32CreateDir for directory creation support in the fat32 file system driver, add a dedicated HAL serial output endpoint for COM1 writes in hal_serial.c and subscribe serial to HAL text streams, introduce waitable kernel timers with KeTimerCreate, KeTimerSet, and KeTimerCancel alongside spinlock-protected global timer list initialization and scheduler tick tracking, implement SyscallWriteFileAsync system call for asynchronous non-blocking file writes, refactor NetSocketConnect and NetSocketSendTo to use generic SYS_SOCKET_ADDRESS_K structures instead of being hardcoded to IPv4, update gethostbyname and DNS name resolution to support IPv6 parsing via ResolveNameFamily, update tcpserve.exe with -4 and -6 command-line flags to accept and display IPv6 addresses, append size and version headers to all kernel telemetry and statistics structures including SYS_PMM_STATS, SYS_CPU_STATS, and SYS_SCHEDULER_STATS, update winmm timeGetTime to look up high-resolution hardware frequencies via SysGetTickFrequency, integrate 14 native smoke test applications.
This commit is contained in:
1 parent
2c4a68a75f
commit
ed3d065abd
156 files changed
+10509
-2643
No files matched your search
@@ -0,0 +1,205 @@
|
||||
// Native handle duplication smoke test.
|
||||
// Verifies explicit rights reduction, same-rights duplication, and invalid duplicate requests.
|
||||
|
||||
#include <stdint.h>
|
||||
#include <stdbool.h>
|
||||
#include <ntlite/syscall.h>
|
||||
|
||||
typedef struct TEST_QUEUE_MESSAGE {
|
||||
uint32_t Type;
|
||||
uint32_t Flags;
|
||||
uint64_t Param[6];
|
||||
} TEST_QUEUE_MESSAGE;
|
||||
|
||||
typedef char TEST_QUEUE_MESSAGE_SIZE_CHECK[
|
||||
(sizeof(TEST_QUEUE_MESSAGE) == SYS_QUEUE_MESSAGE_SIZE) ? 1 : -1
|
||||
];
|
||||
|
||||
// Prints one NUL-terminated string to the kernel console.
|
||||
static void print(const char* s) {
|
||||
SYS_WRITE_CONSOLE_REQUEST req = { SysSvFromCstr(s) };
|
||||
SysWriteConsole(&req);
|
||||
}
|
||||
|
||||
// Prints one unsigned integer to the kernel console.
|
||||
static void print_u64(uint64_t v) {
|
||||
char buf[32];
|
||||
int i = 0;
|
||||
if (v == 0) {
|
||||
print("0");
|
||||
return;
|
||||
}
|
||||
while (v && i < (int)sizeof(buf)) {
|
||||
buf[i++] = (char)('0' + (v % 10));
|
||||
v /= 10;
|
||||
}
|
||||
while (i--) {
|
||||
char c = buf[i];
|
||||
SYS_WRITE_CONSOLE_REQUEST req = { SysSvFromParts(&c, 1) };
|
||||
SysWriteConsole(&req);
|
||||
}
|
||||
}
|
||||
|
||||
// Terminates the current test process.
|
||||
static void exit_now(int code) {
|
||||
for (;;) SysExitProcess(code);
|
||||
}
|
||||
|
||||
// Fails the test with one plain message.
|
||||
static void fail(const char* msg) {
|
||||
print("handle_dup_smoke: ");
|
||||
print(msg);
|
||||
print("\n");
|
||||
exit_now(1);
|
||||
}
|
||||
|
||||
// Fails the test with one status value.
|
||||
static void fail_status(const char* what, uint32_t status) {
|
||||
print("handle_dup_smoke: ");
|
||||
print(what);
|
||||
print(" status=");
|
||||
print_u64(status);
|
||||
print("\n");
|
||||
exit_now(1);
|
||||
}
|
||||
|
||||
// Requires one exact status value.
|
||||
static void expect_status(const char* what, uint32_t got, uint32_t expected) {
|
||||
if (got == expected) return;
|
||||
print("handle_dup_smoke: ");
|
||||
print(what);
|
||||
print(" got=");
|
||||
print_u64(got);
|
||||
print(" expected=");
|
||||
print_u64(expected);
|
||||
print("\n");
|
||||
exit_now(1);
|
||||
}
|
||||
|
||||
// Duplicates one handle into the current process.
|
||||
static uint32_t duplicate_handle(uint32_t source, uint32_t process, uint32_t desiredRights, uint32_t flags, uint32_t* out) {
|
||||
SYS_DUPLICATE_HANDLE_REQUEST req = {
|
||||
source,
|
||||
process,
|
||||
desiredRights,
|
||||
flags,
|
||||
out,
|
||||
};
|
||||
return SysDuplicateHandle(&req);
|
||||
}
|
||||
|
||||
// Sends one queue message.
|
||||
static uint32_t send_message(uint32_t queue, uint32_t type, uint64_t value) {
|
||||
TEST_QUEUE_MESSAGE msg = {0};
|
||||
msg.Type = type;
|
||||
msg.Param[0] = value;
|
||||
SYS_QUEUE_SEND_REQUEST req = {
|
||||
sizeof(req),
|
||||
queue,
|
||||
SYS_QUEUE_FLAG_NONE,
|
||||
0,
|
||||
&msg,
|
||||
};
|
||||
return SysSendQueue(&req);
|
||||
}
|
||||
|
||||
// Receives one queue message.
|
||||
static uint32_t recv_message(uint32_t queue, TEST_QUEUE_MESSAGE* msg) {
|
||||
SYS_QUEUE_RECV_REQUEST req = {
|
||||
sizeof(req),
|
||||
queue,
|
||||
SYS_QUEUE_FLAG_NONE,
|
||||
0,
|
||||
msg,
|
||||
};
|
||||
return SysRecvQueue(&req);
|
||||
}
|
||||
|
||||
// Verifies one received queue message.
|
||||
static void check_message(const TEST_QUEUE_MESSAGE* msg, uint32_t type, uint64_t value) {
|
||||
if (msg->Type != type || msg->Param[0] != value) fail("message payload mismatch");
|
||||
}
|
||||
|
||||
// Runs the native handle duplication smoke test.
|
||||
int main(void) {
|
||||
print("handle_dup_smoke: start\n");
|
||||
|
||||
uint32_t currentPid = SysGetCurrentPid();
|
||||
uint32_t process = 0;
|
||||
uint32_t s = SysOpenProcess(currentPid, &process);
|
||||
if (s != STATUS_SUCCESS) fail_status("open current process", s);
|
||||
|
||||
uint32_t queue = 0;
|
||||
s = SysCreateQueue(&queue);
|
||||
if (s != STATUS_SUCCESS) fail_status("create queue", s);
|
||||
|
||||
uint32_t readOnly = 0;
|
||||
s = duplicate_handle(queue, process, SYS_HANDLE_RIGHT_READ, SYS_DUPLICATE_HANDLE_FLAG_NONE, &readOnly);
|
||||
if (s != STATUS_SUCCESS) fail_status("duplicate read-only", s);
|
||||
|
||||
uint32_t writeOnly = 0;
|
||||
s = duplicate_handle(queue, process, SYS_HANDLE_RIGHT_WRITE, SYS_DUPLICATE_HANDLE_FLAG_NONE, &writeOnly);
|
||||
if (s != STATUS_SUCCESS) fail_status("duplicate write-only", s);
|
||||
|
||||
uint32_t sameRights = 0;
|
||||
s = duplicate_handle(queue, process, 0, SYS_DUPLICATE_HANDLE_FLAG_SAME_RIGHTS, &sameRights);
|
||||
if (s != STATUS_SUCCESS) fail_status("duplicate same rights", s);
|
||||
|
||||
s = send_message(readOnly, 10, 100);
|
||||
if (s == STATUS_SUCCESS) fail("read-only duplicate allowed send");
|
||||
|
||||
TEST_QUEUE_MESSAGE msg;
|
||||
s = recv_message(writeOnly, &msg);
|
||||
if (s == STATUS_SUCCESS) fail("write-only duplicate allowed receive");
|
||||
|
||||
s = send_message(queue, 11, 101);
|
||||
if (s != STATUS_SUCCESS) fail_status("send original", s);
|
||||
s = recv_message(readOnly, &msg);
|
||||
if (s != STATUS_SUCCESS) fail_status("receive read-only", s);
|
||||
check_message(&msg, 11, 101);
|
||||
|
||||
s = send_message(writeOnly, 12, 102);
|
||||
if (s != STATUS_SUCCESS) fail_status("send write-only", s);
|
||||
s = recv_message(queue, &msg);
|
||||
if (s != STATUS_SUCCESS) fail_status("receive original", s);
|
||||
check_message(&msg, 12, 102);
|
||||
|
||||
s = send_message(sameRights, 13, 103);
|
||||
if (s != STATUS_SUCCESS) fail_status("send same-rights", s);
|
||||
s = recv_message(sameRights, &msg);
|
||||
if (s != STATUS_SUCCESS) fail_status("receive same-rights", s);
|
||||
check_message(&msg, 13, 103);
|
||||
|
||||
uint32_t ignored = 0;
|
||||
s = duplicate_handle(readOnly, process, SYS_HANDLE_RIGHT_READ, SYS_DUPLICATE_HANDLE_FLAG_NONE, &ignored);
|
||||
expect_status("duplicate non-duplicable handle", s, STATUS_ACCESS_DENIED);
|
||||
|
||||
s = duplicate_handle(queue, process, SYS_HANDLE_RIGHT_READ | 0x80000000u, SYS_DUPLICATE_HANDLE_FLAG_NONE, &ignored);
|
||||
expect_status("duplicate unknown rights", s, STATUS_INVALID_PARAMETER);
|
||||
|
||||
s = duplicate_handle(queue, process, SYS_HANDLE_RIGHT_READ, SYS_DUPLICATE_HANDLE_FLAG_SAME_RIGHTS, &ignored);
|
||||
expect_status("duplicate same-rights with desired rights", s, STATUS_INVALID_PARAMETER);
|
||||
|
||||
s = duplicate_handle(queue, process, 0, SYS_DUPLICATE_HANDLE_FLAG_NONE, &ignored);
|
||||
expect_status("duplicate zero rights", s, STATUS_INVALID_PARAMETER);
|
||||
|
||||
SYS_DUPLICATE_HANDLE_REQUEST badOut = {
|
||||
queue,
|
||||
process,
|
||||
SYS_HANDLE_RIGHT_READ,
|
||||
SYS_DUPLICATE_HANDLE_FLAG_NONE,
|
||||
0,
|
||||
};
|
||||
s = SysDuplicateHandle(&badOut);
|
||||
expect_status("duplicate null output", s, STATUS_INVALID_PARAMETER);
|
||||
|
||||
SysCloseHandle(sameRights);
|
||||
SysCloseHandle(writeOnly);
|
||||
SysCloseHandle(readOnly);
|
||||
SysCloseHandle(queue);
|
||||
SysCloseHandle(process);
|
||||
|
||||
print("handle_dup_smoke: PASS\n");
|
||||
exit_now(0);
|
||||
return 0;
|
||||
}
|
||||
Reference in new issue
Block a user