mirror of
https://github.com/Mathewnd/Astral.git
synced 2026-10-28 21:28:21 +00:00
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:
@@ -0,0 +1,13 @@
|
||||
#ifndef _ACPI_H
|
||||
#define _ACPI_H
|
||||
|
||||
// Doesn't depend on PCI, only makes table search available
|
||||
void acpi_early_init(void);
|
||||
|
||||
// Loads the actual ACPI namespace, hooks up the power button
|
||||
void acpi_init(void);
|
||||
|
||||
int acpi_poweroff(void);
|
||||
int acpi_reboot(void);
|
||||
|
||||
#endif
|
||||
@@ -19,6 +19,7 @@
|
||||
#define IPL_DISK 500
|
||||
#define IPL_KEYBOARD 600
|
||||
#define IPL_MOUSE 650
|
||||
#define IPL_ACPI 700
|
||||
#define IPL_DPC 900
|
||||
#define IPL_NORMAL 1000
|
||||
|
||||
|
||||
@@ -0,0 +1,11 @@
|
||||
#include <string.h>
|
||||
#include <printf.h>
|
||||
|
||||
#define uacpi_memcpy memcpy
|
||||
#define uacpi_memset memset
|
||||
#define uacpi_memcmp memcmp
|
||||
#define uacpi_strcmp strcmp
|
||||
#define uacpi_strlen strlen
|
||||
|
||||
#define uacpi_snprintf snprintf
|
||||
#define uacpi_vsnprintf vsnprintf
|
||||
@@ -1,92 +1,8 @@
|
||||
#ifndef _ACPI_H
|
||||
#define _ACPI_H
|
||||
#ifndef _ARCH_ACPI_H
|
||||
#define _ARCH_ACPI_H
|
||||
|
||||
#include <stddef.h>
|
||||
#include <stdint.h>
|
||||
#include <stdbool.h>
|
||||
|
||||
typedef struct {
|
||||
char sig[8];
|
||||
uint8_t checksum;
|
||||
char oem[6];
|
||||
uint8_t revision;
|
||||
uint32_t rsdt;
|
||||
uint32_t length;
|
||||
uint64_t xsdt;
|
||||
uint8_t xchecksum;
|
||||
uint8_t reserved[3];
|
||||
} __attribute__((packed)) rsdp_t;
|
||||
|
||||
typedef struct {
|
||||
char sig[4];
|
||||
uint32_t length;
|
||||
uint8_t revision;
|
||||
uint8_t cechksum;
|
||||
char oemid[6];
|
||||
char oemtableid[8];
|
||||
uint32_t oemrevision;
|
||||
uint32_t creatorid;
|
||||
uint32_t creatorrevision;
|
||||
} __attribute__((packed)) sdtheader_t;
|
||||
|
||||
typedef struct {
|
||||
sdtheader_t header;
|
||||
uint64_t tables[];
|
||||
} __attribute__((packed)) xsdt_t;
|
||||
|
||||
typedef struct {
|
||||
sdtheader_t header;
|
||||
uint32_t tables[];
|
||||
} __attribute__((packed)) rsdt_t;
|
||||
|
||||
typedef struct {
|
||||
sdtheader_t header;
|
||||
uint32_t addr;
|
||||
uint32_t flags;
|
||||
} __attribute__((packed)) madt_t;
|
||||
|
||||
typedef struct {
|
||||
sdtheader_t header;
|
||||
uint8_t hwrev;
|
||||
uint8_t comparatorcount:5;
|
||||
uint8_t countersize:1;
|
||||
uint8_t reserved:1;
|
||||
uint8_t legacy_replacement:1;
|
||||
uint16_t pcivendor;
|
||||
uint8_t addrid;
|
||||
uint8_t bitwidth;
|
||||
uint8_t bitoffset;
|
||||
uint8_t reserved2;
|
||||
uint64_t addr;
|
||||
uint8_t hpetnum;
|
||||
uint16_t mintick;
|
||||
uint8_t pageprot;
|
||||
} __attribute__((packed)) hpet_t;
|
||||
|
||||
typedef struct {
|
||||
uint64_t address;
|
||||
uint16_t sgn;
|
||||
uint8_t startbus;
|
||||
uint8_t endbus;
|
||||
uint32_t reserved;
|
||||
} __attribute__((packed)) mcfgentry_t;
|
||||
|
||||
typedef struct {
|
||||
sdtheader_t header;
|
||||
uint64_t reserved;
|
||||
mcfgentry_t entries[];
|
||||
} __attribute__((packed)) mcfg_t;
|
||||
|
||||
#define ACPI_MADT_TYPE_LAPIC 0
|
||||
#define ACPI_MADT_TYPE_IOAPIC 1
|
||||
#define ACPI_MADT_TYPE_OVERRIDE 2
|
||||
#define ACPI_MADT_TYPE_IONMI 3
|
||||
#define ACPI_MADT_TYPE_LANMI 4
|
||||
#define ACPI_MADT_TYPE_64BITADDR 5
|
||||
#define ACPI_MADT_TYPE_X2APIC 9
|
||||
|
||||
bool arch_acpi_checksumok(void *table);
|
||||
void *arch_acpi_findtable(char *sig, int n);
|
||||
void arch_acpi_init();
|
||||
uintptr_t arch_get_rsdp(void);
|
||||
|
||||
#endif
|
||||
|
||||
@@ -11,8 +11,11 @@
|
||||
#include <kernel/alloc.h>
|
||||
#include <arch/cpu.h>
|
||||
|
||||
#include <uacpi/acpi.h>
|
||||
#include <uacpi/tables.h>
|
||||
|
||||
static size_t mcfgentrycount;
|
||||
static mcfgentry_t *mcfgentries;
|
||||
static struct acpi_mcfg_allocation *mcfgentries;
|
||||
static uint32_t (*pci_archread32)(int bus, int device, int function, uint32_t offset);
|
||||
static void (*pci_archwrite32)(int bus, int device, int function, uint32_t offset, uint32_t value);
|
||||
|
||||
@@ -31,13 +34,13 @@ static void legacy_write32(int bus, int device, int function, uint32_t offset, u
|
||||
outd(CONFDATA, value);
|
||||
}
|
||||
|
||||
static inline mcfgentry_t *getmcfgentry(int bus) {
|
||||
mcfgentry_t *entry;
|
||||
static inline struct acpi_mcfg_allocation *getmcfgentry(int bus) {
|
||||
struct acpi_mcfg_allocation *entry;
|
||||
int i;
|
||||
|
||||
for (i = 0; i < mcfgentrycount; ++i) {
|
||||
entry = &mcfgentries[i];
|
||||
if (bus >= entry->startbus && bus <= entry->endbus)
|
||||
if (bus >= entry->start_bus && bus <= entry->end_bus)
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -48,21 +51,21 @@ static inline mcfgentry_t *getmcfgentry(int bus) {
|
||||
}
|
||||
|
||||
static uint32_t mcfg_read32(int bus, int device, int function, uint32_t offset) {
|
||||
mcfgentry_t *entry = getmcfgentry(bus);
|
||||
struct acpi_mcfg_allocation *entry = getmcfgentry(bus);
|
||||
if (entry == NULL)
|
||||
return 0xffffffff;
|
||||
|
||||
uint64_t base = (uint64_t)entry->address;
|
||||
volatile uint32_t *address = (uint32_t *)((uintptr_t)base + (((bus - entry->startbus) << 20) | (device << 15) | (function << 12) | (offset & ~0x3)));
|
||||
volatile uint32_t *address = (uint32_t *)((uintptr_t)base + (((bus - entry->start_bus) << 20) | (device << 15) | (function << 12) | (offset & ~0x3)));
|
||||
|
||||
return *address;
|
||||
}
|
||||
|
||||
static void mcfg_write32(int bus, int device, int function, uint32_t offset, uint32_t value) {
|
||||
mcfgentry_t *entry = getmcfgentry(bus);
|
||||
struct acpi_mcfg_allocation *entry = getmcfgentry(bus);
|
||||
|
||||
uint64_t base = (uint64_t)entry->address;
|
||||
volatile uint32_t *address = (uint32_t *)((uintptr_t)base + (((bus - entry->startbus) << 20) | (device << 15) | (function << 12) | (offset & ~0x3)));
|
||||
volatile uint32_t *address = (uint32_t *)((uintptr_t)base + (((bus - entry->start_bus) << 20) | (device << 15) | (function << 12) | (offset & ~0x3)));
|
||||
|
||||
*address = value;
|
||||
}
|
||||
@@ -77,20 +80,23 @@ static uint64_t msiformatmessage(uint32_t *data, int vector, int edgetrigger, in
|
||||
#define MCFG_MAPPING_SIZE(buscount) (4096l * 8l * 32l * (buscount))
|
||||
|
||||
static void pci_archinit() {
|
||||
mcfg_t *mcfg = arch_acpi_findtable("MCFG", 0);
|
||||
uacpi_table tbl;
|
||||
struct acpi_mcfg *mcfg;
|
||||
|
||||
if (mcfg) {
|
||||
uacpi_status ret = uacpi_table_find_by_signature("MCFG", &tbl);
|
||||
if (ret == UACPI_STATUS_OK) {
|
||||
printf("pci: MCFG table found. Using extended configuration space\n");
|
||||
mcfg = tbl.ptr;
|
||||
pci_archread32 = mcfg_read32;
|
||||
pci_archwrite32 = mcfg_write32;
|
||||
mcfgentrycount = (mcfg->header.length - sizeof(sdtheader_t)) / sizeof(mcfgentry_t);
|
||||
mcfgentries = alloc(sizeof(mcfgentry_t) * mcfgentrycount);
|
||||
mcfgentrycount = (mcfg->hdr.length - sizeof(struct acpi_sdt_hdr)) / sizeof(struct acpi_mcfg_allocation);
|
||||
mcfgentries = alloc(sizeof(struct acpi_mcfg_allocation) * mcfgentrycount);
|
||||
__assert(mcfgentries);
|
||||
memcpy(mcfgentries, mcfg->entries, sizeof(mcfgentry_t) * mcfgentrycount);
|
||||
memcpy(mcfgentries, mcfg->entries, sizeof(struct acpi_mcfg_allocation) * mcfgentrycount);
|
||||
for (int i = 0; i < mcfgentrycount; ++i) {
|
||||
void *phys = (void *)mcfgentries[i].address;
|
||||
uintmax_t pageoffset = (uintptr_t)phys % PAGE_SIZE;
|
||||
size_t mappingsize = pageoffset + MCFG_MAPPING_SIZE(mcfgentries[i].endbus - mcfgentries[i].startbus + 1);
|
||||
size_t mappingsize = pageoffset + MCFG_MAPPING_SIZE(mcfgentries[i].end_bus - mcfgentries[i].start_bus + 1);
|
||||
void *virt = vmm_map(NULL, mappingsize, VMM_FLAGS_PHYSICAL,
|
||||
ARCH_MMU_FLAGS_READ | ARCH_MMU_FLAGS_WRITE | ARCH_MMU_FLAGS_NOEXEC | ARCH_MMU_FLAGS_UC, phys);
|
||||
__assert(virt);
|
||||
|
||||
Reference in New Issue
Block a user