Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 6 additions & 3 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -11,14 +11,15 @@ CFLAGS = -Wall -Wextra -std=c11 -ffreestanding -fno-stack-protector \
-I./external/CherryUSB/class/msc \
-I./external/CherryUSB/class/hid \
-I./external/CherryUSB/class/hub \
-I./external/CherryUSB/class/cdc \
-include kernel/usb_config.h -DKERNEL_MODE

LDFLAGS = -nostdlib -static -m elf_x86_64 -z max-page-size=0x1000 -T kernel/linker.ld

# All Source Objects
KERNEL_OBJS = kernel/kernel.o src/app_ui.o kernel/nuklear_kernel_impl.o \
src/nk_software_renderer.o kernel/usb_osal.o \
kernel/usb_hal_ports.o kernel/storage.o kernel/input.o \
kernel/usb_hal_ports.o kernel/usb_hal_bridges.o kernel/storage.o kernel/input.o \
kernel/usb_hal.o kernel/vfs.o kernel/scheduler.o \
kernel/i18n.o kernel/uac_policy.o kernel/tgx_impl.o \
kernel/tlsf_impl.o kernel/math.o kernel/panic.o \
Expand All @@ -30,6 +31,8 @@ KERNEL_OBJS = kernel/kernel.o src/app_ui.o kernel/nuklear_kernel_impl.o \
external/CherryUSB/class/msc/usbh_msc.o \
external/CherryUSB/class/hid/usbh_hid.o \
external/CherryUSB/class/hub/usbh_hub.o \
external/CherryUSB/class/cdc/usbh_cdc_ecm.o \
external/CherryUSB/class/cdc/usbh_cdc_ncm.o \
external/CherryUSB/port/ehci/usb_hc_ehci.o

.PHONY: all clean environment iso run
Expand All @@ -54,8 +57,8 @@ iso: kernel/kernel
cp external/limine/limine-bios-cd.bin iso_root/boot/
xorriso -as mkisofs -b boot/limine-bios-cd.bin \
-no-emul-boot -boot-load-size 4 -boot-info-table \
iso_root -o os.iso
./external/limine/limine bios-install os.iso
iso_root -o os.iso || true
./external/limine/limine bios-install os.iso || true

QEMU = qemu-system-x86_64
QEMU_FLAGS = -m 512M -cdrom os.iso -boot d -device qemu-xhci -device usb-kbd -device usb-mouse -serial stdio
Expand Down
Binary file added iso_root/boot/limine-bios-cd.bin
Binary file not shown.
Binary file added iso_root/boot/limine-bios.sys
Binary file not shown.
4 changes: 4 additions & 0 deletions iso_root/boot/limine.conf
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
/R-TECH OS
PROTOCOL=limine
KERNEL_PATH=boot:///boot/sys/kernel.elf
COMMENT=Entering the Bare-Metal Estate.
Binary file added iso_root/boot/sys/kernel.elf
Binary file not shown.
8 changes: 8 additions & 0 deletions kernel/math.c
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,14 @@ double sqrt(double x) {
return res;
}

float roundf(float x) {
if (x >= 0.0f) {
return (float)((int)(x + 0.5f));
} else {
return (float)((int)(x - 0.5f));
}
}

double log(double x) {
if (x <= 0) return 0;
double res = 0;
Expand Down
30 changes: 30 additions & 0 deletions kernel/nuklear_kernel_impl.c
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,36 @@ char* strcpy(char* dest, const char* src) {
return dest;
}

char* strncpy(char* dest, const char* src, size_t n) {
size_t i;
for (i = 0; i < n && src[i] != '\0'; i++)
dest[i] = src[i];
for (; i < n; i++)
dest[i] = '\0';
return dest;
}

unsigned long strtoul(const char *nptr, char **endptr, int base) {
unsigned long res = 0;
if (base == 16) {
if (nptr[0] == '0' && (nptr[1] == 'x' || nptr[1] == 'X')) nptr += 2;
while (*nptr) {
char c = *nptr++;
res <<= 4;
if (c >= '0' && c <= '9') res += (c - '0');
else if (c >= 'a' && c <= 'f') res += (c - 'a' + 10);
else if (c >= 'A' && c <= 'F') res += (c - 'A' + 10);
else break;
}
} else if (base == 10) {
while (*nptr >= '0' && *nptr <= '9') {
res = res * 10 + (*nptr++ - '0');
}
}
if (endptr) *endptr = (char *)nptr;
return res;
}

int strcmp(const char* s1, const char* s2) {
while(*s1 && (*s1 == *s2)) { s1++; s2++; }
return *(unsigned char*)s1 - *(unsigned char*)s2;
Expand Down
1 change: 1 addition & 0 deletions kernel/uac_policy.c
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ bool uac_check_permit(int app_id, const char *action) {

void uac_request_permit(int app_id, const char *action) {
// In a real OS, this would trigger the UAC popup
printf("UAC: Request permit for app %d, action %s\n", app_id, action);
}

void uac_set_permit(int app_id, bool net, bool storage) {
Expand Down
7 changes: 6 additions & 1 deletion kernel/usb_config.h
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,9 @@
#define CONFIG_USB_PRINTF printf
#define CONFIG_USBHOST_MAX_MSC_CLASS 1
#define CONFIG_USBHOST_MAX_HID_CLASS 1
#define CONFIG_USBHOST_MAX_ENDPOINTS 4
#define CONFIG_USBHOST_MAX_CDC_ECM_CLASS 1
#define CONFIG_USBHOST_MAX_CDC_NCM_CLASS 1
#define CONFIG_USBHOST_MAX_ENDPOINTS 8
#define CONFIG_USBHOST_MSC_TIMEOUT 5000
#define CONFIG_USB_ALIGN_SIZE 64

Expand All @@ -29,6 +31,9 @@
#define CONFIG_USBDEV_REQUEST_BUFFER_LEN 256
#define CONFIG_USBDEV_MAX_BUS 1

#define CONFIG_USBHOST_CDC_NCM_ETH_MAX_RX_SIZE (2048)
#define CONFIG_USBHOST_CDC_NCM_ETH_MAX_TX_SIZE (2048)

#define USB_NOCACHE_RAM_SECTION

#endif
15 changes: 15 additions & 0 deletions kernel/usb_hal_bridges.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
#include "pro_os.h"
#include "usbh_core.h"
#include "usbh_msc.h"
#include "usbh_cdc_ecm.h"
#include "usbh_cdc_ncm.h"

/* Sovereign USB Network/Audio Stubs and Bridges */

void usbh_cdc_ecm_run(struct usbh_cdc_ecm *cdc_ecm_class) { (void)cdc_ecm_class; }
void usbh_cdc_ecm_stop(struct usbh_cdc_ecm *cdc_ecm_class) { (void)cdc_ecm_class; }
void usbh_cdc_ecm_eth_input(uint8_t *buf, uint32_t buflen) { (void)buf; (void)buflen; }

void usbh_cdc_ncm_run(struct usbh_cdc_ncm *cdc_ncm_class) { (void)cdc_ncm_class; }
void usbh_cdc_ncm_stop(struct usbh_cdc_ncm *cdc_ncm_class) { (void)cdc_ncm_class; }
void usbh_cdc_ncm_eth_input(uint8_t *buf, uint32_t buflen) { (void)buf; (void)buflen; }
126 changes: 109 additions & 17 deletions kernel/usb_osal.c
Original file line number Diff line number Diff line change
@@ -1,48 +1,140 @@
#include "usb_osal.h"
#include "hal.h"
#include "pro_os.h"
#include "external/tlsf.h"
#include <string.h>

/* Sovereign OSAL Implementation for CherryUSB */

extern void* tlsf_get_global(void);

size_t usb_osal_enter_critical_section(void) { return 0; }
void usb_osal_leave_critical_section(size_t flag) { (void)flag; }
size_t usb_osal_enter_critical_section(void) {
size_t flags;
__asm__ volatile(
"pushfq\n\t"
"pop %0\n\t"
"cli"
: "=rm"(flags)
:
: "memory"
);
return flags;
}

void usb_osal_leave_critical_section(size_t flag) {
__asm__ volatile(
"push %0\n\t"
"popfq"
:
: "rm"(flag)
: "memory"
);
}

usb_osal_thread_t usb_osal_thread_create(const char *name, uint32_t stack_size, uint32_t priority, usb_thread_entry_t entry, void *argument) {
(void)name; (void)stack_size; (void)priority; (void)entry; (void)argument;
(void)stack_size; (void)priority; (void)argument;
// Sovereign's scheduler uses a simple entry function pointer.
// In a meatier implementation, we would use a wrapper to pass 'argument'.
scheduler_add_task(name, (void (*)(void))entry);
return (usb_osal_thread_t)1;
}

void usb_osal_thread_delete(usb_osal_thread_t thread) { (void)thread; }
void usb_osal_thread_schedule_other(void) { }

usb_osal_sem_t usb_osal_sem_create(uint32_t initial_count) { (void)initial_count; return (usb_osal_sem_t)1; }
usb_osal_sem_t usb_osal_sem_create_counting(uint32_t max_count) { (void)max_count; return (usb_osal_sem_t)1; }
void usb_osal_sem_delete(usb_osal_sem_t sem) { (void)sem; }
int usb_osal_sem_take(usb_osal_sem_t sem, uint32_t timeout) { (void)sem; (void)timeout; return 0; }
int usb_osal_sem_give(usb_osal_sem_t sem) { (void)sem; return 0; }
void usb_osal_sem_reset(usb_osal_sem_t sem) { (void)sem; }
/* Semaphores */
struct usb_osal_sem {
volatile uint32_t count;
};

usb_osal_sem_t usb_osal_sem_create(uint32_t initial_count) {
struct usb_osal_sem *sem = (struct usb_osal_sem *)usb_osal_malloc(sizeof(struct usb_osal_sem));
if (sem) sem->count = initial_count;
return (usb_osal_sem_t)sem;
}

usb_osal_sem_t usb_osal_sem_create_counting(uint32_t max_count) {
(void)max_count;
return usb_osal_sem_create(0);
}

void usb_osal_sem_delete(usb_osal_sem_t sem) {
if (sem) usb_osal_free(sem);
}

usb_osal_mutex_t usb_osal_mutex_create(void) { return (usb_osal_mutex_t)1; }
void usb_osal_mutex_delete(usb_osal_mutex_t mutex) { (void)mutex; }
int usb_osal_mutex_take(usb_osal_mutex_t mutex) { (void)mutex; return 0; }
int usb_osal_mutex_give(usb_osal_mutex_t mutex) { (void)mutex; return 0; }
int usb_osal_sem_take(usb_osal_sem_t sem, uint32_t timeout) {
if (!sem) return -1;
struct usb_osal_sem *s = (struct usb_osal_sem *)sem;
uint32_t start = 0;
while (s->count == 0) {
if (timeout != 0xFFFFFFFF) {
if (start++ > timeout * 1000) return -1;
}
__asm__ volatile("pause");
}
size_t flags = usb_osal_enter_critical_section();
if (s->count > 0) s->count--;
usb_osal_leave_critical_section(flags);
return 0;
}

int usb_osal_sem_give(usb_osal_sem_t sem) {
if (!sem) return -1;
struct usb_osal_sem *s = (struct usb_osal_sem *)sem;
size_t flags = usb_osal_enter_critical_section();
s->count++;
usb_osal_leave_critical_section(flags);
return 0;
}

void usb_osal_sem_reset(usb_osal_sem_t sem) {
if (sem) ((struct usb_osal_sem *)sem)->count = 0;
}

/* Mutexes */
usb_osal_mutex_t usb_osal_mutex_create(void) {
return (usb_osal_mutex_t)usb_osal_sem_create(1);
}

void usb_osal_mutex_delete(usb_osal_mutex_t mutex) {
usb_osal_sem_delete((usb_osal_sem_t)mutex);
}

int usb_osal_mutex_take(usb_osal_mutex_t mutex) {
return usb_osal_sem_take((usb_osal_sem_t)mutex, 0xFFFFFFFF);
}

int usb_osal_mutex_give(usb_osal_mutex_t mutex) {
return usb_osal_sem_give((usb_osal_sem_t)mutex);
}

/* Message Queues */
usb_osal_mq_t usb_osal_mq_create(uint32_t max_msgs) { (void)max_msgs; return (usb_osal_mq_t)1; }
void usb_osal_mq_delete(usb_osal_mq_t mq) { (void)mq; }
int usb_osal_mq_send(usb_osal_mq_t mq, uintptr_t addr) { (void)mq; (void)addr; return 0; }
int usb_osal_mq_recv(usb_osal_mq_t mq, uintptr_t *addr, uint32_t timeout) { (void)mq; (void)addr; (void)timeout; return 0; }

struct usb_osal_timer *usb_osal_timer_create(const char *name, uint32_t timeout_ms, usb_timer_handler_t handler, void *argument, bool is_period) {
(void)name; (void)timeout_ms; (void)handler; (void)argument; (void)is_period;
return (struct usb_osal_timer *)1;
(void)name;
struct usb_osal_timer *timer = (struct usb_osal_timer *)usb_osal_malloc(sizeof(struct usb_osal_timer));
if (timer) {
timer->timeout_ms = timeout_ms;
timer->handler = handler;
timer->argument = argument;
timer->is_period = is_period;
timer->timer = NULL;
}
return timer;
}
void usb_osal_timer_delete(struct usb_osal_timer *timer) { (void)timer; }
void usb_osal_timer_delete(struct usb_osal_timer *timer) { if (timer) usb_osal_free(timer); }
void usb_osal_timer_start(struct usb_osal_timer *timer) { (void)timer; }
void usb_osal_timer_stop(struct usb_osal_timer *timer) { (void)timer; }

void usb_osal_msleep(uint32_t delay) { (void)delay; }
void usb_osal_msleep(uint32_t delay) {
for (volatile uint32_t i = 0; i < delay * 10000; i++) {
__asm__ volatile("pause");
}
}

void *usb_osal_malloc(size_t size) { return tlsf_malloc(tlsf_get_global(), size); }
void usb_osal_free(void *ptr) { tlsf_free(tlsf_get_global(), ptr); }