summaryrefslogtreecommitdiffhomepage
path: root/dev/ddk/src
diff options
context:
space:
mode:
authorAmlal El Mahrouss <amlal@nekernel.org>2025-03-27 17:24:21 +0100
committerAmlal El Mahrouss <amlal@nekernel.org>2025-03-27 17:24:21 +0100
commitb8f7ef086d1d1b1cd686fff04d0a587f8fd39d81 (patch)
treeb6c2eb3ca2c51dc87ddd81b6170d5f63eabb9090 /dev/ddk/src
parenteb86df50ec5afb392998e2e171de54e1f26d8e7a (diff)
add: new driver device kit API. (DDK)
refactor: rename SCIKit -> user (then libuser.dylib) boot/modules/netboot: fixed compilation for amd64. Signed-off-by: Amlal El Mahrouss <amlal@nekernel.org>
Diffstat (limited to 'dev/ddk/src')
-rw-r--r--dev/ddk/src/ddk_alloc.c36
-rw-r--r--dev/ddk/src/ddk_dev.c30
-rw-r--r--dev/ddk/src/ddk_io.c37
-rw-r--r--dev/ddk/src/ddk_kernel_call.c60
-rw-r--r--dev/ddk/src/ddk_kernel_call_dispatch.S36
-rw-r--r--dev/ddk/src/ddk_rt_cxx.cc29
-rw-r--r--dev/ddk/src/ddk_str.c40
-rw-r--r--dev/ddk/src/ddk_ver.c25
8 files changed, 293 insertions, 0 deletions
diff --git a/dev/ddk/src/ddk_alloc.c b/dev/ddk/src/ddk_alloc.c
new file mode 100644
index 00000000..9d0ac0db
--- /dev/null
+++ b/dev/ddk/src/ddk_alloc.c
@@ -0,0 +1,36 @@
+/* -------------------------------------------
+
+ Copyright Amlal EL Mahrouss.
+
+ Purpose: DDK allocator.
+
+------------------------------------------- */
+
+#include <ddk/ddk.h>
+
+/**
+ \brief Allocates a new heap on the Kernel's side.
+ \param sz the size of the heap block.
+ \return the newly allocated pointer.
+*/
+DDK_EXTERN void* kalloc(size_t sz)
+{
+ if (!sz)
+ ++sz;
+
+ void* ptr = ke_call("mm_new_heap", 1, &sz, sizeof(size_t));
+
+ return ptr;
+}
+
+/**
+ \brief Frees a pointer from the heap.
+ \param ptr the pointer to free.
+*/
+DDK_EXTERN void kfree(void* ptr)
+{
+ if (!ptr)
+ return;
+
+ ke_call("mm_delete_heap", 1, ptr, 0);
+}
diff --git a/dev/ddk/src/ddk_dev.c b/dev/ddk/src/ddk_dev.c
new file mode 100644
index 00000000..7514bf84
--- /dev/null
+++ b/dev/ddk/src/ddk_dev.c
@@ -0,0 +1,30 @@
+/* -------------------------------------------
+
+ Copyright Amlal EL Mahrouss.
+
+ Purpose: DDK Text I/O.
+
+------------------------------------------- */
+
+#include <ddk/dev.h>
+#include <ddk/str.h>
+
+/// @brief Open a new binary device from path.
+DDK_EXTERN DDK_DEVICE_PTR open(const char* devicePath)
+{
+ if (!devicePath)
+ return nil;
+
+ return ke_call("sk_open_dev", 1, (void*)devicePath, kstrlen(devicePath));
+}
+
+/// @brief Close any device.
+/// @param device valid device.
+DDK_EXTERN BOOL close(DDK_DEVICE_PTR device)
+{
+ if (!device)
+ return NO;
+
+ ke_call("sk_close_dev", 1, device, sizeof(DDK_DEVICE));
+ return YES;
+}
diff --git a/dev/ddk/src/ddk_io.c b/dev/ddk/src/ddk_io.c
new file mode 100644
index 00000000..0e10a0ad
--- /dev/null
+++ b/dev/ddk/src/ddk_io.c
@@ -0,0 +1,37 @@
+/* -------------------------------------------
+
+ Copyright Amlal EL Mahrouss.
+
+ Purpose: DDK Text I/O.
+
+------------------------------------------- */
+
+#include <ddk/io.h>
+
+DDK_EXTERN void kputc(const char ch)
+{
+ char assembled[2] = {0};
+ assembled[0] = ch;
+ assembled[1] = 0;
+
+ ke_call("ke_put_string", 1, assembled, 1);
+}
+
+/// @brief print string to UART.
+/// @param message UART to transmit.
+DDK_EXTERN void kprint(const char* message)
+{
+ if (!message)
+ return;
+ if (*message == 0)
+ return;
+
+ size_t index = 0;
+ size_t len = kstrlen(message);
+
+ while (index < len)
+ {
+ kputc(message[index]);
+ ++index;
+ }
+}
diff --git a/dev/ddk/src/ddk_kernel_call.c b/dev/ddk/src/ddk_kernel_call.c
new file mode 100644
index 00000000..71dbebeb
--- /dev/null
+++ b/dev/ddk/src/ddk_kernel_call.c
@@ -0,0 +1,60 @@
+/* -------------------------------------------
+
+ Copyright Amlal EL Mahrouss.
+
+ Purpose: DDK Kernel call.
+
+------------------------------------------- */
+
+#include <ddk/ddk.h>
+#include <stdarg.h>
+
+/// @brief this is an internal call, do not use it.
+DDK_EXTERN ATTRIBUTE(naked) void* ke_call_dispatch(const char* name, int32_t cnt, void* data, size_t sz);
+
+/// @brief Interupt Kernel and call it's RPC.
+/// @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)
+DDK_EXTERN void* ke_call(const char* name, int32_t cnt, void* data, size_t sz)
+{
+ if (!name || *name == 0 || cnt == 0)
+ return nil;
+
+ return ke_call_dispatch(name, cnt, data, sz);
+}
+
+/// @brief Add system call.
+/// @param slot system call slot
+/// @param slotFn, syscall slot.
+DDK_EXTERN void ke_add_syscall(const int slot, void (*slotFn)(void* a0))
+{
+ ke_call("ke_add_syscall", slot, slotFn, 1);
+}
+
+/// @brief Get a Kernel object.
+/// @param slot property id (always 0)
+/// @param name the object's name.
+/// @return Object manifest.
+DDK_EXTERN struct DDK_OBJECT_MANIFEST* ke_get_obj(const int slot, const char* name)
+{
+ struct DDK_OBJECT_MANIFEST* manifest = (struct DDK_OBJECT_MANIFEST*)ke_call("cf_get_kobj", slot, (void*)name, 1);
+
+ if (!manifest)
+ return nil;
+
+ return manifest;
+}
+
+/// @brief Set a Kernel object.
+/// @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.
+DDK_EXTERN void* ke_set_obj(const int slot, const struct DDK_OBJECT_MANIFEST* ddk_pr)
+{
+ return ke_call("cf_set_kobj", slot, (void*)ddk_pr, 1);
+}
diff --git a/dev/ddk/src/ddk_kernel_call_dispatch.S b/dev/ddk/src/ddk_kernel_call_dispatch.S
new file mode 100644
index 00000000..9b32d0c2
--- /dev/null
+++ b/dev/ddk/src/ddk_kernel_call_dispatch.S
@@ -0,0 +1,36 @@
+/**
+ lang: asm
+ compiler: gnu
+ */
+
+.globl ke_call_dispatch
+
+.text
+
+/* Really simple function, takes our va-list,
+ and brings it to the trap handler in the Kernel. */
+
+#if defined(__DDK_AMD64__)
+
+/* args rcx, rdx, r8, r9 */
+ke_call_dispatch:
+ int $0x33
+ ret
+
+#elif defined(__DDK_POWER64__)
+
+/* args r8, r9, r10, r11 */
+ke_call_dispatch:
+ /* 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 */
+ke_call_dispatch:
+ /* 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/src/ddk_rt_cxx.cc b/dev/ddk/src/ddk_rt_cxx.cc
new file mode 100644
index 00000000..1ac66457
--- /dev/null
+++ b/dev/ddk/src/ddk_rt_cxx.cc
@@ -0,0 +1,29 @@
+/* -------------------------------------------
+
+ Copyright Amlal EL Mahrouss.
+
+ Purpose: DDK C++ runtime.
+
+------------------------------------------- */
+
+#include <ddk/ddk.h>
+
+void* operator new(size_t sz)
+{
+ return kalloc(sz);
+}
+
+void operator delete(void* ptr)
+{
+ kfree(ptr);
+}
+
+void* operator new[](size_t sz)
+{
+ return kalloc(sz);
+}
+
+void operator delete[](void* ptr)
+{
+ kfree(ptr);
+}
diff --git a/dev/ddk/src/ddk_str.c b/dev/ddk/src/ddk_str.c
new file mode 100644
index 00000000..1558e636
--- /dev/null
+++ b/dev/ddk/src/ddk_str.c
@@ -0,0 +1,40 @@
+/* -------------------------------------------
+
+ Copyright Amlal EL Mahrouss.
+
+ Purpose: DDK Strings.
+
+------------------------------------------- */
+
+#include <ddk/str.h>
+
+DDK_EXTERN size_t kstrlen(const char* in)
+{
+ if (in == nil)
+ return 0;
+
+ if (*in == 0)
+ return 0;
+
+ size_t index = 0;
+
+ while (in[index] != 0)
+ {
+ ++index;
+ }
+
+ return index;
+}
+
+DDK_EXTERN int kstrncpy(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/src/ddk_ver.c b/dev/ddk/src/ddk_ver.c
new file mode 100644
index 00000000..9641fb34
--- /dev/null
+++ b/dev/ddk/src/ddk_ver.c
@@ -0,0 +1,25 @@
+/* -------------------------------------------
+
+ Copyright Amlal EL Mahrouss.
+
+ Purpose: DDK version symbols.
+
+------------------------------------------- */
+
+#include <ddk/ddk.h>
+
+#ifndef kDDKVersionHighest
+#define kDDKVersionHighest 1
+#endif // !kDDKVersionHighest
+
+#ifndef kDDKVersionLowest
+#define kDDKVersionLowest 1
+#endif // !kDDKVersionLowest
+
+#ifndef kDDKVersion
+#define kDDKVersion 1
+#endif // !kDDKVersion
+
+int32_t kApiVersionHighest = kDDKVersionHighest;
+int32_t kApiVersionLowest = kDDKVersionLowest;
+int32_t kApiVersion = kDDKVersion;