diff options
| author | Amlal <amlal@el-mahrouss-logic.com> | 2024-09-22 17:46:11 +0200 |
|---|---|---|
| committer | Amlal <amlal@el-mahrouss-logic.com> | 2024-09-22 17:46:11 +0200 |
| commit | 8719b4570a2d10dd49a0d3a47e24f5c55bdda85e (patch) | |
| tree | ba095740888f3768e08b2ea058b0ea6da2d0403d /dev/ddk | |
| parent | 45944b3d2dab04b763fcc6d10164fe8069e60b08 (diff) | |
:boom: A big refactor on the filesystem structure.
Signed-off-by: Amlal <amlal@el-mahrouss-logic.com>
Diffstat (limited to 'dev/ddk')
| -rw-r--r-- | dev/ddk/DispatchKernelCall.S | 36 | ||||
| -rw-r--r-- | dev/ddk/KernelAlloc.c | 36 | ||||
| -rw-r--r-- | dev/ddk/KernelCall.c | 60 | ||||
| -rw-r--r-- | dev/ddk/KernelCxxRt.cxx | 29 | ||||
| -rw-r--r-- | dev/ddk/KernelDev.c | 29 | ||||
| -rw-r--r-- | dev/ddk/KernelDev.h | 32 | ||||
| -rw-r--r-- | dev/ddk/KernelPrint.c | 37 | ||||
| -rw-r--r-- | dev/ddk/KernelPrint.h | 18 | ||||
| -rw-r--r-- | dev/ddk/KernelStd.h | 105 | ||||
| -rw-r--r-- | dev/ddk/KernelString.c | 39 | ||||
| -rw-r--r-- | dev/ddk/KernelString.h | 17 | ||||
| -rw-r--r-- | dev/ddk/KernelVersion.c | 25 | ||||
| -rw-r--r-- | dev/ddk/ReadMe.md | 9 | ||||
| -rw-r--r-- | dev/ddk/ddk.json | 24 | ||||
| -rw-r--r-- | dev/ddk/source_deploy.xml | 7 | ||||
| -rw-r--r-- | dev/ddk/x86_64.make | 14 |
16 files changed, 517 insertions, 0 deletions
diff --git a/dev/ddk/DispatchKernelCall.S b/dev/ddk/DispatchKernelCall.S new file mode 100644 index 00000000..3a9a57b5 --- /dev/null +++ b/dev/ddk/DispatchKernelCall.S @@ -0,0 +1,36 @@ +/** + lang: asm + compiler: gnu + */ + +.globl __KernelCallDispatch + +.text + +/* Really simple function, takes our va-list, + and brings it to the trap handler in the Kernel. */ + +#ifdef __DDK_AMD64__ + +/* args rcx, rdx, r8, r9 */ +__KernelCallDispatch: + int $0x33 + ret + +#elif defined(__DDK_POWER64__) + +/* args r8, r9, r10, r11 */ +__KernelCallDispatch: + /* There is no specific interrupt request id for a system call in POWER. */ + sc + blr + +#elif defined(__DDK_ARM64__) + +/* args x0, x8, x9, x10, x11 is kept to tell that this is a Kernel call */ +__KernelCallDispatch: + /* There is no specific interrupt request id for a system call in ARM64 as well. */ + mov x9, #0x33 + svc #0 + +#endif diff --git a/dev/ddk/KernelAlloc.c b/dev/ddk/KernelAlloc.c new file mode 100644 index 00000000..af99f23b --- /dev/null +++ b/dev/ddk/KernelAlloc.c @@ -0,0 +1,36 @@ +/* ------------------------------------------- + + Copyright ZKA Technologies. + + Purpose: DDK allocator. + +------------------------------------------- */ + +#include <ddk/KernelStd.h> + +/** + \brief Allocates a new heap on the Kernel's side. + \param sz the size of the heap block. + \return the newly allocated pointer. +*/ +DK_EXTERN void* KernelAlloc(size_t sz) +{ + if (!sz) + ++sz; + + void* ptr = KernelCall("MmNewKeHeap", 1, &sz, sizeof(size_t)); + + return ptr; +} + +/** + \brief Frees a pointer from the heap. + \param ptr the pointer to free. +*/ +DK_EXTERN void KernelFree(void* ptr) +{ + if (!ptr) + return; + + KernelCall("MmDeleteKeHeap", 1, ptr, 0); +} diff --git a/dev/ddk/KernelCall.c b/dev/ddk/KernelCall.c new file mode 100644 index 00000000..ccb401af --- /dev/null +++ b/dev/ddk/KernelCall.c @@ -0,0 +1,60 @@ +/* ------------------------------------------- + + Copyright ZKA Technologies. + + Purpose: DDK Kernel call. + +------------------------------------------- */ + +#include <ddk/KernelStd.h> +#include <stdarg.h> + +/// @brief this is an internal call, do not use it. +DK_EXTERN ATTRIBUTE(naked) void* __KernelCallDispatch(const char* name, int32_t cnt, void* data, size_t sz); + +/// @brief Interupt Kernel +/// @param KernelRpcName RPC name +/// @param cnt number of elements in **data** pointer. +/// @param data data pointer. +/// @param sz The size of the whole data pointer. +/// @retval void* Kernel call was successful. +/// @retval nil Kernel call failed, call KernelLastError(void) +DK_EXTERN void* KernelCall(const char* name, int32_t cnt, void* data, size_t sz) +{ + if (!name || *name == 0 || cnt == 0) + return nil; + + return __KernelCallDispatch(name, cnt, data, sz); +} + +/// @brief Add system call. +/// @param slot system call slot +/// @param slotFn, syscall slot. +DK_EXTERN void KernelAddSyscall(const int slot, void (*slotFn)(void* a0)) +{ + KernelCall("IntAddSyscall", slot, slotFn, 1); +} + +/// @brief Get a Kernel property. +/// @param slot property id (always 0) +/// @param name the object's name. +/// @return Object manifest. +DK_EXTERN struct DDK_OBJECT_MANIFEST* KernelGetObject(const int slot, const char* name) +{ + struct DDK_OBJECT_MANIFEST* manifest = (struct DDK_OBJECT_MANIFEST*)KernelCall("RtlGetObject", slot, (void*)name, 1); + + if (!manifest) + return nil; + + return manifest; +} + +/// @brief Set a Kernel property. +/// @param slot property id (always 0) +/// @param name the object's name. +/// @param ddk_pr pointer to a object's DDK_OBJECT_MANIFEST. +/// @return property's object. +DK_EXTERN void* KernelSetObject(const int slot, const struct DDK_OBJECT_MANIFEST* ddk_pr) +{ + return KernelCall("RtlSetObject", slot, (void*)ddk_pr, 1); +} diff --git a/dev/ddk/KernelCxxRt.cxx b/dev/ddk/KernelCxxRt.cxx new file mode 100644 index 00000000..947e2de7 --- /dev/null +++ b/dev/ddk/KernelCxxRt.cxx @@ -0,0 +1,29 @@ +/* ------------------------------------------- + + Copyright ZKA Technologies. + + Purpose: DDK C++ runtime. + +------------------------------------------- */ + +#include <ddk/KernelStd.h> + +void* operator new(size_t sz) +{ + return KernelAlloc(sz); +} + +void operator delete(void* ptr) +{ + KernelFree(ptr); +} + +void* operator new[](size_t sz) +{ + return KernelAlloc(sz); +} + +void operator delete[](void* ptr) +{ + KernelFree(ptr); +} diff --git a/dev/ddk/KernelDev.c b/dev/ddk/KernelDev.c new file mode 100644 index 00000000..3cf7ed48 --- /dev/null +++ b/dev/ddk/KernelDev.c @@ -0,0 +1,29 @@ +/* ------------------------------------------- + + Copyright ZKA Technologies. + + Purpose: DDK Text I/O. + +------------------------------------------- */ + +#include <ddk/KernelDev.h> +#include <ddk/KernelString.h> + +/// @brief Open a new binary device from path. +DK_EXTERN KERNEL_DEVICE_PTR KernelOpenDevice(const char* devicePath) +{ + if (!devicePath) + return nil; + + return KernelCall("ZkOpenDevice", 1, (void*)devicePath, KernelStringLength(devicePath)); +} + +/// @brief Close any device. +/// @param device valid device. +DK_EXTERN void KernelCloseDevice(KERNEL_DEVICE_PTR device) +{ + if (!device) + return; + + KernelCall("ZkCloseDevice", 1, device, sizeof(KERNEL_DEVICE)); +} diff --git a/dev/ddk/KernelDev.h b/dev/ddk/KernelDev.h new file mode 100644 index 00000000..b7dce834 --- /dev/null +++ b/dev/ddk/KernelDev.h @@ -0,0 +1,32 @@ +/* ------------------------------------------- + + Copyright ZKA Technologies. + + Purpose: DDK Devices. + +------------------------------------------- */ + +#pragma once + +#include <ddk/KernelStd.h> + +struct _KERNEL_DEVICE; + +/// @brief Kernel Device driver. +typedef struct _KERNEL_DEVICE DK_FINAL +{ + char d_name[255]; // the device name. Could be /./DEVICE_NAME/ + void* (*d_read)(void* arg, int len); // read from device. + void (*d_write)(void* arg, int len); + void (*d_wait)(void); // write to device. + struct _KERNEL_DEVICE* (*d_open)(const char* path); // open device. + void (*d_close)(struct _KERNEL_DEVICE* dev); // close device. +} KERNEL_DEVICE, *KERNEL_DEVICE_PTR; + +/// @brief Open a new device from path. +/// @param devicePath the device's path. +DK_EXTERN KERNEL_DEVICE_PTR KernelOpenDevice(const char* devicePath); + +/// @brief Close any device. +/// @param device valid device. +DK_EXTERN void KernelCloseDevice(KERNEL_DEVICE_PTR device); diff --git a/dev/ddk/KernelPrint.c b/dev/ddk/KernelPrint.c new file mode 100644 index 00000000..7f8c8604 --- /dev/null +++ b/dev/ddk/KernelPrint.c @@ -0,0 +1,37 @@ +/* ------------------------------------------- + + Copyright ZKA Technologies. + + Purpose: DDK Text I/O. + +------------------------------------------- */ + +#include <ddk/KernelPrint.h> + +DK_EXTERN void KernelPrintChar(const char ch) +{ + char assembled[2] = {0}; + assembled[0] = ch; + assembled[1] = 0; + + KernelCall("SrWriteCharacter", 1, assembled, 1); +} + +/// @brief print string to UART. +/// @param message UART to transmit. +DK_EXTERN void KernelPrintStr(const char* message) +{ + if (!message) + return; + if (*message == 0) + return; + + size_t index = 0; + size_t len = KernelStringLength(message); + + while (index < len) + { + KernelPrintChar(message[index]); + ++index; + } +} diff --git a/dev/ddk/KernelPrint.h b/dev/ddk/KernelPrint.h new file mode 100644 index 00000000..6ab6118e --- /dev/null +++ b/dev/ddk/KernelPrint.h @@ -0,0 +1,18 @@ +/* ------------------------------------------- + + Copyright ZKA Technologies. + + Purpose: DDK Text I/O. + +------------------------------------------- */ + +#pragma once + +#include <ddk/KernelString.h> + +/// @brief print character into UART. +DK_EXTERN void KernelPrintChar(const char ch); + +/// @brief print string to UART. +/// @param message string to transmit to UART. +DK_EXTERN void KernelPrintStr(const char* message); diff --git a/dev/ddk/KernelStd.h b/dev/ddk/KernelStd.h new file mode 100644 index 00000000..89fe786d --- /dev/null +++ b/dev/ddk/KernelStd.h @@ -0,0 +1,105 @@ +/* ------------------------------------------- + + Copyright ZKA Technologies. + + FILE: KernelStd.h + PURPOSE: DDK Driver model base header. + +------------------------------------------- */ + +#pragma once + +#include <stdint.h> +#include <stddef.h> + +#if defined(__cplusplus) +#define DK_EXTERN extern "C" __declspec(dllexport) +#define nil nullptr +#undef NULL +#define NULL 0 +#define DK_FINAL final +#else +#define DK_EXTERN extern __declspec(dllexport) +#define nil ((void*)0) +#undef NULL +#define NULL ((void*)0) +#define DK_FINAL +#endif // defined(__cplusplus) + +#ifndef __DDK__ +#undef DK_EXTERN +#if defined(__cplusplus) +#define DK_EXTERN extern "C" __declspec(dllimport) +#else +#define DK_EXTERN __declspec(dllimport) +#endif +#endif + +#define ATTRIBUTE(X) __attribute__((X)) + +#ifndef __NEWOSKRNL__ +#error !!! including header in low exception/ring-3 mode !!! +#endif // __NEWOSKRNL__ + +struct DDK_STATUS_STRUCT; +struct DDK_OBJECT_MANIFEST; + +struct DDK_OBJECT_MANIFEST DK_FINAL +{ + char* p_name; + int32_t p_kind; + void* p_object; +}; + +/// \brief DDK status structure (__at_enable, __at_disable...) +struct DDK_STATUS_STRUCT DK_FINAL +{ + int32_t s_action_id; + int32_t s_issuer_id; + int32_t s_group_id; + void* s_object; +}; + +/// @brief Call Kernel (interrupt 0x33) +/// @param KernelRpcName +/// @param cnt number of elements in **dat** +/// @param dat data ptr +/// @param sz sz of whole data ptr. +/// @return result of call +DK_EXTERN void* KernelCall(const char* name, int32_t cnt, void* dat, size_t sz); + +/// @brief add system call. +/// @param slot system call slot +/// @param slotFn, syscall slot. +DK_EXTERN void KernelAddSyscall(const int32_t slot, void (*slotFn)(void* a0)); + +/// @brief allocate heap ptr. +/// @param sz size of ptr. +/// @return the pointer allocated or **nil**. +DK_EXTERN void* KernelAlloc(size_t sz); + +/// @brief free heap ptr. +/// @param pointer to free +DK_EXTERN void KernelFree(void*); + +/// @brief Get a Kernel property. +/// @param slot property id (always 0) +/// @param name the property's name. +/// @return property's object. +DK_EXTERN struct DDK_OBJECT_MANIFEST* KernelGetObject(const int slot, const char* name); + +/// @brief Set a Kernel property. +/// @param slot property id (always 0) +/// @param name the property's name. +/// @param ddk_pr pointer to a property's DDK_OBJECT_MANIFEST. +/// @return property's object. +DK_EXTERN void* KernelSetObject(const int32_t slot, const struct DDK_OBJECT_MANIFEST* ddk_pr); + +/// @brief The highest API version of the DDK. +DK_EXTERN int32_t c_api_version_highest; + +/// @brief The lowest API version of the DDK. +DK_EXTERN int32_t c_api_version_least; + +/// @brief c_api_version_least+c_api_version_highest combined version. +DK_EXTERN int32_t c_api_version; diff --git a/dev/ddk/KernelString.c b/dev/ddk/KernelString.c new file mode 100644 index 00000000..0030aa02 --- /dev/null +++ b/dev/ddk/KernelString.c @@ -0,0 +1,39 @@ +/* ------------------------------------------- + + Copyright ZKA Technologies. + + Purpose: DDK Strings. + +------------------------------------------- */ + +#include <ddk/KernelString.h> + +DK_EXTERN size_t KernelStringLength(const char* in) +{ + if (in == nil) + return 0; + if (*in == 0) + return 0; + + size_t index = 0; + + while (in[index] != 0) + { + ++index; + } + + return index; +} + +DK_EXTERN int KernelStringCopy(char* dst, const char* src, size_t len) +{ + size_t index = 0; + + while (index != len) + { + dst[index] = src[index]; + ++index; + } + + return index; +} diff --git a/dev/ddk/KernelString.h b/dev/ddk/KernelString.h new file mode 100644 index 00000000..01d7d919 --- /dev/null +++ b/dev/ddk/KernelString.h @@ -0,0 +1,17 @@ +/* ------------------------------------------- + + Copyright ZKA Technologies. + + Purpose: DDK Strings. + +------------------------------------------- */ + +#pragma once + +#include <ddk/KernelStd.h> + +/// @brief DDK equivalent of POSIX's string.h +/// @file KernelString.h + +DK_EXTERN size_t KernelStringLength(const char* in); +DK_EXTERN int KernelStringCopy(char* dst, const char* src, size_t len); diff --git a/dev/ddk/KernelVersion.c b/dev/ddk/KernelVersion.c new file mode 100644 index 00000000..c40e8ff9 --- /dev/null +++ b/dev/ddk/KernelVersion.c @@ -0,0 +1,25 @@ +/* -------------------------------------------
+
+ Copyright ZKA Technologies.
+
+ Purpose: DDK versioning.
+
+------------------------------------------- */
+
+#include <KernelStd.h>
+
+#ifndef cDDKVersionHighest
+#define cDDKVersionHighest 1
+#endif // !cDDKVersionHighest
+
+#ifndef cDDKVersionLowest
+#define cDDKVersionLowest 1
+#endif // !cDDKVersionLowest
+
+#ifndef cDDKVersion
+#define cDDKVersion 1
+#endif // !cDDKVersion
+
+int32_t c_api_version_highest = cDDKVersionHighest;
+int32_t c_api_version_least = cDDKVersionLowest;
+int32_t c_api_version = cDDKVersion;
diff --git a/dev/ddk/ReadMe.md b/dev/ddk/ReadMe.md new file mode 100644 index 00000000..48e35ef2 --- /dev/null +++ b/dev/ddk/ReadMe.md @@ -0,0 +1,9 @@ +# ZKA's Device Driver Kit. + +A kit used to write Kernel HALs, using the NDK compiler suite. + +## How to use it + +Simply link against ddk.dll. + +###### Copyright 2024 ZKA Technologies, all rights reserved. diff --git a/dev/ddk/ddk.json b/dev/ddk/ddk.json new file mode 100644 index 00000000..b930f99c --- /dev/null +++ b/dev/ddk/ddk.json @@ -0,0 +1,24 @@ +{ + "compiler_path": "x86_64-w64-mingw32-gcc", + "compiler_std": "c++20", + "headers_path": ["../", "./"], + "sources_path": ["*.c", "*.cxx", "*.S"], + "output_name": "ddk.dll", + "compiler_flags": [ + "-ffreestanding", + "-shared", + "-std=c17", + "-std=c++20", + "-fno-rtti", + "-fno-exceptions", + " -Wl,--subsystem=17" + ], + "cpp_macros": [ + "__NEWOSKRNL__", + "__DDK_AMD64__", + "__DDK__", + "cDDKVersionHighest=0x0100", + "cDDKVersionLowest=0x0100", + "cDDKVersion=0x0100" + ] +} diff --git a/dev/ddk/source_deploy.xml b/dev/ddk/source_deploy.xml new file mode 100644 index 00000000..3d2325a8 --- /dev/null +++ b/dev/ddk/source_deploy.xml @@ -0,0 +1,7 @@ +<SourceDeploy>
+<HiddenFiles>
+ <SourceFile>*.cxx</SourceFile>
+ <SourceFile>*.c</SourceFile>
+ <SourceFile>*.S</SourceFile>
+</HiddenFiles>
+</SourceDeploy>
diff --git a/dev/ddk/x86_64.make b/dev/ddk/x86_64.make new file mode 100644 index 00000000..f1f7bb4b --- /dev/null +++ b/dev/ddk/x86_64.make @@ -0,0 +1,14 @@ +##################################################
+# (C) ZKA Technologies, all rights reserved.
+# This is the DDK's makefile.
+##################################################
+
+CC=x86_64-w64-mingw32-gcc
+INC=-I./ -I../
+FLAGS=-ffreestanding -shared -std=c17 -std=c++20 -D__NEWOSKRNL__ -fno-rtti -fno-exceptions -D__DDK_AMD64__ -Wl,--subsystem=17
+VERSION=-DcDDKVersionLowest=1 -DcDDKVersionHighest=1
+OUTPUT=ddk.dll
+
+.PHONY: x86_64-build
+x86_64-build:
+ $(CC) $(INC) $(FLAGS) $(VERSION) $(wildcard *.c) $(wildcard *.S) $(wildcard *.cxx) -o $(OUTPUT)
\ No newline at end of file |
