38310e4f23
Signed-off-by: Chloe M. <chloe@mensia.org>
70 lines
1.5 KiB
C
70 lines
1.5 KiB
C
/*
|
|
* Copyright (c) 2026, Chloe M.
|
|
* Provided under the BSD-3 clause.
|
|
*
|
|
* Description: Local APIC driver
|
|
* Author: Chloe M.
|
|
*/
|
|
|
|
#include <machine/lapic.h>
|
|
#include <machine/lapicreg.h>
|
|
#include <machine/msr.h>
|
|
#include <machine/cpuid.h>
|
|
#include <ex/trace.h>
|
|
#include <ke/knot.h>
|
|
#include <stdef.h>
|
|
|
|
/*
|
|
* Trace only on the bootstrap processor but not on any others
|
|
* to avoid log spam...
|
|
*/
|
|
#define DTRACE_BSP(Fmt, ...) do { \
|
|
ULONG ApicBase; \
|
|
\
|
|
ApicBase = MdRdmsr(IA32_APIC_BASE_MSR); \
|
|
if (ISSET(ApicBase, BIT(8))) { \
|
|
TRACE("[ LAPIC ]: " Fmt, ##__VA_ARGS__); \
|
|
} \
|
|
} while (0);
|
|
|
|
/*
|
|
* Returns true if the Local APIC unit is supported on the
|
|
* current processor.
|
|
*/
|
|
static BOOLEAN
|
|
LapicIsSupported(VOID)
|
|
{
|
|
ULONG Edx, Unused;
|
|
|
|
CPUID(1, Unused, Unused, Unused, Edx);
|
|
return ISSET(Edx, BIT(9)) != 0;
|
|
}
|
|
|
|
/*
|
|
* Enable the Local APIC unit
|
|
*/
|
|
static VOID
|
|
LapicEnable(VOID)
|
|
{
|
|
UQUAD ApicBase;
|
|
|
|
/* Hardware enable the Local APIC unit */
|
|
ApicBase = MdRdmsr(IA32_APIC_BASE_MSR);
|
|
ApicBase |= LAPIC_HW_ENABLE;
|
|
MdWrmsr(IA32_APIC_BASE_MSR, ApicBase);
|
|
}
|
|
|
|
VOID
|
|
MdLapicInit(KPCR *Kpcr)
|
|
{
|
|
if (Kpcr == NULL) {
|
|
KeKnot(KNOT_MISC, "failed to initialize lapic driver\n");
|
|
}
|
|
|
|
if (!LapicIsSupported()) {
|
|
KeKnot(KNOT_MISSING_HARDWARE, "local apic not supported\n");
|
|
}
|
|
|
|
LapicEnable();
|
|
}
|