From d824b4610a2b08ff890802d34f684e9eca84604e Mon Sep 17 00:00:00 2001 From: boreddevnl Date: Mon, 16 Mar 2026 17:22:42 +0100 Subject: [PATCH] FIX: Replace blocking k_beep with an asynchronous k_beep --- src/core/kutils.c | 27 ++++++++++++++++++++++++--- src/core/kutils.h | 2 ++ src/dev/ps2.c | 3 +++ src/sys/syscall.c | 12 ++---------- 4 files changed, 31 insertions(+), 13 deletions(-) diff --git a/src/core/kutils.c b/src/core/kutils.c index 3878258..9d37534 100644 --- a/src/core/kutils.c +++ b/src/core/kutils.c @@ -113,14 +113,35 @@ void k_shutdown(void) { outw(0x4004, 0x3400); // VirtualBox fallback } +volatile uint64_t beep_end_tick = 0; +bool beep_active = false; + void k_beep(int freq, int ms) { - if (freq <= 0) return; + if (freq <= 0) { + outb(0x61, inb(0x61) & 0xFC); + beep_active = false; + return; + } int div = 1193180 / freq; outb(0x43, 0xB6); outb(0x42, div & 0xFF); outb(0x42, (div >> 8) & 0xFF); outb(0x61, inb(0x61) | 0x03); - k_sleep(ms); - outb(0x61, inb(0x61) & 0xFC); + + uint32_t ticks = ms / 16; + if (ticks == 0 && ms > 0) ticks = 1; + extern volatile uint64_t kernel_ticks; + beep_end_tick = kernel_ticks + ticks; + beep_active = true; +} + +void k_beep_process(void) { + if (beep_active) { + extern volatile uint64_t kernel_ticks; + if (kernel_ticks >= beep_end_tick) { + outb(0x61, inb(0x61) & 0xFC); + beep_active = false; + } + } } diff --git a/src/core/kutils.h b/src/core/kutils.h index ec0f342..24c50c0 100644 --- a/src/core/kutils.h +++ b/src/core/kutils.h @@ -6,6 +6,7 @@ #include #include +#include // Kernel string utilities void k_memset(void *dest, int val, size_t len); @@ -23,5 +24,6 @@ void k_sleep(int ms); void k_reboot(void); void k_shutdown(void); void k_beep(int freq, int ms); +void k_beep_process(void); #endif diff --git a/src/dev/ps2.c b/src/dev/ps2.c index 2dc57c0..5aed3e1 100644 --- a/src/dev/ps2.c +++ b/src/dev/ps2.c @@ -18,6 +18,9 @@ uint64_t timer_handler(registers_t *regs) { wm_timer_tick(); network_process_frames(); + extern void k_beep_process(void); + k_beep_process(); + outb(0x20, 0x20); // EOI after processing to prevent nested timer interrupts extern uint64_t process_schedule(uint64_t current_rsp); return process_schedule((uint64_t)regs); diff --git a/src/sys/syscall.c b/src/sys/syscall.c index 182030b..fd8a08e 100644 --- a/src/sys/syscall.c +++ b/src/sys/syscall.c @@ -929,16 +929,8 @@ static uint64_t syscall_handler_inner(registers_t *regs) { } else if (cmd == 14) { // SYSTEM_CMD_BEEP int freq = (int)arg2; int ms = (int)arg3; - if (freq > 0) { - int div = 1193180 / freq; - outb(0x43, 0xB6); - outb(0x42, div & 0xFF); - outb(0x42, (div >> 8) & 0xFF); - outb(0x61, inb(0x61) | 0x03); - } - // Sleep - kernel side - k_sleep(ms); - outb(0x61, inb(0x61) & 0xFC); + extern void k_beep(int freq, int ms); + k_beep(freq, ms); return 0; } else if (cmd == 15) { // SYSTEM_CMD_MEMINFO uint64_t *out = (uint64_t *)arg2;