704 lines
17 KiB
Markdown
704 lines
17 KiB
Markdown
<!-- Moved from docs/03-architecture/hal/interfaces.md to docs/working/architecture/03-architecture/hal/interfaces.md on 2026-06-16 (docs reorg Phase 2) -->
|
|
# HAL Interface Specifications
|
|
|
|
## Overview
|
|
|
|
This document defines the **contract** for each HAL subsystem. These interfaces are platform-agnostic and must be implemented identically (semantically) on all platforms.
|
|
|
|
> **HISTORICAL — L4Re/Fiasco.OC**: L4Re references below describe a target that was a supported platform through mid-2026. L4Re support has since been removed as an active target — `src/platform/l4re/time.c` and related `#ifdef __l4__` code are retained for reference but no longer wired into any build.
|
|
|
|
**Critical:** These are not optional "convenience wrappers"—they are the **only** way VM and physics code access platform resources.
|
|
|
|
---
|
|
|
|
## 1. Time & Timers (`include/hal/hal_time.h`)
|
|
|
|
### Purpose
|
|
Provide monotonic time, periodic/oneshot timers, and calibration for physics subsystems.
|
|
|
|
### Interface
|
|
|
|
```c
|
|
#ifndef HAL_TIME_H
|
|
#define HAL_TIME_H
|
|
|
|
#include <stdint.h>
|
|
|
|
/**
|
|
* Initialize time subsystem.
|
|
* Must be called before any other hal_time_* functions.
|
|
*
|
|
* Responsibilities:
|
|
* - Calibrate high-resolution timer (TSC, HPET, etc.)
|
|
* - Validate monotonicity
|
|
* - Set up timer interrupt sources (if needed)
|
|
*
|
|
* Error handling:
|
|
* - hal_panic() if no suitable time source available
|
|
* - hal_panic() if calibration fails
|
|
*/
|
|
void hal_time_init(void);
|
|
|
|
/**
|
|
* Get current monotonic time in nanoseconds.
|
|
*
|
|
* Guarantees:
|
|
* - MUST be monotonic (never goes backward)
|
|
* - SHOULD have sub-microsecond resolution
|
|
* - MUST be callable from interrupt context (ISR-safe)
|
|
* - MUST be callable concurrently (thread-safe)
|
|
*
|
|
* Performance:
|
|
* - Target: < 50 cycles on x86_64
|
|
* - Acceptable: < 200 cycles
|
|
*
|
|
* Returns:
|
|
* - Nanoseconds since arbitrary epoch (typically boot time)
|
|
*/
|
|
uint64_t hal_time_now_ns(void);
|
|
|
|
/**
|
|
* Busy-wait delay for specified nanoseconds.
|
|
* Used for calibration and short delays.
|
|
*
|
|
* Guarantees:
|
|
* - MUST delay for at least `ns` nanoseconds
|
|
* - MAY delay longer (but not by more than 10%)
|
|
* - MUST be callable from interrupt context
|
|
*
|
|
* Parameters:
|
|
* - ns: Nanoseconds to delay (0 = no delay)
|
|
*
|
|
* Notes:
|
|
* - This is a busy-wait, not a sleep
|
|
* - For delays > 1ms, prefer hal_timer_oneshot()
|
|
*/
|
|
void hal_time_delay_ns(uint64_t ns);
|
|
|
|
/**
|
|
* Timer callback function type.
|
|
*
|
|
* Parameters:
|
|
* - ctx: User-provided context pointer
|
|
*
|
|
* Context:
|
|
* - MAY be called from interrupt context (ISR)
|
|
* - MUST NOT block or sleep
|
|
* - MUST complete quickly (< 10µs target)
|
|
*/
|
|
typedef void (*hal_timer_callback_t)(void *ctx);
|
|
|
|
/**
|
|
* Schedule a oneshot timer to fire after specified nanoseconds.
|
|
*
|
|
* Guarantees:
|
|
* - Callback will fire at least `ns` nanoseconds in the future
|
|
* - MAY fire up to 10% late (jitter allowed)
|
|
* - Callback runs in interrupt context (ISR)
|
|
*
|
|
* Parameters:
|
|
* - ns: Nanoseconds until callback fires (0 = ASAP)
|
|
* - callback: Function to call when timer fires
|
|
* - ctx: User context passed to callback
|
|
*
|
|
* Error handling:
|
|
* - Returns 0 on success
|
|
* - Returns -1 if timer resources exhausted
|
|
*
|
|
* Concurrency:
|
|
* - Thread-safe (can be called from multiple threads)
|
|
* - NOT reentrant from same timer callback
|
|
*/
|
|
int hal_timer_oneshot(uint64_t ns, hal_timer_callback_t callback, void *ctx);
|
|
|
|
/**
|
|
* Schedule a periodic timer to fire every `period_ns` nanoseconds.
|
|
*
|
|
* Guarantees:
|
|
* - Callback will fire repeatedly at ~period_ns intervals
|
|
* - Jitter: < 10% of period (target: < 1%)
|
|
* - Callback runs in interrupt context (ISR)
|
|
* - Timer continues until hal_timer_cancel() called
|
|
*
|
|
* Parameters:
|
|
* - period_ns: Period in nanoseconds (minimum: 1000ns = 1µs)
|
|
* - callback: Function to call on each period
|
|
* - ctx: User context passed to callback
|
|
*
|
|
* Returns:
|
|
* - Timer ID (> 0) on success
|
|
* - -1 if timer resources exhausted
|
|
* - -2 if period_ns < minimum
|
|
*
|
|
* Notes:
|
|
* - This is the PRIMARY mechanism for heartbeat ISR
|
|
* - Platform MUST minimize jitter for experimental validity
|
|
*/
|
|
int hal_timer_periodic(uint64_t period_ns, hal_timer_callback_t callback, void *ctx);
|
|
|
|
/**
|
|
* Cancel a periodic timer.
|
|
*
|
|
* Parameters:
|
|
* - timer_id: ID returned from hal_timer_periodic()
|
|
*
|
|
* Guarantees:
|
|
* - Callback will not fire after this call returns
|
|
* - Safe to call even if timer already fired or was cancelled
|
|
*
|
|
* Returns:
|
|
* - 0 on success
|
|
* - -1 if timer_id invalid
|
|
*/
|
|
int hal_timer_cancel(int timer_id);
|
|
|
|
/**
|
|
* Get timer frequency in Hz.
|
|
* Used for diagnostics and experiment metadata.
|
|
*
|
|
* Returns:
|
|
* - Frequency of underlying time source (e.g., TSC frequency)
|
|
* - 0 if frequency is variable or unknown
|
|
*/
|
|
uint64_t hal_time_frequency_hz(void);
|
|
|
|
#endif /* HAL_TIME_H */
|
|
```
|
|
|
|
### Platform Implementation Notes
|
|
|
|
**Linux (`platform/linux/hal_time.c`):**
|
|
- `hal_time_now_ns()` → `clock_gettime(CLOCK_MONOTONIC)`
|
|
- `hal_timer_periodic()` → `timer_create()` with `SIGRTMIN` + signal handler
|
|
- Challenge: Signal-based timers have ~1-10µs latency jitter
|
|
|
|
**L4Re (`platform/l4re/hal_time.c`):**
|
|
- `hal_time_now_ns()` → `l4re_kip_clock()`
|
|
- `hal_timer_periodic()` → L4Re IPC-based timer + IRQ object
|
|
- Challenge: IPC overhead, but lower jitter than Linux
|
|
|
|
**Kernel (`platform/kernel/hal_time.c`):**
|
|
- `hal_time_now_ns()` → `rdtsc()` calibrated against HPET
|
|
- `hal_timer_periodic()` → APIC timer interrupt
|
|
- Challenge: TSC drift on old hardware, calibration complexity
|
|
|
|
---
|
|
|
|
## 2. Interrupts (`include/hal/hal_interrupt.h`)
|
|
|
|
### Purpose
|
|
Enable/disable interrupts, register ISRs, query interrupt context.
|
|
|
|
### Interface
|
|
|
|
```c
|
|
#ifndef HAL_INTERRUPT_H
|
|
#define HAL_INTERRUPT_H
|
|
|
|
#include <stdint.h>
|
|
|
|
/**
|
|
* Initialize interrupt subsystem.
|
|
* Must be called before any other hal_interrupt_* functions.
|
|
*
|
|
* Responsibilities:
|
|
* - Set up interrupt controller (PIC/APIC on x86_64)
|
|
* - Initialize IDT (on kernel platforms)
|
|
* - Prepare for ISR registration
|
|
*
|
|
* Error handling:
|
|
* - hal_panic() if interrupt controller unavailable
|
|
*/
|
|
void hal_interrupt_init(void);
|
|
|
|
/**
|
|
* Enable interrupts globally.
|
|
*
|
|
* Guarantees:
|
|
* - Interrupts will be delivered after this call
|
|
* - Safe to call multiple times (idempotent)
|
|
* - NOT callable from interrupt context
|
|
*
|
|
* Notes:
|
|
* - On x86_64 kernel: sti
|
|
* - On Linux: no-op (interrupts always enabled)
|
|
*/
|
|
void hal_irq_enable(void);
|
|
|
|
/**
|
|
* Disable interrupts globally.
|
|
*
|
|
* Guarantees:
|
|
* - Interrupts will NOT be delivered after this call
|
|
* - Safe to call multiple times (idempotent)
|
|
* - Callable from interrupt context
|
|
*
|
|
* Returns:
|
|
* - Previous interrupt state (for hal_irq_restore)
|
|
*
|
|
* Notes:
|
|
* - On x86_64 kernel: cli
|
|
* - On Linux: no-op (interrupts always enabled)
|
|
*/
|
|
unsigned long hal_irq_disable(void);
|
|
|
|
/**
|
|
* Restore previous interrupt state.
|
|
*
|
|
* Parameters:
|
|
* - state: Value returned from hal_irq_disable()
|
|
*
|
|
* Use case:
|
|
* unsigned long flags = hal_irq_disable();
|
|
* // critical section
|
|
* hal_irq_restore(flags);
|
|
*/
|
|
void hal_irq_restore(unsigned long state);
|
|
|
|
/**
|
|
* Interrupt service routine function type.
|
|
*
|
|
* Parameters:
|
|
* - irq: IRQ number that triggered
|
|
* - ctx: User-provided context pointer
|
|
*
|
|
* Context:
|
|
* - ALWAYS called from interrupt context
|
|
* - MUST NOT block or sleep
|
|
* - MUST complete quickly (< 10µs target, < 100µs acceptable)
|
|
* - MUST NOT call non-ISR-safe HAL functions
|
|
*/
|
|
typedef void (*hal_isr_t)(unsigned int irq, void *ctx);
|
|
|
|
/**
|
|
* Register an interrupt service routine.
|
|
*
|
|
* Parameters:
|
|
* - irq: IRQ number to register (platform-specific numbering)
|
|
* - isr: Function to call when IRQ fires
|
|
* - ctx: User context passed to ISR
|
|
*
|
|
* Guarantees:
|
|
* - ISR will be called when IRQ fires
|
|
* - Only one ISR per IRQ (replaces previous if registered)
|
|
* - ISR runs with interrupts disabled (not reentrant)
|
|
*
|
|
* Returns:
|
|
* - 0 on success
|
|
* - -1 if IRQ number invalid
|
|
* - -2 if ISR registration failed
|
|
*
|
|
* Notes:
|
|
* - Used by hal_timer_periodic() internally
|
|
* - Used by device drivers for hardware IRQs
|
|
*/
|
|
int hal_irq_register(unsigned int irq, hal_isr_t isr, void *ctx);
|
|
|
|
/**
|
|
* Unregister an interrupt service routine.
|
|
*
|
|
* Parameters:
|
|
* - irq: IRQ number to unregister
|
|
*
|
|
* Returns:
|
|
* - 0 on success
|
|
* - -1 if IRQ was not registered
|
|
*/
|
|
int hal_irq_unregister(unsigned int irq);
|
|
|
|
/**
|
|
* Check if currently executing in interrupt context.
|
|
*
|
|
* Returns:
|
|
* - 1 if in interrupt context (ISR)
|
|
* - 0 if in normal execution context
|
|
*
|
|
* Use case:
|
|
* - Validate ISR-only functions (e.g., heartbeat sampling)
|
|
* - Conditional behavior (ISR vs. normal path)
|
|
*
|
|
* Performance:
|
|
* - MUST be fast (< 10 cycles)
|
|
* - Often implemented as checking a per-CPU flag
|
|
*/
|
|
int hal_in_interrupt_context(void);
|
|
|
|
#endif /* HAL_INTERRUPT_H */
|
|
```
|
|
|
|
### Platform Implementation Notes
|
|
|
|
**Linux:**
|
|
- `hal_irq_enable/disable()` → no-op (can't disable signals)
|
|
- `hal_irq_register()` → `sigaction()` + signal handler
|
|
- `hal_in_interrupt_context()` → thread-local flag set by signal handler
|
|
|
|
**Kernel:**
|
|
- `hal_irq_enable/disable()` → `sti`/`cli` (x86_64)
|
|
- `hal_irq_register()` → IDT entry + APIC configuration
|
|
- `hal_in_interrupt_context()` → check per-CPU interrupt nesting count
|
|
|
|
---
|
|
|
|
## 3. Memory (`include/hal/hal_memory.h`)
|
|
|
|
### Purpose
|
|
Allocate/free memory, map pages, manage heap.
|
|
|
|
### Interface
|
|
|
|
```c
|
|
#ifndef HAL_MEMORY_H
|
|
#define HAL_MEMORY_H
|
|
|
|
#include <stddef.h>
|
|
#include <stdint.h>
|
|
|
|
/**
|
|
* Initialize memory subsystem.
|
|
* Must be called before any other hal_mem_* functions.
|
|
*
|
|
* Responsibilities:
|
|
* - Set up heap allocator
|
|
* - Initialize page tables (kernel platforms)
|
|
* - Parse memory map (kernel platforms)
|
|
*
|
|
* Error handling:
|
|
* - hal_panic() if insufficient memory
|
|
*/
|
|
void hal_mem_init(void);
|
|
|
|
/**
|
|
* Allocate memory from heap.
|
|
*
|
|
* Parameters:
|
|
* - size: Bytes to allocate (0 = returns NULL)
|
|
*
|
|
* Guarantees:
|
|
* - Returns aligned pointer (at least 8-byte aligned)
|
|
* - Memory is zero-initialized
|
|
* - Thread-safe (can be called concurrently)
|
|
* - NOT callable from interrupt context
|
|
*
|
|
* Returns:
|
|
* - Pointer to allocated memory
|
|
* - NULL if allocation failed
|
|
*
|
|
* Notes:
|
|
* - On Linux: wrapper around malloc()
|
|
* - On kernel: custom heap allocator (kmalloc)
|
|
*/
|
|
void *hal_mem_alloc(size_t size);
|
|
|
|
/**
|
|
* Free memory allocated by hal_mem_alloc().
|
|
*
|
|
* Parameters:
|
|
* - ptr: Pointer returned from hal_mem_alloc() (NULL = no-op)
|
|
*
|
|
* Guarantees:
|
|
* - Thread-safe
|
|
* - NOT callable from interrupt context
|
|
* - Safe to call with NULL
|
|
*/
|
|
void hal_mem_free(void *ptr);
|
|
|
|
/**
|
|
* Allocate contiguous physical pages.
|
|
* Used for DMA buffers, page tables, large allocations.
|
|
*
|
|
* Parameters:
|
|
* - count: Number of pages to allocate (page size is platform-specific)
|
|
*
|
|
* Returns:
|
|
* - Physical address of first page
|
|
* - 0 if allocation failed
|
|
*
|
|
* Notes:
|
|
* - Pages are NOT mapped into virtual address space
|
|
* - Caller must call hal_mem_map() to access
|
|
* - On Linux: may use mmap() with MAP_ANONYMOUS
|
|
* - On kernel: physical memory manager (PMM)
|
|
*/
|
|
uint64_t hal_mem_alloc_pages(size_t count);
|
|
|
|
/**
|
|
* Free physical pages allocated by hal_mem_alloc_pages().
|
|
*
|
|
* Parameters:
|
|
* - paddr: Physical address returned from hal_mem_alloc_pages()
|
|
* - count: Number of pages to free
|
|
*/
|
|
void hal_mem_free_pages(uint64_t paddr, size_t count);
|
|
|
|
/**
|
|
* Map physical memory into virtual address space.
|
|
*
|
|
* Parameters:
|
|
* - vaddr: Virtual address to map (must be page-aligned)
|
|
* - paddr: Physical address to map (must be page-aligned)
|
|
* - size: Size in bytes (must be page-multiple)
|
|
* - flags: Mapping flags (HAL_MEM_*)
|
|
*
|
|
* Returns:
|
|
* - 0 on success
|
|
* - -1 if mapping failed
|
|
*
|
|
* Flags:
|
|
* - HAL_MEM_READ: Readable
|
|
* - HAL_MEM_WRITE: Writable
|
|
* - HAL_MEM_EXEC: Executable
|
|
* - HAL_MEM_NOCACHE: Uncached (for MMIO)
|
|
*
|
|
* Notes:
|
|
* - On Linux: no-op (identity mapping assumed)
|
|
* - On kernel: update page tables, flush TLB
|
|
*/
|
|
int hal_mem_map(uint64_t vaddr, uint64_t paddr, size_t size, unsigned int flags);
|
|
|
|
/* Mapping flags */
|
|
#define HAL_MEM_READ (1 << 0)
|
|
#define HAL_MEM_WRITE (1 << 1)
|
|
#define HAL_MEM_EXEC (1 << 2)
|
|
#define HAL_MEM_NOCACHE (1 << 3)
|
|
|
|
/**
|
|
* Get page size in bytes.
|
|
*
|
|
* Returns:
|
|
* - Page size (typically 4096 on x86_64)
|
|
*/
|
|
size_t hal_mem_page_size(void);
|
|
|
|
#endif /* HAL_MEMORY_H */
|
|
```
|
|
|
|
---
|
|
|
|
## 4. Console (`include/hal/hal_console.h`)
|
|
|
|
### Purpose
|
|
Character I/O for REPL and diagnostics.
|
|
|
|
### Interface
|
|
|
|
```c
|
|
#ifndef HAL_CONSOLE_H
|
|
#define HAL_CONSOLE_H
|
|
|
|
/**
|
|
* Initialize console subsystem.
|
|
* Must be called before any other hal_console_* functions.
|
|
*
|
|
* Responsibilities:
|
|
* - Initialize UART (kernel platforms)
|
|
* - Set up framebuffer (if available)
|
|
* - Configure terminal settings (Linux)
|
|
*
|
|
* Error handling:
|
|
* - hal_panic() if no console available
|
|
*/
|
|
void hal_console_init(void);
|
|
|
|
/**
|
|
* Write a single character to console.
|
|
*
|
|
* Parameters:
|
|
* - c: Character to write
|
|
*
|
|
* Guarantees:
|
|
* - Character will be visible on console
|
|
* - Blocking (waits if output buffer full)
|
|
* - Callable from interrupt context (for panic messages)
|
|
*
|
|
* Performance:
|
|
* - May be slow (UART is ~1µs per char)
|
|
* - Buffering recommended for bulk output
|
|
*/
|
|
void hal_console_putc(char c);
|
|
|
|
/**
|
|
* Write a null-terminated string to console.
|
|
*
|
|
* Parameters:
|
|
* - s: String to write (NULL = no-op)
|
|
*
|
|
* Notes:
|
|
* - Convenience wrapper around hal_console_putc()
|
|
*/
|
|
void hal_console_puts(const char *s);
|
|
|
|
/**
|
|
* Read a single character from console.
|
|
*
|
|
* Guarantees:
|
|
* - Blocking (waits until character available)
|
|
* - NOT callable from interrupt context
|
|
*
|
|
* Returns:
|
|
* - Character read (0-255)
|
|
* - -1 on error or EOF
|
|
*/
|
|
int hal_console_getc(void);
|
|
|
|
/**
|
|
* Check if input is available (non-blocking).
|
|
*
|
|
* Returns:
|
|
* - 1 if character available (hal_console_getc() will not block)
|
|
* - 0 if no character available
|
|
*/
|
|
int hal_console_has_input(void);
|
|
|
|
#endif /* HAL_CONSOLE_H */
|
|
```
|
|
|
|
---
|
|
|
|
## 5. CPU (`include/hal/hal_cpu.h`)
|
|
|
|
### Purpose
|
|
CPU identification, relax/halt, SMP coordination.
|
|
|
|
### Interface
|
|
|
|
```c
|
|
#ifndef HAL_CPU_H
|
|
#define HAL_CPU_H
|
|
|
|
#include <stdint.h>
|
|
|
|
/**
|
|
* Initialize CPU subsystem.
|
|
* Must be called before any other hal_cpu_* functions.
|
|
*
|
|
* Responsibilities:
|
|
* - Detect CPU features (SSE, AVX, etc.)
|
|
* - Set up per-CPU storage
|
|
* - Bring up secondary CPUs (SMP)
|
|
*
|
|
* Error handling:
|
|
* - hal_panic() if CPU unsupported
|
|
*/
|
|
void hal_cpu_init(void);
|
|
|
|
/**
|
|
* Get current CPU ID.
|
|
*
|
|
* Returns:
|
|
* - CPU ID (0 = boot processor, 1+ = application processors)
|
|
*
|
|
* Guarantees:
|
|
* - Callable from interrupt context
|
|
* - Fast (< 10 cycles)
|
|
*
|
|
* Notes:
|
|
* - On x86_64 kernel: APIC ID
|
|
* - On Linux: thread ID (not true CPU ID)
|
|
*/
|
|
unsigned int hal_cpu_id(void);
|
|
|
|
/**
|
|
* Hint to CPU to relax (pause in spin-wait loop).
|
|
*
|
|
* Guarantees:
|
|
* - Callable from interrupt context
|
|
* - No functional effect (pure performance hint)
|
|
*
|
|
* Notes:
|
|
* - On x86_64: pause instruction
|
|
* - On ARM: yield instruction
|
|
* - On Linux: sched_yield()
|
|
*/
|
|
void hal_cpu_relax(void);
|
|
|
|
/**
|
|
* Halt CPU until next interrupt.
|
|
*
|
|
* Guarantees:
|
|
* - CPU enters low-power state
|
|
* - Wakes on next interrupt
|
|
* - NOT callable from interrupt context
|
|
*
|
|
* Notes:
|
|
* - On x86_64 kernel: hlt instruction
|
|
* - On Linux: select() or nanosleep()
|
|
*/
|
|
void hal_cpu_halt(void);
|
|
|
|
/**
|
|
* Get number of CPUs in system.
|
|
*
|
|
* Returns:
|
|
* - Number of CPUs (1 = single-core, 2+ = multi-core)
|
|
*/
|
|
unsigned int hal_cpu_count(void);
|
|
|
|
#endif /* HAL_CPU_H */
|
|
```
|
|
|
|
---
|
|
|
|
## 6. Panic/Error Handling (`include/hal/hal_panic.h`)
|
|
|
|
### Purpose
|
|
Fatal error handling (system halt or abort).
|
|
|
|
### Interface
|
|
|
|
```c
|
|
#ifndef HAL_PANIC_H
|
|
#define HAL_PANIC_H
|
|
|
|
/**
|
|
* Fatal error: print message and halt system.
|
|
*
|
|
* Parameters:
|
|
* - msg: Error message (NULL = "panic")
|
|
*
|
|
* Guarantees:
|
|
* - NEVER returns
|
|
* - Message printed to console (if available)
|
|
* - System halted (kernel) or abort() (hosted)
|
|
* - Callable from interrupt context
|
|
*
|
|
* Notes:
|
|
* - Use for unrecoverable errors only
|
|
* - On kernel: disable interrupts + hlt loop
|
|
* - On Linux: fprintf(stderr) + abort()
|
|
*/
|
|
void hal_panic(const char *msg) __attribute__((noreturn));
|
|
|
|
#endif /* HAL_PANIC_H */
|
|
```
|
|
|
|
---
|
|
|
|
## Interface Summary
|
|
|
|
| Subsystem | Key Functions | ISR-Safe | Thread-Safe |
|
|
|-----------|---------------|----------|-------------|
|
|
| **Time** | `hal_time_now_ns()` | ✅ | ✅ |
|
|
| | `hal_timer_periodic()` | ❌ | ✅ |
|
|
| **Interrupt** | `hal_in_interrupt_context()` | ✅ | ✅ |
|
|
| | `hal_irq_disable()` | ✅ | ✅ |
|
|
| **Memory** | `hal_mem_alloc()` | ❌ | ✅ |
|
|
| | `hal_mem_map()` | ❌ | ⚠️ |
|
|
| **Console** | `hal_console_putc()` | ✅ | ⚠️ |
|
|
| | `hal_console_getc()` | ❌ | ❌ |
|
|
| **CPU** | `hal_cpu_id()` | ✅ | ✅ |
|
|
| | `hal_cpu_relax()` | ✅ | ✅ |
|
|
|
|
**Legend:**
|
|
- ✅ = Safe
|
|
- ❌ = Unsafe
|
|
- ⚠️ = Platform-dependent
|
|
|
|
---
|
|
|
|
## Next Steps
|
|
|
|
See companion documentation:
|
|
- `platform-implementations.md` - How to implement HAL for a platform
|
|
- `migration-plan.md` - Refactoring existing code to use HAL
|
|
- `starkernel-integration.md` - StarKernel-specific HAL implementation |