diff --git a/kernel/src/cpu/idt.rs b/kernel/src/cpu/idt.rs index 43ededc..dfbeee0 100644 --- a/kernel/src/cpu/idt.rs +++ b/kernel/src/cpu/idt.rs @@ -562,7 +562,7 @@ pub fn setup_idt() { set_address(&mut idt.entries[250], isr250); set_address(&mut idt.entries[251], isr251); set_address(&mut idt.entries[252], isr252); - set_address(&mut idt.entries[253], isr253); - set_address(&mut idt.entries[254], isr254); + set_address(&mut idt.entries[253], isr253); // SCI + set_address(&mut idt.entries[254], isr254); // Scheduler set_address(&mut idt.entries[255], isr255); // Spurious interrupt } diff --git a/kernel/src/main.rs b/kernel/src/main.rs index 9812088..cb28b47 100644 --- a/kernel/src/main.rs +++ b/kernel/src/main.rs @@ -12,7 +12,7 @@ use core::{ }; use acpi::AcpiTables; -use acpica_rs::{AcpiInitializeSubsystem, AcpiInitializeTables, AcpiLoadTables}; +use acpica_rs::{AcpiEnableSubsystem, AcpiInitializeObjects, AcpiInitializeSubsystem, AcpiInitializeTables, AcpiLoadTables, ACPI_FULL_INITIALIZATION}; use buddy_system_allocator::LockedHeap; use cpu::{gdt::setup_gdt, idt::setup_idt, paging::setup_paging}; use kernel_common::{ @@ -76,6 +76,10 @@ fn main() { assert_eq!(status, AE_OK); status = unsafe { AcpiLoadTables() }; assert_eq!(status, AE_OK); + status = unsafe { AcpiEnableSubsystem(ACPI_FULL_INITIALIZATION) }; + assert_eq!(status, AE_OK); + status = unsafe { AcpiInitializeObjects(ACPI_FULL_INITIALIZATION) }; + assert_eq!(status, AE_OK); } #[panic_handler] fn panic(info: &PanicInfo) -> ! { diff --git a/kernel/src/sys/acpica_osl.rs b/kernel/src/sys/acpica_osl.rs index 4c6f1bc..043fec4 100644 --- a/kernel/src/sys/acpica_osl.rs +++ b/kernel/src/sys/acpica_osl.rs @@ -2,22 +2,27 @@ use core::{ alloc::Layout, ffi::{c_char, c_void, CStr}, ptr::null_mut, - sync::atomic::Ordering, + sync::atomic::{AtomicPtr, Ordering}, }; -use acpica_rs::{ACPI_IO_ADDRESS, ACPI_PHYSICAL_ADDRESS, ACPI_PREDEFINED_NAMES, ACPI_SIZE, ACPI_STATUS, ACPI_STRING, ACPI_TABLE_HEADER, UINT16, UINT32, UINT64, UINT8}; +use acpica_rs::{ACPI_IO_ADDRESS, ACPI_OSD_HANDLER, ACPI_PHYSICAL_ADDRESS, ACPI_PREDEFINED_NAMES, ACPI_SIZE, ACPI_STATUS, ACPI_STRING, ACPI_TABLE_HEADER, UINT16, UINT32, UINT64, UINT8}; use alloc::{boxed::Box, sync::Arc}; use kernel_common::{ ioports::{inb, inl, inw, outb, outl, outw}, log::log_raw, }; +use spin::Mutex; use crate::{ cpu::paging::{map_physical, unmap_physical}, misc::wrapped_alloc::{wrapped_alloc, wrapped_dealloc}, + sys::ioapic::{register_irq_handler, set_irq_override}, RSDP_ADDRESS, }; +static SCI_HANDLER: Mutex UINT32>> = Mutex::new(None); +static SCI_CONTEXT: AtomicPtr = AtomicPtr::new(null_mut()); + use super::{ sync::{create_semaphore, lock_semaphore, unlock_semaphore, Semaphore, Spinlock}, task::{CURRENT_TASK, CURRENT_TASK_LOCK, MULTITASKING_ENABLED}, @@ -57,11 +62,11 @@ extern "C" fn AcpiOsCreateSemaphore(max: UINT32, initial: UINT32, out: *mut *mut } #[no_mangle] extern "C" fn AcpiOsDeleteLock() { - panic!("Unimplemented"); + unimplemented!(); } #[no_mangle] extern "C" fn AcpiOsDeleteSemaphore() { - panic!("Unimplemented"); + unimplemented!(); } #[no_mangle] extern "C" fn AcpiOsEnterSleep(_sleep_state: UINT8, _reg_a_val: UINT32, _reg_b_val: UINT32) -> ACPI_STATUS { @@ -69,7 +74,7 @@ extern "C" fn AcpiOsEnterSleep(_sleep_state: UINT8, _reg_a_val: UINT32, _reg_b_v } #[no_mangle] extern "C" fn AcpiOsExecute() { - panic!("Unimplemented"); + unimplemented!(); } #[no_mangle] extern "C" fn AcpiOsFree(memory: *mut c_void) { @@ -96,15 +101,25 @@ extern "C" fn AcpiOsGetThreadId() -> UINT64 { } #[no_mangle] extern "C" fn AcpiOsGetTimer() { - panic!("Unimplemented"); + unimplemented!(); } #[no_mangle] extern "C" fn AcpiOsInitialize() -> ACPI_STATUS { AE_OK } +fn sci_handler() { + let handler = SCI_HANDLER.lock().unwrap(); + unsafe { + handler(SCI_CONTEXT.load(Ordering::Relaxed)); + } +} #[no_mangle] -extern "C" fn AcpiOsInstallInterruptHandler() { - panic!("Unimplemented"); +extern "C" fn AcpiOsInstallInterruptHandler(gsi: UINT32, handler: ACPI_OSD_HANDLER, context: *mut c_void) -> ACPI_STATUS { + *SCI_HANDLER.lock() = handler; + SCI_CONTEXT.store(context, Ordering::Relaxed); + set_irq_override(gsi as usize, 253, 1, 1); + register_irq_handler(253, sci_handler); + AE_OK } #[no_mangle] extern "C" fn AcpiOsMapMemory(phys: ACPI_PHYSICAL_ADDRESS, size: ACPI_SIZE) -> *mut c_void { @@ -129,11 +144,11 @@ extern "C" fn AcpiOsPredefinedOverride(_init: *const ACPI_PREDEFINED_NAMES, new: } #[no_mangle] extern "C" fn AcpiOsReadMemory() { - panic!("Unimplemented"); + unimplemented!(); } #[no_mangle] extern "C" fn AcpiOsReadPciConfiguration() { - panic!("Unimplemented"); + unimplemented!(); } #[no_mangle] extern "C" fn AcpiOsReadPort(address: ACPI_IO_ADDRESS, value: *mut UINT32, width: UINT32) -> ACPI_STATUS { @@ -155,15 +170,15 @@ extern "C" fn AcpiOsReleaseLock(handle: *mut c_void, _cpu_flags: ACPI_SIZE) { } #[no_mangle] extern "C" fn AcpiOsStall() { - panic!("Unimplemented"); + unimplemented!(); } #[no_mangle] extern "C" fn AcpiOsRemoveInterruptHandler() { - panic!("Unimplemented"); + unimplemented!(); } #[no_mangle] extern "C" fn AcpiOsSignal() { - panic!("Unimplemented"); + unimplemented!(); } #[no_mangle] extern "C" fn AcpiOsSignalSemaphore(handle: *mut c_void, units: UINT32) -> ACPI_STATUS { @@ -177,7 +192,7 @@ extern "C" fn AcpiOsSignalSemaphore(handle: *mut c_void, units: UINT32) -> ACPI_ } #[no_mangle] extern "C" fn AcpiOsSleep() { - panic!("Unimplemented"); + unimplemented!(); } #[no_mangle] extern "C" fn AcpiOsTableOverride(_existing: *mut ACPI_TABLE_HEADER, new: *mut *mut ACPI_TABLE_HEADER) -> ACPI_STATUS { @@ -203,7 +218,7 @@ extern "C" fn AcpiOsPrint(raw_str: *const c_char) { } #[no_mangle] extern "C" fn AcpiOsWaitEventsComplete() { - panic!("Unimplemented"); + unimplemented!(); } #[no_mangle] extern "C" fn AcpiOsWaitSemaphore(handle: *mut c_void, units: UINT32, _timeout: UINT16) -> ACPI_STATUS { @@ -218,11 +233,11 @@ extern "C" fn AcpiOsWaitSemaphore(handle: *mut c_void, units: UINT32, _timeout: } #[no_mangle] extern "C" fn AcpiOsWriteMemory() { - panic!("Unimplemented"); + unimplemented!(); } #[no_mangle] extern "C" fn AcpiOsWritePciConfiguration() { - panic!("Unimplemented"); + unimplemented!(); } #[no_mangle] extern "C" fn AcpiOsWritePort(address: ACPI_IO_ADDRESS, value: UINT32, width: UINT32) -> ACPI_STATUS { diff --git a/kernel/src/sys/hpet.rs b/kernel/src/sys/hpet.rs index 81ba7cd..0a6eb9f 100644 --- a/kernel/src/sys/hpet.rs +++ b/kernel/src/sys/hpet.rs @@ -12,7 +12,7 @@ use crate::cpu::paging::map_physical; use super::{ early_acpi::EarlyACPIHandler, - ioapic::register_isa_irq_handler, + ioapic::register_irq_handler, scheduler::{schedule_task, yield_task, SCHEDULER_LOCK}, sync::Spinlock, task::{Task, TaskState, CURRENT_TASK, CURRENT_TASK_LOCK, MULTITASKING_ENABLED}, @@ -139,5 +139,5 @@ pub fn setup_hpet(tables: &AcpiTables) { let current_config = address.add(REGISTER_CONFIG).read_volatile(); address.add(REGISTER_CONFIG).write_volatile(current_config | CONFIG_ENABLE | CONFIG_LEGACY_REPLACEMENT); } - register_isa_irq_handler(0, handler); + register_irq_handler(48, handler); } diff --git a/kernel/src/sys/ioapic.rs b/kernel/src/sys/ioapic.rs index f0bb72d..2d6952e 100644 --- a/kernel/src/sys/ioapic.rs +++ b/kernel/src/sys/ioapic.rs @@ -72,22 +72,20 @@ fn write_redirection(mut gsi: usize, redirection: RedirectionEntry) { } pub fn set_irq_override(gsi: usize, vector: usize, polarity: u8, trigger: u8) { let mut redirection = read_redirection(gsi); - redirection.set_vector(48 + vector as u64); + redirection.set_vector(vector as u64); redirection.set_pin_polarity(polarity as u64); redirection.set_trigger_mode(trigger as u64); write_redirection(gsi, redirection); } -pub fn register_isa_irq_handler(irq: usize, handler: fn()) { - if ISR_HANDLERS.lock()[48 + irq] != None { - panic!("IRQ handler already registered"); - } - ISR_HANDLERS.lock()[48 + irq] = Some(handler); +pub fn register_irq_handler(vector: usize, handler: fn()) { + assert!(ISR_HANDLERS.lock()[vector].is_none()); + ISR_HANDLERS.lock()[vector] = Some(handler); for i in 0..32 { let start = IOAPICS[i].start_gsi.load(Ordering::Relaxed); let end = IOAPICS[i].end_gsi.load(Ordering::Relaxed); for j in start..end { let mut redirection = read_redirection(j as usize); - if redirection.vector() == 48 + irq as u64 { + if redirection.vector() == vector as u64 { redirection.set_mask(0); write_redirection(j as usize, redirection); } diff --git a/kernel/src/sys/madt.rs b/kernel/src/sys/madt.rs index 1a9e046..55b44d2 100644 --- a/kernel/src/sys/madt.rs +++ b/kernel/src/sys/madt.rs @@ -28,7 +28,7 @@ pub fn parse_madt(tables: &AcpiTables) { if let MadtEntry::InterruptSourceOverride(irq_override) = i { set_irq_override( irq_override.global_system_interrupt as usize, - irq_override.irq as usize, + 48 + irq_override.irq as usize, irq_override.flags as u8 & 3, irq_override.flags as u8 & 0xc, );