stos/amd64: hpet: Implement HPET register checking
Signed-off-by: Chloe M. <chloe@mensia.org>
This commit is contained in:
@@ -7,18 +7,64 @@
|
||||
*/
|
||||
|
||||
#include <machine/hpet.h>
|
||||
#include <machine/hpetreg.h>
|
||||
#include <drivers/acpi/tables.h>
|
||||
#include <drivers/acpi/acpi.h>
|
||||
#include <hal/mmio.h>
|
||||
#include <mm/vmm.h>
|
||||
#include <ke/knot.h>
|
||||
#include <ex/trace.h>
|
||||
|
||||
#define DTRACE(Fmt, ...) \
|
||||
TRACE("[ HPET ]: " Fmt, ##__VA_ARGS__)
|
||||
|
||||
static VOID *MMIOBase = NULL;
|
||||
|
||||
/*
|
||||
* Write a 64-bit value to an HPET register
|
||||
*
|
||||
* @Register: Register to write to
|
||||
* @Value: Value to write
|
||||
*/
|
||||
static VOID
|
||||
HpetWriteq(UCHAR Register, UQUAD Value)
|
||||
{
|
||||
VOID *RegBase;
|
||||
|
||||
if (MMIOBase == NULL) {
|
||||
return;
|
||||
}
|
||||
|
||||
RegBase = PTR_OFFSET(MMIOBase, Register);
|
||||
MMIOWrite64(MMIOBase, Value);
|
||||
}
|
||||
|
||||
/*
|
||||
* Read a 64-bit value from an HPET register
|
||||
*
|
||||
* @Register: Register to read from
|
||||
*/
|
||||
static UQUAD
|
||||
HpetReadq(UCHAR Register)
|
||||
{
|
||||
VOID *RegBase;
|
||||
|
||||
if (MMIOBase == NULL) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
RegBase = PTR_OFFSET(MMIOBase, Register);
|
||||
return MMIORead64(RegBase);
|
||||
}
|
||||
|
||||
VOID
|
||||
MdHpetInit(VOID)
|
||||
{
|
||||
ACPI_HPET *Hpet;
|
||||
UQUAD GeneralCap;
|
||||
ULONG ClkPeriod;
|
||||
UCHAR RevId;
|
||||
const ACPI_GAS *Gas;
|
||||
|
||||
Hpet = AcpiQuery("HPET");
|
||||
if (Hpet == NULL) {
|
||||
@@ -32,4 +78,22 @@ MdHpetInit(VOID)
|
||||
DTRACE("detected hpet with pci vendor id : %x\n", Hpet->PciVendorId);
|
||||
DTRACE("counter size : %d\n", Hpet->CounterSize);
|
||||
DTRACE("minimum tick : %d\n", Hpet->MinimumTick);
|
||||
|
||||
/* Obtain the MMIO base address */
|
||||
Gas = &Hpet->Gas;
|
||||
MMIOBase = PMA_TO_VMA(Gas->Address);
|
||||
|
||||
GeneralCap = HpetReadq(HPET_GENERAL_CAP);
|
||||
ClkPeriod = (GeneralCap >> HPET_PERIOD_SHIFT) & HPET_PERIOD_MASK;
|
||||
RevId = GeneralCap & 0xFF;
|
||||
DTRACE("counter clk period : %d\n", ClkPeriod);
|
||||
|
||||
/*
|
||||
* Verify that the clock period and the revision ID are not
|
||||
* garbage values.
|
||||
*/
|
||||
if (ClkPeriod > HPET_MAX_CLK_PERIOD)
|
||||
KeKnot(KNOT_MISC, "hpet: bad counter clk period\n");
|
||||
if (RevId == 0)
|
||||
KeKnot(KNOT_MISC, "hpet: bad revision id, must not be zero\n");
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user