From 114cc434d2d2e3105385d57f591ba727353b1a3b Mon Sep 17 00:00:00 2001 From: "Chloe M." Date: Tue, 23 Jun 2026 22:01:52 +0000 Subject: [PATCH] stos/amd64: intr: Add IRQL management Signed-off-by: Chloe M. --- paw/stos/arch/amd64/cpu/intr.c | 57 ++++++++++++++++++++++++++++++++++ paw/stos/head/hal/intr.h | 23 ++++++++++++++ paw/stos/head/ke/knot.h | 6 +++- paw/stos/ke/knot.c | 4 ++- 4 files changed, 88 insertions(+), 2 deletions(-) diff --git a/paw/stos/arch/amd64/cpu/intr.c b/paw/stos/arch/amd64/cpu/intr.c index 7028e77..4f599f6 100644 --- a/paw/stos/arch/amd64/cpu/intr.c +++ b/paw/stos/arch/amd64/cpu/intr.c @@ -8,6 +8,7 @@ #include #include +#include #include /* Interrupt priority level shift */ @@ -16,6 +17,20 @@ /* Globals */ static INTR_HANDLER Handlers[256]; +/* + * Set a new IRQL + */ +static inline VOID +SetIrql(IRQL Irql) +{ + ASMV( + "mov %0, %%cr8" + : + : "r" ((UQUAD)Irql) + : "memory" + ); +} + ST_STATUS HalRegisterIntr(const INTR_HANDLER *Handler, BOOLEAN IsUser) { @@ -74,3 +89,45 @@ HalRegisterIntr(const INTR_HANDLER *Handler, BOOLEAN IsUser) /* No entry found */ return STATUS_NOT_FOUND; } + +IRQL +HalGetIrql(VOID) +{ + UQUAD CurrentIrql; + + ASMV( + "mov %%cr8, %0" + : "=r" (CurrentIrql) + : + : "memory" + ); + + return (IRQL)CurrentIrql; +} + +IRQL +HalRaiseIrql(IRQL Irql) +{ + IRQL CurrentIrql; + + CurrentIrql = HalGetIrql(); + if (Irql < CurrentIrql) { + KeKnot(IRQL_NOT_GTE, "got bad irql\n"); + } + + SetIrql(Irql); + return CurrentIrql; +} + +IRQL +HalLowerIrql(IRQL Irql) +{ + IRQL CurrentIrql; + + CurrentIrql = HalGetIrql(); + if (Irql > CurrentIrql) { + KeKnot(IRQL_NOT_LTE, "got bad irql\n"); + } + + return CurrentIrql; +} diff --git a/paw/stos/head/hal/intr.h b/paw/stos/head/hal/intr.h index 1818a31..d000020 100644 --- a/paw/stos/head/hal/intr.h +++ b/paw/stos/head/hal/intr.h @@ -69,4 +69,27 @@ typedef struct { */ ST_STATUS HalRegisterIntr(const INTR_HANDLER *Handler, BOOLEAN IsUser); +/* + * Returns the current IRQL + */ +IRQL HalGetIrql(VOID); + +/* + * Raise the IRQL level to a higher level + * + * @Irql: IRQL to raise to + * + * Returns the previous IRQL + */ +IRQL HalRaiseIrql(IRQL Irql); + +/* + * Lower the IRQL level to a lower level + * + * @Irql: IRQL to lower to + * + * Returns the previous IRQL + */ +IRQL HalLowerIrql(IRQL Irql); + #endif /* !_HAL_INTR_H_ */ diff --git a/paw/stos/head/ke/knot.h b/paw/stos/head/ke/knot.h index 3d47316..91502d3 100644 --- a/paw/stos/head/ke/knot.h +++ b/paw/stos/head/ke/knot.h @@ -19,13 +19,17 @@ * @KNOT_BAD_BOOT_PROTO: Bad boot protocol * @KNOT_OOM: Fatal out of memory * @KNOT_EXCEPTION: Fatal exception + * @IRQL_NOT_LTE: IRQL not less than or equal + * @IRQL_NOT_GTE: IRQL not greater than or equal */ typedef enum { KNOT_MISC, KNOT_UNBOUND_RSRC, KNOT_BAD_BOOT_PROTO, KNOT_OOM, - KNOT_EXCEPTION + KNOT_EXCEPTION, + IRQL_NOT_LTE, + IRQL_NOT_GTE } KNOT_REASON; /* diff --git a/paw/stos/ke/knot.c b/paw/stos/ke/knot.c index ca5513f..ea5831d 100644 --- a/paw/stos/ke/knot.c +++ b/paw/stos/ke/knot.c @@ -22,7 +22,9 @@ static const CHAR *ReasonTable[] = { [KNOT_UNBOUND_RSRC] = "unbounded resource", [KNOT_BAD_BOOT_PROTO] = "bad boot protocol", [KNOT_OOM] = "out of memory", - [KNOT_EXCEPTION] = "fatal exception" + [KNOT_EXCEPTION] = "fatal exception", + [IRQL_NOT_LTE] = "irql not less than or equal", + [IRQL_NOT_GTE] = "irql not greater than or equal" }; /* Globals */