diff --git a/Makefile b/Makefile index 1d3fa47..f6ce083 100644 --- a/Makefile +++ b/Makefile @@ -46,8 +46,10 @@ all: amd64 deps: mkdir -p $(BUILD_DIR) || true rm -rf build/limine - git clone https://github.com/limine-bootloader/limine.git --branch=v8.x-binary --depth=1 build/limine + git clone https://github.com/limine-bootloader/limine.git --branch=v10.x-binary --depth=1 build/limine + git clone https://codeberg.org/Limine/limine-protocol/ build/limine-protocol make -C build/limine + cp build/limine-protocol/include/limine.h include/ rm -rf build/flanterm git clone https://codeberg.org/mintsuki/flanterm build/flanterm rm -rf build/uACPI diff --git a/include/io.h b/include/arch/amd64/io.h similarity index 100% rename from include/io.h rename to include/arch/amd64/io.h diff --git a/include/limine.h b/include/limine.h index b4b49c5..e48dff1 100644 --- a/include/limine.h +++ b/include/limine.h @@ -1,6 +1,6 @@ -/* BSD Zero Clause License */ +/* SPDX-License-Identifier: 0BSD */ -/* Copyright (C) 2022-2024 mintsuki and contributors. +/* Copyright (C) 2022-2026 Mintsuki and contributors. * * Permission to use, copy, modify, and/or distribute this software for any * purpose with or without fee is hereby granted. @@ -17,12 +17,12 @@ #ifndef LIMINE_H #define LIMINE_H 1 +#include + #ifdef __cplusplus extern "C" { #endif -#include - /* Misc */ #ifdef LIMINE_NO_POINTERS @@ -31,31 +31,16 @@ extern "C" { # define LIMINE_PTR(TYPE) TYPE #endif -#ifdef __GNUC__ -# define LIMINE_DEPRECATED __attribute__((__deprecated__)) -# define LIMINE_DEPRECATED_IGNORE_START \ - _Pragma("GCC diagnostic push") \ - _Pragma("GCC diagnostic ignored \"-Wdeprecated-declarations\"") -# define LIMINE_DEPRECATED_IGNORE_END \ - _Pragma("GCC diagnostic pop") -#else -# define LIMINE_DEPRECATED -# define LIMINE_DEPRECATED_IGNORE_START -# define LIMINE_DEPRECATED_IGNORE_END -#endif +#define LIMINE_REQUESTS_START_MARKER { 0xf6b8f4b39de7d1ae, 0xfab91a6940fcb9cf, \ + 0x785c6ed015d3e316, 0x181e920a7852b9d9 } +#define LIMINE_REQUESTS_END_MARKER { 0xadc0e0531bb10d03, 0x9572709f31764c62 } -#define LIMINE_REQUESTS_START_MARKER \ - uint64_t limine_requests_start_marker[4] = { 0xf6b8f4b39de7d1ae, 0xfab91a6940fcb9cf, \ - 0x785c6ed015d3e316, 0x181e920a7852b9d9 }; -#define LIMINE_REQUESTS_END_MARKER \ - uint64_t limine_requests_end_marker[2] = { 0xadc0e0531bb10d03, 0x9572709f31764c62 }; +#define LIMINE_BASE_REVISION(N) { 0xf9562b2d5c95a6c8, 0x6a7b384944536bdc, (N) } -#define LIMINE_REQUESTS_DELIMITER LIMINE_REQUESTS_END_MARKER +#define LIMINE_BASE_REVISION_SUPPORTED(VAR) ((VAR)[2] == 0) -#define LIMINE_BASE_REVISION(N) \ - uint64_t limine_base_revision[3] = { 0xf9562b2d5c95a6c8, 0x6a7b384944536bdc, (N) }; - -#define LIMINE_BASE_REVISION_SUPPORTED (limine_base_revision[2] == 0) +#define LIMINE_LOADED_BASE_REVISION_VALID(VAR) ((VAR)[1] != 0x6a7b384944536bdc) +#define LIMINE_LOADED_BASE_REVISION(VAR) ((VAR)[1]) #define LIMINE_COMMON_MAGIC 0xc7b1dd30df4c8b88, 0x0a82e883a194f07b @@ -75,7 +60,7 @@ struct limine_file { LIMINE_PTR(void *) address; uint64_t size; LIMINE_PTR(char *) path; - LIMINE_PTR(char *) cmdline; + LIMINE_PTR(char *) string; uint32_t media_type; uint32_t unused; uint32_t tftp_ip; @@ -89,7 +74,7 @@ struct limine_file { /* Boot info */ -#define LIMINE_BOOTLOADER_INFO_REQUEST { LIMINE_COMMON_MAGIC, 0xf55038d8e2a1202f, 0x279426fcf5f59740 } +#define LIMINE_BOOTLOADER_INFO_REQUEST_ID { LIMINE_COMMON_MAGIC, 0xf55038d8e2a1202f, 0x279426fcf5f59740 } struct limine_bootloader_info_response { uint64_t revision; @@ -103,13 +88,29 @@ struct limine_bootloader_info_request { LIMINE_PTR(struct limine_bootloader_info_response *) response; }; +/* Executable command line */ + +#define LIMINE_EXECUTABLE_CMDLINE_REQUEST_ID { LIMINE_COMMON_MAGIC, 0x4b161536e598651e, 0xb390ad4a2f1f303a } + +struct limine_executable_cmdline_response { + uint64_t revision; + LIMINE_PTR(char *) cmdline; +}; + +struct limine_executable_cmdline_request { + uint64_t id[4]; + uint64_t revision; + LIMINE_PTR(struct limine_executable_cmdline_response *) response; +}; + /* Firmware type */ -#define LIMINE_FIRMWARE_TYPE_REQUEST { LIMINE_COMMON_MAGIC, 0x8c2f75d90bef28a8, 0x7045a4688eac00c3 } +#define LIMINE_FIRMWARE_TYPE_REQUEST_ID { LIMINE_COMMON_MAGIC, 0x8c2f75d90bef28a8, 0x7045a4688eac00c3 } #define LIMINE_FIRMWARE_TYPE_X86BIOS 0 -#define LIMINE_FIRMWARE_TYPE_UEFI32 1 -#define LIMINE_FIRMWARE_TYPE_UEFI64 2 +#define LIMINE_FIRMWARE_TYPE_EFI32 1 +#define LIMINE_FIRMWARE_TYPE_EFI64 2 +#define LIMINE_FIRMWARE_TYPE_SBI 3 struct limine_firmware_type_response { uint64_t revision; @@ -124,7 +125,7 @@ struct limine_firmware_type_request { /* Stack size */ -#define LIMINE_STACK_SIZE_REQUEST { LIMINE_COMMON_MAGIC, 0x224ef0460a8e8926, 0xe1cb0fc25f46ea3d } +#define LIMINE_STACK_SIZE_REQUEST_ID { LIMINE_COMMON_MAGIC, 0x224ef0460a8e8926, 0xe1cb0fc25f46ea3d } struct limine_stack_size_response { uint64_t revision; @@ -139,7 +140,7 @@ struct limine_stack_size_request { /* HHDM */ -#define LIMINE_HHDM_REQUEST { LIMINE_COMMON_MAGIC, 0x48dcf1cb8ad2b852, 0x63984e959a98244b } +#define LIMINE_HHDM_REQUEST_ID { LIMINE_COMMON_MAGIC, 0x48dcf1cb8ad2b852, 0x63984e959a98244b } struct limine_hhdm_response { uint64_t revision; @@ -154,7 +155,7 @@ struct limine_hhdm_request { /* Framebuffer */ -#define LIMINE_FRAMEBUFFER_REQUEST { LIMINE_COMMON_MAGIC, 0x9d5827dcd881dd75, 0xa3148604f6fab11b } +#define LIMINE_FRAMEBUFFER_REQUEST_ID { LIMINE_COMMON_MAGIC, 0x9d5827dcd881dd75, 0xa3148604f6fab11b } #define LIMINE_FRAMEBUFFER_RGB 1 @@ -205,93 +206,29 @@ struct limine_framebuffer_request { LIMINE_PTR(struct limine_framebuffer_response *) response; }; -/* Terminal */ - -#define LIMINE_TERMINAL_REQUEST { LIMINE_COMMON_MAGIC, 0xc8ac59310c2b0844, 0xa68d0c7265d38878 } - -#define LIMINE_TERMINAL_CB_DEC 10 -#define LIMINE_TERMINAL_CB_BELL 20 -#define LIMINE_TERMINAL_CB_PRIVATE_ID 30 -#define LIMINE_TERMINAL_CB_STATUS_REPORT 40 -#define LIMINE_TERMINAL_CB_POS_REPORT 50 -#define LIMINE_TERMINAL_CB_KBD_LEDS 60 -#define LIMINE_TERMINAL_CB_MODE 70 -#define LIMINE_TERMINAL_CB_LINUX 80 - -#define LIMINE_TERMINAL_CTX_SIZE ((uint64_t)(-1)) -#define LIMINE_TERMINAL_CTX_SAVE ((uint64_t)(-2)) -#define LIMINE_TERMINAL_CTX_RESTORE ((uint64_t)(-3)) -#define LIMINE_TERMINAL_FULL_REFRESH ((uint64_t)(-4)) - -/* Response revision 1 */ -#define LIMINE_TERMINAL_OOB_OUTPUT_GET ((uint64_t)(-10)) -#define LIMINE_TERMINAL_OOB_OUTPUT_SET ((uint64_t)(-11)) - -#define LIMINE_TERMINAL_OOB_OUTPUT_OCRNL (1 << 0) -#define LIMINE_TERMINAL_OOB_OUTPUT_OFDEL (1 << 1) -#define LIMINE_TERMINAL_OOB_OUTPUT_OFILL (1 << 2) -#define LIMINE_TERMINAL_OOB_OUTPUT_OLCUC (1 << 3) -#define LIMINE_TERMINAL_OOB_OUTPUT_ONLCR (1 << 4) -#define LIMINE_TERMINAL_OOB_OUTPUT_ONLRET (1 << 5) -#define LIMINE_TERMINAL_OOB_OUTPUT_ONOCR (1 << 6) -#define LIMINE_TERMINAL_OOB_OUTPUT_OPOST (1 << 7) - -LIMINE_DEPRECATED_IGNORE_START - -struct LIMINE_DEPRECATED limine_terminal; - -typedef void (*limine_terminal_write)(struct limine_terminal *, const char *, uint64_t); -typedef void (*limine_terminal_callback)(struct limine_terminal *, uint64_t, uint64_t, uint64_t, uint64_t); - -struct LIMINE_DEPRECATED limine_terminal { - uint64_t columns; - uint64_t rows; - LIMINE_PTR(struct limine_framebuffer *) framebuffer; -}; - -struct LIMINE_DEPRECATED limine_terminal_response { - uint64_t revision; - uint64_t terminal_count; - LIMINE_PTR(struct limine_terminal **) terminals; - LIMINE_PTR(limine_terminal_write) write; -}; - -struct LIMINE_DEPRECATED limine_terminal_request { - uint64_t id[4]; - uint64_t revision; - LIMINE_PTR(struct limine_terminal_response *) response; - LIMINE_PTR(limine_terminal_callback) callback; -}; - -LIMINE_DEPRECATED_IGNORE_END - /* Paging mode */ -#define LIMINE_PAGING_MODE_REQUEST { LIMINE_COMMON_MAGIC, 0x95c1a0edab0944cb, 0xa4e5cb3842f7488a } +#define LIMINE_PAGING_MODE_REQUEST_ID { LIMINE_COMMON_MAGIC, 0x95c1a0edab0944cb, 0xa4e5cb3842f7488a } -#if defined (__x86_64__) || defined (__i386__) #define LIMINE_PAGING_MODE_X86_64_4LVL 0 #define LIMINE_PAGING_MODE_X86_64_5LVL 1 -#define LIMINE_PAGING_MODE_MIN LIMINE_PAGING_MODE_X86_64_4LVL -#define LIMINE_PAGING_MODE_DEFAULT LIMINE_PAGING_MODE_X86_64_4LVL -#elif defined (__aarch64__) +#define LIMINE_PAGING_MODE_X86_64_MIN LIMINE_PAGING_MODE_X86_64_4LVL +#define LIMINE_PAGING_MODE_X86_64_DEFAULT LIMINE_PAGING_MODE_X86_64_4LVL + #define LIMINE_PAGING_MODE_AARCH64_4LVL 0 #define LIMINE_PAGING_MODE_AARCH64_5LVL 1 -#define LIMINE_PAGING_MODE_MIN LIMINE_PAGING_MODE_AARCH64_4LVL -#define LIMINE_PAGING_MODE_DEFAULT LIMINE_PAGING_MODE_AARCH64_4LVL -#elif defined (__riscv) && (__riscv_xlen == 64) +#define LIMINE_PAGING_MODE_AARCH64_MIN LIMINE_PAGING_MODE_AARCH64_4LVL +#define LIMINE_PAGING_MODE_AARCH64_DEFAULT LIMINE_PAGING_MODE_AARCH64_4LVL + #define LIMINE_PAGING_MODE_RISCV_SV39 0 #define LIMINE_PAGING_MODE_RISCV_SV48 1 #define LIMINE_PAGING_MODE_RISCV_SV57 2 -#define LIMINE_PAGING_MODE_MIN LIMINE_PAGING_MODE_RISCV_SV39 -#define LIMINE_PAGING_MODE_DEFAULT LIMINE_PAGING_MODE_RISCV_SV48 -#elif defined (__loongarch__) && (__loongarch_grlen == 64) -#define LIMINE_PAGING_MODE_LOONGARCH64_4LVL 0 -#define LIMINE_PAGING_MODE_MIN LIMINE_PAGING_MODE_LOONGARCH64_4LVL -#define LIMINE_PAGING_MODE_DEFAULT LIMINE_PAGING_MODE_LOONGARCH64_4LVL -#else -#error Unknown architecture -#endif +#define LIMINE_PAGING_MODE_RISCV_MIN LIMINE_PAGING_MODE_RISCV_SV39 +#define LIMINE_PAGING_MODE_RISCV_DEFAULT LIMINE_PAGING_MODE_RISCV_SV48 + +#define LIMINE_PAGING_MODE_LOONGARCH_4LVL 0 +#define LIMINE_PAGING_MODE_LOONGARCH_MIN LIMINE_PAGING_MODE_LOONGARCH_4LVL +#define LIMINE_PAGING_MODE_LOONGARCH_DEFAULT LIMINE_PAGING_MODE_LOONGARCH_4LVL struct limine_paging_mode_response { uint64_t revision; @@ -307,37 +244,19 @@ struct limine_paging_mode_request { uint64_t min_mode; }; -/* 5-level paging */ +/* MP */ -#define LIMINE_5_LEVEL_PAGING_REQUEST { LIMINE_COMMON_MAGIC, 0x94469551da9b3192, 0xebe5e86db7382888 } +#define LIMINE_MP_REQUEST_ID { LIMINE_COMMON_MAGIC, 0x95a67b819a1b857e, 0xa0b61b723b6a73e0 } -LIMINE_DEPRECATED_IGNORE_START +struct limine_mp_info; -struct LIMINE_DEPRECATED limine_5_level_paging_response { - uint64_t revision; -}; - -struct LIMINE_DEPRECATED limine_5_level_paging_request { - uint64_t id[4]; - uint64_t revision; - LIMINE_PTR(struct limine_5_level_paging_response *) response; -}; - -LIMINE_DEPRECATED_IGNORE_END - -/* SMP */ - -#define LIMINE_SMP_REQUEST { LIMINE_COMMON_MAGIC, 0x95a67b819a1b857e, 0xa0b61b723b6a73e0 } - -struct limine_smp_info; - -typedef void (*limine_goto_address)(struct limine_smp_info *); +typedef void (*limine_goto_address)(struct limine_mp_info *); #if defined (__x86_64__) || defined (__i386__) -#define LIMINE_SMP_X2APIC (1 << 0) +#define LIMINE_MP_RESPONSE_X86_64_X2APIC (1 << 0) -struct limine_smp_info { +struct limine_mp_info { uint32_t processor_id; uint32_t lapic_id; uint64_t reserved; @@ -345,17 +264,17 @@ struct limine_smp_info { uint64_t extra_argument; }; -struct limine_smp_response { +struct limine_mp_response { uint64_t revision; uint32_t flags; uint32_t bsp_lapic_id; uint64_t cpu_count; - LIMINE_PTR(struct limine_smp_info **) cpus; + LIMINE_PTR(struct limine_mp_info **) cpus; }; #elif defined (__aarch64__) -struct limine_smp_info { +struct limine_mp_info { uint32_t processor_id; uint32_t reserved1; uint64_t mpidr; @@ -364,17 +283,17 @@ struct limine_smp_info { uint64_t extra_argument; }; -struct limine_smp_response { +struct limine_mp_response { uint64_t revision; uint64_t flags; uint64_t bsp_mpidr; uint64_t cpu_count; - LIMINE_PTR(struct limine_smp_info **) cpus; + LIMINE_PTR(struct limine_mp_info **) cpus; }; #elif defined (__riscv) && (__riscv_xlen == 64) -struct limine_smp_info { +struct limine_mp_info { uint64_t processor_id; uint64_t hartid; uint64_t reserved; @@ -382,39 +301,41 @@ struct limine_smp_info { uint64_t extra_argument; }; -struct limine_smp_response { +struct limine_mp_response { uint64_t revision; uint64_t flags; uint64_t bsp_hartid; uint64_t cpu_count; - LIMINE_PTR(struct limine_smp_info **) cpus; + LIMINE_PTR(struct limine_mp_info **) cpus; }; #elif defined (__loongarch__) && (__loongarch_grlen == 64) -struct limine_smp_info { +struct limine_mp_info { uint64_t reserved; }; -struct limine_smp_response { +struct limine_mp_response { uint64_t cpu_count; - LIMINE_PTR(struct limine_smp_info **) cpus; + LIMINE_PTR(struct limine_mp_info **) cpus; }; #else #error Unknown architecture #endif -struct limine_smp_request { +#define LIMINE_MP_REQUEST_X86_64_X2APIC (1 << 0) + +struct limine_mp_request { uint64_t id[4]; uint64_t revision; - LIMINE_PTR(struct limine_smp_response *) response; + LIMINE_PTR(struct limine_mp_response *) response; uint64_t flags; }; /* Memory map */ -#define LIMINE_MEMMAP_REQUEST { LIMINE_COMMON_MAGIC, 0x67cf3d9d378a806f, 0xe304acdfc50c3c62 } +#define LIMINE_MEMMAP_REQUEST_ID { LIMINE_COMMON_MAGIC, 0x67cf3d9d378a806f, 0xe304acdfc50c3c62 } #define LIMINE_MEMMAP_USABLE 0 #define LIMINE_MEMMAP_RESERVED 1 @@ -422,8 +343,9 @@ struct limine_smp_request { #define LIMINE_MEMMAP_ACPI_NVS 3 #define LIMINE_MEMMAP_BAD_MEMORY 4 #define LIMINE_MEMMAP_BOOTLOADER_RECLAIMABLE 5 -#define LIMINE_MEMMAP_KERNEL_AND_MODULES 6 +#define LIMINE_MEMMAP_EXECUTABLE_AND_MODULES 6 #define LIMINE_MEMMAP_FRAMEBUFFER 7 +#define LIMINE_MEMMAP_RESERVED_MAPPED 8 struct limine_memmap_entry { uint64_t base; @@ -445,7 +367,7 @@ struct limine_memmap_request { /* Entry point */ -#define LIMINE_ENTRY_POINT_REQUEST { LIMINE_COMMON_MAGIC, 0x13d86c035a1cd3e1, 0x2b0caa89d8f3026a } +#define LIMINE_ENTRY_POINT_REQUEST_ID { LIMINE_COMMON_MAGIC, 0x13d86c035a1cd3e1, 0x2b0caa89d8f3026a } typedef void (*limine_entry_point)(void); @@ -460,31 +382,31 @@ struct limine_entry_point_request { LIMINE_PTR(limine_entry_point) entry; }; -/* Kernel File */ +/* Executable File */ -#define LIMINE_KERNEL_FILE_REQUEST { LIMINE_COMMON_MAGIC, 0xad97e90e83f1ed67, 0x31eb5d1c5ff23b69 } +#define LIMINE_EXECUTABLE_FILE_REQUEST_ID { LIMINE_COMMON_MAGIC, 0xad97e90e83f1ed67, 0x31eb5d1c5ff23b69 } -struct limine_kernel_file_response { +struct limine_executable_file_response { uint64_t revision; - LIMINE_PTR(struct limine_file *) kernel_file; + LIMINE_PTR(struct limine_file *) executable_file; }; -struct limine_kernel_file_request { +struct limine_executable_file_request { uint64_t id[4]; uint64_t revision; - LIMINE_PTR(struct limine_kernel_file_response *) response; + LIMINE_PTR(struct limine_executable_file_response *) response; }; /* Module */ -#define LIMINE_MODULE_REQUEST { LIMINE_COMMON_MAGIC, 0x3e7e279702be32af, 0xca1c4f3bd1280cee } +#define LIMINE_MODULE_REQUEST_ID { LIMINE_COMMON_MAGIC, 0x3e7e279702be32af, 0xca1c4f3bd1280cee } #define LIMINE_INTERNAL_MODULE_REQUIRED (1 << 0) #define LIMINE_INTERNAL_MODULE_COMPRESSED (1 << 1) struct limine_internal_module { LIMINE_PTR(const char *) path; - LIMINE_PTR(const char *) cmdline; + LIMINE_PTR(const char *) string; uint64_t flags; }; @@ -506,7 +428,7 @@ struct limine_module_request { /* RSDP */ -#define LIMINE_RSDP_REQUEST { LIMINE_COMMON_MAGIC, 0xc5e77b6b397e7b43, 0x27637845accdcf3c } +#define LIMINE_RSDP_REQUEST_ID { LIMINE_COMMON_MAGIC, 0xc5e77b6b397e7b43, 0x27637845accdcf3c } struct limine_rsdp_response { uint64_t revision; @@ -521,7 +443,7 @@ struct limine_rsdp_request { /* SMBIOS */ -#define LIMINE_SMBIOS_REQUEST { LIMINE_COMMON_MAGIC, 0x9e9046f11e095391, 0xaa4a520fefbde5ee } +#define LIMINE_SMBIOS_REQUEST_ID { LIMINE_COMMON_MAGIC, 0x9e9046f11e095391, 0xaa4a520fefbde5ee } struct limine_smbios_response { uint64_t revision; @@ -537,7 +459,7 @@ struct limine_smbios_request { /* EFI system table */ -#define LIMINE_EFI_SYSTEM_TABLE_REQUEST { LIMINE_COMMON_MAGIC, 0x5ceba5163eaaf6d6, 0x0a6981610cf65fcc } +#define LIMINE_EFI_SYSTEM_TABLE_REQUEST_ID { LIMINE_COMMON_MAGIC, 0x5ceba5163eaaf6d6, 0x0a6981610cf65fcc } struct limine_efi_system_table_response { uint64_t revision; @@ -552,7 +474,7 @@ struct limine_efi_system_table_request { /* EFI memory map */ -#define LIMINE_EFI_MEMMAP_REQUEST { LIMINE_COMMON_MAGIC, 0x7df62a431d6872d5, 0xa4fcdfb3e57306c8 } +#define LIMINE_EFI_MEMMAP_REQUEST_ID { LIMINE_COMMON_MAGIC, 0x7df62a431d6872d5, 0xa4fcdfb3e57306c8 } struct limine_efi_memmap_response { uint64_t revision; @@ -568,40 +490,40 @@ struct limine_efi_memmap_request { LIMINE_PTR(struct limine_efi_memmap_response *) response; }; -/* Boot time */ +/* Date at boot */ -#define LIMINE_BOOT_TIME_REQUEST { LIMINE_COMMON_MAGIC, 0x502746e184c088aa, 0xfbc5ec83e6327893 } +#define LIMINE_DATE_AT_BOOT_REQUEST_ID { LIMINE_COMMON_MAGIC, 0x502746e184c088aa, 0xfbc5ec83e6327893 } -struct limine_boot_time_response { +struct limine_date_at_boot_response { uint64_t revision; - int64_t boot_time; + int64_t timestamp; }; -struct limine_boot_time_request { +struct limine_date_at_boot_request { uint64_t id[4]; uint64_t revision; - LIMINE_PTR(struct limine_boot_time_response *) response; + LIMINE_PTR(struct limine_date_at_boot_response *) response; }; -/* Kernel address */ +/* Executable address */ -#define LIMINE_KERNEL_ADDRESS_REQUEST { LIMINE_COMMON_MAGIC, 0x71ba76863cc55f63, 0xb2644a48c516a487 } +#define LIMINE_EXECUTABLE_ADDRESS_REQUEST_ID { LIMINE_COMMON_MAGIC, 0x71ba76863cc55f63, 0xb2644a48c516a487 } -struct limine_kernel_address_response { +struct limine_executable_address_response { uint64_t revision; uint64_t physical_base; uint64_t virtual_base; }; -struct limine_kernel_address_request { +struct limine_executable_address_request { uint64_t id[4]; uint64_t revision; - LIMINE_PTR(struct limine_kernel_address_response *) response; + LIMINE_PTR(struct limine_executable_address_response *) response; }; /* Device Tree Blob */ -#define LIMINE_DTB_REQUEST { LIMINE_COMMON_MAGIC, 0xb40ddb48fb54bac7, 0x545081493f81ffb7 } +#define LIMINE_DTB_REQUEST_ID { LIMINE_COMMON_MAGIC, 0xb40ddb48fb54bac7, 0x545081493f81ffb7 } struct limine_dtb_response { uint64_t revision; @@ -614,6 +536,50 @@ struct limine_dtb_request { LIMINE_PTR(struct limine_dtb_response *) response; }; +/* RISC-V Boot Hart ID */ + +#define LIMINE_RISCV_BSP_HARTID_REQUEST_ID { LIMINE_COMMON_MAGIC, 0x1369359f025525f9, 0x2ff2a56178391bb6 } + +struct limine_riscv_bsp_hartid_response { + uint64_t revision; + uint64_t bsp_hartid; +}; + +struct limine_riscv_bsp_hartid_request { + uint64_t id[4]; + uint64_t revision; + LIMINE_PTR(struct limine_riscv_bsp_hartid_response *) response; +}; + +/* Bootloader Performance */ + +#define LIMINE_BOOTLOADER_PERFORMANCE_REQUEST_ID { LIMINE_COMMON_MAGIC, 0x6b50ad9bf36d13ad, 0xdc4c7e88fc759e17 } + +struct limine_bootloader_performance_response { + uint64_t revision; + uint64_t reset_usec; + uint64_t init_usec; + uint64_t exec_usec; +}; + +struct limine_bootloader_performance_request { + uint64_t id[4]; + uint64_t revision; + LIMINE_PTR(struct limine_bootloader_performance_response *) response; +}; + +#define LIMINE_X86_64_KEEP_IOMMU_REQUEST_ID { LIMINE_COMMON_MAGIC, 0x8ebaabe51f490179, 0x2aa86a59ffb4ab0f } + +struct limine_x86_64_keep_iommu_response { + uint64_t revision; +}; + +struct limine_x86_64_keep_iommu_request { + uint64_t id[4]; + uint64_t revision; + LIMINE_PTR(struct limine_x86_64_keep_iommu_response *) response; +}; + #ifdef __cplusplus } #endif diff --git a/include/neobbo.h b/include/neobbo.h index 105f7ab..597ca10 100644 --- a/include/neobbo.h +++ b/include/neobbo.h @@ -1,5 +1,15 @@ +#pragma once + #include -void kkill(void); + +typedef struct kernel_info { + char *cmdline; // kernel commandline options (maybe split into char**'s?) + uint64_t hhdmoffset; // HHDM offset + uint64_t cpu_count; // number of cpus + uint64_t usable_memory; // amount of usable memory the system has + uint64_t bsp_id; // id of the bsp cpu + int64_t boot_timestamp; // timestamp at boot +} kernel_info; typedef char link_symbol_ptr[]; @@ -17,4 +27,6 @@ typedef char link_symbol_ptr[]; #define SIZE_IN_PAGES(size) size/PAGE_SIZE -void *kmalloc(uint64_t size); \ No newline at end of file +struct kernel_info *get_kinfo(); +void initialize_kinfo(); +void kkill(void); // phase this out in favor of assert \ No newline at end of file diff --git a/include/scheduler/sched.h b/include/scheduler/sched.h index 975c1a0..2ccd202 100644 --- a/include/scheduler/sched.h +++ b/include/scheduler/sched.h @@ -22,13 +22,12 @@ struct thread { proc_state state; uint16_t pid; struct context *context; + char name[8]; }; void scheduler_init(); [[noreturn]] void sched(); void yield(); -#define PROC_MAX 512 // Max number of processes - -#define INITIAL_STACK_SIZE 0x10000 +#define PROC_MAX 1024 // Max number of processes per cpu diff --git a/include/arch/amd64/hal/smp.h b/include/smp.h similarity index 93% rename from include/arch/amd64/hal/smp.h rename to include/smp.h index c260230..fb57db6 100644 --- a/include/arch/amd64/hal/smp.h +++ b/include/smp.h @@ -8,7 +8,7 @@ #define KERNELGSBASE 0xC0000102 typedef struct cpu_state { - uint32_t lapic_id; + uint32_t id; uint64_t lapic_timer_ticks; struct thread *head; struct thread *base; @@ -22,5 +22,6 @@ typedef struct cpu_state { void smp_init(); cpu_state *get_cpu_struct(); uint64_t get_cpu_count(); +void bsp_early_init(); bool get_cpu_struct_initialized(); diff --git a/include/string.h b/include/string.h index 665ae57..51ad28b 100644 --- a/include/string.h +++ b/include/string.h @@ -13,4 +13,6 @@ int memcmp(const void *s1, const void *s2, uint64_t n); uint64_t strlen(const char* str); +void itoa(char *str, int number); + #endif \ No newline at end of file diff --git a/include/sys/time.h b/include/sys/time.h index 1aa683b..5322da4 100644 --- a/include/sys/time.h +++ b/include/sys/time.h @@ -1,3 +1,3 @@ #include -uint64_t get_timestamp_ns(); +uint64_t get_timestamp_us(); void sleep(int ms); \ No newline at end of file diff --git a/src/arch/amd64/hal/amd64_smp.c b/src/arch/amd64/hal/amd64_smp.c new file mode 100644 index 0000000..e69de29 diff --git a/src/arch/amd64/hal/apic.c b/src/arch/amd64/hal/apic.c index 579d2e8..cb8b41b 100644 --- a/src/arch/amd64/hal/apic.c +++ b/src/arch/amd64/hal/apic.c @@ -1,14 +1,16 @@ #include #include -#include +#include #include #include +#include #include #include #include #include // GCC specific +#define IA32_APIC_BASE_MSR 0x1B #define LAPIC_ID_REG 0x020 #define LAPIC_EOI_REG 0x0B0 #define LAPIC_SPURIOUS_REG 0x0F0 @@ -31,7 +33,6 @@ #define LAPIC_TIMER_VECTOR 69 -extern madt_t *madt; extern uint64_t hhdmoffset; uint64_t lapic_address = 0; @@ -87,7 +88,7 @@ void lapic_timer_init(int us){ void apic_init(void){ asm("cli"); - lapic_address = madt->lic_address + hhdmoffset; + lapic_address = rdmsr(IA32_APIC_BASE_MSR) + get_kinfo()->hhdmoffset; lapic_ao_t *lapic_ao = (lapic_ao_t*) find_ics(0x5); // Local APIC Address Override @@ -95,7 +96,7 @@ void apic_init(void){ if(lapic_ao){ /* Check that the field isnt 0 */ if(lapic_ao->lapic_address != 0){ - lapic_address = lapic_ao->lapic_address + hhdmoffset; + lapic_address = lapic_ao->lapic_address + get_kinfo()->hhdmoffset; } } @@ -108,8 +109,8 @@ void apic_init(void){ /* Start the timers for calibration of the APIC timer */ timer_init(); - /* Start the APIC timer with 10ms timer */ - lapic_timer_init(10000); + /* Start the APIC timer with 1us timer */ + lapic_timer_init(1); asm("sti"); } @@ -120,7 +121,7 @@ void ap_apic_init(){ lapic_write_reg(LAPIC_SPURIOUS_REG, 0x1FF); /* Start the APIC timer */ - lapic_timer_init(10000); + lapic_timer_init(1); asm("sti"); } @@ -133,7 +134,6 @@ void apic_timer_handler(){ lapic_write_reg(LAPIC_EOI_REG, 0); - } void apic_send_ipi(uint8_t dest_field, uint8_t dest_shorthand, uint8_t trigger, uint8_t level, uint8_t status, uint8_t destination, uint8_t delivery_mode, uint8_t vector){ diff --git a/src/arch/amd64/hal/idt.c b/src/arch/amd64/hal/idt.c index d9c3636..a5d64ae 100644 --- a/src/arch/amd64/hal/idt.c +++ b/src/arch/amd64/hal/idt.c @@ -1,6 +1,6 @@ #include #include -#include +#include #include #include #include @@ -205,8 +205,10 @@ extern void *next_frame(void *addr); void interrupt_handler(interrupt_frame *r){ + //asm("cli"); + if(r->int_no < 32){ - kprintf("\nOh no! Received interrupt {d}, '{s}'. Below is the provided stack frame\n\n", r->int_no, exception_messages[r->int_no]); + kprintf("\nOh no! Received interrupt 0x{x}, '{s}'. Below is the provided stack frame\n\n", r->int_no, exception_messages[r->int_no]); if(r->err != 0){ kprintf("error code 0x{xn}", r->err); @@ -235,16 +237,21 @@ void interrupt_handler(interrupt_frame *r){ if(r->int_no == 69){ apic_timer_handler(); + return; } if(r->int_no == 69 && get_cpu_struct_initialized() && get_cpu_struct()->scheduler_initialized){ yield(); + return; } if(r->int_no == 70){ for(;;){ - asm("cli;hlt"); + for(;;){ + asm("cli"); + __builtin_ia32_pause(); + } } } diff --git a/src/arch/amd64/hal/ioapic.c b/src/arch/amd64/hal/ioapic.c index 3c75ddc..a589c84 100644 --- a/src/arch/amd64/hal/ioapic.c +++ b/src/arch/amd64/hal/ioapic.c @@ -13,8 +13,6 @@ #define IOAPICARB 0x2 #define IOREDTBL(x) (0x10 + (x * 2)) // 0-23 registers -extern uint64_t hhdmoffset; - extern madt_t *madt; uint64_t ioapic_address; @@ -57,6 +55,6 @@ void ioapic_init(void){ kkill(); } - ioapic_address = ioapic->ioapic_address + hhdmoffset; + ioapic_address = ioapic->ioapic_address + get_kinfo()->hhdmoffset; } \ No newline at end of file diff --git a/src/arch/amd64/hal/timer.c b/src/arch/amd64/hal/timer.c index 12876ee..4956a01 100644 --- a/src/arch/amd64/hal/timer.c +++ b/src/arch/amd64/hal/timer.c @@ -15,7 +15,7 @@ int calibration_timer = -1; void timer_init(void){ if(pmt_init() == -1){ klog(__func__, "PMT Timer not found, falling back"); - /* Fall back to PIT */ + /* Fall back to HPET */ }else{ calibration_timer = PMT; } diff --git a/src/arch/amd64/hal/tsc.c b/src/arch/amd64/hal/tsc.c index 82610ca..3a5015b 100644 --- a/src/arch/amd64/hal/tsc.c +++ b/src/arch/amd64/hal/tsc.c @@ -73,5 +73,5 @@ uint64_t tsc_get_timestamp(){ return 0; } uint64_t read = read_tsc(); - return read / core_crystal_clock; + return (read * 1000ULL) / core_crystal_clock; } \ No newline at end of file diff --git a/src/lib/io.c b/src/arch/amd64/io.c similarity index 100% rename from src/lib/io.c rename to src/arch/amd64/io.c diff --git a/src/drivers/ahci.c b/src/drivers/ahci.c index 37d5630..116c856 100644 --- a/src/drivers/ahci.c +++ b/src/drivers/ahci.c @@ -54,7 +54,7 @@ void ahci_init(){ /* Map the AHCI registers */ kmap_pages((uint64_t*)ahci_base_address, 1, PTE_BIT_RW | PTE_BIT_NX | PTE_BIT_UNCACHABLE); - ahci_base_address += hhdmoffset; + ahci_base_address += get_kinfo()->hhdmoffset; /* BIOS/OS Handoff */ kprintf("ahci: Performing BIOS/OS handoff\n"); diff --git a/src/drivers/pmt.c b/src/drivers/pmt.c index 0504dca..fc7f0ad 100644 --- a/src/drivers/pmt.c +++ b/src/drivers/pmt.c @@ -1,7 +1,7 @@ #include #include #include -#include +#include #define PMT_TIMER_RATE 3579545 @@ -40,7 +40,7 @@ int pmt_init(){ kkill(); } - fadt = (fadt_t*)((uint64_t)fadt + hhdmoffset); + fadt = (fadt_t*)((uint64_t)fadt + get_kinfo()->hhdmoffset); /* Check if timer exists */ if(fadt->PMTimerLength == 0){ diff --git a/src/drivers/serial.c b/src/drivers/serial.c index b54ceb2..4b047e9 100644 --- a/src/drivers/serial.c +++ b/src/drivers/serial.c @@ -1,7 +1,7 @@ #include #include -#include +#include #include #define COM1 0x3F8 @@ -56,13 +56,25 @@ void serial_init(){ } uint8_t serial_read(){ - while((inb(COM1 + LINE_STAT_REG) & 0x1) == 0){ asm("nop"); } + while((inb(COM1 + LINE_STAT_REG) & 0x1) == 0){ + #ifdef __x86_64__ + __builtin_ia32_pause(); + #else + asm("hlt"); + #endif + } return inb(COM1); } void serial_write(uint8_t data){ - while((inb(COM1 + LINE_STAT_REG) & (1 << 5)) == 0){ asm("nop"); } + while((inb(COM1 + LINE_STAT_REG) & (1 << 5)) == 0){ + #ifdef __x86_64__ + __builtin_ia32_pause(); + #else + asm("hlt"); + #endif + } outb(COM1, data); } diff --git a/src/kinfo.c b/src/kinfo.c new file mode 100644 index 0000000..ef1bbf8 --- /dev/null +++ b/src/kinfo.c @@ -0,0 +1,47 @@ +#include +#include +#include +#include +#include +#include + +static volatile struct limine_hhdm_request hhdm_request = { + .id = LIMINE_HHDM_REQUEST_ID, + .revision = 0, +}; + +volatile struct limine_mp_request smp_request = { + .id = LIMINE_MP_REQUEST_ID, + .revision = 0, +}; + +static volatile struct limine_executable_cmdline_request executable_cmdline_request = { + .id = LIMINE_EXECUTABLE_CMDLINE_REQUEST_ID, + .revision = 0, +}; + +static volatile struct limine_date_at_boot_request date_at_boot_request = { + .id = LIMINE_DATE_AT_BOOT_REQUEST_ID, + .revision = 0, +}; + +extern struct kernel_info kinfo; + +void initialize_kinfo(){ + assert(hhdm_request.response != NULL && "HHDM response is NULL"); + assert(smp_request.response != NULL && "SMP response is NULL"); + assert(executable_cmdline_request.response != NULL && "Exec cmdline response is NULL"); + assert(date_at_boot_request.response != NULL && "Date at boot response is NULL"); + + kinfo.hhdmoffset = hhdm_request.response->offset; + kinfo.cmdline = executable_cmdline_request.response->cmdline; + kinfo.cpu_count = smp_request.response->cpu_count; + kinfo.boot_timestamp = date_at_boot_request.response->timestamp; + #ifdef __x86_64__ + kinfo.bsp_id = smp_request.response->bsp_lapic_id; + #endif +} + +struct kernel_info *get_kinfo(){ + return &kinfo; +} \ No newline at end of file diff --git a/src/lib/kprint.c b/src/lib/kprint.c index 9e1c10c..cedbcfa 100644 --- a/src/lib/kprint.c +++ b/src/lib/kprint.c @@ -7,6 +7,7 @@ #include #include #include +#include #define FORMAT_LENGTH 1 @@ -28,7 +29,35 @@ void klog(const char *func, const char *msg, ...){ serial_kprintf("{ksk}: {s}\n", ANSI_COLOR_MAGENTA, func, ANSI_COLOR_RESET, msg); return; - +} + +void print_timestamp(struct flanterm_context *ft_ctx){ + uint64_t time = get_timestamp_us(); + char str[100]; + uint64_t seconds = time / 1000000ULL; + uint64_t millis = (time % 1000000ULL) / 1000ULL; + + str[0] = '['; + str[1] = '\0'; + + itoa(str + 1, seconds); + + size_t len = strlen(str); + str[len] = '.'; + str[len + 1] = '\0'; + + len = strlen(str); + if (millis < 100) str[len++] = '0'; + if (millis < 10) str[len++] = '0'; + str[len] = '\0'; + itoa(str + len, millis); + + len = strlen(str); + str[len] = ']'; + str[len + 1] = '\0'; + + print_str(ft_ctx, str); + print_char(ft_ctx, ' '); } atomic_flag printf_lock = ATOMIC_FLAG_INIT; @@ -55,6 +84,7 @@ int kprintf(const char *format_string, ...){ int state = NORMAL; va_list a_list; va_start(a_list, format_string); + print_timestamp(ft_ctx); for(uint64_t i = 0; i < strlen(format_string); i++){ char current = format_string[i]; // current char in string switch (state){ @@ -123,6 +153,67 @@ int kprintf(const char *format_string, ...){ return 0; } +int ksnprintf(char * str, const char *format_string, ...){ + int state = NORMAL; + va_list a_list; + va_start(a_list, format_string); + for(uint64_t i = 0; i < strlen(format_string); i++){ + char current = format_string[i]; // current char in string + switch (state){ + case NORMAL: + switch (current) { + case '{': + state = FORMAT_SPECIFIER; + break; + default: + *(str+i) = current; + break; + } + break; + case FORMAT_SPECIFIER: + switch (current) { + case 'k': + break; + case 'd': + case 'i': + break; + case 's': + + break; + case 'c': + ; + int ch = va_arg(a_list, int); + + break; + case 'x': + + break; + case 'b': + + break; + case 'l': + current++; + switch (current) { + case 'd': + + break; + + } + break; + case '}': + state = NORMAL; + break; + + } + break; + } + + } + + va_end(a_list); + return 0; +} + int serial_kprintf(const char *format_string, ...){ int state = NORMAL; va_list a_list; @@ -192,7 +283,7 @@ int serial_kprintf(const char *format_string, ...){ return 0; } -#define MAX_INTERGER_SIZE 128 +#define MAX_INTEGER_SIZE 128 void print_char(struct flanterm_context *ft_ctx, char c){ kernel_framebuffer_print(&c, 1); @@ -207,13 +298,13 @@ void print_str(struct flanterm_context *ft_ctx, char *str){ } void print_int(struct flanterm_context *ft_ctx, uint64_t num){ - char buffer[MAX_INTERGER_SIZE] = {0}; + char buffer[MAX_INTEGER_SIZE] = {0}; if(num == 0){ buffer[0] = '0'; } - int arr[MAX_INTERGER_SIZE] = {0}; + int arr[MAX_INTEGER_SIZE] = {0}; int j = 0; while(num != 0){ @@ -222,7 +313,7 @@ void print_int(struct flanterm_context *ft_ctx, uint64_t num){ num /= 10; j++; - if(j == MAX_INTERGER_SIZE){ + if(j == MAX_INTEGER_SIZE){ return; } } @@ -236,13 +327,13 @@ void print_int(struct flanterm_context *ft_ctx, uint64_t num){ } void print_hex(struct flanterm_context *ft_ctx, uint64_t num){ - char buffer[MAX_INTERGER_SIZE] = {0}; + char buffer[MAX_INTEGER_SIZE] = {0}; if(num == 0){ buffer[0] = '0'; } - int arr[MAX_INTERGER_SIZE] = {0}; + int arr[MAX_INTEGER_SIZE] = {0}; int j = 0; while(num != 0){ @@ -251,7 +342,7 @@ void print_hex(struct flanterm_context *ft_ctx, uint64_t num){ num /= 16; j++; - if(j == MAX_INTERGER_SIZE){ + if(j == MAX_INTEGER_SIZE){ return; } } @@ -265,9 +356,9 @@ void print_hex(struct flanterm_context *ft_ctx, uint64_t num){ } void print_bin(struct flanterm_context *ft_ctx, uint64_t num){ - char buffer[MAX_INTERGER_SIZE] = {0}; + char buffer[MAX_INTEGER_SIZE] = {0}; - int arr[MAX_INTERGER_SIZE] = {0}; + int arr[MAX_INTEGER_SIZE] = {0}; int j = 0; while(num != 0){ @@ -276,7 +367,7 @@ void print_bin(struct flanterm_context *ft_ctx, uint64_t num){ num /= 2; j++; - if(j == MAX_INTERGER_SIZE){ + if(j == MAX_INTEGER_SIZE){ return; } } @@ -290,9 +381,9 @@ void print_bin(struct flanterm_context *ft_ctx, uint64_t num){ } void serial_print_int(uint64_t num){ - char buffer[MAX_INTERGER_SIZE] = {0}; + char buffer[MAX_INTEGER_SIZE] = {0}; - int arr[MAX_INTERGER_SIZE] = {0}; + int arr[MAX_INTEGER_SIZE] = {0}; int j = 0; while(num != 0){ @@ -301,7 +392,7 @@ void serial_print_int(uint64_t num){ num /= 10; j++; - if(j == MAX_INTERGER_SIZE){ + if(j == MAX_INTEGER_SIZE){ return; } } @@ -315,9 +406,9 @@ void serial_print_int(uint64_t num){ } void serial_print_hex(uint64_t num){ - char buffer[MAX_INTERGER_SIZE] = {0}; + char buffer[MAX_INTEGER_SIZE] = {0}; - int arr[MAX_INTERGER_SIZE] = {0}; + int arr[MAX_INTEGER_SIZE] = {0}; int j = 0; while(num != 0){ @@ -326,7 +417,7 @@ void serial_print_hex(uint64_t num){ num /= 16; j++; - if(j == MAX_INTERGER_SIZE){ + if(j == MAX_INTEGER_SIZE){ return; } } @@ -340,9 +431,9 @@ void serial_print_hex(uint64_t num){ } void serial_print_bin(uint64_t num){ - char buffer[MAX_INTERGER_SIZE] = {0}; + char buffer[MAX_INTEGER_SIZE] = {0}; - int arr[MAX_INTERGER_SIZE] = {0}; + int arr[MAX_INTEGER_SIZE] = {0}; int j = 0; while(num != 0){ @@ -351,7 +442,7 @@ void serial_print_bin(uint64_t num){ num /= 2; j++; - if(j == MAX_INTERGER_SIZE){ + if(j == MAX_INTEGER_SIZE){ return; } } @@ -365,62 +456,10 @@ void serial_print_bin(uint64_t num){ } -char toupper(char c){ - switch(c){ - case 'a': - return 'A'; - case 'b': - return 'B'; - case 'c': - return 'C'; - case 'd': - return 'D'; - case 'e': - return 'E'; - case 'f': - return 'F'; - case 'g': - return 'G'; - case 'h': - return 'H'; - case 'i': - return 'I'; - case 'j': - return 'J'; - case 'k': - return 'K'; - case 'l': - return 'L'; - case 'm': - return 'M'; - case 'n': - return 'N'; - case 'o': - return 'O'; - case 'p': - return 'P'; - case 't': - return 'T'; - case 'r': - return 'R'; - case 's': - return 'S'; - case 'u': - return 'U'; - case 'v': - return 'V'; - case 'w': - return 'W'; - case 'x': - return 'X'; - case 'y': - return 'Y'; - case 'z': - return 'Z'; - default: - return c; - - } +char toupper(char c) { + if (c >= 'a' && c <= 'z') + return c - ('a' - 'A'); + return c; } /* Eventually fix printf so that these print_* functions dont diff --git a/src/lib/lock.c b/src/lib/lock.c index 9fdcf0b..6cc0c88 100644 --- a/src/lib/lock.c +++ b/src/lib/lock.c @@ -1,4 +1,4 @@ -#include "arch/amd64/hal/smp.h" +#include "smp.h" #include "error.h" #include #include diff --git a/src/lib/string.c b/src/lib/string.c index 7b15214..2e55ef7 100644 --- a/src/lib/string.c +++ b/src/lib/string.c @@ -76,7 +76,29 @@ char dtoc(int digit){ if(digit < 10){ return '0' + digit; }else{ - return 'A' + digit - 10; + return 'a' + digit - 10; + } +} + +void itoa(char *str, uint64_t number){ + int i = 0; + if (number == 0) { + str[i++] = '0'; + str[i] = '\0'; + return; + } + while (number != 0) { + str[i++] = (number % 10) + '0'; + number /= 10; + } + str[i] = '\0'; + int start = 0, end = i - 1; + while (start < end) { + char temp = str[start]; + str[start] = str[end]; + str[end] = temp; + start++; + end--; } } diff --git a/src/main.c b/src/main.c index 8c45fdc..98043ad 100644 --- a/src/main.c +++ b/src/main.c @@ -11,7 +11,7 @@ #include #include #include -#include +#include #include #include #include @@ -25,30 +25,19 @@ #include #include #include +#include static volatile struct limine_framebuffer_request framebuffer_request = { - .id = LIMINE_FRAMEBUFFER_REQUEST, - .revision = 0, -}; - -static volatile struct limine_hhdm_request hhdm_request = { - .id = LIMINE_HHDM_REQUEST, + .id = LIMINE_FRAMEBUFFER_REQUEST_ID, .revision = 0, }; struct flanterm_context *ft_ctx; -uint64_t hhdmoffset = 0; +struct kernel_info kinfo; void _start(void){ - if(hhdm_request.response == NULL){ - goto death; - } - - - hhdmoffset = hhdm_request.response->offset; - /* initalize framebuffer */ struct limine_framebuffer_response *fb_response = framebuffer_request.response; @@ -78,19 +67,25 @@ void _start(void){ 0, 0 ); - kprintf("Welcome to Neobbo{n}"); extern link_symbol_ptr text_start_addr, text_end_addr; - - serial_init(); - krand_init(); set_gdt(); set_idt(); + initialize_kinfo(); + + kprintf("Welcome to Neobbo\n"); + + serial_init(); + krand_init(); + klog("acpi", "Reading ACPI tables"); acpi_init(); + bsp_early_init(); + + klog("apic", "Initalizing APIC"); apic_init(); @@ -116,18 +111,25 @@ void _start(void){ scheduler_init(); -/* klog(LOG_INFO, "ahci", "Initializing AHCI controller"); - ahci_init(); - klog(LOG_SUCCESS, "ahci", "Done!"); */ - death: - for(;;); + for(;;){ + //kprintf("d\n"); + __builtin_ia32_pause(); + } } bool kernel_killed = false; -void kkill(void){ +[[noreturn]] void kkill(void){ kernel_killed = true; kprintf("The kernel has been killed.\n"); - asm volatile("cli; hlt"); - for(;;); + + #ifdef __x86_64__ + asm("cli"); + for(;;){ + __builtin_ia32_pause(); + } + #else + asm("hlt"); + #endif + } diff --git a/src/mm/page.c b/src/mm/page.c index 1a83a66..60d4a06 100644 --- a/src/mm/page.c +++ b/src/mm/page.c @@ -1,3 +1,4 @@ +#include #include #include #include @@ -50,11 +51,7 @@ void init_page_array(){ pages = va_alloc_contigious_pages((page_count * sizeof(struct page)) / PAGE_SIZE); - if(pages == NULL){ - klog(__func__, "Couldn't allocate page structure"); - kkill(); - return; - } + assert(pages != NULL && "Couldn't allocate page structure"); memset(pages, 0, (page_count * sizeof(struct page)) / PAGE_SIZE); diff --git a/src/mm/pmm.c b/src/mm/pmm.c index ecf2c03..612fac7 100644 --- a/src/mm/pmm.c +++ b/src/mm/pmm.c @@ -6,7 +6,7 @@ #include static volatile struct limine_memmap_request memmap_request = { - .id = LIMINE_MEMMAP_REQUEST, + .id = LIMINE_MEMMAP_REQUEST_ID, .revision = 0, }; @@ -25,7 +25,7 @@ atomic_flag pmm_lock = ATOMIC_FLAG_INIT; void pmm_free(uint64_t *addr){ acquire_spinlock(&pmm_lock); - uint64_t *virt_addr = (uint64_t*)((uint64_t)addr+hhdmoffset); + uint64_t *virt_addr = (uint64_t*)((uint64_t)addr+get_kinfo()->hhdmoffset); /* Make the given page point to the previous free page */ *virt_addr = (uint64_t)free_list; @@ -45,7 +45,7 @@ uint64_t *pmm_alloc(){ } /* Fetch the address of the free page in free_list and make it point to the next free page */ - uint64_t *addr = (uint64_t*)((uint64_t)free_list - hhdmoffset); + uint64_t *addr = (uint64_t*)((uint64_t)free_list - get_kinfo()->hhdmoffset); free_list = (uint64_t*)(*free_list); pmm_free_page_count--; free_spinlock(&pmm_lock); @@ -78,10 +78,10 @@ void pmm_init(){ kprintf("pmm: got a total of {d}MB of memory\n", mem_size / 1048576); + get_kinfo()->usable_memory = mem_size / 1048576; bool first_entry = true; - uint64_t j; uint64_t i; @@ -92,7 +92,7 @@ void pmm_init(){ /* First set the first entry if it isn't set already */ if(first_entry == true){ first_entry = false; - free_list = (uint64_t*)(entries[i]->base + hhdmoffset); + free_list = (uint64_t*)(entries[i]->base + get_kinfo()->hhdmoffset); j = 1; }else{ j = 0; diff --git a/src/mm/vmm.c b/src/mm/vmm.c index 063f79f..4a3ab2b 100644 --- a/src/mm/vmm.c +++ b/src/mm/vmm.c @@ -10,12 +10,12 @@ #include #include -struct limine_kernel_address_request kernel_addr_request = { - .id = LIMINE_KERNEL_ADDRESS_REQUEST, +struct limine_executable_address_request kernel_addr_request = { + .id = LIMINE_EXECUTABLE_ADDRESS_REQUEST_ID, .revision = 0 }; -struct limine_kernel_address_response *kernel_address; +struct limine_executable_address_response *kernel_address; extern uint64_t hhdmoffset; @@ -29,20 +29,20 @@ uint64_t kernel_start, kernel_end; void vmm_set_ctx(uint64_t *page_map){ __asm__ volatile ( "movq %0, %%cr3\n" - : : "r" ((uint64_t)((uint64_t)(page_map) - hhdmoffset)) : "memory" + : : "r" ((uint64_t)((uint64_t)(page_map) - get_kinfo()->hhdmoffset)) : "memory" ); } void vmm_init(){ - struct limine_kernel_address_response *kernel_address = kernel_addr_request.response; + struct limine_executable_address_response *kernel_address = kernel_addr_request.response; if(!kernel_address){ klog(__func__, "Kernel address not recieved"); } - kernel_page_map = (uint64_t*)((uint64_t)pmm_alloc() + hhdmoffset); + kernel_page_map = (uint64_t*)((uint64_t)pmm_alloc() + get_kinfo()->hhdmoffset); if(!kernel_page_map){ klog(__func__, "Allocating block for page map failed"); @@ -68,22 +68,22 @@ void vmm_init(){ for(uint64_t i = 0; i < memmap_response->entry_count; i++){ if(memmap_response->entries[i]->type == LIMINE_MEMMAP_USABLE){ for(uint64_t j = 0; j < memmap_response->entries[i]->length; j+=PAGE_SIZE){ - vmm_map_page(kernel_page_map, memmap_response->entries[i]->base+j+hhdmoffset, memmap_response->entries[i]->base+j, PTE_BIT_PRESENT | PTE_BIT_RW); + vmm_map_page(kernel_page_map, memmap_response->entries[i]->base+j+get_kinfo()->hhdmoffset, memmap_response->entries[i]->base+j, PTE_BIT_PRESENT | PTE_BIT_RW); } } if(memmap_response->entries[i]->type == LIMINE_MEMMAP_FRAMEBUFFER){ for(uint64_t j = 0; j < memmap_response->entries[i]->length; j+=PAGE_SIZE){ - vmm_map_page(kernel_page_map, memmap_response->entries[i]->base+j+hhdmoffset, memmap_response->entries[i]->base+j, PTE_BIT_PRESENT | PTE_BIT_RW | PTE_BIT_NX); + vmm_map_page(kernel_page_map, memmap_response->entries[i]->base+j+get_kinfo()->hhdmoffset, memmap_response->entries[i]->base+j, PTE_BIT_PRESENT | PTE_BIT_RW | PTE_BIT_NX); } } if(memmap_response->entries[i]->type == LIMINE_MEMMAP_BOOTLOADER_RECLAIMABLE){ for(uint64_t j = 0; j < memmap_response->entries[i]->length; j+=PAGE_SIZE){ - vmm_map_page(kernel_page_map, memmap_response->entries[i]->base+j+hhdmoffset, memmap_response->entries[i]->base+j, PTE_BIT_PRESENT | PTE_BIT_RW); + vmm_map_page(kernel_page_map, memmap_response->entries[i]->base+j+get_kinfo()->hhdmoffset, memmap_response->entries[i]->base+j, PTE_BIT_PRESENT | PTE_BIT_RW); } } if(memmap_response->entries[i]->type == LIMINE_MEMMAP_ACPI_RECLAIMABLE){ for(uint64_t j = 0; j < memmap_response->entries[i]->length; j+=PAGE_SIZE){ - vmm_map_page(kernel_page_map, memmap_response->entries[i]->base+j+hhdmoffset, memmap_response->entries[i]->base+j, PTE_BIT_PRESENT | PTE_BIT_RW); + vmm_map_page(kernel_page_map, memmap_response->entries[i]->base+j+get_kinfo()->hhdmoffset, memmap_response->entries[i]->base+j, PTE_BIT_PRESENT | PTE_BIT_RW); } } @@ -118,7 +118,7 @@ void vmm_init(){ extern uint64_t lapic_address; /* Map the APIC */ - vmm_map_page(kernel_page_map, lapic_address, lapic_address - hhdmoffset, PTE_BIT_PRESENT | PTE_BIT_RW | PTE_BIT_NX); + vmm_map_page(kernel_page_map, lapic_address, lapic_address - get_kinfo()->hhdmoffset, PTE_BIT_PRESENT | PTE_BIT_RW | PTE_BIT_NX); /* Map the ACPI tables */ extern xsdt_t *xsdt; @@ -129,12 +129,12 @@ void vmm_init(){ fill an entire page it still requires a page */ for(uint64_t i = 0; i < rsdt->header.length / PAGE_SIZE + 1; i++){ kprintf("mapping 0x{xn}", (uint64_t)rsdt + i * PAGE_SIZE); - vmm_map_page(kernel_page_map, (uint64_t)rsdt + i * PAGE_SIZE, ((uint64_t)rsdt - hhdmoffset) + i * PAGE_SIZE, PTE_BIT_PRESENT | PTE_BIT_RW | PTE_BIT_NX); + vmm_map_page(kernel_page_map, (uint64_t)rsdt + i * PAGE_SIZE, ((uint64_t)rsdt - get_kinfo()->hhdmoffset) + i * PAGE_SIZE, PTE_BIT_PRESENT | PTE_BIT_RW | PTE_BIT_NX); } }else{ for(uint64_t i = 0; i < xsdt->header.length / PAGE_SIZE + 1; i++){ kprintf("mapping 0x{xn}", (uint64_t)xsdt + i * PAGE_SIZE); - vmm_map_page(kernel_page_map, (uint64_t)xsdt + i * PAGE_SIZE, ((uint64_t)xsdt - hhdmoffset) + i * PAGE_SIZE, PTE_BIT_PRESENT | PTE_BIT_RW | PTE_BIT_NX); + vmm_map_page(kernel_page_map, (uint64_t)xsdt + i * PAGE_SIZE, ((uint64_t)xsdt - get_kinfo()->hhdmoffset) + i * PAGE_SIZE, PTE_BIT_PRESENT | PTE_BIT_RW | PTE_BIT_NX); } } @@ -151,7 +151,7 @@ void vmm_init(){ uint64_t *get_lower_table(uint64_t *page_map, uint64_t offset){ if((page_map[offset] & PTE_BIT_PRESENT) != 0){ - return (uint64_t*)( ((uint64_t)page_map[offset] & 0x000ffffffffff000) + hhdmoffset); + return (uint64_t*)( ((uint64_t)page_map[offset] & 0x000ffffffffff000) + get_kinfo()->hhdmoffset); } @@ -165,11 +165,11 @@ uint64_t *get_lower_table(uint64_t *page_map, uint64_t offset){ return NULL; } - memset((uint64_t*)((uint64_t)ret + hhdmoffset), 0, PAGE_SIZE); + memset((uint64_t*)((uint64_t)ret + get_kinfo()->hhdmoffset), 0, PAGE_SIZE); page_map[offset] = (uint64_t)ret | PTE_BIT_PRESENT | PTE_BIT_RW | PTE_BIT_US; - return (uint64_t*)((uint64_t)ret + hhdmoffset); + return (uint64_t*)((uint64_t)ret + get_kinfo()->hhdmoffset); } @@ -274,15 +274,15 @@ uint64_t vmm_get_phys_addr(uint64_t *page_map, uint64_t virt_addr){ uint64_t pml4e = page_map[pml4_offset]; if (!(pml4e & 1)) return 0; // - uint64_t *pdp = (uint64_t *)((pml4e & 0x000ffffffffff000) + hhdmoffset); + uint64_t *pdp = (uint64_t *)((pml4e & 0x000ffffffffff000) + get_kinfo()->hhdmoffset); uint64_t pdpe = pdp[pdp_offset]; if (!(pdpe & 1)) return 0; - uint64_t *pd = (uint64_t *)((pdpe & 0x000ffffffffff000) + hhdmoffset); + uint64_t *pd = (uint64_t *)((pdpe & 0x000ffffffffff000) + get_kinfo()->hhdmoffset); uint64_t pde = pd[pd_offset]; if (!(pde & 1)) return 0; - uint64_t *pt = (uint64_t *)((pde & 0x000ffffffffff000) + hhdmoffset); + uint64_t *pt = (uint64_t *)((pde & 0x000ffffffffff000) + get_kinfo()->hhdmoffset); uint64_t pte = pt[pt_offset]; if (!(pte & 1)) return 0; @@ -326,7 +326,7 @@ void *va_alloc_contigious_pages(size_t pages){ return NULL; } - vmm_map_page(kernel_page_map, va_base+hhdmoffset+i*PAGE_SIZE, (uint64_t)t, PTE_BIT_RW | PTE_BIT_PRESENT); + vmm_map_page(kernel_page_map, va_base+get_kinfo()->hhdmoffset+i*PAGE_SIZE, (uint64_t)t, PTE_BIT_RW | PTE_BIT_PRESENT); } uint64_t va_base_old = va_base; @@ -335,14 +335,14 @@ void *va_alloc_contigious_pages(size_t pages){ free_spinlock(&va_lock); - return (void*)(va_base_old+hhdmoffset); + return (void*)(va_base_old+get_kinfo()->hhdmoffset); } /* Maps pages from phys_addr to phys_addr+size into the kernels address space */ void kmap_pages(void *phys_addr, uint64_t size, uint64_t flags){ for(uint64_t i = 0; i < size; i++){ - vmm_map_page(kernel_page_map, (uint64_t)phys_addr + hhdmoffset + (i * PAGE_SIZE), (uint64_t)phys_addr + (i * PAGE_SIZE), PTE_BIT_PRESENT | flags); + vmm_map_page(kernel_page_map, (uint64_t)phys_addr + get_kinfo()->hhdmoffset + (i * PAGE_SIZE), (uint64_t)phys_addr + (i * PAGE_SIZE), PTE_BIT_PRESENT | flags); } } diff --git a/src/scheduler/sched.c b/src/scheduler/sched.c index 25dcf24..55354af 100644 --- a/src/scheduler/sched.c +++ b/src/scheduler/sched.c @@ -3,7 +3,7 @@ #include #include #include -#include +#include #include #include #include @@ -11,6 +11,7 @@ #include extern void switch_context(struct context **old, struct context *new); +extern void sched_enter(void *a); struct ma_cache *thread_cache; struct thread *idle; @@ -21,7 +22,7 @@ int next_pid = 1; void idle_task(){ for(;;){ - kprintf("idling!\n"); + __builtin_ia32_pause(); } } @@ -36,21 +37,22 @@ void best_task(){ } void thread_exit(){ + + #ifdef __x86_64__ + asm("cli"); + #endif + cpu_state *cpu = get_cpu_struct(); struct thread *p = cpu->current_process; - if(p == p->next){ + if(p == p->next && p->prev == p){ // If this is the only thread in the queue then set cpu->head to NULL, so scheduler knows to idle cpu->head = NULL; }else{ // Remove process from circular linked list p->next->prev = p->prev; p->prev->next = p->next; - - if(p == cpu->head){ - //cpu->head = p->next; - } - + cpu->head = p->next; } p->state = ZOMBIE; @@ -71,6 +73,7 @@ struct thread *alloc_thread(void){ t->pid = next_pid++; uint64_t *sp = (uint64_t*)((uint64_t)t->kstack + 8 * 4096); + // Push the exit function (the thread will return to it when it finishes) *--sp = (uint64_t)thread_exit; @@ -80,7 +83,7 @@ struct thread *alloc_thread(void){ t->context = (struct context*)sp; t->context->rbp = (uint64_t)sp; - + return t; } @@ -115,28 +118,28 @@ struct thread *add_thread(uint64_t *entry){ [[noreturn]] void sched(){ + cpu_state *cpu = get_cpu_struct(); + cpu->scheduler_initialized = true; // Allow us to get interrupts that schedule us for(;;){ - asm("cli"); // we sti at the end of switch_context - cpu_state *cpu = get_cpu_struct(); + #ifdef __x86_64__ + asm("cli"); // we sti at the end of switch_context + #endif + struct thread *prev = cpu->current_process; + if(cpu->head == NULL){ + cpu->current_process = idle; + }else{ + cpu->current_process = cpu->head; + cpu->head = cpu->head->next; + } + if(prev->state == ZOMBIE){ - kprintf("we are freeing allocated thread 0x{x}\n", prev); ma_cache_dealloc(prev); }else{ prev->state = READY; } - if(cpu->head == NULL){ - cpu->current_process = idle; - }else{ - if(prev->next){ - cpu->current_process = prev->next; - }else{ - cpu->current_process = cpu->head; - } - } - cpu->current_process->state = RUNNING; switch_context(&(get_cpu_struct()->scheduler_context), get_cpu_struct()->current_process->context); } @@ -148,31 +151,29 @@ void scheduler_init(){ cpu_state *cpu = get_cpu_struct(); if(cpu->current_process != NULL){ - kprintf("scheduler on CPU {d} already initialized!\n", cpu->lapic_id); + kprintf("scheduler on CPU {d} already initialized!\n", cpu->id); return; } - - idle = alloc_thread(); - idle->context->rip = (uint64_t)idle; - - assert(idle != NULL && "Failed to allocate idle task!"); + + if(cpu->id == get_kinfo()->bsp_id){ + idle = alloc_thread(); + idle->context->rip = (uint64_t)idle_task; + assert(idle != NULL && "Failed to allocate idle task!"); + } cpu->current_process = idle; - cpu->scheduler_stack = kzalloc(4096); - cpu->scheduler_context = (struct context*)((uint64_t)cpu->scheduler_stack + 4096); - cpu->scheduler_context->rbp = (uint64_t)cpu->scheduler_context; - cpu->scheduler_context->rip = (uint64_t)sched; + kprintf("scheduler on CPU {d} initialized!", cpu->id); + + sched(); - add_thread((uint64_t*)test_task); - - add_thread((uint64_t *)best_task); - - // Initialize scheduler -> we will now get timer interrupts to switch us into sched() - cpu->scheduler_initialized = true; + for(;;); } void yield(){ + #ifdef __x86_64__ + asm("cli"); + #endif switch_context(&get_cpu_struct()->current_process->context, get_cpu_struct()->scheduler_context); } \ No newline at end of file diff --git a/src/arch/amd64/hal/smp.c b/src/smp.c similarity index 61% rename from src/arch/amd64/hal/smp.c rename to src/smp.c index 3d96056..adab05e 100644 --- a/src/arch/amd64/hal/smp.c +++ b/src/smp.c @@ -1,25 +1,23 @@ +#include #include #include #include #include #include #include -#include +#include #include #include #include +#include #include -#include +#include #include -static volatile struct limine_smp_request smp_request = { - .id = LIMINE_SMP_REQUEST, - .revision = 0, -}; extern void s_load_idt(); extern void s_load_gdt(); -extern uint64_t hhdmoffset; +extern volatile struct limine_mp_request smp_request; /* Returns the CPU structure for this particular CPU */ cpu_state *get_cpu_struct(){ @@ -27,11 +25,15 @@ cpu_state *get_cpu_struct(){ } uint64_t get_cpu_count(){ - return smp_request.response->cpu_count; + if(smp_request.response != NULL){ + return smp_request.response->cpu_count; + } + + return 0; } bool get_cpu_struct_initialized(){ - if(rdmsr(GSBASE) < hhdmoffset){ + if(rdmsr(GSBASE) < get_kinfo()->hhdmoffset){ return false; } @@ -40,7 +42,7 @@ bool get_cpu_struct_initialized(){ atomic_flag ap_init_lock = ATOMIC_FLAG_INIT; -void ap_init(struct limine_smp_info *smp_info){ +void ap_init(struct limine_mp_info *smp_info){ acquire_spinlock(&ap_init_lock); @@ -61,9 +63,9 @@ void ap_init(struct limine_smp_info *smp_info){ : : : "rax" ); - cpu_state *cpu_struct = (cpu_state*)kmalloc(sizeof(cpu_state)); - memset(cpu_struct, 0, sizeof(cpu_state)); - cpu_struct->lapic_id = smp_info->lapic_id; + cpu_state *cpu_struct = (cpu_state*)kzalloc(sizeof(cpu_state)); + + cpu_struct->id = smp_info->lapic_id; wrmsr(KERNELGSBASE, (uint64_t)cpu_struct); wrmsr(GSBASE, (uint64_t)cpu_struct); @@ -78,14 +80,11 @@ void ap_init(struct limine_smp_info *smp_info){ scheduler_init(); } -void smp_init(){ - - if(!smp_request.response){ - klog(__func__, "Failed to get SMP request"); - kkill(); - } +static cpu_state bsp_cpu; - struct limine_smp_response *smp_response = smp_request.response; +void smp_init(){ + + struct limine_mp_response *smp_response = smp_request.response; kprintf("smp: {d} CPUs\n", smp_response->cpu_count); @@ -94,16 +93,7 @@ void smp_init(){ smp_response->cpus[i]->goto_address = &ap_init; } - /* -- Setup CPU structure for BSP -- */ - - /* Allocate CPU structure */ - cpu_state *cpu_struct = (cpu_state*)kmalloc(sizeof(cpu_state)); - cpu_struct->lapic_id = smp_response->cpus[0]->lapic_id; - - cpu_struct->scheduler_context = (struct context*)kmalloc(sizeof(struct context)); - - wrmsr(KERNELGSBASE, (uint64_t)cpu_struct); - wrmsr(GSBASE, (uint64_t)cpu_struct); + bsp_cpu.scheduler_context = (struct context*)kmalloc(sizeof(struct context)); /* If one of the APs has halted, then halt the BSP */ extern bool kernel_killed; @@ -111,4 +101,15 @@ void smp_init(){ kkill(); } +} + +void bsp_early_init(){ + + assert(smp_request.response != NULL && "Failed to get SMP request"); + + struct limine_mp_response *smp_response = smp_request.response; + + bsp_cpu.id = smp_response->cpus[0]->lapic_id; + wrmsr(KERNELGSBASE, (uint64_t)&bsp_cpu); + wrmsr(GSBASE, (uint64_t)&bsp_cpu); } \ No newline at end of file diff --git a/src/sys/acpi.c b/src/sys/acpi.c index 7acb58c..a123692 100644 --- a/src/sys/acpi.c +++ b/src/sys/acpi.c @@ -7,7 +7,7 @@ #include static volatile struct limine_rsdp_request rsdp_request = { - .id = LIMINE_RSDP_REQUEST, + .id = LIMINE_RSDP_REQUEST_ID, .revision = 0, }; @@ -39,7 +39,7 @@ uint64_t *find_acpi_table(char *signature){ } /* Get the virtual address of the header so we can access its signature */ - desc_header_t *virt = (desc_header_t*)((uint64_t)header + hhdmoffset); + desc_header_t *virt = (desc_header_t*)((uint64_t)header + get_kinfo()->hhdmoffset); if(memcmp(virt->signature, signature, 4) == 0){ return (uint64_t*)header; @@ -64,13 +64,13 @@ void acpi_init(void){ /* If the systems ACPI revision is higher/equal than 2, then use XSDT */ if(rsdp->revision >= 2){ rsdt = NULL; - xsdt = (xsdt_t*)(rsdp->xsdt_address + hhdmoffset); + xsdt = (xsdt_t*)(rsdp->xsdt_address + get_kinfo()->hhdmoffset); klog("acpi", "Using XSDT header"); kprintf("XSDT address: 0x{x}\n", (uint64_t)xsdt); kprintf("OEMID: {cccccc}\n", xsdt->header.oemid[0], xsdt->header.oemid[1], xsdt->header.oemid[2], xsdt->header.oemid[3], xsdt->header.oemid[4], xsdt->header.oemid[5]); }else{ xsdt = NULL; - rsdt = (rsdt_t*)(rsdp->rsdt_address + hhdmoffset); + rsdt = (rsdt_t*)(rsdp->rsdt_address + get_kinfo()->hhdmoffset); klog("acpi", "Using RSDT header"); kprintf("RSDT address: 0x{x}\n", (uint64_t)rsdt); kprintf("OEMID: {cccccc}\n", rsdt->header.oemid[0], rsdt->header.oemid[1], rsdt->header.oemid[2], rsdt->header.oemid[3], rsdt->header.oemid[4], rsdt->header.oemid[5]); diff --git a/src/sys/pci.c b/src/sys/pci.c index 45732b8..ae1abb6 100644 --- a/src/sys/pci.c +++ b/src/sys/pci.c @@ -4,6 +4,7 @@ #include #include #include +#include #include #include @@ -40,7 +41,7 @@ void pci_add_device(pci_structure structure){ /* Find first unused space */ while(pci_array[i].func_addr[0] != 0){ if(i >= PCI_DEVICE_BUS){ - klog(__func__, "No more space in the PCI array!"); + klog(__func__, "No more space in the PCI array!"); kkill(); } i++; @@ -93,7 +94,7 @@ void parse_conf_space(){ kprintf(" start pci bus number: 0x{xn}", header.start_pci_num); kprintf(" end pci bus number: 0x{xn}", header.end_pci_num); - config_space_base_addr = header.base_ecm + hhdmoffset; + config_space_base_addr = header.base_ecm + get_kinfo()->hhdmoffset; start_pci_num = header.start_pci_num; end_pci_num = header.end_pci_num; } @@ -175,15 +176,15 @@ void pci_init(){ kkill(); } - mcfg = (mcfg_t*)((uint64_t)mcfg + hhdmoffset); + mcfg = (mcfg_t*)((uint64_t)mcfg + get_kinfo()->hhdmoffset); parse_conf_space(); /* Map the config space */ - kmap_pages((uint64_t*)(config_space_base_addr - hhdmoffset), (PCIE_CONF_SPACE_WIDTH * end_pci_num) / PAGE_SIZE, PTE_BIT_RW | PTE_BIT_NX); + kmap_pages((uint64_t*)(config_space_base_addr - get_kinfo()->hhdmoffset), (PCIE_CONF_SPACE_WIDTH * end_pci_num) / PAGE_SIZE, PTE_BIT_RW | PTE_BIT_NX); /* Stores enough for an entire configuration space */ - pci_array = kmalloc((256 * 32) * sizeof(pci_structure)); + pci_array = kzalloc((256 * 32) * sizeof(pci_structure)); if(!pci_array){ klog(__func__, "Failed to allocate memory for PCI structures!"); @@ -200,7 +201,7 @@ l84_pci_function_return check_device(uint64_t bus, uint64_t device){ pci_header_t *header = (pci_header_t*)get_header(bus, device, 0); - vmm_map_page(kernel_page_map, (uint64_t)header, (uint64_t)header - hhdmoffset, PTE_BIT_PRESENT | PTE_BIT_RW | PTE_BIT_NX); + vmm_map_page(kernel_page_map, (uint64_t)header, (uint64_t)header - get_kinfo()->hhdmoffset, PTE_BIT_PRESENT | PTE_BIT_RW | PTE_BIT_NX); /* If vendor id is 0xffff, that means that this device is unimplemented */ if(header->vendor_id == 0xffff){ @@ -217,7 +218,7 @@ l84_pci_function_return check_device(uint64_t bus, uint64_t device){ uint64_t *addr = (uint64_t*)(config_space_base_addr + ((bus) << 20 | device << 15 | function << 12)); pci_header_t *func = (pci_header_t*)((uint64_t)addr); - vmm_map_page(kernel_page_map, (uint64_t)func, (uint64_t)func - hhdmoffset, PTE_BIT_PRESENT | PTE_BIT_RW | PTE_BIT_NX); + vmm_map_page(kernel_page_map, (uint64_t)func, (uint64_t)func - get_kinfo()->hhdmoffset, PTE_BIT_PRESENT | PTE_BIT_RW | PTE_BIT_NX); if(func->vendor_id != 0xffff){ //kprintf("pci multi: bus: 0x{x} device: 0x{x} type: 0x{x} class: 0x{x} subclass: 0x{x} vendorid: 0x{xn}", bus, func->device_id, multi_header_type, func->class_code, func->subclass, func->vendor_id); @@ -230,7 +231,7 @@ l84_pci_function_return check_device(uint64_t bus, uint64_t device){ ret.multi = false; ret.func_addr[0] = (uint64_t)header; - //kprintf("pci: bus: 0x{x} device: 0x{x} type: 0x{x} class: 0x{x} subclass: 0x{x} vendorid: 0x{xn}", bus, header->device_id, header->header_type, header->class_code, header->subclass, header->vendor_id); + kprintf("pci: bus: 0x{x} device: 0x{x} type: 0x{x} class: 0x{x} subclass: 0x{x} vendorid: 0x{xn}", bus, header->device_id, header->header_type, header->class_code, header->subclass, header->vendor_id); //serial_kprintf("pci: bus: 0x{x} device: 0x{x} type: 0x{x} class: 0x{x} subclass: 0x{x} vendorid: 0x{xn}", bus, header->header_type, header->class_code, header->subclass, header->vendor_id); return ret; diff --git a/src/sys/rand.c b/src/sys/rand.c index 1973c6a..a01a0e1 100644 --- a/src/sys/rand.c +++ b/src/sys/rand.c @@ -17,7 +17,7 @@ void krand_init(){ uint32_t unused, ecx; __get_cpuid(0x01, &unused, &unused, &ecx, &unused); - ecx = (ecx & 2) >> 1; + ecx = (ecx >> 30) & 1; if(ecx == 1){ /* RDRAND supported */ diff --git a/src/sys/time.c b/src/sys/time.c index 3f3b743..008a538 100644 --- a/src/sys/time.c +++ b/src/sys/time.c @@ -1,19 +1,28 @@ /* Time keeping */ +#include "smp.h" #include #include #include +#include -uint64_t get_timestamp_ns(){ - uint64_t ret = 0; - uint64_t tsc = tsc_get_timestamp(); - - if(tsc == 0){ - /* Get APIC timestamp */ +uint64_t get_timestamp_us(){ + + #ifdef __x86_64__ + + uint64_t tsc = tsc_get_timestamp(); - } + if(tsc != 0){ + return tsc; + } - return tsc; + if(get_cpu_struct_initialized()){ + return get_cpu_struct()->lapic_timer_ticks * 1000ULL; + } + + #endif + + return 0; } diff --git a/uacpi_kernel_api.c b/uacpi_kernel_api.c index cdf25ce..e900cbd 100644 --- a/uacpi_kernel_api.c +++ b/uacpi_kernel_api.c @@ -1,4 +1,4 @@ -#include "arch/amd64/hal/smp.h" +#include "smp.h" #include #include #include @@ -15,7 +15,7 @@ #include #include #include -#include +#include #include extern uint64_t hhdmoffset; @@ -76,17 +76,17 @@ uacpi_status uacpi_kernel_pci_read32(uacpi_handle device, uacpi_size offset, uac } uacpi_status uacpi_kernel_pci_write8(uacpi_handle device, uacpi_size offset, uacpi_u8 value){ - *(uint8_t*)((uint64_t)device + offset + hhdmoffset) = value; + *(uint8_t*)((uint64_t)device + offset + get_kinfo()->hhdmoffset) = value; return UACPI_STATUS_OK; } uacpi_status uacpi_kernel_pci_write16(uacpi_handle device, uacpi_size offset, uacpi_u16 value){ - *(uint16_t*)((uint64_t)device + offset + hhdmoffset) = value; + *(uint16_t*)((uint64_t)device + offset + get_kinfo()->hhdmoffset) = value; return UACPI_STATUS_OK; } uacpi_status uacpi_kernel_pci_write32(uacpi_handle device, uacpi_size offset, uacpi_u32 value){ - *(uint32_t*)((uint64_t)device + offset + hhdmoffset) = value; + *(uint32_t*)((uint64_t)device + offset + get_kinfo()->hhdmoffset) = value; return UACPI_STATUS_OK; } @@ -149,7 +149,7 @@ uacpi_status uacpi_kernel_io_write(uacpi_handle handle, uacpi_size offset, uacpi void *uacpi_kernel_map(uacpi_phys_addr addr, uacpi_size len){ uint64_t offset = addr % PAGE_SIZE; kmap_pages((void*)addr, len, 0); - return (void*)addr + hhdmoffset + offset; + return (void*)addr + get_kinfo()->hhdmoffset + offset; } void uacpi_kernel_unmap(void *addr, uacpi_size len){ @@ -177,7 +177,7 @@ void uacpi_kernel_free(void *mem){ } uacpi_u64 uacpi_kernel_get_nanoseconds_since_boot(void){ - return get_timestamp_ns(); + return get_timestamp_us() * 1000; } void uacpi_kernel_stall(uacpi_u8 usec){ @@ -185,7 +185,7 @@ void uacpi_kernel_stall(uacpi_u8 usec){ } void uacpi_kernel_sleep(uacpi_u64 msec){ - sleep(msec ); + sleep(msec); } uacpi_handle uacpi_kernel_create_mutex(){