Integrate uACPI & remove own ACPI parsing code

This commit adds uACPI as a submodule and removes all handwritten table
parsing code as well as struct definitions, since they now work via
uACPI. There's also now an ability to shut down by using the power
button.
This commit is contained in:
8infy
2024-09-01 19:51:39 +03:00
parent 476d4bad74
commit db55f99e23
14 changed files with 758 additions and 266 deletions
+86
View File
@@ -0,0 +1,86 @@
#include "uacpi/kernel_api.h"
#include "uacpi/status.h"
#include "uacpi/types.h"
#include <kernel/acpi.h>
#include <kernel/interrupt.h>
#include <arch/acpi.h>
#include <logging.h>
#include <uacpi/uacpi.h>
#include <uacpi/utilities.h>
#include <uacpi/sleep.h>
#include <uacpi/event.h>
void acpi_early_init(void) {
struct uacpi_init_params params = {
.rsdp = arch_get_rsdp(),
.log_level = UACPI_LOG_INFO,
};
uacpi_status ret = uacpi_initialize(&params);
__assert(ret == UACPI_STATUS_OK);
}
void acpi_dopoweroff(uacpi_handle ctx) {
(void)ctx;
acpi_poweroff();
}
static uacpi_interrupt_ret handle_pwrbtn(uacpi_handle ctx) {
uacpi_kernel_schedule_work(UACPI_WORK_GPE_EXECUTION, acpi_dopoweroff, ctx);
return UACPI_INTERRUPT_HANDLED;
}
void acpi_init(void) {
uacpi_status ret;
ret = uacpi_namespace_load();
__assert(ret == UACPI_STATUS_OK);
uacpi_set_interrupt_model(UACPI_INTERRUPT_MODEL_IOAPIC);
ret = uacpi_namespace_initialize();
__assert(ret == UACPI_STATUS_OK);
uacpi_install_fixed_event_handler(
UACPI_FIXED_EVENT_POWER_BUTTON,
handle_pwrbtn, UACPI_NULL
);
}
int acpi_poweroff(void) {
uacpi_status ret = uacpi_prepare_for_sleep_state(UACPI_SLEEP_STATE_S5);
if (uacpi_unlikely_error(ret)) {
printf("acpi: unable to prepare for sleep: %s", uacpi_status_to_string(ret));
return EIO;
}
interrupt_set(false);
ret = uacpi_enter_sleep_state(UACPI_SLEEP_STATE_S5);
if (uacpi_unlikely_error(ret)) {
interrupt_set(true);
printf("acpi: unable to enter S5: %s", uacpi_status_to_string(ret));
return EIO;
}
return 0;
}
int acpi_reboot(void) {
/*
* Windows does reboot via shutdown, so some hardware expects \_PTS(5)
* to be called prior to rebooting, do that.
*/
uacpi_prepare_for_sleep_state(UACPI_SLEEP_STATE_S5);
uacpi_status ret = uacpi_reboot();
if (uacpi_unlikely_error(ret)) {
printf("unable to perform system reset: %s\n", uacpi_status_to_string(ret));
return EIO;
}
return 0;
}