From e8749de7f7a713099f31a9e8d965cf8db2545c3d Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Sun, 13 Sep 2026 01:50:31 +0100 Subject: [PATCH 01/27] init the ps2.h file --- includes/driver/ps2.h | 48 +++++++++++++++++++++++++++++++++++++++++++ src/driver/pit.c | 0 2 files changed, 48 insertions(+) delete mode 100644 src/driver/pit.c diff --git a/includes/driver/ps2.h b/includes/driver/ps2.h index e69de29..9e8fac9 100644 --- a/includes/driver/ps2.h +++ b/includes/driver/ps2.h @@ -0,0 +1,48 @@ +#ifndef PS2_H +#define PS2_H + +#include + +#define PS2_DATA_PORT 0x60 +#define PS2_STATUS_PORT 0x64 + +// control commands +#define PS2_CC_READ_CONFIG 0x20 // read configuration byte +#define PS2_CC_WRITE_CONFIG 0x60 // write configuration byte +#define PS2_CC_SELF_TEST 0xAA // controller self-test +#define PS2_CC_TEST_PORT1 0xAB // test port 1 +#define PS2_CC_TEST_PORT2 0xA9 // test port 2 +#define PS2_CC_DISABLE_PORT1 0xAD // disable port 1 +#define PS2_CC_ENABLE_PORT1 0xAE // enable port 1 +#define PS2_CC_DISABLE_PORT2 0xA7 // disable port 2 +#define PS2_CC_ENABLE_PORT2 0xA8 // enable port 2 +#define PS2_CC_READ_OUTPUT_PORT 0xD0 // read output port +#define PS2_CC_WRITE_OUTPUT_PORT 0xD1 // write output port +#define PS2_CC_WRITE_TO_PORT2 0xD4 // next byte goes to port 2 + +// device commands +#define PS2_DC_RESET 0xFF // reset device +#define PS2_DC_DISABLE_SCANNING 0xF5 // disable scanning +#define PS2_DC_IDENTIFY_DEVICE 0xF2 // identify device +#define PS2_DC_ENABLE_SCANNING 0xF4 // enable scanning + +struct ps2_config { + uint8_t port1_interrupt : 1; + uint8_t port2_interrupt : 1; + uint8_t system_flag : 1; + uint8_t zero1 : 1; + uint8_t port1_clock : 1; + uint8_t port2_clock : 1; + uint8_t _ : 2; +}; + +// ps2_read(); +// ps2_write(); +// ps2_wait_input(); +// ps2_wait_output(); +// ps2_send_device_command(); +// ps2_read_config(); +// ps2_write_config(); +// ps2_status(); + +#endif \ No newline at end of file diff --git a/src/driver/pit.c b/src/driver/pit.c deleted file mode 100644 index e69de29..0000000 From 2ae8c08a64876c587427095f6dc606e60789bc72 Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Sun, 13 Sep 2026 01:54:46 +0100 Subject: [PATCH 02/27] fix struct issue --- includes/driver/ps2.h | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-) diff --git a/includes/driver/ps2.h b/includes/driver/ps2.h index 9e8fac9..3e8e87c 100644 --- a/includes/driver/ps2.h +++ b/includes/driver/ps2.h @@ -26,14 +26,15 @@ #define PS2_DC_IDENTIFY_DEVICE 0xF2 // identify device #define PS2_DC_ENABLE_SCANNING 0xF4 // enable scanning -struct ps2_config { - uint8_t port1_interrupt : 1; - uint8_t port2_interrupt : 1; - uint8_t system_flag : 1; - uint8_t zero1 : 1; - uint8_t port1_clock : 1; - uint8_t port2_clock : 1; - uint8_t _ : 2; +typedef struct ps2_config { + uint8_t port1_interrupt : 1; + uint8_t port2_interrupt : 1; + uint8_t system_flag : 1; + uint8_t zero1 : 1; + uint8_t port1_clock : 1; + uint8_t port2_clock : 1; + uint8_t translation : 1; + uint8_t zero2 : 1; }; // ps2_read(); From d62646a51516f9af8c19cafba9b48ccef167e300 Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Sun, 13 Sep 2026 18:40:03 +0100 Subject: [PATCH 03/27] init ps2 --- includes/driver/ps2.h | 27 +++++++++++++++++++++++++-- includes/utils/types.h | 10 ++++++++++ includes/{ => utils}/utils.h | 0 src/driver/ps2.c | 17 +++++++++++++++++ 4 files changed, 52 insertions(+), 2 deletions(-) create mode 100644 includes/utils/types.h rename includes/{ => utils}/utils.h (100%) diff --git a/includes/driver/ps2.h b/includes/driver/ps2.h index 3e8e87c..767c01b 100644 --- a/includes/driver/ps2.h +++ b/includes/driver/ps2.h @@ -5,6 +5,7 @@ #define PS2_DATA_PORT 0x60 #define PS2_STATUS_PORT 0x64 +#define PS2_COMMAND_PORT PS2_STATUS_PORT // control commands #define PS2_CC_READ_CONFIG 0x20 // read configuration byte @@ -26,7 +27,7 @@ #define PS2_DC_IDENTIFY_DEVICE 0xF2 // identify device #define PS2_DC_ENABLE_SCANNING 0xF4 // enable scanning -typedef struct ps2_config { +typedef struct ps2_config_t { uint8_t port1_interrupt : 1; uint8_t port2_interrupt : 1; uint8_t system_flag : 1; @@ -35,7 +36,29 @@ typedef struct ps2_config { uint8_t port2_clock : 1; uint8_t translation : 1; uint8_t zero2 : 1; -}; +} ps2_config_t; + +typedef union { + uint8_t raw; + + struct { + uint8_t output_buffer_full : 1; // Bit 0 + uint8_t input_buffer_full : 1; // Bit 1 + uint8_t system_flag : 1; // Bit 2 + uint8_t command_data : 1; // Bit 3 + uint8_t unknown : 1; // Bit 4 + uint8_t timeout_error : 1; // Bit 5 + uint8_t parity_error : 1; // Bit 6 + uint8_t zero : 1; // Bit 7 + }; +} ps2_status_t; + + +ps2_status_t ps2_status(void); + +uint8_t ps2_read(void); +void ps2_command(uint8_t cmd); + // ps2_read(); // ps2_write(); diff --git a/includes/utils/types.h b/includes/utils/types.h new file mode 100644 index 0000000..19f9a61 --- /dev/null +++ b/includes/utils/types.h @@ -0,0 +1,10 @@ +#ifndef UTILS_H +#define UTILS_H + +#include + +#define bool uint8_t +#define True 1 +#define False 0 + +#endif diff --git a/includes/utils.h b/includes/utils/utils.h similarity index 100% rename from includes/utils.h rename to includes/utils/utils.h diff --git a/src/driver/ps2.c b/src/driver/ps2.c index e69de29..8210877 100644 --- a/src/driver/ps2.c +++ b/src/driver/ps2.c @@ -0,0 +1,17 @@ +#include "ps2.h" +#include "utils.h" + + + +ps2_status_t ps2_status(void){ + return inb(PS2_STATUS_PORT); +} + +void ps2_command(uint8_t cmd){ + outb(PS2_COMMAND_PORT, cmd); +} + +uint8_t ps2_read(void){ + return inb(PS2_DATA_PORT); +} + From 60e51cfc43efa119283ab70bfb19b8cdfff0ead8 Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Sun, 13 Sep 2026 18:41:12 +0100 Subject: [PATCH 04/27] add com types interface --- includes/driver/ps2.h | 2 +- includes/driver/vga.h | 2 +- includes/interrupt/idt.h | 2 +- includes/interrupt/isr.h | 2 +- includes/interrupt/pic.h | 2 +- includes/interrupt/pit.h | 2 +- includes/lib/vga_lib.h | 2 +- includes/timer.h | 2 +- includes/utils/types.h | 2 +- includes/utils/utils.h | 2 +- src/interrupt/pit.c | 2 +- 11 files changed, 11 insertions(+), 11 deletions(-) diff --git a/includes/driver/ps2.h b/includes/driver/ps2.h index 767c01b..5d12fdb 100644 --- a/includes/driver/ps2.h +++ b/includes/driver/ps2.h @@ -1,7 +1,7 @@ #ifndef PS2_H #define PS2_H -#include +#include "types.h" #define PS2_DATA_PORT 0x60 #define PS2_STATUS_PORT 0x64 diff --git a/includes/driver/vga.h b/includes/driver/vga.h index 7ac5eaf..6dec5a0 100644 --- a/includes/driver/vga.h +++ b/includes/driver/vga.h @@ -1,7 +1,7 @@ #ifndef VGA_H #define VGA_H -#include +#include "types.h" #define VGA_ADDRESS 0xB8000 diff --git a/includes/interrupt/idt.h b/includes/interrupt/idt.h index 95909f4..4eb04e0 100644 --- a/includes/interrupt/idt.h +++ b/includes/interrupt/idt.h @@ -1,7 +1,7 @@ #ifndef IDT_H #define IDT_H -#include +#include "types.h" #define IDT_ENTRIES 256 diff --git a/includes/interrupt/isr.h b/includes/interrupt/isr.h index a719e6e..8946e9f 100644 --- a/includes/interrupt/isr.h +++ b/includes/interrupt/isr.h @@ -1,7 +1,7 @@ #ifndef ISR_H #define ISR_H -#include +#include "types.h" char *EXCEPTIONS[] = { "Division Error", // 00 diff --git a/includes/interrupt/pic.h b/includes/interrupt/pic.h index 54704b7..e569e00 100644 --- a/includes/interrupt/pic.h +++ b/includes/interrupt/pic.h @@ -1,7 +1,7 @@ #ifndef PIC_H #define PIC_H -#include +#include "types.h" #define PIC1 0x20 /* IO base address for master PIC */ #define PIC2 0xA0 /* IO base address for slave PIC */ diff --git a/includes/interrupt/pit.h b/includes/interrupt/pit.h index 80c244e..db9ac75 100644 --- a/includes/interrupt/pit.h +++ b/includes/interrupt/pit.h @@ -7,7 +7,7 @@ #define PIT_COMMAND 0x43 #define PIT_BASE_FREQ 1193182 -#include +#include "types.h" /* Channels */ #define PIT_CHANNEL_0 0 diff --git a/includes/lib/vga_lib.h b/includes/lib/vga_lib.h index 492d4a5..ab13197 100644 --- a/includes/lib/vga_lib.h +++ b/includes/lib/vga_lib.h @@ -1,7 +1,7 @@ #ifndef VGA_LIB_H #define VGA_LIB_H -#include +#include "types.h" /* * Logging diff --git a/includes/timer.h b/includes/timer.h index c1979dc..2ac048d 100644 --- a/includes/timer.h +++ b/includes/timer.h @@ -1,7 +1,7 @@ #ifndef TIMER_H #define TIMER_H -#include +#include "types.h" void timer_init(uint32_t frequency); diff --git a/includes/utils/types.h b/includes/utils/types.h index 19f9a61..2c0afe6 100644 --- a/includes/utils/types.h +++ b/includes/utils/types.h @@ -1,7 +1,7 @@ #ifndef UTILS_H #define UTILS_H -#include +#include "types.h" #define bool uint8_t #define True 1 diff --git a/includes/utils/utils.h b/includes/utils/utils.h index eeb906f..0753d4d 100644 --- a/includes/utils/utils.h +++ b/includes/utils/utils.h @@ -1,7 +1,7 @@ #ifndef UTILS_H #define UTILS_H -#include +#include "types.h" void outb(uint16_t port, uint8_t value); uint8_t inb(uint16_t port); diff --git a/src/interrupt/pit.c b/src/interrupt/pit.c index 1737898..4a1b30c 100644 --- a/src/interrupt/pit.c +++ b/src/interrupt/pit.c @@ -1,6 +1,6 @@ #include "pit.h" #include "utils.h" -#include +#include "types.h" uint16_t div; uint32_t freq; From 8c5913234711cd40a678c8f39d8666e162edaf2d Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Sun, 13 Sep 2026 18:47:11 +0100 Subject: [PATCH 05/27] ps2 status functions --- includes/driver/ps2.h | 9 +++++++++ src/driver/ps2.c | 41 ++++++++++++++++++++++++++++++++++++++++- 2 files changed, 49 insertions(+), 1 deletion(-) diff --git a/includes/driver/ps2.h b/includes/driver/ps2.h index 5d12fdb..be99242 100644 --- a/includes/driver/ps2.h +++ b/includes/driver/ps2.h @@ -55,6 +55,15 @@ typedef union { ps2_status_t ps2_status(void); +bool ps2_output_buffer_full(void); +bool ps2_input_buffer_full(void); +bool ps2_system_flag(void); +bool ps2_command_data(void); +bool ps2_timeout_error(void); +bool ps2_parity_error(void); +bool ps2_wait_input_clear(void); +bool ps2_wait_output_full(void); + uint8_t ps2_read(void); void ps2_command(uint8_t cmd); diff --git a/src/driver/ps2.c b/src/driver/ps2.c index 8210877..9573238 100644 --- a/src/driver/ps2.c +++ b/src/driver/ps2.c @@ -2,11 +2,50 @@ #include "utils.h" - +// --------------------------------------------------------------------- ps2_status_t ps2_status(void){ return inb(PS2_STATUS_PORT); } +bool ps2_output_buffer_full(void){ + return ps2_status().output_buffer_full; +} + +bool ps2_input_buffer_full(void){ + return ps2_status().input_buffer_full; +} + +bool ps2_system_flag(void){ + return ps2_status().system_flag; +} + +bool ps2_command_data(void){ + return ps2_status().command_data; +} + +bool ps2_timeout_error(void){ + return ps2_status().timeout_error; +} + +bool ps2_parity_error(void){ + return ps2_status().parity_error; +} + +bool ps2_zero(void){ + return ps2_status().zero; +} + +bool ps2_wait_input_clear(void){ + while(ps2_input_buffer_full()); + return true; +} + +bool ps2_wait_output_full(void){ + while(!ps2_output_buffer_full()); + return true; +} +// --------------------------------------------------------------------- + void ps2_command(uint8_t cmd){ outb(PS2_COMMAND_PORT, cmd); } From 576313357c8dabf17b8384a390aac9649c1ed701 Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Sun, 13 Sep 2026 18:47:37 +0100 Subject: [PATCH 06/27] code formate --- includes/driver/ps2.h | 65 ++++++++++++++++++++---------------------- includes/utils/types.h | 4 +-- src/driver/ps2.c | 52 +++++++++++---------------------- src/interrupt/pit.c | 2 +- src/kernel/kernel.c | 4 +-- 5 files changed, 52 insertions(+), 75 deletions(-) diff --git a/includes/driver/ps2.h b/includes/driver/ps2.h index be99242..5ea5239 100644 --- a/includes/driver/ps2.h +++ b/includes/driver/ps2.h @@ -3,39 +3,39 @@ #include "types.h" -#define PS2_DATA_PORT 0x60 -#define PS2_STATUS_PORT 0x64 +#define PS2_DATA_PORT 0x60 +#define PS2_STATUS_PORT 0x64 #define PS2_COMMAND_PORT PS2_STATUS_PORT // control commands -#define PS2_CC_READ_CONFIG 0x20 // read configuration byte -#define PS2_CC_WRITE_CONFIG 0x60 // write configuration byte -#define PS2_CC_SELF_TEST 0xAA // controller self-test -#define PS2_CC_TEST_PORT1 0xAB // test port 1 -#define PS2_CC_TEST_PORT2 0xA9 // test port 2 -#define PS2_CC_DISABLE_PORT1 0xAD // disable port 1 -#define PS2_CC_ENABLE_PORT1 0xAE // enable port 1 -#define PS2_CC_DISABLE_PORT2 0xA7 // disable port 2 -#define PS2_CC_ENABLE_PORT2 0xA8 // enable port 2 -#define PS2_CC_READ_OUTPUT_PORT 0xD0 // read output port +#define PS2_CC_READ_CONFIG 0x20 // read configuration byte +#define PS2_CC_WRITE_CONFIG 0x60 // write configuration byte +#define PS2_CC_SELF_TEST 0xAA // controller self-test +#define PS2_CC_TEST_PORT1 0xAB // test port 1 +#define PS2_CC_TEST_PORT2 0xA9 // test port 2 +#define PS2_CC_DISABLE_PORT1 0xAD // disable port 1 +#define PS2_CC_ENABLE_PORT1 0xAE // enable port 1 +#define PS2_CC_DISABLE_PORT2 0xA7 // disable port 2 +#define PS2_CC_ENABLE_PORT2 0xA8 // enable port 2 +#define PS2_CC_READ_OUTPUT_PORT 0xD0 // read output port #define PS2_CC_WRITE_OUTPUT_PORT 0xD1 // write output port -#define PS2_CC_WRITE_TO_PORT2 0xD4 // next byte goes to port 2 +#define PS2_CC_WRITE_TO_PORT2 0xD4 // next byte goes to port 2 // device commands -#define PS2_DC_RESET 0xFF // reset device +#define PS2_DC_RESET 0xFF // reset device #define PS2_DC_DISABLE_SCANNING 0xF5 // disable scanning -#define PS2_DC_IDENTIFY_DEVICE 0xF2 // identify device -#define PS2_DC_ENABLE_SCANNING 0xF4 // enable scanning +#define PS2_DC_IDENTIFY_DEVICE 0xF2 // identify device +#define PS2_DC_ENABLE_SCANNING 0xF4 // enable scanning typedef struct ps2_config_t { - uint8_t port1_interrupt : 1; - uint8_t port2_interrupt : 1; - uint8_t system_flag : 1; - uint8_t zero1 : 1; - uint8_t port1_clock : 1; - uint8_t port2_clock : 1; - uint8_t translation : 1; - uint8_t zero2 : 1; + uint8_t port1_interrupt : 1; + uint8_t port2_interrupt : 1; + uint8_t system_flag : 1; + uint8_t zero1 : 1; + uint8_t port1_clock : 1; + uint8_t port2_clock : 1; + uint8_t translation : 1; + uint8_t zero2 : 1; } ps2_config_t; typedef union { @@ -43,17 +43,16 @@ typedef union { struct { uint8_t output_buffer_full : 1; // Bit 0 - uint8_t input_buffer_full : 1; // Bit 1 - uint8_t system_flag : 1; // Bit 2 - uint8_t command_data : 1; // Bit 3 - uint8_t unknown : 1; // Bit 4 - uint8_t timeout_error : 1; // Bit 5 - uint8_t parity_error : 1; // Bit 6 - uint8_t zero : 1; // Bit 7 + uint8_t input_buffer_full : 1; // Bit 1 + uint8_t system_flag : 1; // Bit 2 + uint8_t command_data : 1; // Bit 3 + uint8_t unknown : 1; // Bit 4 + uint8_t timeout_error : 1; // Bit 5 + uint8_t parity_error : 1; // Bit 6 + uint8_t zero : 1; // Bit 7 }; } ps2_status_t; - ps2_status_t ps2_status(void); bool ps2_output_buffer_full(void); bool ps2_input_buffer_full(void); @@ -64,11 +63,9 @@ bool ps2_parity_error(void); bool ps2_wait_input_clear(void); bool ps2_wait_output_full(void); - uint8_t ps2_read(void); void ps2_command(uint8_t cmd); - // ps2_read(); // ps2_write(); // ps2_wait_input(); diff --git a/includes/utils/types.h b/includes/utils/types.h index 2c0afe6..04240a1 100644 --- a/includes/utils/types.h +++ b/includes/utils/types.h @@ -3,8 +3,8 @@ #include "types.h" -#define bool uint8_t -#define True 1 +#define bool uint8_t +#define True 1 #define False 0 #endif diff --git a/src/driver/ps2.c b/src/driver/ps2.c index 9573238..ef381f4 100644 --- a/src/driver/ps2.c +++ b/src/driver/ps2.c @@ -1,56 +1,36 @@ #include "ps2.h" #include "utils.h" - // --------------------------------------------------------------------- -ps2_status_t ps2_status(void){ - return inb(PS2_STATUS_PORT); -} +ps2_status_t ps2_status(void) { return inb(PS2_STATUS_PORT); } -bool ps2_output_buffer_full(void){ - return ps2_status().output_buffer_full; -} +bool ps2_output_buffer_full(void) { return ps2_status().output_buffer_full; } -bool ps2_input_buffer_full(void){ - return ps2_status().input_buffer_full; -} +bool ps2_input_buffer_full(void) { return ps2_status().input_buffer_full; } -bool ps2_system_flag(void){ - return ps2_status().system_flag; -} +bool ps2_system_flag(void) { return ps2_status().system_flag; } -bool ps2_command_data(void){ - return ps2_status().command_data; -} +bool ps2_command_data(void) { return ps2_status().command_data; } -bool ps2_timeout_error(void){ - return ps2_status().timeout_error; -} +bool ps2_timeout_error(void) { return ps2_status().timeout_error; } -bool ps2_parity_error(void){ - return ps2_status().parity_error; -} +bool ps2_parity_error(void) { return ps2_status().parity_error; } -bool ps2_zero(void){ - return ps2_status().zero; -} +bool ps2_zero(void) { return ps2_status().zero; } -bool ps2_wait_input_clear(void){ - while(ps2_input_buffer_full()); +bool ps2_wait_input_clear(void) { + while (ps2_input_buffer_full()) + ; return true; } -bool ps2_wait_output_full(void){ - while(!ps2_output_buffer_full()); +bool ps2_wait_output_full(void) { + while (!ps2_output_buffer_full()) + ; return true; } // --------------------------------------------------------------------- -void ps2_command(uint8_t cmd){ - outb(PS2_COMMAND_PORT, cmd); -} - -uint8_t ps2_read(void){ - return inb(PS2_DATA_PORT); -} +void ps2_command(uint8_t cmd) { outb(PS2_COMMAND_PORT, cmd); } +uint8_t ps2_read(void) { return inb(PS2_DATA_PORT); } diff --git a/src/interrupt/pit.c b/src/interrupt/pit.c index 4a1b30c..2ba1839 100644 --- a/src/interrupt/pit.c +++ b/src/interrupt/pit.c @@ -1,6 +1,6 @@ #include "pit.h" -#include "utils.h" #include "types.h" +#include "utils.h" uint16_t div; uint32_t freq; diff --git a/src/kernel/kernel.c b/src/kernel/kernel.c index 775cd3c..cb3b044 100644 --- a/src/kernel/kernel.c +++ b/src/kernel/kernel.c @@ -30,14 +30,14 @@ void kernel_main() { vga_log_info("[", "init", "] pit and timer"); pic_clear_mask(0); timer_init(1000); // 1000 Hz - + sti(); for (int i = 0; i < 53; i++) { vga_print("."); timer_sleep(0.02); } - vga_print_at_end_c("... Ok\n", GREEN); // timer + vga_print_at_end_c("... Ok\n", GREEN); // timer for (;;) { asm volatile("hlt"); From 1dc3421257d2a704b89b28ec7577c4567fef5d99 Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Sat, 19 Sep 2026 20:09:59 +0100 Subject: [PATCH 07/27] Add PS/2 controller functions and integrate into kernel initialization --- includes/driver/ps2.h | 22 ++++++---- includes/utils/types.h | 8 ++-- src/driver/ps2.c | 99 +++++++++++++++++++++++++++++++++++++++++- src/kernel/kernel.c | 43 ++++++++++++------ 4 files changed, 145 insertions(+), 27 deletions(-) diff --git a/includes/driver/ps2.h b/includes/driver/ps2.h index 5ea5239..d6b7a38 100644 --- a/includes/driver/ps2.h +++ b/includes/driver/ps2.h @@ -62,17 +62,21 @@ bool ps2_timeout_error(void); bool ps2_parity_error(void); bool ps2_wait_input_clear(void); bool ps2_wait_output_full(void); +void ps2_flush_output(void); -uint8_t ps2_read(void); void ps2_command(uint8_t cmd); -// ps2_read(); -// ps2_write(); -// ps2_wait_input(); -// ps2_wait_output(); -// ps2_send_device_command(); -// ps2_read_config(); -// ps2_write_config(); -// ps2_status(); +uint8_t ps2_read(void); +void ps2_write(uint8_t data); +uint8_t ps2_read_config(void); +void ps2_write_config(uint8_t config); +bool ps2_test_controller(void); +bool ps2_test_port1(void); +bool ps2_test_port2(void); +void ps2_disable_port1(void); +void ps2_enable_port1(void); +void ps2_disable_port2(void); +void ps2_enable_port2(void); +void ps2_init(void); #endif \ No newline at end of file diff --git a/includes/utils/types.h b/includes/utils/types.h index 04240a1..538bfa2 100644 --- a/includes/utils/types.h +++ b/includes/utils/types.h @@ -1,9 +1,11 @@ -#ifndef UTILS_H -#define UTILS_H +#ifndef TYPES_H +#define TYPES_H -#include "types.h" +#include #define bool uint8_t +#define true 1 +#define false 0 #define True 1 #define False 0 diff --git a/src/driver/ps2.c b/src/driver/ps2.c index ef381f4..8b4b1ff 100644 --- a/src/driver/ps2.c +++ b/src/driver/ps2.c @@ -2,7 +2,11 @@ #include "utils.h" // --------------------------------------------------------------------- -ps2_status_t ps2_status(void) { return inb(PS2_STATUS_PORT); } +ps2_status_t ps2_status(void) { + ps2_status_t status; + status.raw = inb(PS2_STATUS_PORT); + return status; +} bool ps2_output_buffer_full(void) { return ps2_status().output_buffer_full; } @@ -29,8 +33,101 @@ bool ps2_wait_output_full(void) { ; return true; } + +void ps2_flush_output(void) { + while (ps2_output_buffer_full()) { + (void)ps2_read(); + } +} // --------------------------------------------------------------------- void ps2_command(uint8_t cmd) { outb(PS2_COMMAND_PORT, cmd); } uint8_t ps2_read(void) { return inb(PS2_DATA_PORT); } + +void ps2_write(uint8_t data) { + ps2_wait_input_clear(); + outb(PS2_DATA_PORT, data); +} + +uint8_t ps2_read_config(void) { + ps2_wait_input_clear(); + ps2_command(PS2_CC_READ_CONFIG); + ps2_wait_output_full(); + return ps2_read(); +} + +void ps2_write_config(uint8_t config) { + ps2_wait_input_clear(); + ps2_command(PS2_CC_WRITE_CONFIG); + ps2_wait_input_clear(); + ps2_write(config); +} + +bool ps2_test_controller(void) { + ps2_flush_output(); + ps2_wait_input_clear(); + ps2_command(PS2_CC_SELF_TEST); + ps2_wait_output_full(); + return ps2_read() == 0x55; +} + +bool ps2_test_port1(void) { + ps2_flush_output(); + ps2_wait_input_clear(); + ps2_command(PS2_CC_TEST_PORT1); + ps2_wait_output_full(); + return ps2_read() == 0x00; +} + +bool ps2_test_port2(void) { + ps2_flush_output(); + ps2_wait_input_clear(); + ps2_command(PS2_CC_TEST_PORT2); + ps2_wait_output_full(); + return ps2_read() == 0x00; +} + +void ps2_disable_port1(void) { + ps2_wait_input_clear(); + ps2_command(PS2_CC_DISABLE_PORT1); +} + +void ps2_enable_port1(void) { + ps2_wait_input_clear(); + ps2_command(PS2_CC_ENABLE_PORT1); +} + +void ps2_disable_port2(void) { + ps2_wait_input_clear(); + ps2_command(PS2_CC_DISABLE_PORT2); +} + +void ps2_enable_port2(void) { + ps2_wait_input_clear(); + ps2_command(PS2_CC_ENABLE_PORT2); +} + +void ps2_init(void) { + ps2_flush_output(); + ps2_disable_port1(); + ps2_disable_port2(); + + if (!ps2_test_controller()) { + return; + } + + uint8_t config = ps2_read_config(); + config &= ~(1u << 0); + config &= ~(1u << 1); + config &= ~(1u << 6); + ps2_write_config(config); + + if (ps2_test_port1()) { + ps2_enable_port1(); + } + + if (ps2_test_port2()) { + ps2_enable_port2(); + } +} \ No newline at end of file diff --git a/src/kernel/kernel.c b/src/kernel/kernel.c index cb3b044..07dc32a 100644 --- a/src/kernel/kernel.c +++ b/src/kernel/kernel.c @@ -5,6 +5,7 @@ #include "pic.h" #include "pit.h" #include "timer.h" +#include "ps2.h" #include "vga.h" #include "vga_lib.h" @@ -13,35 +14,49 @@ #include "utils.h" -void kernel_main() { - vga_init(); - vga_log_info("[", "init", "] vga"); - vga_print_at_end_c("... Ok\n", GREEN); - vga_log_info("[", "init", "] pic"); - pic_init(); - vga_print_at_end_c("... Ok\n", GREEN); +#define TIMER_FREQ 1000 // 1000 Hz + + +void KERNEL_INIT(const char *name, void (*init_function)(void)) +{ + vga_log_info("[", "init", "] "); + vga_print(name); + + init_function(); - vga_log_info("[", "init", "] idt"); - idt_init(); vga_print_at_end_c("... Ok\n", GREEN); +} - vga_log_info("[", "init", "] pit and timer"); + +void timer_setup() { pic_clear_mask(0); - timer_init(1000); // 1000 Hz + timer_init(TIMER_FREQ); // 1000 Hz sti(); - for (int i = 0; i < 53; i++) { + for (int i = 0; i < 33; i++) { vga_print("."); timer_sleep(0.02); } - vga_print_at_end_c("... Ok\n", GREEN); // timer +} + +void kernel_main() { + + KERNEL_INIT("VGA console",vga_init); + + KERNEL_INIT("PIC - Programmable Interrupt Controller",pic_init); + + KERNEL_INIT("IDT - Interrupt Descriptor Table",idt_init); + + KERNEL_INIT("PIT - Programmable Interval Timer",timer_setup); // 1000 Hz + + KERNEL_INIT("PS/2 controller",ps2_init); for (;;) { asm volatile("hlt"); } return; -} +} \ No newline at end of file From 9f0e74fd16eb83393e9a4550bfc68cfbe7a42956 Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Sat, 19 Sep 2026 21:06:39 +0100 Subject: [PATCH 08/27] add strlib --- includes/lib/string.h | 18 +++++++++++++ src/libs/string.c | 59 +++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 77 insertions(+) create mode 100644 includes/lib/string.h create mode 100644 src/libs/string.c diff --git a/includes/lib/string.h b/includes/lib/string.h new file mode 100644 index 0000000..532b4b6 --- /dev/null +++ b/includes/lib/string.h @@ -0,0 +1,18 @@ +#ifndef STRING_H +#define STRING_H + +#include "types.h" + +int strlen(char *str); + +void strcpy(char *dest, char *src); +void strcat(char *dest, char *src); + +int strcmp(const char *str1, const char *str2); + +char *strchr(const char *str, char c); //find first occurrence of character c in string str + +char *strstr(const char *str, const char *substr); // find first occurrence of substring substr in string str + +#endif + diff --git a/src/libs/string.c b/src/libs/string.c new file mode 100644 index 0000000..cf80f22 --- /dev/null +++ b/src/libs/string.c @@ -0,0 +1,59 @@ +#include "types.h" +#include "string.h" + +int strlen(char *str){ + int len = 0; + while (*str++) { + len++; + } + return len; +} +void strcpy(char *dest, char *src){ + while (*src) { + *dest++ = *src++; + } + *dest = '\0'; +} +void strcat(char *dest, char *src){ + while (*dest) { + dest++; + } + while (*src) { + *dest++ = *src++; + } + *dest = '\0'; +} + +int strcmp(const char *str1, const char *str2){ + while (*str1 && (*str1 == *str2)) { + str1++; + str2++; + } + return *(const unsigned char *)str1 - *(const unsigned char *)str2; +} + +char *strchr(const char *str, int c){ + while (*str) { + if (*str == (char)c) { + return (char *)str; + } + str++; + } + return NULL; +} + +char *strstr(const char *str, const char *substr){ + if (!*substr) { + return (char *)str; + } + for (; *str; str++) { + if (*str == *substr) { + const char *h, *n; + for (h = str, n = substr; *h && *n && *h == *n; ++h, ++n); + if (!*n) { + return (char *)str; + } + } + } + return NULL; +} \ No newline at end of file From f6785042a3adfa168504bc935ec77ec35e68e6c7 Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Sat, 19 Sep 2026 22:27:00 +0100 Subject: [PATCH 09/27] update str lib --- includes/lib/string.h | 6 ++++-- src/libs/string.c | 48 +++++++++++++++++++++++++++++++++++++++---- 2 files changed, 48 insertions(+), 6 deletions(-) diff --git a/includes/lib/string.h b/includes/lib/string.h index 532b4b6..460f720 100644 --- a/includes/lib/string.h +++ b/includes/lib/string.h @@ -6,11 +6,13 @@ int strlen(char *str); void strcpy(char *dest, char *src); -void strcat(char *dest, char *src); +void strcat(char *dest, const char *src); int strcmp(const char *str1, const char *str2); -char *strchr(const char *str, char c); //find first occurrence of character c in string str +char *int2str(int num); //convert integer to string + +char *strchr(const char *str, int c); //find first occurrence of character c in string str char *strstr(const char *str, const char *substr); // find first occurrence of substring substr in string str diff --git a/src/libs/string.c b/src/libs/string.c index cf80f22..accf760 100644 --- a/src/libs/string.c +++ b/src/libs/string.c @@ -1,3 +1,4 @@ +#include #include "types.h" #include "string.h" @@ -8,13 +9,47 @@ int strlen(char *str){ } return len; } + +char *int2str(int num) +{ + static char str[33]; + + char *p = str + 32; + + *p = '\0'; + + if (num == 0) + { + *(--p) = '0'; + } + else + { + bool negative = num < 0; + + if (negative) + num = -num; + + while (num > 0) + { + *(--p) = (num % 10) + '0'; + num /= 10; + } + + if (negative) + *(--p) = '-'; + } + + return p; +} + void strcpy(char *dest, char *src){ while (*src) { *dest++ = *src++; } *dest = '\0'; } -void strcat(char *dest, char *src){ + +void strcat(char *dest,const char *src){ while (*dest) { dest++; } @@ -24,6 +59,7 @@ void strcat(char *dest, char *src){ *dest = '\0'; } + int strcmp(const char *str1, const char *str2){ while (*str1 && (*str1 == *str2)) { str1++; @@ -32,16 +68,20 @@ int strcmp(const char *str1, const char *str2){ return *(const unsigned char *)str1 - *(const unsigned char *)str2; } -char *strchr(const char *str, int c){ - while (*str) { +char *strchr(const char *str, int c) +{ + while (*str != '\0') { if (*str == (char)c) { return (char *)str; } + str++; } - return NULL; + + return (c == '\0') ? (char *)str : NULL; } + char *strstr(const char *str, const char *substr){ if (!*substr) { return (char *)str; From 002abad6a6fe3dcdafb794f0415e10fa1e2bf0c2 Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Sat, 19 Sep 2026 22:27:11 +0100 Subject: [PATCH 10/27] add sdtio lib --- includes/lib/stdio.h | 17 ++++ src/libs/stdio.c | 197 +++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 214 insertions(+) create mode 100644 includes/lib/stdio.h create mode 100644 src/libs/stdio.c diff --git a/includes/lib/stdio.h b/includes/lib/stdio.h new file mode 100644 index 0000000..3b24fa2 --- /dev/null +++ b/includes/lib/stdio.h @@ -0,0 +1,17 @@ +#ifndef STDIO_H +#define STDIO_H + +#include "types.h" +#include + +void print(const char *str); +void println(const char *str); +void print_at_end(const char *str, uint8_t color); + +void printf(const char *format, ...); +void snprintf(char *buffer, size_t buffer_size, const char *format, ...); + +char *vformatter(const char *format, va_list args); +char *formatter(const char *format, ...); + +#endif \ No newline at end of file diff --git a/src/libs/stdio.c b/src/libs/stdio.c new file mode 100644 index 0000000..3bdb22f --- /dev/null +++ b/src/libs/stdio.c @@ -0,0 +1,197 @@ +#include + +#include "types.h" +#include "vga.h" +#include "vga_lib.h" + +#include "string.h" + +#include "stdio.h" + +#define FORMATTER_BUFFER_SIZE 1024 +static char buffer[FORMATTER_BUFFER_SIZE]; + + +void print(const char *str) +{ + while (*str) { + + if (*str == '\033') { + str++; + + if (*str == '[') { + str++; + + if (*str == '3') { + str++; + + switch (*str) { + case '0': + vga_set_color(BLACK, DEFUALT_B); + break; + + case '1': + vga_set_color(RED, DEFUALT_B); + break; + + case '2': + vga_set_color(GREEN, DEFUALT_B); + break; + + case '3': + vga_set_color(YELLOW, DEFUALT_B); + break; + + case '4': + vga_set_color(BLUE, DEFUALT_B); + break; + + case '5': + vga_set_color(MAGENTA, DEFUALT_B); + break; + + case '6': + vga_set_color(CYAN, DEFUALT_B); + break; + + case '7': + vga_set_color(WHITE, DEFUALT_B); + break; + } + + if (*str) + str++; + + if (*str == 'm') + str++; + }else if (*str == '0') { + str++; + + if (*str == 'm') { + vga_set_color(DEFUALT_F, DEFUALT_B); + str++; + } + } + } + + continue; + } + + vga_print_char(*str); + str++; + } +} + +void println(const char *str){ + vga_print("\n"); + vga_print(str); +} + +void print_at_end(const char *str, uint8_t color) { + vga_print_at_end_c(str, color); +} + +void printf(const char *format, ...){ + va_list args; + + va_start(args, format); + + char *result = vformatter(format, args); + + va_end(args); + + vga_print(result); +} + +void snprintf(char *buffer, size_t buffer_size, const char *format, ...){ + va_list args; + + va_start(args, format); + + char *result = vformatter(format, args); + + va_end(args); + + size_t i; + for (i = 0; i < buffer_size - 1 && result[i] != '\0'; i++) { + buffer[i] = result[i]; + } + buffer[i] = '\0'; +} + + +char *formatter(const char *format, ...) +{ + va_list args; + + va_start(args, format); + + char *result = vformatter(format, args); + + va_end(args); + + return result; +} + +char *vformatter(const char *format, va_list args) +{ + buffer[0] = '\0'; + + while (*format) + { + if (*format != '%') + { + char temp[2] = {*format, '\0'}; + strcat(buffer, temp); + + format++; + continue; + } + + format++; + + switch (*format) + { + case 's': + { + const char *str = va_arg(args, const char *); + strcat(buffer, str); + break; + } + + case 'd': + { + int number = va_arg(args, int); + strcat(buffer, int2str(number)); + break; + } + + case 'c': + { + char temp[2]; + + temp[0] = (char)va_arg(args, int); + temp[1] = '\0'; + + strcat(buffer, temp); + break; + } + + case '%': + { + strcat(buffer, "%"); + break; + } + + default: + { + strcat(buffer, "%"); + break; + } + } + + format++; + } + + return buffer; +} \ No newline at end of file From 3a35d54429b6ed5902d893e5cb78c11f19d6ac3e Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Sat, 19 Sep 2026 22:27:35 +0100 Subject: [PATCH 11/27] formate code --- includes/driver/vga.h | 9 +++ includes/lib/string.h | 8 +-- includes/utils/types.h | 1 + src/kernel/kernel.c | 24 +++----- src/libs/stdio.c | 137 ++++++++++++++++++----------------------- src/libs/string.c | 35 +++++------ 6 files changed, 99 insertions(+), 115 deletions(-) diff --git a/includes/driver/vga.h b/includes/driver/vga.h index 6dec5a0..c613f5e 100644 --- a/includes/driver/vga.h +++ b/includes/driver/vga.h @@ -27,6 +27,15 @@ #define BROWN 0x06 // YELLOW #define LIGHT_GRAY 0x07 // WHITE +#define DARK_GRAY BLACk | LIGHT_FLAG +#define LIGHT_BLUE BLUE | LIGHT_FLAG +#define LIGHT_GREEN GREEN | LIGHT_FLAG +#define LIGHT_CYAN CYAN | LIGHT_FLAG +#define LIGHT_RED RED | LIGHT_FLAG +#define LIGHT_MAGENTA MAGENTA | LIGHT_FLAG +#define YELLOW BROWN | LIGHT_FLAG +#define WHITE LIGHT_GRAY | LIGHT_FLAG + #define LIGHT_FLAG 0x08 #define DEFUALT_F LIGHT_GRAY diff --git a/includes/lib/string.h b/includes/lib/string.h index 460f720..7dfcc02 100644 --- a/includes/lib/string.h +++ b/includes/lib/string.h @@ -10,11 +10,11 @@ void strcat(char *dest, const char *src); int strcmp(const char *str1, const char *str2); -char *int2str(int num); //convert integer to string +char *int2str(int num); // convert integer to string -char *strchr(const char *str, int c); //find first occurrence of character c in string str +char *strchr(const char *str, int c); // find first occurrence of character c in string str -char *strstr(const char *str, const char *substr); // find first occurrence of substring substr in string str +char *strstr(const char *str, + const char *substr); // find first occurrence of substring substr in string str #endif - diff --git a/includes/utils/types.h b/includes/utils/types.h index 538bfa2..6642d2f 100644 --- a/includes/utils/types.h +++ b/includes/utils/types.h @@ -1,6 +1,7 @@ #ifndef TYPES_H #define TYPES_H +#include #include #define bool uint8_t diff --git a/src/kernel/kernel.c b/src/kernel/kernel.c index 07dc32a..4d210e1 100644 --- a/src/kernel/kernel.c +++ b/src/kernel/kernel.c @@ -4,32 +4,28 @@ #include "pic.h" #include "pit.h" -#include "timer.h" #include "ps2.h" +#include "timer.h" #include "vga.h" #include "vga_lib.h" #include "panic.h" +#include "stdio.h" #include "utils.h" - - #define TIMER_FREQ 1000 // 1000 Hz - -void KERNEL_INIT(const char *name, void (*init_function)(void)) -{ - vga_log_info("[", "init", "] "); +void KERNEL_INIT(const char *name, void (*init_function)(void)) { + print("[\033[34minit\033[0m] "); vga_print(name); init_function(); - vga_print_at_end_c("... Ok\n", GREEN); + print_at_end("... Ok\n", GREEN); } - void timer_setup() { pic_clear_mask(0); timer_init(TIMER_FREQ); // 1000 Hz @@ -44,15 +40,15 @@ void timer_setup() { void kernel_main() { - KERNEL_INIT("VGA console",vga_init); + KERNEL_INIT("VGA console", vga_init); - KERNEL_INIT("PIC - Programmable Interrupt Controller",pic_init); + KERNEL_INIT("PIC - Programmable Interrupt Controller", pic_init); - KERNEL_INIT("IDT - Interrupt Descriptor Table",idt_init); + KERNEL_INIT("IDT - Interrupt Descriptor Table", idt_init); - KERNEL_INIT("PIT - Programmable Interval Timer",timer_setup); // 1000 Hz + KERNEL_INIT("PIT - Programmable Interval Timer", timer_setup); // 1000 Hz - KERNEL_INIT("PS/2 controller",ps2_init); + KERNEL_INIT("PS/2 controller", ps2_init); for (;;) { asm volatile("hlt"); diff --git a/src/libs/stdio.c b/src/libs/stdio.c index 3bdb22f..061a88f 100644 --- a/src/libs/stdio.c +++ b/src/libs/stdio.c @@ -11,9 +11,7 @@ #define FORMATTER_BUFFER_SIZE 1024 static char buffer[FORMATTER_BUFFER_SIZE]; - -void print(const char *str) -{ +void print(const char *str) { while (*str) { if (*str == '\033') { @@ -26,37 +24,37 @@ void print(const char *str) str++; switch (*str) { - case '0': - vga_set_color(BLACK, DEFUALT_B); - break; + case '0': + vga_set_color(BLACK, DEFUALT_B); + break; - case '1': - vga_set_color(RED, DEFUALT_B); - break; + case '1': + vga_set_color(RED, DEFUALT_B); + break; - case '2': - vga_set_color(GREEN, DEFUALT_B); - break; + case '2': + vga_set_color(GREEN, DEFUALT_B); + break; - case '3': - vga_set_color(YELLOW, DEFUALT_B); - break; + case '3': + vga_set_color(YELLOW, DEFUALT_B); + break; - case '4': - vga_set_color(BLUE, DEFUALT_B); - break; + case '4': + vga_set_color(BLUE, DEFUALT_B); + break; - case '5': - vga_set_color(MAGENTA, DEFUALT_B); - break; + case '5': + vga_set_color(MAGENTA, DEFUALT_B); + break; - case '6': - vga_set_color(CYAN, DEFUALT_B); - break; + case '6': + vga_set_color(CYAN, DEFUALT_B); + break; - case '7': - vga_set_color(WHITE, DEFUALT_B); - break; + case '7': + vga_set_color(WHITE, DEFUALT_B); + break; } if (*str) @@ -64,7 +62,7 @@ void print(const char *str) if (*str == 'm') str++; - }else if (*str == '0') { + } else if (*str == '0') { str++; if (*str == 'm') { @@ -82,16 +80,14 @@ void print(const char *str) } } -void println(const char *str){ +void println(const char *str) { vga_print("\n"); vga_print(str); } -void print_at_end(const char *str, uint8_t color) { - vga_print_at_end_c(str, color); -} +void print_at_end(const char *str, uint8_t color) { vga_print_at_end_c(str, color); } -void printf(const char *format, ...){ +void printf(const char *format, ...) { va_list args; va_start(args, format); @@ -99,11 +95,11 @@ void printf(const char *format, ...){ char *result = vformatter(format, args); va_end(args); - + vga_print(result); } -void snprintf(char *buffer, size_t buffer_size, const char *format, ...){ +void snprintf(char *buffer, size_t buffer_size, const char *format, ...) { va_list args; va_start(args, format); @@ -119,9 +115,7 @@ void snprintf(char *buffer, size_t buffer_size, const char *format, ...){ buffer[i] = '\0'; } - -char *formatter(const char *format, ...) -{ +char *formatter(const char *format, ...) { va_list args; va_start(args, format); @@ -133,14 +127,11 @@ char *formatter(const char *format, ...) return result; } -char *vformatter(const char *format, va_list args) -{ +char *vformatter(const char *format, va_list args) { buffer[0] = '\0'; - while (*format) - { - if (*format != '%') - { + while (*format) { + if (*format != '%') { char temp[2] = {*format, '\0'}; strcat(buffer, temp); @@ -150,44 +141,38 @@ char *vformatter(const char *format, va_list args) format++; - switch (*format) - { - case 's': - { - const char *str = va_arg(args, const char *); - strcat(buffer, str); - break; - } + switch (*format) { + case 's': { + const char *str = va_arg(args, const char *); + strcat(buffer, str); + break; + } - case 'd': - { - int number = va_arg(args, int); - strcat(buffer, int2str(number)); - break; - } + case 'd': { + int number = va_arg(args, int); + strcat(buffer, int2str(number)); + break; + } - case 'c': - { - char temp[2]; + case 'c': { + char temp[2]; - temp[0] = (char)va_arg(args, int); - temp[1] = '\0'; + temp[0] = (char)va_arg(args, int); + temp[1] = '\0'; - strcat(buffer, temp); - break; - } + strcat(buffer, temp); + break; + } - case '%': - { - strcat(buffer, "%"); - break; - } + case '%': { + strcat(buffer, "%"); + break; + } - default: - { - strcat(buffer, "%"); - break; - } + default: { + strcat(buffer, "%"); + break; + } } format++; diff --git a/src/libs/string.c b/src/libs/string.c index accf760..116f987 100644 --- a/src/libs/string.c +++ b/src/libs/string.c @@ -1,8 +1,8 @@ -#include -#include "types.h" #include "string.h" +#include "types.h" +#include -int strlen(char *str){ +int strlen(char *str) { int len = 0; while (*str++) { len++; @@ -10,27 +10,22 @@ int strlen(char *str){ return len; } -char *int2str(int num) -{ +char *int2str(int num) { static char str[33]; char *p = str + 32; *p = '\0'; - if (num == 0) - { + if (num == 0) { *(--p) = '0'; - } - else - { + } else { bool negative = num < 0; if (negative) num = -num; - while (num > 0) - { + while (num > 0) { *(--p) = (num % 10) + '0'; num /= 10; } @@ -42,14 +37,14 @@ char *int2str(int num) return p; } -void strcpy(char *dest, char *src){ +void strcpy(char *dest, char *src) { while (*src) { *dest++ = *src++; } *dest = '\0'; } -void strcat(char *dest,const char *src){ +void strcat(char *dest, const char *src) { while (*dest) { dest++; } @@ -59,8 +54,7 @@ void strcat(char *dest,const char *src){ *dest = '\0'; } - -int strcmp(const char *str1, const char *str2){ +int strcmp(const char *str1, const char *str2) { while (*str1 && (*str1 == *str2)) { str1++; str2++; @@ -68,8 +62,7 @@ int strcmp(const char *str1, const char *str2){ return *(const unsigned char *)str1 - *(const unsigned char *)str2; } -char *strchr(const char *str, int c) -{ +char *strchr(const char *str, int c) { while (*str != '\0') { if (*str == (char)c) { return (char *)str; @@ -81,15 +74,15 @@ char *strchr(const char *str, int c) return (c == '\0') ? (char *)str : NULL; } - -char *strstr(const char *str, const char *substr){ +char *strstr(const char *str, const char *substr) { if (!*substr) { return (char *)str; } for (; *str; str++) { if (*str == *substr) { const char *h, *n; - for (h = str, n = substr; *h && *n && *h == *n; ++h, ++n); + for (h = str, n = substr; *h && *n && *h == *n; ++h, ++n) + ; if (!*n) { return (char *)str; } From a61e174b66f99b9fb736e7b2111015822f456ebd Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Sun, 20 Sep 2026 16:35:34 +0100 Subject: [PATCH 12/27] update ps2 --- includes/driver/ps2.h | 24 +++++++++++++++--------- src/driver/ps2.c | 10 ++++++++++ 2 files changed, 25 insertions(+), 9 deletions(-) diff --git a/includes/driver/ps2.h b/includes/driver/ps2.h index d6b7a38..064832b 100644 --- a/includes/driver/ps2.h +++ b/includes/driver/ps2.h @@ -27,15 +27,19 @@ #define PS2_DC_IDENTIFY_DEVICE 0xF2 // identify device #define PS2_DC_ENABLE_SCANNING 0xF4 // enable scanning -typedef struct ps2_config_t { - uint8_t port1_interrupt : 1; - uint8_t port2_interrupt : 1; - uint8_t system_flag : 1; - uint8_t zero1 : 1; - uint8_t port1_clock : 1; - uint8_t port2_clock : 1; - uint8_t translation : 1; - uint8_t zero2 : 1; +typedef union ps2_config_t { + uint8_t raw; + + struct { + uint8_t first_port_irq : 1; + uint8_t port2_interrupt : 1; + uint8_t system_flag : 1; + uint8_t zero1 : 1; + uint8_t port1_clock : 1; + uint8_t port2_clock : 1; + uint8_t translation : 1; + uint8_t zero2 : 1; + }; } ps2_config_t; typedef union { @@ -69,7 +73,9 @@ void ps2_command(uint8_t cmd); uint8_t ps2_read(void); void ps2_write(uint8_t data); uint8_t ps2_read_config(void); +ps2_config_t ps2_get_config(void); void ps2_write_config(uint8_t config); +void ps2_set_config(ps2_config_t config); bool ps2_test_controller(void); bool ps2_test_port1(void); bool ps2_test_port2(void); diff --git a/src/driver/ps2.c b/src/driver/ps2.c index 8b4b1ff..9935cfd 100644 --- a/src/driver/ps2.c +++ b/src/driver/ps2.c @@ -57,6 +57,12 @@ uint8_t ps2_read_config(void) { return ps2_read(); } +ps2_config_t ps2_get_config(void) { + ps2_config_t config; + config.raw = ps2_read_config(); + return config; +} + void ps2_write_config(uint8_t config) { ps2_wait_input_clear(); ps2_command(PS2_CC_WRITE_CONFIG); @@ -64,6 +70,10 @@ void ps2_write_config(uint8_t config) { ps2_write(config); } +void ps2_set_config(ps2_config_t config) { + ps2_write_config(config.raw); +} + bool ps2_test_controller(void) { ps2_flush_output(); ps2_wait_input_clear(); From b5c54eb28fb18a4cf865f750a0539592eb0f8cbd Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Sun, 20 Sep 2026 20:03:42 +0100 Subject: [PATCH 13/27] add keyboard driver --- includes/driver/keyboard.h | 23 ++++++++++ includes/driver/ps2.h | 2 + src/driver/keyboard.c | 92 ++++++++++++++++++++++++++++++++++++++ src/interrupt/irq/irq.c | 6 +++ src/kernel/kernel.c | 19 ++++++++ 5 files changed, 142 insertions(+) create mode 100644 includes/driver/keyboard.h create mode 100644 src/driver/keyboard.c diff --git a/includes/driver/keyboard.h b/includes/driver/keyboard.h new file mode 100644 index 0000000..d4898d1 --- /dev/null +++ b/includes/driver/keyboard.h @@ -0,0 +1,23 @@ +#ifndef keyboard_H +#define keyboard_H + +#include "types.h" +#include "ps2.h" + +typedef enum { + K_ACK = 0xFA, + K_RESEND = 0xFE, + K_ERROR = 0xFC, + k_BAT = 0xAA, // Basic Assurance Test +} k_response_t; + +void init_keyboard(void); + +void reset_keyboard(void); +void set_scaning(bool state); +void select_scancode_set(uint8_t set); + +void keyboard_irq_handler(void); + + +#endif \ No newline at end of file diff --git a/includes/driver/ps2.h b/includes/driver/ps2.h index 064832b..a695c81 100644 --- a/includes/driver/ps2.h +++ b/includes/driver/ps2.h @@ -26,6 +26,8 @@ #define PS2_DC_DISABLE_SCANNING 0xF5 // disable scanning #define PS2_DC_IDENTIFY_DEVICE 0xF2 // identify device #define PS2_DC_ENABLE_SCANNING 0xF4 // enable scanning +#define PS2_DC_SELECT_SET 0xF0 // select scancode set +#define PS2_DC_SET_LED_STATE 0xED // set LED state typedef union ps2_config_t { uint8_t raw; diff --git a/src/driver/keyboard.c b/src/driver/keyboard.c new file mode 100644 index 0000000..a15773b --- /dev/null +++ b/src/driver/keyboard.c @@ -0,0 +1,92 @@ +#include "ps2.h" +#include "keyboard.h" +#include "utils.h" + +#include "stdio.h" +#include "stdio.h" + + +void init_keyboard(void){ + reset_keyboard(); + set_scaning(false); + select_scancode_set(0x02); + set_scaning(true); +} + +void reset_keyboard(void) +{ + ps2_wait_input_clear(); + ps2_write(PS2_DC_RESET); + + ps2_wait_output_full(); + + if (ps2_read() != K_ACK) { + printf("\033[31mERROR:\033[0m Keyboard did not acknowledge reset.\n"); + return; + } + + ps2_wait_output_full(); + + if (ps2_read() != k_BAT) { + printf("\033[31mERROR:\033[0m Keyboard BAT failed.\n"); + return; + } +} + + +void set_scaning(bool state){ + ps2_flush_output(); + ps2_wait_input_clear(); + + if (state) { + ps2_write(PS2_DC_ENABLE_SCANNING); + } else { + ps2_write(PS2_DC_DISABLE_SCANNING); + } + + ps2_wait_output_full(); + + if (ps2_read() != K_ACK) { + printf("\033[31mERROR:\033[0m Keyboard did not acknowledge scanning command.\n"); + return; + } +} + +void select_scancode_set(uint8_t set){ + ps2_flush_output(); + ps2_wait_input_clear(); + + if (set <= 3){ + ps2_write(PS2_DC_SELECT_SET); + } + + ps2_wait_output_full(); + + if (ps2_read() != K_ACK) { + printf("\033[31mERROR:\033[0m keyboard.h:53 select_scancode_set .\n"); + return; + } + + ps2_flush_output(); + ps2_wait_input_clear(); + + ps2_write(set); + + ps2_wait_output_full(); + + if (ps2_read() != K_ACK) { + printf("\033[31mERROR:\033[0m keyboard.h:65 select_scancode_set .\n"); + return; + } + +} + + +void keyboard_irq_handler(void){ + printf("KEYBOARD IRQ!\n"); + + uint8_t data = ps2_read(); + + printf("SCAN: %d\n", data); + +} \ No newline at end of file diff --git a/src/interrupt/irq/irq.c b/src/interrupt/irq/irq.c index 33d5b7a..2539f29 100644 --- a/src/interrupt/irq/irq.c +++ b/src/interrupt/irq/irq.c @@ -1,6 +1,7 @@ #include "irq.h" #include "pic.h" #include "timer.h" +#include "keyboard.h" #include "vga.h" #include "vga_lib.h" @@ -12,6 +13,11 @@ void irq_handler(uint32_t vector) { pic_send_eoi((uint8_t)vector); break; + case 1: + keyboard_irq_handler(); + pic_send_eoi((uint8_t)vector); + break; + default: vga_print("IRQ: "); vga_print_hex(vector); diff --git a/src/kernel/kernel.c b/src/kernel/kernel.c index 4d210e1..656f8c2 100644 --- a/src/kernel/kernel.c +++ b/src/kernel/kernel.c @@ -8,6 +8,8 @@ #include "timer.h" #include "vga.h" +#include "keyboard.h" + #include "vga_lib.h" #include "panic.h" @@ -50,6 +52,23 @@ void kernel_main() { KERNEL_INIT("PS/2 controller", ps2_init); + if (ps2_output_buffer_full()) { + uint8_t data = ps2_read(); + printf("SCAN: %x\n", data); + } + + printf("====================================\n"); + KERNEL_INIT("Keyboard Driver", init_keyboard); + while (1){ + if (ps2_output_buffer_full()) { + uint8_t data = ps2_read(); + printf("SCAN: %d\n", data); + } + } + + + + for (;;) { asm volatile("hlt"); } From 5ca31c8ce082622ab089d5a6c31d94ab91b63041 Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Sun, 20 Sep 2026 20:03:58 +0100 Subject: [PATCH 14/27] code formate --- includes/driver/keyboard.h | 3 +-- src/driver/keyboard.c | 27 ++++++++++----------------- src/driver/ps2.c | 4 +--- src/interrupt/irq/irq.c | 2 +- src/kernel/kernel.c | 15 ++++++--------- 5 files changed, 19 insertions(+), 32 deletions(-) diff --git a/includes/driver/keyboard.h b/includes/driver/keyboard.h index d4898d1..4431f9d 100644 --- a/includes/driver/keyboard.h +++ b/includes/driver/keyboard.h @@ -1,8 +1,8 @@ #ifndef keyboard_H #define keyboard_H -#include "types.h" #include "ps2.h" +#include "types.h" typedef enum { K_ACK = 0xFA, @@ -19,5 +19,4 @@ void select_scancode_set(uint8_t set); void keyboard_irq_handler(void); - #endif \ No newline at end of file diff --git a/src/driver/keyboard.c b/src/driver/keyboard.c index a15773b..3567595 100644 --- a/src/driver/keyboard.c +++ b/src/driver/keyboard.c @@ -1,20 +1,17 @@ -#include "ps2.h" #include "keyboard.h" +#include "ps2.h" #include "utils.h" #include "stdio.h" -#include "stdio.h" - -void init_keyboard(void){ +void init_keyboard(void) { reset_keyboard(); set_scaning(false); select_scancode_set(0x02); set_scaning(true); } -void reset_keyboard(void) -{ +void reset_keyboard(void) { ps2_wait_input_clear(); ps2_write(PS2_DC_RESET); @@ -33,8 +30,7 @@ void reset_keyboard(void) } } - -void set_scaning(bool state){ +void set_scaning(bool state) { ps2_flush_output(); ps2_wait_input_clear(); @@ -45,23 +41,23 @@ void set_scaning(bool state){ } ps2_wait_output_full(); - + if (ps2_read() != K_ACK) { printf("\033[31mERROR:\033[0m Keyboard did not acknowledge scanning command.\n"); return; } } -void select_scancode_set(uint8_t set){ +void select_scancode_set(uint8_t set) { ps2_flush_output(); ps2_wait_input_clear(); - if (set <= 3){ + if (set <= 3) { ps2_write(PS2_DC_SELECT_SET); } ps2_wait_output_full(); - + if (ps2_read() != K_ACK) { printf("\033[31mERROR:\033[0m keyboard.h:53 select_scancode_set .\n"); return; @@ -73,20 +69,17 @@ void select_scancode_set(uint8_t set){ ps2_write(set); ps2_wait_output_full(); - + if (ps2_read() != K_ACK) { printf("\033[31mERROR:\033[0m keyboard.h:65 select_scancode_set .\n"); return; } - } - -void keyboard_irq_handler(void){ +void keyboard_irq_handler(void) { printf("KEYBOARD IRQ!\n"); uint8_t data = ps2_read(); printf("SCAN: %d\n", data); - } \ No newline at end of file diff --git a/src/driver/ps2.c b/src/driver/ps2.c index 9935cfd..687e4a5 100644 --- a/src/driver/ps2.c +++ b/src/driver/ps2.c @@ -70,9 +70,7 @@ void ps2_write_config(uint8_t config) { ps2_write(config); } -void ps2_set_config(ps2_config_t config) { - ps2_write_config(config.raw); -} +void ps2_set_config(ps2_config_t config) { ps2_write_config(config.raw); } bool ps2_test_controller(void) { ps2_flush_output(); diff --git a/src/interrupt/irq/irq.c b/src/interrupt/irq/irq.c index 2539f29..515a5f3 100644 --- a/src/interrupt/irq/irq.c +++ b/src/interrupt/irq/irq.c @@ -1,7 +1,7 @@ #include "irq.h" +#include "keyboard.h" #include "pic.h" #include "timer.h" -#include "keyboard.h" #include "vga.h" #include "vga_lib.h" diff --git a/src/kernel/kernel.c b/src/kernel/kernel.c index 656f8c2..5c0dfae 100644 --- a/src/kernel/kernel.c +++ b/src/kernel/kernel.c @@ -7,8 +7,8 @@ #include "ps2.h" #include "timer.h" -#include "vga.h" #include "keyboard.h" +#include "vga.h" #include "vga_lib.h" @@ -53,21 +53,18 @@ void kernel_main() { KERNEL_INIT("PS/2 controller", ps2_init); if (ps2_output_buffer_full()) { - uint8_t data = ps2_read(); - printf("SCAN: %x\n", data); + uint8_t data = ps2_read(); + printf("SCAN: %x\n", data); } printf("====================================\n"); KERNEL_INIT("Keyboard Driver", init_keyboard); - while (1){ + while (1) { if (ps2_output_buffer_full()) { - uint8_t data = ps2_read(); - printf("SCAN: %d\n", data); + uint8_t data = ps2_read(); + printf("SCAN: %d\n", data); } } - - - for (;;) { asm volatile("hlt"); From 7309b1f1b0bb95393bc667014e00916d252f817d Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Sun, 20 Sep 2026 20:34:38 +0100 Subject: [PATCH 15/27] add secroling to vga --- includes/driver/vga.h | 2 ++ src/driver/vga.c | 43 ++++++++++++++++++++++++++++++++++++++++++- 2 files changed, 44 insertions(+), 1 deletion(-) diff --git a/includes/driver/vga.h b/includes/driver/vga.h index c613f5e..899208d 100644 --- a/includes/driver/vga.h +++ b/includes/driver/vga.h @@ -54,6 +54,8 @@ void vga_init(void); void vga_clear(void); +void vga_scroll_up(void); + void vga_print_char(char c); void vga_print(const char *str); diff --git a/src/driver/vga.c b/src/driver/vga.c index d489ce7..961000b 100644 --- a/src/driver/vga.c +++ b/src/driver/vga.c @@ -25,6 +25,7 @@ void vga_init(void) { void vga_print_char(char c) { + vga_buf[cursor_position] = (current_color << 8 | c); vga_set_cursor_position((cursor_position + 1)); @@ -38,7 +39,11 @@ void vga_print(const char *str) { for (uint32_t i = 0; str[i] != '\0'; i++) { if (str[i] == '\n') { uint8_t y = vga_get_cursor_y() + 1; - vga_set_cursor(0, y); + if (y >= VGA_HEIGHT) { + vga_scroll_up(); + }else { + vga_set_cursor(0, y); + } } else { vga_print_char(str[i]); @@ -119,6 +124,13 @@ uint8_t vga_get_cursor_x(void) { return vga_get_cursor_position() % VGA_WIDTH; } uint8_t vga_get_cursor_y(void) { return vga_get_cursor_position() / VGA_WIDTH; } +uint8_t vga_calc_cursor_x(uint16_t pos) { return pos % VGA_WIDTH; } + +uint8_t vga_calc_cursor_y(uint16_t pos) { return pos / VGA_WIDTH; } + +uint16_t vga_calc_cursor_position(uint8_t x, uint8_t y) { return y * VGA_WIDTH + x; } + + // Clear void vga_clear(void) { @@ -131,3 +143,32 @@ void vga_clear(void) { vga_set_cursor(0, 0); } + + +// secrole + +void vga_scroll_up(void) +{ + /* Move every row one line upward */ + for (uint16_t y = 0; y < VGA_HEIGHT - 1; y++) { + + for (uint16_t x = 0; x < VGA_WIDTH; x++) { + + uint16_t dst = y * VGA_WIDTH + x; + uint16_t src = (y + 1) * VGA_WIDTH + x; + + vga_buf[dst] = vga_buf[src]; + } + } + + /* Clear the new bottom line */ + for (uint16_t x = 0; x < VGA_WIDTH; x++) { + + uint16_t pos = (VGA_HEIGHT - 1) * VGA_WIDTH + x; + + vga_buf[pos] = + ((uint16_t)current_color << 8) | ' '; + } + + vga_set_cursor(0, VGA_HEIGHT - 1); +} From 66d92f0e0747574c44ac4c2f4a260ed3e51c00ea Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Sun, 20 Sep 2026 20:52:31 +0100 Subject: [PATCH 16/27] add hex to formater and bin --- includes/lib/string.h | 1 + src/libs/stdio.c | 25 +++++++++++++++++++++++-- src/libs/string.c | 30 ++++++++++++++++++++++++++++++ 3 files changed, 54 insertions(+), 2 deletions(-) diff --git a/includes/lib/string.h b/includes/lib/string.h index 7dfcc02..004e7dd 100644 --- a/includes/lib/string.h +++ b/includes/lib/string.h @@ -11,6 +11,7 @@ void strcat(char *dest, const char *src); int strcmp(const char *str1, const char *str2); char *int2str(int num); // convert integer to string +char *uint2str(uint32_t number, uint8_t base, bool uppercase); char *strchr(const char *str, int c); // find first occurrence of character c in string str diff --git a/src/libs/stdio.c b/src/libs/stdio.c index 061a88f..c2f1784 100644 --- a/src/libs/stdio.c +++ b/src/libs/stdio.c @@ -127,10 +127,12 @@ char *formatter(const char *format, ...) { return result; } -char *vformatter(const char *format, va_list args) { +char *vformatter(const char *format, va_list args) +{ buffer[0] = '\0'; while (*format) { + if (*format != '%') { char temp[2] = {*format, '\0'}; strcat(buffer, temp); @@ -142,6 +144,7 @@ char *vformatter(const char *format, va_list args) { format++; switch (*format) { + case 's': { const char *str = va_arg(args, const char *); strcat(buffer, str); @@ -154,6 +157,24 @@ char *vformatter(const char *format, va_list args) { break; } + case 'x': { + uint32_t number = va_arg(args, uint32_t); + strcat(buffer, uint2str(number, 16, false)); + break; + } + + case 'h': { + uint32_t number = va_arg(args, uint32_t); + strcat(buffer, uint2str(number, 16, true)); + break; + } + + case 'b': { + uint32_t number = va_arg(args, uint32_t); + strcat(buffer, uint2str(number, 2, false)); + break; + } + case 'c': { char temp[2]; @@ -179,4 +200,4 @@ char *vformatter(const char *format, va_list args) { } return buffer; -} \ No newline at end of file +} diff --git a/src/libs/string.c b/src/libs/string.c index 116f987..3b1c145 100644 --- a/src/libs/string.c +++ b/src/libs/string.c @@ -37,6 +37,36 @@ char *int2str(int num) { return p; } +char *uint2str(uint32_t number, uint8_t base, bool uppercase) +{ + static char buffer[33]; + + const char *digits_lower = "0123456789abcdef"; + const char *digits_upper = "0123456789ABCDEF"; + const char *digits = uppercase ? digits_upper : digits_lower; + + if (base < 2 || base > 16) { + buffer[0] = '\0'; + return buffer; + } + + char *ptr = &buffer[32]; + *ptr = '\0'; + + if (number == 0) { + *--ptr = '0'; + return ptr; + } + + while (number > 0) { + uint32_t remainder = number % base; + *--ptr = digits[remainder]; + number /= base; + } + + return ptr; +} + void strcpy(char *dest, char *src) { while (*src) { *dest++ = *src++; From 89d27578723df13e5b992af3f9f6bfea1c73298b Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Sun, 20 Sep 2026 20:57:54 +0100 Subject: [PATCH 17/27] set code function reader --- includes/driver/ps2.h | 3 +++ src/driver/ps2.c | 23 +++++++++++++++++++++++ 2 files changed, 26 insertions(+) diff --git a/includes/driver/ps2.h b/includes/driver/ps2.h index a695c81..2759fef 100644 --- a/includes/driver/ps2.h +++ b/includes/driver/ps2.h @@ -87,4 +87,7 @@ void ps2_disable_port2(void); void ps2_enable_port2(void); void ps2_init(void); +uint8_t keyboard_get_scan_code_set(void); + + #endif \ No newline at end of file diff --git a/src/driver/ps2.c b/src/driver/ps2.c index 687e4a5..0f43bae 100644 --- a/src/driver/ps2.c +++ b/src/driver/ps2.c @@ -138,4 +138,27 @@ void ps2_init(void) { if (ps2_test_port2()) { ps2_enable_port2(); } +} + +uint8_t keyboard_get_scan_code_set(void) +{ + uint8_t response; + + ps2_write(0xF0); // Command to get the current scan-code set. + + response = ps2_read(); + + if (response != 0xFA) { + return 0; + } + + ps2_write(0x00); // Request to get the current scan-code set. + + response = ps2_read(); + + if (response != 0xFA) { + return 0; + } + + return ps2_read(); } \ No newline at end of file From e424f39c5877b03719dce94d5f605e971f5c626a Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Sun, 20 Sep 2026 20:58:06 +0100 Subject: [PATCH 18/27] formate code --- includes/driver/ps2.h | 1 - src/driver/keyboard.c | 2 +- src/driver/ps2.c | 3 +-- src/driver/vga.c | 13 ++++--------- src/kernel/kernel.c | 13 ++++++------- src/libs/stdio.c | 3 +-- src/libs/string.c | 3 +-- 7 files changed, 14 insertions(+), 24 deletions(-) diff --git a/includes/driver/ps2.h b/includes/driver/ps2.h index 2759fef..d690776 100644 --- a/includes/driver/ps2.h +++ b/includes/driver/ps2.h @@ -89,5 +89,4 @@ void ps2_init(void); uint8_t keyboard_get_scan_code_set(void); - #endif \ No newline at end of file diff --git a/src/driver/keyboard.c b/src/driver/keyboard.c index 3567595..bb6b77f 100644 --- a/src/driver/keyboard.c +++ b/src/driver/keyboard.c @@ -81,5 +81,5 @@ void keyboard_irq_handler(void) { uint8_t data = ps2_read(); - printf("SCAN: %d\n", data); + printf("SCAN: %h\n", data); } \ No newline at end of file diff --git a/src/driver/ps2.c b/src/driver/ps2.c index 0f43bae..ada2371 100644 --- a/src/driver/ps2.c +++ b/src/driver/ps2.c @@ -140,8 +140,7 @@ void ps2_init(void) { } } -uint8_t keyboard_get_scan_code_set(void) -{ +uint8_t keyboard_get_scan_code_set(void) { uint8_t response; ps2_write(0xF0); // Command to get the current scan-code set. diff --git a/src/driver/vga.c b/src/driver/vga.c index 961000b..b75bd7a 100644 --- a/src/driver/vga.c +++ b/src/driver/vga.c @@ -25,7 +25,6 @@ void vga_init(void) { void vga_print_char(char c) { - vga_buf[cursor_position] = (current_color << 8 | c); vga_set_cursor_position((cursor_position + 1)); @@ -41,7 +40,7 @@ void vga_print(const char *str) { uint8_t y = vga_get_cursor_y() + 1; if (y >= VGA_HEIGHT) { vga_scroll_up(); - }else { + } else { vga_set_cursor(0, y); } @@ -130,7 +129,6 @@ uint8_t vga_calc_cursor_y(uint16_t pos) { return pos / VGA_WIDTH; } uint16_t vga_calc_cursor_position(uint8_t x, uint8_t y) { return y * VGA_WIDTH + x; } - // Clear void vga_clear(void) { @@ -144,11 +142,9 @@ void vga_clear(void) { vga_set_cursor(0, 0); } +// secrole -// secrole - -void vga_scroll_up(void) -{ +void vga_scroll_up(void) { /* Move every row one line upward */ for (uint16_t y = 0; y < VGA_HEIGHT - 1; y++) { @@ -166,8 +162,7 @@ void vga_scroll_up(void) uint16_t pos = (VGA_HEIGHT - 1) * VGA_WIDTH + x; - vga_buf[pos] = - ((uint16_t)current_color << 8) | ' '; + vga_buf[pos] = ((uint16_t)current_color << 8) | ' '; } vga_set_cursor(0, VGA_HEIGHT - 1); diff --git a/src/kernel/kernel.c b/src/kernel/kernel.c index 5c0dfae..d487f9e 100644 --- a/src/kernel/kernel.c +++ b/src/kernel/kernel.c @@ -17,6 +17,8 @@ #include "stdio.h" #include "utils.h" +#include "string.h" + #define TIMER_FREQ 1000 // 1000 Hz void KERNEL_INIT(const char *name, void (*init_function)(void)) { @@ -51,18 +53,15 @@ void kernel_main() { KERNEL_INIT("PIT - Programmable Interval Timer", timer_setup); // 1000 Hz KERNEL_INIT("PS/2 controller", ps2_init); + KERNEL_INIT("Keyboard Driver", init_keyboard); - if (ps2_output_buffer_full()) { - uint8_t data = ps2_read(); - printf("SCAN: %x\n", data); - } + uint8_t scan_code_set = keyboard_get_scan_code_set(); - printf("====================================\n"); - KERNEL_INIT("Keyboard Driver", init_keyboard); + printf("Keyboard Scan Code Set: %h\n", scan_code_set); while (1) { if (ps2_output_buffer_full()) { uint8_t data = ps2_read(); - printf("SCAN: %d\n", data); + printf("SCAN: %h\n", data); } } diff --git a/src/libs/stdio.c b/src/libs/stdio.c index c2f1784..2a9de85 100644 --- a/src/libs/stdio.c +++ b/src/libs/stdio.c @@ -127,8 +127,7 @@ char *formatter(const char *format, ...) { return result; } -char *vformatter(const char *format, va_list args) -{ +char *vformatter(const char *format, va_list args) { buffer[0] = '\0'; while (*format) { diff --git a/src/libs/string.c b/src/libs/string.c index 3b1c145..4911539 100644 --- a/src/libs/string.c +++ b/src/libs/string.c @@ -37,8 +37,7 @@ char *int2str(int num) { return p; } -char *uint2str(uint32_t number, uint8_t base, bool uppercase) -{ +char *uint2str(uint32_t number, uint8_t base, bool uppercase) { static char buffer[33]; const char *digits_lower = "0123456789abcdef"; From 12c55db7a79cfd14257354ff4299341594465f10 Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Mon, 21 Sep 2026 02:42:50 +0100 Subject: [PATCH 19/27] fix irq keyboard isse --- includes/driver/keyboard.h | 2 ++ src/driver/keyboard.c | 12 ++++++++++-- src/driver/ps2.c | 8 +++++--- src/kernel/kernel.c | 10 +--------- 4 files changed, 18 insertions(+), 14 deletions(-) diff --git a/includes/driver/keyboard.h b/includes/driver/keyboard.h index 4431f9d..1197dfc 100644 --- a/includes/driver/keyboard.h +++ b/includes/driver/keyboard.h @@ -17,6 +17,8 @@ void reset_keyboard(void); void set_scaning(bool state); void select_scancode_set(uint8_t set); +uint8_t keyboard_get_scan_code_set(void); + void keyboard_irq_handler(void); #endif \ No newline at end of file diff --git a/src/driver/keyboard.c b/src/driver/keyboard.c index bb6b77f..5c0dbbd 100644 --- a/src/driver/keyboard.c +++ b/src/driver/keyboard.c @@ -9,6 +9,8 @@ void init_keyboard(void) { set_scaning(false); select_scancode_set(0x02); set_scaning(true); + + ps2_flush_output(); } void reset_keyboard(void) { @@ -77,9 +79,15 @@ void select_scancode_set(uint8_t set) { } void keyboard_irq_handler(void) { - printf("KEYBOARD IRQ!\n"); + if (!ps2_wait_output_full()) { + return; + } uint8_t data = ps2_read(); - printf("SCAN: %h\n", data); + printf("\n SCAN: %h", data); + if (data == 0xf0) { + data = ps2_read(); + printf("%h\n", data); + } } \ No newline at end of file diff --git a/src/driver/ps2.c b/src/driver/ps2.c index ada2371..561de21 100644 --- a/src/driver/ps2.c +++ b/src/driver/ps2.c @@ -126,9 +126,11 @@ void ps2_init(void) { } uint8_t config = ps2_read_config(); - config &= ~(1u << 0); - config &= ~(1u << 1); - config &= ~(1u << 6); + + config |= (1u << 0); // IRQ1 enabled + config &= ~(1u << 1); // IRQ12 disabled + config &= ~(1u << 6); // translation disabled + ps2_write_config(config); if (ps2_test_port1()) { diff --git a/src/kernel/kernel.c b/src/kernel/kernel.c index d487f9e..c802222 100644 --- a/src/kernel/kernel.c +++ b/src/kernel/kernel.c @@ -55,15 +55,7 @@ void kernel_main() { KERNEL_INIT("PS/2 controller", ps2_init); KERNEL_INIT("Keyboard Driver", init_keyboard); - uint8_t scan_code_set = keyboard_get_scan_code_set(); - - printf("Keyboard Scan Code Set: %h\n", scan_code_set); - while (1) { - if (ps2_output_buffer_full()) { - uint8_t data = ps2_read(); - printf("SCAN: %h\n", data); - } - } + pic_clear_mask(1); for (;;) { asm volatile("hlt"); From 9853b2877ca8d8633990a8bd091bba43bf82f783 Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Mon, 21 Sep 2026 03:25:22 +0100 Subject: [PATCH 20/27] add keyboard driver files and enhance IRQ handler for keycode mapping --- includes/driver/{ => keyboard}/keyboard.h | 1 + includes/driver/keyboard/keyboard_keys.h | 327 ++++++++++++++++++++++ src/driver/keyboard.c | 5 +- 3 files changed, 332 insertions(+), 1 deletion(-) rename includes/driver/{ => keyboard}/keyboard.h (93%) create mode 100644 includes/driver/keyboard/keyboard_keys.h diff --git a/includes/driver/keyboard.h b/includes/driver/keyboard/keyboard.h similarity index 93% rename from includes/driver/keyboard.h rename to includes/driver/keyboard/keyboard.h index 1197dfc..45f7785 100644 --- a/includes/driver/keyboard.h +++ b/includes/driver/keyboard/keyboard.h @@ -1,6 +1,7 @@ #ifndef keyboard_H #define keyboard_H +#include "keyboard_keys.h" #include "ps2.h" #include "types.h" diff --git a/includes/driver/keyboard/keyboard_keys.h b/includes/driver/keyboard/keyboard_keys.h new file mode 100644 index 0000000..fe98aea --- /dev/null +++ b/includes/driver/keyboard/keyboard_keys.h @@ -0,0 +1,327 @@ +#ifndef keyboard_keys_H +#define keyboard_keys_H + +#include "ps2.h" +#include "types.h" + +typedef enum { + SCAN_STATE_NORMAL, + SCAN_STATE_BREAK, + SCAN_STATE_EXTENDED, + SCAN_STATE_EXTENDED_BREAK +} scancode_state_t; + +typedef enum { + KEY_PRESSED, + KEY_RELEASED +} key_action_t; + +typedef struct { + keycode_t key; + key_action_t action; +} key_event_t; + + +typedef enum { + KEY_NONE = 0, + + /* Function keys */ + KEY_ESC, + + KEY_F1, + KEY_F2, + KEY_F3, + KEY_F4, + KEY_F5, + KEY_F6, + KEY_F7, + KEY_F8, + KEY_F9, + KEY_F10, + KEY_F11, + KEY_F12, + + /* Number row */ + KEY_GRAVE, /* ` ~ */ + KEY_1, + KEY_2, + KEY_3, + KEY_4, + KEY_5, + KEY_6, + KEY_7, + KEY_8, + KEY_9, + KEY_0, + KEY_MINUS, /* - _ */ + KEY_EQUAL, /* = + */ + KEY_BACKSPACE, + + /* First row */ + KEY_TAB, + KEY_Q, + KEY_W, + KEY_E, + KEY_R, + KEY_T, + KEY_Y, + KEY_U, + KEY_I, + KEY_O, + KEY_P, + KEY_LEFT_BRACKET, /* [ { */ + KEY_RIGHT_BRACKET, /* ] } */ + KEY_BACKSLASH, /* \ | */ + + /* Second row */ + KEY_CAPS_LOCK, + KEY_A, + KEY_S, + KEY_D, + KEY_F, + KEY_G, + KEY_H, + KEY_J, + KEY_K, + KEY_L, + KEY_SEMICOLON, /* ; : */ + KEY_APOSTROPHE, /* ' " */ + KEY_ENTER, + + /* Third row */ + KEY_LEFT_SHIFT, + KEY_Z, + KEY_X, + KEY_C, + KEY_V, + KEY_B, + KEY_N, + KEY_M, + KEY_COMMA, /* , < */ + KEY_DOT, /* . > */ + KEY_SLASH, /* / ? */ + KEY_RIGHT_SHIFT, + + /* Bottom row */ + KEY_LEFT_CTRL, + KEY_LEFT_GUI, + KEY_LEFT_ALT, + KEY_SPACE, + KEY_RIGHT_ALT, + KEY_RIGHT_GUI, + KEY_MENU, + KEY_RIGHT_CTRL, + + /* Navigation */ + KEY_INSERT, + KEY_DELETE, + KEY_HOME, + KEY_END, + KEY_PAGE_UP, + KEY_PAGE_DOWN, + + /* Arrow keys */ + KEY_UP, + KEY_DOWN, + KEY_LEFT, + KEY_RIGHT, + + /* Numeric keypad */ + KEY_NUM_LOCK, + + KEY_KP_DIVIDE, + KEY_KP_MULTIPLY, + KEY_KP_MINUS, + KEY_KP_PLUS, + KEY_KP_ENTER, + + KEY_KP_0, + KEY_KP_1, + KEY_KP_2, + KEY_KP_3, + KEY_KP_4, + KEY_KP_5, + KEY_KP_6, + KEY_KP_7, + KEY_KP_8, + KEY_KP_9, + + KEY_KP_DOT, + + /* Lock keys */ + KEY_SCROLL_LOCK, + + /* Special / system keys */ + KEY_PRINT_SCREEN, + KEY_PAUSE, + + /* Additional common keys */ + KEY_POWER, + KEY_SLEEP, + KEY_WAKE, + + KEY_VOLUME_UP, + KEY_VOLUME_DOWN, + KEY_MUTE, + + KEY_MEDIA_PLAY_PAUSE, + KEY_MEDIA_STOP, + KEY_MEDIA_PREVIOUS, + KEY_MEDIA_NEXT, + + KEY_CALCULATOR, + + KEY_COUNT +} keycode_t; + +typedef struct { + keycode_t normal[256]; + keycode_t extended[256]; +} keyboard_scancode_table_t; + +static const keyboard_scancode_table_t scancode_set2 = {.normal = + { + + [0x76] = KEY_ESC, + + [0x05] = KEY_F1, + [0x06] = KEY_F2, + [0x04] = KEY_F3, + [0x0C] = KEY_F4, + [0x03] = KEY_F5, + [0x0B] = KEY_F6, + [0x83] = KEY_F7, + [0x0A] = KEY_F8, + [0x01] = KEY_F9, + [0x09] = KEY_F10, + [0x78] = KEY_F11, + [0x07] = KEY_F12, + + [0x0E] = KEY_GRAVE, + + [0x16] = KEY_1, + [0x1E] = KEY_2, + [0x26] = KEY_3, + [0x25] = KEY_4, + [0x2E] = KEY_5, + [0x36] = KEY_6, + [0x3D] = KEY_7, + [0x3E] = KEY_8, + [0x46] = KEY_9, + [0x45] = KEY_0, + + [0x4E] = KEY_MINUS, + [0x55] = KEY_EQUAL, + + [0x66] = KEY_BACKSPACE, + + [0x0D] = KEY_TAB, + + [0x15] = KEY_Q, + [0x1D] = KEY_W, + [0x24] = KEY_E, + [0x2D] = KEY_R, + [0x2C] = KEY_T, + [0x35] = KEY_Y, + [0x3C] = KEY_U, + [0x43] = KEY_I, + [0x44] = KEY_O, + [0x4D] = KEY_P, + + [0x54] = KEY_LEFT_BRACKET, + [0x5B] = KEY_RIGHT_BRACKET, + [0x5D] = KEY_BACKSLASH, + + [0x58] = KEY_CAPS_LOCK, + + [0x1C] = KEY_A, + [0x1B] = KEY_S, + [0x23] = KEY_D, + [0x2B] = KEY_F, + [0x34] = KEY_G, + [0x33] = KEY_H, + [0x3B] = KEY_J, + [0x42] = KEY_K, + [0x4B] = KEY_L, + + [0x4C] = KEY_SEMICOLON, + [0x52] = KEY_APOSTROPHE, + + [0x5A] = KEY_ENTER, + + [0x12] = KEY_LEFT_SHIFT, + + [0x1A] = KEY_Z, + [0x22] = KEY_X, + [0x21] = KEY_C, + [0x2A] = KEY_V, + [0x32] = KEY_B, + [0x31] = KEY_N, + [0x3A] = KEY_M, + + [0x41] = KEY_COMMA, + [0x49] = KEY_DOT, + [0x4A] = KEY_SLASH, + + [0x59] = KEY_RIGHT_SHIFT, + + [0x14] = KEY_LEFT_CTRL, + [0x11] = KEY_LEFT_ALT, + + [0x29] = KEY_SPACE, + + [0x77] = KEY_NUM_LOCK, + + [0x7C] = KEY_KP_MULTIPLY, + [0x7B] = KEY_KP_MINUS, + [0x79] = KEY_KP_PLUS, + + [0x70] = KEY_KP_0, + [0x69] = KEY_KP_1, + [0x72] = KEY_KP_2, + [0x7A] = KEY_KP_3, + [0x6B] = KEY_KP_4, + [0x73] = KEY_KP_5, + [0x74] = KEY_KP_6, + [0x6C] = KEY_KP_7, + [0x75] = KEY_KP_8, + [0x7D] = KEY_KP_9, + [0x71] = KEY_KP_DOT, + + [0x7E] = KEY_SCROLL_LOCK, + }, + + .extended = { + + /* Modifiers */ + [0x14] = KEY_RIGHT_CTRL, + [0x11] = KEY_RIGHT_ALT, + + /* Navigation */ + [0x70] = KEY_INSERT, + [0x71] = KEY_DELETE, + [0x6C] = KEY_HOME, + [0x69] = KEY_END, + [0x7D] = KEY_PAGE_UP, + [0x7A] = KEY_PAGE_DOWN, + + /* Arrows */ + [0x75] = KEY_UP, + [0x72] = KEY_DOWN, + [0x6B] = KEY_LEFT, + [0x74] = KEY_RIGHT, + + /* Keypad */ + [0x4A] = KEY_KP_DIVIDE, + [0x5A] = KEY_KP_ENTER, + + /* GUI keys */ + [0x1F] = KEY_LEFT_GUI, + [0x27] = KEY_RIGHT_GUI, + [0x2F] = KEY_MENU, + + /* Print Screen */ + [0x12] = KEY_PRINT_SCREEN, + }}; + +#endif \ No newline at end of file diff --git a/src/driver/keyboard.c b/src/driver/keyboard.c index 5c0dbbd..adf9943 100644 --- a/src/driver/keyboard.c +++ b/src/driver/keyboard.c @@ -85,7 +85,10 @@ void keyboard_irq_handler(void) { uint8_t data = ps2_read(); - printf("\n SCAN: %h", data); + keycode_t keycode = scancode_set2.normal[data]; + + printf("\n SCAN: %h -> %h", data, keycode); + if (data == 0xf0) { data = ps2_read(); printf("%h\n", data); From 8bea3c874efd4c861b3136e4242cc3f1b6cbfe8c Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Mon, 21 Sep 2026 19:47:05 +0100 Subject: [PATCH 21/27] fix print and print f funciton --- includes/driver/vga.h | 1 + src/driver/vga.c | 100 ++++++++++++++++++++++++++++++++++++++++-- src/libs/stdio.c | 2 +- 3 files changed, 98 insertions(+), 5 deletions(-) diff --git a/includes/driver/vga.h b/includes/driver/vga.h index 899208d..615cf60 100644 --- a/includes/driver/vga.h +++ b/includes/driver/vga.h @@ -8,6 +8,7 @@ #define VGA_WIDTH 80 #define VGA_HEIGHT 25 #define VGA_RES (VGA_HEIGHT * VGA_WIDTH) +#define VGA_TAB_WIDTH 4 #define VGA_INDEX_PORT 0x3D4 #define VGA_DATA_PORT 0x3D5 diff --git a/src/driver/vga.c b/src/driver/vga.c index b75bd7a..3a18b4d 100644 --- a/src/driver/vga.c +++ b/src/driver/vga.c @@ -21,15 +21,105 @@ void vga_init(void) { vga_cursor_enable(); } -// Print -void vga_print_char(char c) { +// helper functions + +void vga_cursor_carriage_return(void) +{ + uint16_t column = cursor_position % VGA_WIDTH; - vga_buf[cursor_position] = (current_color << 8 | c); + cursor_position -= column; - vga_set_cursor_position((cursor_position + 1)); + vga_set_cursor_position(cursor_position); } + +void vga_cursor_newline(void) +{ + uint16_t row = cursor_position / VGA_WIDTH; + + row++; + + if (row >= VGA_HEIGHT) { + vga_scroll_up(); + row = VGA_HEIGHT - 1; + } + + cursor_position = row * VGA_WIDTH; + + vga_set_cursor_position(cursor_position); +} + + +void vga_cursor_tab(void) +{ + uint16_t column = cursor_position % VGA_WIDTH; + + uint16_t spaces = + VGA_TAB_WIDTH - (column % VGA_TAB_WIDTH); + + for (uint16_t i = 0; i < spaces; i++) { + + if (cursor_position >= VGA_WIDTH * VGA_HEIGHT) { + vga_scroll_up(); + + cursor_position = + (VGA_HEIGHT - 1) * VGA_WIDTH; + } + + vga_buf[cursor_position] = + ((uint16_t)current_color << 8) | ' '; + + cursor_position++; + } + + vga_set_cursor_position(cursor_position); +} + + +void vga_cursor_backspace(void) +{ + if (cursor_position == 0) + return; + + cursor_position--; + + vga_buf[cursor_position] = + ((uint16_t)current_color << 8) | ' '; + + vga_set_cursor_position(cursor_position); +} + +// Print + +void vga_print_char(char c) +{ + switch (c) { + + case '\n': + vga_cursor_newline(); + break; + + case '\r': + vga_cursor_carriage_return(); + break; + + case '\t': + vga_cursor_tab(); + break; + + case '\b': + vga_cursor_backspace(); + break; + + default: + vga_buf[cursor_position] = + ((uint16_t)current_color << 8) | (uint8_t)c; + + vga_set_cursor_position(cursor_position + 1); + break; + } +} void vga_print(const char *str) { if (str == 0) { return; @@ -167,3 +257,5 @@ void vga_scroll_up(void) { vga_set_cursor(0, VGA_HEIGHT - 1); } + + diff --git a/src/libs/stdio.c b/src/libs/stdio.c index 2a9de85..9fba101 100644 --- a/src/libs/stdio.c +++ b/src/libs/stdio.c @@ -96,7 +96,7 @@ void printf(const char *format, ...) { va_end(args); - vga_print(result); + print(result); } void snprintf(char *buffer, size_t buffer_size, const char *format, ...) { From ef9c349b3ea82de2193a775807044a84a36eeb35 Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Mon, 21 Sep 2026 19:47:29 +0100 Subject: [PATCH 22/27] add event queue ofor keyboard --- includes/driver/keyboard/event_queue.h | 25 ++++++++++++++ src/driver/keyboard/event_queue.c | 45 ++++++++++++++++++++++++++ 2 files changed, 70 insertions(+) create mode 100644 includes/driver/keyboard/event_queue.h create mode 100644 src/driver/keyboard/event_queue.c diff --git a/includes/driver/keyboard/event_queue.h b/includes/driver/keyboard/event_queue.h new file mode 100644 index 0000000..68836fb --- /dev/null +++ b/includes/driver/keyboard/event_queue.h @@ -0,0 +1,25 @@ +#ifndef EVENT_QUEUE_H +#define EVENT_QUEUE_H + +#include "keyboard_keys.h" +#include "keyboard.h" +#include "ps2.h" +#include "types.h" + + +#define KEYBOARD_EVENT_QUEUE_SIZE 256 + +typedef struct { + key_event_t events[KEYBOARD_EVENT_QUEUE_SIZE]; + uint32_t head; + uint32_t tail; +} keyboard_event_queue_t; + +extern keyboard_event_queue_t keyboard_queue; + +bool keyboard_queue_push(key_event_t event); +bool keyboard_queue_pop(key_event_t *event); + +void keyboard_queue_print(); + +#endif \ No newline at end of file diff --git a/src/driver/keyboard/event_queue.c b/src/driver/keyboard/event_queue.c new file mode 100644 index 0000000..6264118 --- /dev/null +++ b/src/driver/keyboard/event_queue.c @@ -0,0 +1,45 @@ +#include "event_queue.h" +#include "stdio.h" + +keyboard_event_queue_t keyboard_queue = {0}; + + +bool keyboard_queue_push(key_event_t event) +{ + uint32_t next = + (keyboard_queue.head + 1) % KEYBOARD_EVENT_QUEUE_SIZE; + + if (next == keyboard_queue.tail) { + return false; /* queue full */ + } + + keyboard_queue.events[keyboard_queue.head] = event; + keyboard_queue.head = next; + + return true; +} + +bool keyboard_queue_pop(key_event_t *event) +{ + if (keyboard_queue.head == keyboard_queue.tail) { + return false; /* queue empty */ + } + + *event = keyboard_queue.events[keyboard_queue.tail]; + + keyboard_queue.tail = + (keyboard_queue.tail + 1) % KEYBOARD_EVENT_QUEUE_SIZE; + + return true; +} + + +void keyboard_queue_print() { + + + printf("\033[32mKeyboard Queue: \033[0m head=%d, tail=%d\n", keyboard_queue.head, keyboard_queue.tail); + for (uint32_t i = 0; i < keyboard_queue.head - keyboard_queue.tail; i++) { + key_event_t event = keyboard_queue.events[i]; + printf("Event[%d]: key=%d, action=%d\n", i, event.key, event.action); + } +} \ No newline at end of file From 7371613aaf8fc3786e9eef0864cbdaec29eb2376 Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Mon, 21 Sep 2026 19:47:56 +0100 Subject: [PATCH 23/27] add keyboard heandler --- includes/driver/keyboard/handler.h | 21 ++++ includes/driver/keyboard/keyboard_keys.h | 37 ++++--- src/driver/keyboard/handler.c | 127 +++++++++++++++++++++++ src/driver/{ => keyboard}/keyboard.c | 16 --- src/interrupt/irq/irq.c | 1 + 5 files changed, 170 insertions(+), 32 deletions(-) create mode 100644 includes/driver/keyboard/handler.h create mode 100644 src/driver/keyboard/handler.c rename src/driver/{ => keyboard}/keyboard.c (83%) diff --git a/includes/driver/keyboard/handler.h b/includes/driver/keyboard/handler.h new file mode 100644 index 0000000..ddce5d9 --- /dev/null +++ b/includes/driver/keyboard/handler.h @@ -0,0 +1,21 @@ +#ifndef HANDLER_H +#define HANDLER_H + +#include "keyboard_keys.h" +#include "keyboard.h" +#include "ps2.h" +#include "types.h" +#include "stdio.h" + +extern scancode_state_t scan_state; + + +void keyboard_irq_handler(void); + +void keyboard_process_scancode(uint8_t data); +void keyboard_handle_event(key_event_t event); + + +// queue for keyboard events + +#endif \ No newline at end of file diff --git a/includes/driver/keyboard/keyboard_keys.h b/includes/driver/keyboard/keyboard_keys.h index fe98aea..126c268 100644 --- a/includes/driver/keyboard/keyboard_keys.h +++ b/includes/driver/keyboard/keyboard_keys.h @@ -4,23 +4,10 @@ #include "ps2.h" #include "types.h" -typedef enum { - SCAN_STATE_NORMAL, - SCAN_STATE_BREAK, - SCAN_STATE_EXTENDED, - SCAN_STATE_EXTENDED_BREAK -} scancode_state_t; - -typedef enum { - KEY_PRESSED, - KEY_RELEASED -} key_action_t; - -typedef struct { - keycode_t key; - key_action_t action; -} key_event_t; +#define KP_BREAK 0xF0 +#define KP_EXTENDED 0xE0 +#define KP_EXTENDED_BREAK 0xE0F0 typedef enum { KEY_NONE = 0, @@ -174,6 +161,24 @@ typedef enum { KEY_COUNT } keycode_t; + +typedef enum { + SCAN_STATE_NORMAL, + SCAN_STATE_BREAK, + SCAN_STATE_EXTENDED, + SCAN_STATE_EXTENDED_BREAK +} scancode_state_t; + +typedef enum { + KEY_PRESSED, + KEY_RELEASED +} key_action_t; + +typedef struct { + keycode_t key; + key_action_t action; +} key_event_t; + typedef struct { keycode_t normal[256]; keycode_t extended[256]; diff --git a/src/driver/keyboard/handler.c b/src/driver/keyboard/handler.c new file mode 100644 index 0000000..9c9b1c8 --- /dev/null +++ b/src/driver/keyboard/handler.c @@ -0,0 +1,127 @@ +#include "handler.h" +#include "keyboard.h" +#include "keyboard/event_queue.h" +#include "ps2.h" +#include "utils.h" + +#include "stdio.h" + +scancode_state_t scan_state = SCAN_STATE_NORMAL; + +void keyboard_irq_handler(void) { + if (!ps2_wait_output_full()) { + return; + } + + uint8_t data = ps2_read(); + + keyboard_process_scancode(data); + + // keycode_t keycode = scancode_set2.normal[data]; + + // printf("\n SCAN: %h -> %h", data, keycode); + + // if (data == 0xf0) { + // data = ps2_read(); + // printf("%h\n", data); + // } +} + +void keyboard_process_scancode(uint8_t data) +{ + keycode_t key; + key_event_t event; + + switch (scan_state) { + + case SCAN_STATE_NORMAL: + + if (data == 0xF0) { + scan_state = SCAN_STATE_BREAK; + return; + } + + if (data == 0xE0) { + scan_state = SCAN_STATE_EXTENDED; + return; + } + + key = scancode_set2.normal[data]; + + if (key == KEY_NONE) { + return; + } + + event.key = key; + event.action = KEY_PRESSED; + + keyboard_handle_event(event); + + return; + + + case SCAN_STATE_BREAK: + + key = scancode_set2.normal[data]; + + scan_state = SCAN_STATE_NORMAL; + + if (key == KEY_NONE) { + return; + } + + event.key = key; + event.action = KEY_RELEASED; + + keyboard_handle_event(event); + + return; + + + case SCAN_STATE_EXTENDED: + + if (data == 0xF0) { + scan_state = SCAN_STATE_EXTENDED_BREAK; + return; + } + + key = scancode_set2.extended[data]; + + scan_state = SCAN_STATE_NORMAL; + + if (key == KEY_NONE) { + return; + } + + event.key = key; + event.action = KEY_PRESSED; + + keyboard_handle_event(event); + + return; + + + case SCAN_STATE_EXTENDED_BREAK: + + key = scancode_set2.extended[data]; + + scan_state = SCAN_STATE_NORMAL; + + if (key == KEY_NONE) { + return; + } + + event.key = key; + event.action = KEY_RELEASED; + + keyboard_handle_event(event); + + return; + } +} + +void keyboard_handle_event(key_event_t event){ + keyboard_queue_push(event); + printf("\n"); + keyboard_queue_print(); +} \ No newline at end of file diff --git a/src/driver/keyboard.c b/src/driver/keyboard/keyboard.c similarity index 83% rename from src/driver/keyboard.c rename to src/driver/keyboard/keyboard.c index adf9943..0716d37 100644 --- a/src/driver/keyboard.c +++ b/src/driver/keyboard/keyboard.c @@ -78,19 +78,3 @@ void select_scancode_set(uint8_t set) { } } -void keyboard_irq_handler(void) { - if (!ps2_wait_output_full()) { - return; - } - - uint8_t data = ps2_read(); - - keycode_t keycode = scancode_set2.normal[data]; - - printf("\n SCAN: %h -> %h", data, keycode); - - if (data == 0xf0) { - data = ps2_read(); - printf("%h\n", data); - } -} \ No newline at end of file diff --git a/src/interrupt/irq/irq.c b/src/interrupt/irq/irq.c index 515a5f3..a22605c 100644 --- a/src/interrupt/irq/irq.c +++ b/src/interrupt/irq/irq.c @@ -1,5 +1,6 @@ #include "irq.h" #include "keyboard.h" +#include "keyboard/handler.h" #include "pic.h" #include "timer.h" #include "vga.h" From 847b09f76b1adab739f08fbfde150facb015fb06 Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Mon, 21 Sep 2026 19:48:13 +0100 Subject: [PATCH 24/27] code formate --- includes/driver/keyboard/event_queue.h | 3 +- includes/driver/keyboard/handler.h | 6 ++-- includes/driver/keyboard/keyboard_keys.h | 11 ++----- includes/driver/vga.h | 6 ++-- src/driver/keyboard/event_queue.c | 18 ++++------- src/driver/keyboard/handler.c | 8 ++--- src/driver/keyboard/keyboard.c | 1 - src/driver/vga.c | 38 +++++++----------------- 8 files changed, 28 insertions(+), 63 deletions(-) diff --git a/includes/driver/keyboard/event_queue.h b/includes/driver/keyboard/event_queue.h index 68836fb..dd27589 100644 --- a/includes/driver/keyboard/event_queue.h +++ b/includes/driver/keyboard/event_queue.h @@ -1,12 +1,11 @@ #ifndef EVENT_QUEUE_H #define EVENT_QUEUE_H -#include "keyboard_keys.h" #include "keyboard.h" +#include "keyboard_keys.h" #include "ps2.h" #include "types.h" - #define KEYBOARD_EVENT_QUEUE_SIZE 256 typedef struct { diff --git a/includes/driver/keyboard/handler.h b/includes/driver/keyboard/handler.h index ddce5d9..740a82a 100644 --- a/includes/driver/keyboard/handler.h +++ b/includes/driver/keyboard/handler.h @@ -1,21 +1,19 @@ #ifndef HANDLER_H #define HANDLER_H -#include "keyboard_keys.h" #include "keyboard.h" +#include "keyboard_keys.h" #include "ps2.h" -#include "types.h" #include "stdio.h" +#include "types.h" extern scancode_state_t scan_state; - void keyboard_irq_handler(void); void keyboard_process_scancode(uint8_t data); void keyboard_handle_event(key_event_t event); - // queue for keyboard events #endif \ No newline at end of file diff --git a/includes/driver/keyboard/keyboard_keys.h b/includes/driver/keyboard/keyboard_keys.h index 126c268..2243e18 100644 --- a/includes/driver/keyboard/keyboard_keys.h +++ b/includes/driver/keyboard/keyboard_keys.h @@ -4,9 +4,8 @@ #include "ps2.h" #include "types.h" - -#define KP_BREAK 0xF0 -#define KP_EXTENDED 0xE0 +#define KP_BREAK 0xF0 +#define KP_EXTENDED 0xE0 #define KP_EXTENDED_BREAK 0xE0F0 typedef enum { @@ -161,7 +160,6 @@ typedef enum { KEY_COUNT } keycode_t; - typedef enum { SCAN_STATE_NORMAL, SCAN_STATE_BREAK, @@ -169,10 +167,7 @@ typedef enum { SCAN_STATE_EXTENDED_BREAK } scancode_state_t; -typedef enum { - KEY_PRESSED, - KEY_RELEASED -} key_action_t; +typedef enum { KEY_PRESSED, KEY_RELEASED } key_action_t; typedef struct { keycode_t key; diff --git a/includes/driver/vga.h b/includes/driver/vga.h index 615cf60..7b90c93 100644 --- a/includes/driver/vga.h +++ b/includes/driver/vga.h @@ -5,9 +5,9 @@ #define VGA_ADDRESS 0xB8000 -#define VGA_WIDTH 80 -#define VGA_HEIGHT 25 -#define VGA_RES (VGA_HEIGHT * VGA_WIDTH) +#define VGA_WIDTH 80 +#define VGA_HEIGHT 25 +#define VGA_RES (VGA_HEIGHT * VGA_WIDTH) #define VGA_TAB_WIDTH 4 #define VGA_INDEX_PORT 0x3D4 diff --git a/src/driver/keyboard/event_queue.c b/src/driver/keyboard/event_queue.c index 6264118..b920a1e 100644 --- a/src/driver/keyboard/event_queue.c +++ b/src/driver/keyboard/event_queue.c @@ -3,11 +3,8 @@ keyboard_event_queue_t keyboard_queue = {0}; - -bool keyboard_queue_push(key_event_t event) -{ - uint32_t next = - (keyboard_queue.head + 1) % KEYBOARD_EVENT_QUEUE_SIZE; +bool keyboard_queue_push(key_event_t event) { + uint32_t next = (keyboard_queue.head + 1) % KEYBOARD_EVENT_QUEUE_SIZE; if (next == keyboard_queue.tail) { return false; /* queue full */ @@ -19,25 +16,22 @@ bool keyboard_queue_push(key_event_t event) return true; } -bool keyboard_queue_pop(key_event_t *event) -{ +bool keyboard_queue_pop(key_event_t *event) { if (keyboard_queue.head == keyboard_queue.tail) { return false; /* queue empty */ } *event = keyboard_queue.events[keyboard_queue.tail]; - keyboard_queue.tail = - (keyboard_queue.tail + 1) % KEYBOARD_EVENT_QUEUE_SIZE; + keyboard_queue.tail = (keyboard_queue.tail + 1) % KEYBOARD_EVENT_QUEUE_SIZE; return true; } - void keyboard_queue_print() { - - printf("\033[32mKeyboard Queue: \033[0m head=%d, tail=%d\n", keyboard_queue.head, keyboard_queue.tail); + printf("\033[32mKeyboard Queue: \033[0m head=%d, tail=%d\n", keyboard_queue.head, + keyboard_queue.tail); for (uint32_t i = 0; i < keyboard_queue.head - keyboard_queue.tail; i++) { key_event_t event = keyboard_queue.events[i]; printf("Event[%d]: key=%d, action=%d\n", i, event.key, event.action); diff --git a/src/driver/keyboard/handler.c b/src/driver/keyboard/handler.c index 9c9b1c8..6cc82cf 100644 --- a/src/driver/keyboard/handler.c +++ b/src/driver/keyboard/handler.c @@ -27,8 +27,7 @@ void keyboard_irq_handler(void) { // } } -void keyboard_process_scancode(uint8_t data) -{ +void keyboard_process_scancode(uint8_t data) { keycode_t key; key_event_t event; @@ -59,7 +58,6 @@ void keyboard_process_scancode(uint8_t data) return; - case SCAN_STATE_BREAK: key = scancode_set2.normal[data]; @@ -77,7 +75,6 @@ void keyboard_process_scancode(uint8_t data) return; - case SCAN_STATE_EXTENDED: if (data == 0xF0) { @@ -100,7 +97,6 @@ void keyboard_process_scancode(uint8_t data) return; - case SCAN_STATE_EXTENDED_BREAK: key = scancode_set2.extended[data]; @@ -120,7 +116,7 @@ void keyboard_process_scancode(uint8_t data) } } -void keyboard_handle_event(key_event_t event){ +void keyboard_handle_event(key_event_t event) { keyboard_queue_push(event); printf("\n"); keyboard_queue_print(); diff --git a/src/driver/keyboard/keyboard.c b/src/driver/keyboard/keyboard.c index 0716d37..f95ea07 100644 --- a/src/driver/keyboard/keyboard.c +++ b/src/driver/keyboard/keyboard.c @@ -77,4 +77,3 @@ void select_scancode_set(uint8_t set) { return; } } - diff --git a/src/driver/vga.c b/src/driver/vga.c index 3a18b4d..0fe1104 100644 --- a/src/driver/vga.c +++ b/src/driver/vga.c @@ -21,11 +21,9 @@ void vga_init(void) { vga_cursor_enable(); } +// helper functions -// helper functions - -void vga_cursor_carriage_return(void) -{ +void vga_cursor_carriage_return(void) { uint16_t column = cursor_position % VGA_WIDTH; cursor_position -= column; @@ -33,9 +31,7 @@ void vga_cursor_carriage_return(void) vga_set_cursor_position(cursor_position); } - -void vga_cursor_newline(void) -{ +void vga_cursor_newline(void) { uint16_t row = cursor_position / VGA_WIDTH; row++; @@ -50,25 +46,20 @@ void vga_cursor_newline(void) vga_set_cursor_position(cursor_position); } - -void vga_cursor_tab(void) -{ +void vga_cursor_tab(void) { uint16_t column = cursor_position % VGA_WIDTH; - uint16_t spaces = - VGA_TAB_WIDTH - (column % VGA_TAB_WIDTH); + uint16_t spaces = VGA_TAB_WIDTH - (column % VGA_TAB_WIDTH); for (uint16_t i = 0; i < spaces; i++) { if (cursor_position >= VGA_WIDTH * VGA_HEIGHT) { vga_scroll_up(); - cursor_position = - (VGA_HEIGHT - 1) * VGA_WIDTH; + cursor_position = (VGA_HEIGHT - 1) * VGA_WIDTH; } - vga_buf[cursor_position] = - ((uint16_t)current_color << 8) | ' '; + vga_buf[cursor_position] = ((uint16_t)current_color << 8) | ' '; cursor_position++; } @@ -76,24 +67,20 @@ void vga_cursor_tab(void) vga_set_cursor_position(cursor_position); } - -void vga_cursor_backspace(void) -{ +void vga_cursor_backspace(void) { if (cursor_position == 0) return; cursor_position--; - vga_buf[cursor_position] = - ((uint16_t)current_color << 8) | ' '; + vga_buf[cursor_position] = ((uint16_t)current_color << 8) | ' '; vga_set_cursor_position(cursor_position); } // Print -void vga_print_char(char c) -{ +void vga_print_char(char c) { switch (c) { case '\n': @@ -113,8 +100,7 @@ void vga_print_char(char c) break; default: - vga_buf[cursor_position] = - ((uint16_t)current_color << 8) | (uint8_t)c; + vga_buf[cursor_position] = ((uint16_t)current_color << 8) | (uint8_t)c; vga_set_cursor_position(cursor_position + 1); break; @@ -257,5 +243,3 @@ void vga_scroll_up(void) { vga_set_cursor(0, VGA_HEIGHT - 1); } - - From a875d3bbdfca45d3528cf71cddd9dcf1f61a5b25 Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Mon, 21 Sep 2026 20:29:08 +0100 Subject: [PATCH 25/27] add keyboard layout support and enhance event handling --- includes/driver/keyboard/event_queue.h | 2 + includes/driver/keyboard/keyboard.h | 3 + includes/driver/keyboard/keyboard_keys.h | 15 ++ includes/driver/keyboard/keyboard_layout.h | 32 +++ src/driver/keyboard/event_queue.c | 11 + src/driver/keyboard/handler.c | 69 +++++- src/driver/keyboard/keyboard.c | 16 ++ src/driver/keyboard/layout/us.c | 274 +++++++++++++++++++++ 8 files changed, 421 insertions(+), 1 deletion(-) create mode 100644 includes/driver/keyboard/keyboard_layout.h create mode 100644 src/driver/keyboard/layout/us.c diff --git a/includes/driver/keyboard/event_queue.h b/includes/driver/keyboard/event_queue.h index dd27589..739b092 100644 --- a/includes/driver/keyboard/event_queue.h +++ b/includes/driver/keyboard/event_queue.h @@ -20,5 +20,7 @@ bool keyboard_queue_push(key_event_t event); bool keyboard_queue_pop(key_event_t *event); void keyboard_queue_print(); +void keyboard_queue_print_last(); + #endif \ No newline at end of file diff --git a/includes/driver/keyboard/keyboard.h b/includes/driver/keyboard/keyboard.h index 45f7785..51842ef 100644 --- a/includes/driver/keyboard/keyboard.h +++ b/includes/driver/keyboard/keyboard.h @@ -2,6 +2,7 @@ #define keyboard_H #include "keyboard_keys.h" +#include "keyboard_layout.h" #include "ps2.h" #include "types.h" @@ -17,6 +18,8 @@ void init_keyboard(void); void reset_keyboard(void); void set_scaning(bool state); void select_scancode_set(uint8_t set); +void keyboard_set_layout(const keyboard_layout_t *layout); +char keyboard_translate(keycode_t key, const keyboard_state_t *state); uint8_t keyboard_get_scan_code_set(void); diff --git a/includes/driver/keyboard/keyboard_keys.h b/includes/driver/keyboard/keyboard_keys.h index 2243e18..40e3dfc 100644 --- a/includes/driver/keyboard/keyboard_keys.h +++ b/includes/driver/keyboard/keyboard_keys.h @@ -160,6 +160,21 @@ typedef enum { KEY_COUNT } keycode_t; +typedef struct { + bool left_shift; + bool right_shift; + + bool left_ctrl; + bool right_ctrl; + + bool left_alt; + bool right_alt; + + bool caps_lock; + bool num_lock; + bool scroll_lock; +} keyboard_state_t; + typedef enum { SCAN_STATE_NORMAL, SCAN_STATE_BREAK, diff --git a/includes/driver/keyboard/keyboard_layout.h b/includes/driver/keyboard/keyboard_layout.h new file mode 100644 index 0000000..1b03a40 --- /dev/null +++ b/includes/driver/keyboard/keyboard_layout.h @@ -0,0 +1,32 @@ +#ifndef KEYBOARD_LAYOUT_H +#define KEYBOARD_LAYOUT_H + +#include "keyboard_keys.h" +#include "types.h" + + +#define KEY_COUNT 256 + +typedef struct { + char normal; + char shift; +} keyboard_layout_entry_t; + + +typedef struct { + const char *name; + + keyboard_layout_entry_t keys[KEY_COUNT]; +} keyboard_layout_t; + + +extern const keyboard_layout_t keyboard_layout_us; + +char keyboard_layout_translate( + const keyboard_layout_t *layout, + keycode_t key, + const keyboard_state_t *state +); + + +#endif \ No newline at end of file diff --git a/src/driver/keyboard/event_queue.c b/src/driver/keyboard/event_queue.c index b920a1e..27edf8f 100644 --- a/src/driver/keyboard/event_queue.c +++ b/src/driver/keyboard/event_queue.c @@ -36,4 +36,15 @@ void keyboard_queue_print() { key_event_t event = keyboard_queue.events[i]; printf("Event[%d]: key=%d, action=%d\n", i, event.key, event.action); } +} + +void keyboard_queue_print_last() { + if (keyboard_queue.head == keyboard_queue.tail) { + printf("\033[31mKeyboard Queue: \033[0m Empty\n"); + return; + } + + uint32_t last = (keyboard_queue.head - 1 + KEYBOARD_EVENT_QUEUE_SIZE) % KEYBOARD_EVENT_QUEUE_SIZE; + key_event_t event = keyboard_queue.events[last]; + printf("\033[32mKeyboard Queue:\033[0m Last event[%d] : key=%d, action=%d\n", last, event.key, event.action); } \ No newline at end of file diff --git a/src/driver/keyboard/handler.c b/src/driver/keyboard/handler.c index 6cc82cf..b948043 100644 --- a/src/driver/keyboard/handler.c +++ b/src/driver/keyboard/handler.c @@ -3,11 +3,14 @@ #include "keyboard/event_queue.h" #include "ps2.h" #include "utils.h" +#include "vga.h" #include "stdio.h" scancode_state_t scan_state = SCAN_STATE_NORMAL; +keyboard_state_t keyboard_state = {0}; + void keyboard_irq_handler(void) { if (!ps2_wait_output_full()) { return; @@ -116,8 +119,72 @@ void keyboard_process_scancode(uint8_t data) { } } + void keyboard_handle_event(key_event_t event) { keyboard_queue_push(event); printf("\n"); - keyboard_queue_print(); + keyboard_queue_print_last(); +} + +void keyboard_update_state(const key_event_t *event) +{ + switch (event->key) { + + case KEY_LEFT_SHIFT: + keyboard_state.left_shift = + event->action == KEY_PRESSED; + break; + + case KEY_RIGHT_SHIFT: + keyboard_state.right_shift = + event->action == KEY_PRESSED; + break; + + case KEY_LEFT_CTRL: + keyboard_state.left_ctrl = + event->action == KEY_PRESSED; + break; + + case KEY_RIGHT_CTRL: + keyboard_state.right_ctrl = + event->action == KEY_PRESSED; + break; + + case KEY_LEFT_ALT: + keyboard_state.left_alt = + event->action == KEY_PRESSED; + break; + + case KEY_RIGHT_ALT: + keyboard_state.right_alt = + event->action == KEY_PRESSED; + break; + + default: + break; + } +} + +// void keyboard_process(void) +// { +// key_event_t event; + +// while (keyboard_queue_pop(&event)) { +// keyboard_process_event(&event); +// } +// } + +void keyboard_process_event(const key_event_t *event) +{ + keyboard_update_state(event); + + if (event->action != KEY_PRESSED) { + return; + } + + char character = keyboard_translate(event->key, &keyboard_state); + + if (character != '\0') { + vga_print_char(character); + } } \ No newline at end of file diff --git a/src/driver/keyboard/keyboard.c b/src/driver/keyboard/keyboard.c index f95ea07..e0edceb 100644 --- a/src/driver/keyboard/keyboard.c +++ b/src/driver/keyboard/keyboard.c @@ -2,8 +2,13 @@ #include "ps2.h" #include "utils.h" +#include "keyboard_layout.h" + #include "stdio.h" +static const keyboard_layout_t *active_layout; + + void init_keyboard(void) { reset_keyboard(); set_scaning(false); @@ -11,6 +16,17 @@ void init_keyboard(void) { set_scaning(true); ps2_flush_output(); + + keyboard_set_layout(&keyboard_layout_us); +} + + +void keyboard_set_layout(const keyboard_layout_t *layout) { + active_layout = layout; +} + +char keyboard_translate(keycode_t key, const keyboard_state_t *state) { + return keyboard_layout_translate(active_layout, key, state); } void reset_keyboard(void) { diff --git a/src/driver/keyboard/layout/us.c b/src/driver/keyboard/layout/us.c new file mode 100644 index 0000000..5cabd9b --- /dev/null +++ b/src/driver/keyboard/layout/us.c @@ -0,0 +1,274 @@ +#include "keyboard_layout.h" + +const keyboard_layout_t keyboard_layout_us = { + .name = "US QWERTY", + + .keys = { + [KEY_A] = { + .normal = 'a', + .shift = 'A' + }, + + [KEY_B] = { + .normal = 'b', + .shift = 'B' + }, + + [KEY_C] = { + .normal = 'c', + .shift = 'C' + }, + + [KEY_D] = { + .normal = 'd', + .shift = 'D' + }, + + [KEY_E] = { + .normal = 'e', + .shift = 'E' + }, + + [KEY_F] = { + .normal = 'f', + .shift = 'F' + }, + + [KEY_G] = { + .normal = 'g', + .shift = 'G' + }, + + [KEY_H] = { + .normal = 'h', + .shift = 'H' + }, + + [KEY_I] = { + .normal = 'i', + .shift = 'I' + }, + + [KEY_J] = { + .normal = 'j', + .shift = 'J' + }, + + [KEY_K] = { + .normal = 'k', + .shift = 'K' + }, + + [KEY_L] = { + .normal = 'l', + .shift = 'L' + }, + + [KEY_M] = { + .normal = 'm', + .shift = 'M' + }, + + [KEY_N] = { + .normal = 'n', + .shift = 'N' + }, + + [KEY_O] = { + .normal = 'o', + .shift = 'O' + }, + + [KEY_P] = { + .normal = 'p', + .shift = 'P' + }, + + [KEY_Q] = { + .normal = 'q', + .shift = 'Q' + }, + + [KEY_R] = { + .normal = 'r', + .shift = 'R' + }, + + [KEY_S] = { + .normal = 's', + .shift = 'S' + }, + + [KEY_T] = { + .normal = 't', + .shift = 'T' + }, + + [KEY_U] = { + .normal = 'u', + .shift = 'U' + }, + + [KEY_V] = { + .normal = 'v', + .shift = 'V' + }, + + [KEY_W] = { + .normal = 'w', + .shift = 'W' + }, + + [KEY_X] = { + .normal = 'x', + .shift = 'X' + }, + + [KEY_Y] = { + .normal = 'y', + .shift = 'Y' + }, + + [KEY_Z] = { + .normal = 'z', + .shift = 'Z' + }, + + [KEY_1] = { + .normal = '1', + .shift = '!' + }, + + [KEY_2] = { + .normal = '2', + .shift = '@' + }, + + [KEY_3] = { + .normal = '3', + .shift = '#' + }, + + [KEY_4] = { + .normal = '4', + .shift = '$' + }, + + [KEY_5] = { + .normal = '5', + .shift = '%' + }, + + [KEY_6] = { + .normal = '6', + .shift = '^' + }, + + [KEY_7] = { + .normal = '7', + .shift = '&' + }, + + [KEY_8] = { + .normal = '8', + .shift = '*' + }, + + [KEY_9] = { + .normal = '9', + .shift = '(' + }, + + [KEY_0] = { + .normal = '0', + .shift = ')' + }, + + [KEY_SPACE] = { + .normal = ' ', + .shift = ' ' + }, + + [KEY_MINUS] = { + .normal = '-', + .shift = '_' + }, + + [KEY_EQUAL] = { + .normal = '=', + .shift = '+' + }, + + [KEY_COMMA] = { + .normal = ',', + .shift = '<' + }, + + [KEY_DOT] = { + .normal = '.', + .shift = '>' + }, + + [KEY_SLASH] = { + .normal = '/', + .shift = '?' + }, + + [KEY_SEMICOLON] = { + .normal = ';', + .shift = ':' + }, + + [KEY_APOSTROPHE] = { + .normal = '\'', + .shift = '"' + }, + + [KEY_GRAVE] = { + .normal = '`', + .shift = '~' + }, + + [KEY_LEFT_BRACKET] = { + .normal = '[', + .shift = '{' + }, + + [KEY_RIGHT_BRACKET] = { + .normal = ']', + .shift = '}' + }, + + [KEY_BACKSLASH] = { + .normal = '\\', + .shift = '|' + }, + } +}; + +char keyboard_layout_translate( + const keyboard_layout_t *layout, + keycode_t key, + const keyboard_state_t *state +){ + if (key >= KEY_COUNT) { + return '\0'; + } + + keyboard_layout_entry_t entry = layout->keys[key]; + + if (entry.normal == '\0') { + return '\0'; + } + + bool shifted = + state->left_shift || + state->right_shift; + + if (shifted) { + return entry.shift; + } + + + return entry.normal; +} \ No newline at end of file From 43c67d4456d92201c51281e87a0d59c1adea0017 Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Mon, 21 Sep 2026 21:31:46 +0100 Subject: [PATCH 26/27] add princt cahr and print hex --- includes/lib/stdio.h | 2 ++ src/libs/stdio.c | 8 ++++++++ 2 files changed, 10 insertions(+) diff --git a/includes/lib/stdio.h b/includes/lib/stdio.h index 3b24fa2..d3097bf 100644 --- a/includes/lib/stdio.h +++ b/includes/lib/stdio.h @@ -6,6 +6,8 @@ void print(const char *str); void println(const char *str); +void print_char(char c); +void print_hex(uint32_t value); void print_at_end(const char *str, uint8_t color); void printf(const char *format, ...); diff --git a/src/libs/stdio.c b/src/libs/stdio.c index 9fba101..1d965b1 100644 --- a/src/libs/stdio.c +++ b/src/libs/stdio.c @@ -85,6 +85,14 @@ void println(const char *str) { vga_print(str); } +void print_char(char c) { + vga_print_char(c); +} + +void print_hex(uint32_t value) { + vga_print_hex(value); +} + void print_at_end(const char *str, uint8_t color) { vga_print_at_end_c(str, color); } void printf(const char *format, ...) { From f3451498a77221a35100331a5f052c1b83d1ea66 Mon Sep 17 00:00:00 2001 From: Ox03bb Date: Mon, 21 Sep 2026 21:32:15 +0100 Subject: [PATCH 27/27] complite keyboard --- includes/driver/keyboard/event_queue.h | 25 +- includes/driver/keyboard/handler.h | 3 +- includes/driver/keyboard/keyboard_layout.h | 11 +- src/driver/keyboard/event_queue.c | 64 ++-- src/driver/keyboard/handler.c | 184 ++++++----- src/driver/keyboard/keyboard.c | 6 +- src/driver/keyboard/layout/us.c | 349 ++++++--------------- src/kernel/kernel.c | 16 + src/libs/stdio.c | 8 +- 9 files changed, 291 insertions(+), 375 deletions(-) diff --git a/includes/driver/keyboard/event_queue.h b/includes/driver/keyboard/event_queue.h index 739b092..bc5ae83 100644 --- a/includes/driver/keyboard/event_queue.h +++ b/includes/driver/keyboard/event_queue.h @@ -16,11 +16,28 @@ typedef struct { extern keyboard_event_queue_t keyboard_queue; -bool keyboard_queue_push(key_event_t event); -bool keyboard_queue_pop(key_event_t *event); +typedef enum { + INPUT_CHAR, + INPUT_ENTER, + INPUT_BACKSPACE, + INPUT_TAB, + INPUT_UP, + INPUT_DOWN, + INPUT_LEFT, + INPUT_RIGHT, +} input_type_t; -void keyboard_queue_print(); -void keyboard_queue_print_last(); +typedef struct { + input_type_t type; + char character; +} input_event_t; + +void input_queue_push(input_event_t event); +void input_queue_pop(input_event_t *event); +void input_queue_print(); +void input_queue_print_last(); +void input_queue_clear(); +extern input_event_t input_queue[KEYBOARD_EVENT_QUEUE_SIZE]; #endif \ No newline at end of file diff --git a/includes/driver/keyboard/handler.h b/includes/driver/keyboard/handler.h index 740a82a..d81592a 100644 --- a/includes/driver/keyboard/handler.h +++ b/includes/driver/keyboard/handler.h @@ -12,7 +12,8 @@ extern scancode_state_t scan_state; void keyboard_irq_handler(void); void keyboard_process_scancode(uint8_t data); -void keyboard_handle_event(key_event_t event); +void keyboard_handle_key(keycode_t key, key_action_t action); +void keyboard_update_state(keycode_t key, key_action_t action); // queue for keyboard events diff --git a/includes/driver/keyboard/keyboard_layout.h b/includes/driver/keyboard/keyboard_layout.h index 1b03a40..47239bb 100644 --- a/includes/driver/keyboard/keyboard_layout.h +++ b/includes/driver/keyboard/keyboard_layout.h @@ -4,7 +4,6 @@ #include "keyboard_keys.h" #include "types.h" - #define KEY_COUNT 256 typedef struct { @@ -12,21 +11,15 @@ typedef struct { char shift; } keyboard_layout_entry_t; - typedef struct { const char *name; keyboard_layout_entry_t keys[KEY_COUNT]; } keyboard_layout_t; - extern const keyboard_layout_t keyboard_layout_us; -char keyboard_layout_translate( - const keyboard_layout_t *layout, - keycode_t key, - const keyboard_state_t *state -); - +char keyboard_layout_translate(const keyboard_layout_t *layout, keycode_t key, + const keyboard_state_t *state); #endif \ No newline at end of file diff --git a/src/driver/keyboard/event_queue.c b/src/driver/keyboard/event_queue.c index 27edf8f..5d87d42 100644 --- a/src/driver/keyboard/event_queue.c +++ b/src/driver/keyboard/event_queue.c @@ -1,50 +1,54 @@ #include "event_queue.h" #include "stdio.h" -keyboard_event_queue_t keyboard_queue = {0}; +// Input event queue -bool keyboard_queue_push(key_event_t event) { - uint32_t next = (keyboard_queue.head + 1) % KEYBOARD_EVENT_QUEUE_SIZE; +input_event_t input_queue[KEYBOARD_EVENT_QUEUE_SIZE]; +uint32_t input_queue_head = 0; +uint32_t input_queue_tail = 0; - if (next == keyboard_queue.tail) { - return false; /* queue full */ - } +void input_queue_push(input_event_t event) { + uint32_t next = (input_queue_head + 1) % KEYBOARD_EVENT_QUEUE_SIZE; - keyboard_queue.events[keyboard_queue.head] = event; - keyboard_queue.head = next; + if (next == input_queue_tail) { + return; /* queue full */ + } - return true; + input_queue[input_queue_head] = event; + input_queue_head = next; } -bool keyboard_queue_pop(key_event_t *event) { - if (keyboard_queue.head == keyboard_queue.tail) { - return false; /* queue empty */ +void input_queue_pop(input_event_t *event) { + if (input_queue_head == input_queue_tail) { + return; /* queue empty */ } - *event = keyboard_queue.events[keyboard_queue.tail]; + *event = input_queue[input_queue_tail]; - keyboard_queue.tail = (keyboard_queue.tail + 1) % KEYBOARD_EVENT_QUEUE_SIZE; - - return true; + input_queue_tail = (input_queue_tail + 1) % KEYBOARD_EVENT_QUEUE_SIZE; } -void keyboard_queue_print() { - - printf("\033[32mKeyboard Queue: \033[0m head=%d, tail=%d\n", keyboard_queue.head, - keyboard_queue.tail); - for (uint32_t i = 0; i < keyboard_queue.head - keyboard_queue.tail; i++) { - key_event_t event = keyboard_queue.events[i]; - printf("Event[%d]: key=%d, action=%d\n", i, event.key, event.action); +void input_queue_print() { + printf("\033[32mInput Queue: \033[0m head=%d, tail=%d\n", input_queue_head, input_queue_tail); + for (uint32_t i = 0; i < input_queue_head - input_queue_tail; i++) { + input_event_t event = input_queue[i]; + printf("Event[%d]: type=%d, character=%c\n", i, event.type, event.character); } } -void keyboard_queue_print_last() { - if (keyboard_queue.head == keyboard_queue.tail) { - printf("\033[31mKeyboard Queue: \033[0m Empty\n"); +void input_queue_print_last() { + if (input_queue_head == input_queue_tail) { + printf("\033[31mInput Queue: \033[0m Empty\n"); return; } - uint32_t last = (keyboard_queue.head - 1 + KEYBOARD_EVENT_QUEUE_SIZE) % KEYBOARD_EVENT_QUEUE_SIZE; - key_event_t event = keyboard_queue.events[last]; - printf("\033[32mKeyboard Queue:\033[0m Last event[%d] : key=%d, action=%d\n", last, event.key, event.action); -} \ No newline at end of file + uint32_t last = (input_queue_head - 1 + KEYBOARD_EVENT_QUEUE_SIZE) % KEYBOARD_EVENT_QUEUE_SIZE; + input_event_t event = input_queue[last]; + printf("\033[32mInput Queue:\033[0m Last event[%d] : type=%d, character=%c\n", last, event.type, + event.character); +} + +void input_queue_clear() { + input_queue_head = 0; + input_queue_tail = 0; +} diff --git a/src/driver/keyboard/handler.c b/src/driver/keyboard/handler.c index b948043..baaf715 100644 --- a/src/driver/keyboard/handler.c +++ b/src/driver/keyboard/handler.c @@ -3,14 +3,15 @@ #include "keyboard/event_queue.h" #include "ps2.h" #include "utils.h" -#include "vga.h" - -#include "stdio.h" scancode_state_t scan_state = SCAN_STATE_NORMAL; keyboard_state_t keyboard_state = {0}; +/* -------------------------------------------------------------------------- */ +/* IRQ handler */ +/* -------------------------------------------------------------------------- */ + void keyboard_irq_handler(void) { if (!ps2_wait_output_full()) { return; @@ -19,20 +20,14 @@ void keyboard_irq_handler(void) { uint8_t data = ps2_read(); keyboard_process_scancode(data); - - // keycode_t keycode = scancode_set2.normal[data]; - - // printf("\n SCAN: %h -> %h", data, keycode); - - // if (data == 0xf0) { - // data = ps2_read(); - // printf("%h\n", data); - // } } +/* -------------------------------------------------------------------------- */ +/* Scan-code processing */ +/* -------------------------------------------------------------------------- */ + void keyboard_process_scancode(uint8_t data) { keycode_t key; - key_event_t event; switch (scan_state) { @@ -54,11 +49,7 @@ void keyboard_process_scancode(uint8_t data) { return; } - event.key = key; - event.action = KEY_PRESSED; - - keyboard_handle_event(event); - + keyboard_handle_key(key, KEY_PRESSED); return; case SCAN_STATE_BREAK: @@ -71,11 +62,7 @@ void keyboard_process_scancode(uint8_t data) { return; } - event.key = key; - event.action = KEY_RELEASED; - - keyboard_handle_event(event); - + keyboard_handle_key(key, KEY_RELEASED); return; case SCAN_STATE_EXTENDED: @@ -93,11 +80,7 @@ void keyboard_process_scancode(uint8_t data) { return; } - event.key = key; - event.action = KEY_PRESSED; - - keyboard_handle_event(event); - + keyboard_handle_key(key, KEY_PRESSED); return; case SCAN_STATE_EXTENDED_BREAK: @@ -110,81 +93,142 @@ void keyboard_process_scancode(uint8_t data) { return; } - event.key = key; - event.action = KEY_RELEASED; + keyboard_handle_key(key, KEY_RELEASED); + return; + } +} + +/* -------------------------------------------------------------------------- */ +/* Key processing */ +/* -------------------------------------------------------------------------- */ - keyboard_handle_event(event); +void keyboard_handle_key(keycode_t key, key_action_t action) { + keyboard_update_state(key, action); + /* + * Key release events are used only to update the keyboard state. + */ + if (action != KEY_PRESSED) { return; } -} + input_event_t input = {0}; + + /* ---------------------------------------------------------------------- */ + /* Character input */ + /* ---------------------------------------------------------------------- */ + + char character = keyboard_translate(key, &keyboard_state); + + if (character != '\0') { + + input.type = INPUT_CHAR; + input.character = character; + + input_queue_push(input); + + return; + } + + /* ---------------------------------------------------------------------- */ + /* Special keys */ + /* ---------------------------------------------------------------------- */ + + switch (key) { + + case KEY_ENTER: + input.type = INPUT_ENTER; + break; + + case KEY_BACKSPACE: + input.type = INPUT_BACKSPACE; + break; + + case KEY_TAB: + input.type = INPUT_TAB; + break; + + case KEY_UP: + input.type = INPUT_UP; + break; + + case KEY_DOWN: + input.type = INPUT_DOWN; + break; + + case KEY_LEFT: + input.type = INPUT_LEFT; + break; + + case KEY_RIGHT: + input.type = INPUT_RIGHT; + break; + + default: + return; + } -void keyboard_handle_event(key_event_t event) { - keyboard_queue_push(event); - printf("\n"); - keyboard_queue_print_last(); + input_queue_push(input); } -void keyboard_update_state(const key_event_t *event) -{ - switch (event->key) { +/* -------------------------------------------------------------------------- */ +/* Keyboard state */ +/* -------------------------------------------------------------------------- */ + +void keyboard_update_state(keycode_t key, key_action_t action) { + bool pressed = action == KEY_PRESSED; + + switch (key) { case KEY_LEFT_SHIFT: - keyboard_state.left_shift = - event->action == KEY_PRESSED; + keyboard_state.left_shift = pressed; break; case KEY_RIGHT_SHIFT: - keyboard_state.right_shift = - event->action == KEY_PRESSED; + keyboard_state.right_shift = pressed; break; case KEY_LEFT_CTRL: - keyboard_state.left_ctrl = - event->action == KEY_PRESSED; + keyboard_state.left_ctrl = pressed; break; case KEY_RIGHT_CTRL: - keyboard_state.right_ctrl = - event->action == KEY_PRESSED; + keyboard_state.right_ctrl = pressed; break; case KEY_LEFT_ALT: - keyboard_state.left_alt = - event->action == KEY_PRESSED; + keyboard_state.left_alt = pressed; break; case KEY_RIGHT_ALT: - keyboard_state.right_alt = - event->action == KEY_PRESSED; + keyboard_state.right_alt = pressed; break; - default: + case KEY_CAPS_LOCK: + + if (pressed) { + keyboard_state.caps_lock = !keyboard_state.caps_lock; + } + break; - } -} -// void keyboard_process(void) -// { -// key_event_t event; + case KEY_NUM_LOCK: + + if (pressed) { + keyboard_state.num_lock = !keyboard_state.num_lock; + } -// while (keyboard_queue_pop(&event)) { -// keyboard_process_event(&event); -// } -// } + break; -void keyboard_process_event(const key_event_t *event) -{ - keyboard_update_state(event); + case KEY_SCROLL_LOCK: - if (event->action != KEY_PRESSED) { - return; - } + if (pressed) { + keyboard_state.scroll_lock = !keyboard_state.scroll_lock; + } - char character = keyboard_translate(event->key, &keyboard_state); + break; - if (character != '\0') { - vga_print_char(character); + default: + break; } } \ No newline at end of file diff --git a/src/driver/keyboard/keyboard.c b/src/driver/keyboard/keyboard.c index e0edceb..f325aa6 100644 --- a/src/driver/keyboard/keyboard.c +++ b/src/driver/keyboard/keyboard.c @@ -8,7 +8,6 @@ static const keyboard_layout_t *active_layout; - void init_keyboard(void) { reset_keyboard(); set_scaning(false); @@ -20,10 +19,7 @@ void init_keyboard(void) { keyboard_set_layout(&keyboard_layout_us); } - -void keyboard_set_layout(const keyboard_layout_t *layout) { - active_layout = layout; -} +void keyboard_set_layout(const keyboard_layout_t *layout) { active_layout = layout; } char keyboard_translate(keycode_t key, const keyboard_state_t *state) { return keyboard_layout_translate(active_layout, key, state); diff --git a/src/driver/keyboard/layout/us.c b/src/driver/keyboard/layout/us.c index 5cabd9b..b334008 100644 --- a/src/driver/keyboard/layout/us.c +++ b/src/driver/keyboard/layout/us.c @@ -4,253 +4,105 @@ const keyboard_layout_t keyboard_layout_us = { .name = "US QWERTY", .keys = { - [KEY_A] = { - .normal = 'a', - .shift = 'A' - }, - - [KEY_B] = { - .normal = 'b', - .shift = 'B' - }, - - [KEY_C] = { - .normal = 'c', - .shift = 'C' - }, - - [KEY_D] = { - .normal = 'd', - .shift = 'D' - }, - - [KEY_E] = { - .normal = 'e', - .shift = 'E' - }, - - [KEY_F] = { - .normal = 'f', - .shift = 'F' - }, - - [KEY_G] = { - .normal = 'g', - .shift = 'G' - }, - - [KEY_H] = { - .normal = 'h', - .shift = 'H' - }, - - [KEY_I] = { - .normal = 'i', - .shift = 'I' - }, - - [KEY_J] = { - .normal = 'j', - .shift = 'J' - }, - - [KEY_K] = { - .normal = 'k', - .shift = 'K' - }, - - [KEY_L] = { - .normal = 'l', - .shift = 'L' - }, - - [KEY_M] = { - .normal = 'm', - .shift = 'M' - }, - - [KEY_N] = { - .normal = 'n', - .shift = 'N' - }, - - [KEY_O] = { - .normal = 'o', - .shift = 'O' - }, - - [KEY_P] = { - .normal = 'p', - .shift = 'P' - }, - - [KEY_Q] = { - .normal = 'q', - .shift = 'Q' - }, - - [KEY_R] = { - .normal = 'r', - .shift = 'R' - }, - - [KEY_S] = { - .normal = 's', - .shift = 'S' - }, - - [KEY_T] = { - .normal = 't', - .shift = 'T' - }, - - [KEY_U] = { - .normal = 'u', - .shift = 'U' - }, - - [KEY_V] = { - .normal = 'v', - .shift = 'V' - }, - - [KEY_W] = { - .normal = 'w', - .shift = 'W' - }, - - [KEY_X] = { - .normal = 'x', - .shift = 'X' - }, - - [KEY_Y] = { - .normal = 'y', - .shift = 'Y' - }, - - [KEY_Z] = { - .normal = 'z', - .shift = 'Z' - }, - - [KEY_1] = { - .normal = '1', - .shift = '!' - }, - - [KEY_2] = { - .normal = '2', - .shift = '@' - }, - - [KEY_3] = { - .normal = '3', - .shift = '#' - }, - - [KEY_4] = { - .normal = '4', - .shift = '$' - }, - - [KEY_5] = { - .normal = '5', - .shift = '%' - }, - - [KEY_6] = { - .normal = '6', - .shift = '^' - }, - - [KEY_7] = { - .normal = '7', - .shift = '&' - }, - - [KEY_8] = { - .normal = '8', - .shift = '*' - }, - - [KEY_9] = { - .normal = '9', - .shift = '(' - }, - - [KEY_0] = { - .normal = '0', - .shift = ')' - }, - - [KEY_SPACE] = { - .normal = ' ', - .shift = ' ' - }, - - [KEY_MINUS] = { - .normal = '-', - .shift = '_' - }, - - [KEY_EQUAL] = { - .normal = '=', - .shift = '+' - }, - - [KEY_COMMA] = { - .normal = ',', - .shift = '<' - }, - - [KEY_DOT] = { - .normal = '.', - .shift = '>' - }, - - [KEY_SLASH] = { - .normal = '/', - .shift = '?' - }, - - [KEY_SEMICOLON] = { - .normal = ';', - .shift = ':' - }, - - [KEY_APOSTROPHE] = { - .normal = '\'', - .shift = '"' - }, - - [KEY_GRAVE] = { - .normal = '`', - .shift = '~' - }, - - [KEY_LEFT_BRACKET] = { - .normal = '[', - .shift = '{' - }, - - [KEY_RIGHT_BRACKET] = { - .normal = ']', - .shift = '}' - }, - - [KEY_BACKSLASH] = { - .normal = '\\', - .shift = '|' - }, - } -}; + [KEY_A] = {.normal = 'a', .shift = 'A'}, + + [KEY_B] = {.normal = 'b', .shift = 'B'}, + + [KEY_C] = {.normal = 'c', .shift = 'C'}, + + [KEY_D] = {.normal = 'd', .shift = 'D'}, + + [KEY_E] = {.normal = 'e', .shift = 'E'}, + + [KEY_F] = {.normal = 'f', .shift = 'F'}, + + [KEY_G] = {.normal = 'g', .shift = 'G'}, + + [KEY_H] = {.normal = 'h', .shift = 'H'}, + + [KEY_I] = {.normal = 'i', .shift = 'I'}, + + [KEY_J] = {.normal = 'j', .shift = 'J'}, + + [KEY_K] = {.normal = 'k', .shift = 'K'}, + + [KEY_L] = {.normal = 'l', .shift = 'L'}, + + [KEY_M] = {.normal = 'm', .shift = 'M'}, + + [KEY_N] = {.normal = 'n', .shift = 'N'}, + + [KEY_O] = {.normal = 'o', .shift = 'O'}, + + [KEY_P] = {.normal = 'p', .shift = 'P'}, + + [KEY_Q] = {.normal = 'q', .shift = 'Q'}, + + [KEY_R] = {.normal = 'r', .shift = 'R'}, + + [KEY_S] = {.normal = 's', .shift = 'S'}, + + [KEY_T] = {.normal = 't', .shift = 'T'}, + + [KEY_U] = {.normal = 'u', .shift = 'U'}, + + [KEY_V] = {.normal = 'v', .shift = 'V'}, + + [KEY_W] = {.normal = 'w', .shift = 'W'}, + + [KEY_X] = {.normal = 'x', .shift = 'X'}, + + [KEY_Y] = {.normal = 'y', .shift = 'Y'}, -char keyboard_layout_translate( - const keyboard_layout_t *layout, - keycode_t key, - const keyboard_state_t *state -){ + [KEY_Z] = {.normal = 'z', .shift = 'Z'}, + + [KEY_1] = {.normal = '1', .shift = '!'}, + + [KEY_2] = {.normal = '2', .shift = '@'}, + + [KEY_3] = {.normal = '3', .shift = '#'}, + + [KEY_4] = {.normal = '4', .shift = '$'}, + + [KEY_5] = {.normal = '5', .shift = '%'}, + + [KEY_6] = {.normal = '6', .shift = '^'}, + + [KEY_7] = {.normal = '7', .shift = '&'}, + + [KEY_8] = {.normal = '8', .shift = '*'}, + + [KEY_9] = {.normal = '9', .shift = '('}, + + [KEY_0] = {.normal = '0', .shift = ')'}, + + [KEY_SPACE] = {.normal = ' ', .shift = ' '}, + + [KEY_MINUS] = {.normal = '-', .shift = '_'}, + + [KEY_EQUAL] = {.normal = '=', .shift = '+'}, + + [KEY_COMMA] = {.normal = ',', .shift = '<'}, + + [KEY_DOT] = {.normal = '.', .shift = '>'}, + + [KEY_SLASH] = {.normal = '/', .shift = '?'}, + + [KEY_SEMICOLON] = {.normal = ';', .shift = ':'}, + + [KEY_APOSTROPHE] = {.normal = '\'', .shift = '"'}, + + [KEY_GRAVE] = {.normal = '`', .shift = '~'}, + + [KEY_LEFT_BRACKET] = {.normal = '[', .shift = '{'}, + + [KEY_RIGHT_BRACKET] = {.normal = ']', .shift = '}'}, + + [KEY_BACKSLASH] = {.normal = '\\', .shift = '|'}, + }}; + +char keyboard_layout_translate(const keyboard_layout_t *layout, keycode_t key, + const keyboard_state_t *state) { if (key >= KEY_COUNT) { return '\0'; } @@ -261,14 +113,11 @@ char keyboard_layout_translate( return '\0'; } - bool shifted = - state->left_shift || - state->right_shift; + bool shifted = state->left_shift || state->right_shift; if (shifted) { return entry.shift; } - return entry.normal; } \ No newline at end of file diff --git a/src/kernel/kernel.c b/src/kernel/kernel.c index c802222..dfda71f 100644 --- a/src/kernel/kernel.c +++ b/src/kernel/kernel.c @@ -19,6 +19,9 @@ #include "string.h" +#include "keyboard/event_queue.h" +#include "keyboard/handler.h" + #define TIMER_FREQ 1000 // 1000 Hz void KERNEL_INIT(const char *name, void (*init_function)(void)) { @@ -57,6 +60,19 @@ void kernel_main() { pic_clear_mask(1); + while (1) { + input_event_t event; + input_queue_pop(&event); + + if (event.type == INPUT_CHAR) { + print("Character: "); + print_char(event.character); + print("\n"); + event = (input_event_t){0}; + event.type = 11; + } + } + for (;;) { asm volatile("hlt"); } diff --git a/src/libs/stdio.c b/src/libs/stdio.c index 1d965b1..fa49dad 100644 --- a/src/libs/stdio.c +++ b/src/libs/stdio.c @@ -85,13 +85,9 @@ void println(const char *str) { vga_print(str); } -void print_char(char c) { - vga_print_char(c); -} +void print_char(char c) { vga_print_char(c); } -void print_hex(uint32_t value) { - vga_print_hex(value); -} +void print_hex(uint32_t value) { vga_print_hex(value); } void print_at_end(const char *str, uint8_t color) { vga_print_at_end_c(str, color); }