feature: add mkdocs-material documentation site with CI deployment

Generate comprehensive documentation for all 173 source units and
integrate mkdocs-material into the build toolchain. Documentation
covers kernel core, x86 architecture, drivers, applications, and
all subsystems with a tabbed navigation structure.

- Add mkdocs.yml with material theme, mermaid support, and tabbed nav
- Add doc/index.md landing page
- Generate doc/src/ markdown for every Pascal unit in src/
- Reorganize planning docs into doc/planning/
- Add compat, lvglh, and toolchain doc sections
- Update Dockerfile to install python3 and mkdocs-material (pinned <2)
- Replace pasdoc-based compile_docs.sh with mkdocs build --strict
- Add compile_docs.sh to the main build pipeline in compile.sh
- Add deploy-docs step in .drone.yml with host volume mount to nginx
- Add site/.gitkeep for build output directory
This commit is contained in:
t3hn3rd committed 2026-03-08 21:06:14 +00:00
1 parent 7157a57513
commit 26e2fd947e
209 files changed
+16996 -13

No files matched your search

+95
View File
@@ -0,0 +1,95 @@
# core.panic
Architecture-agnostic kernel panic (BSOD) engine.
## Overview
`core.panic` implements a graphical and serial kernel panic handler for the Asuro kernel. When a fatal condition is detected anywhere in the kernel, `panic` is called with a fault identifier, a human-readable description, and an optional CPU register snapshot. The unit outputs the fault information to the serial syslog for headless debugging and, if LVGL has been initialised, displays a graphical Blue Screen of Death (BSOD).
The BSOD screen and all its LVGL widgets are pre-allocated at `init` time so that no dynamic LVGL allocation is needed when a panic fires. At panic time only label text is updated via `lv_label_set_text`, the pre-built screen is loaded, and a single render pass is forced. Text formatting uses static heap buffers and avoids calling any string library routines that might themselves fault.
Architecture-specific code is responsible for registering a CPU halt routine with `registerHaltProc` before any panic can occur. If no halt procedure is registered, the default fallback loops forever.
If `init` has not been called before a panic (early boot panic), the unit gracefully falls back to syslog-only output.
## Dependencies
- `io.syslog` — serial fault output
- `debug.tracer` — call-stack capture and freeze
- `driver.video` — frame buffer flush
- `memory.heap` — buffer allocation
- `driver.video.lvgl` — LVGL widget creation and rendering
- `core.version` — version constants for the system info panel
- `proc.mgr` — current process information
- `proc.types` — process state enumeration
- `core.fmt.targa` — teapot TGA image decoding
- `core.gfx.texture` — pixel buffer type
## Constants
### MAX_REGISTER_ENTRIES
Maximum number of register name/value pairs an architecture can supply in a `TRegisterSnapshot`. Value: `32`.
### PANIC_TEXT_BUF_SIZE
Size in bytes of the pre-allocated text buffers used to format register, trace, process, and system information. Value: `2048`.
## Types
### TRegisterEntry
```pascal
TRegisterEntry = record
Name : pchar;
Value : uint32;
end;
```
A single name/value pair representing one CPU register. `Name` must be a static string literal or a pointer that remains valid for the kernel lifetime.
### TRegisterSnapshot / PRegisterSnapshot
```pascal
TRegisterSnapshot = record
Count : uint32;
Entries : array[0..MAX_REGISTER_ENTRIES-1] of TRegisterEntry;
end;
```
A snapshot of CPU register state at the time of a fault. `Count` specifies how many entries in `Entries` are valid.
### THaltProc
```pascal
THaltProc = procedure;
```
Procedure type for the architecture-specific CPU halt routine.
## Functions and Procedures
### init
```pascal
procedure init;
```
Creates the hidden BSOD LVGL screen and pre-allocates all widget objects and text buffers. Must be called once after LVGL has been initialised. Subsequent calls to `panic` will display the graphical BSOD only if `init` has been called first.
### panic
```pascal
procedure panic(fault : pchar; info : pchar; regs : PRegisterSnapshot);
```
Triggers a kernel panic. Freezes the call-stack tracer, dumps fault information to syslog, and (if the BSOD screen is ready) displays the graphical panic screen. Then calls the registered halt procedure. Re-entrant calls are detected by a guard flag; if `panic` is called while a panic is already in progress, the system halts immediately without further output.
Parameters:
- `fault` — short fault identifier string, e.g. `'arch.x86.fault.gpf'`.
- `info` — human-readable description of the fault.
- `regs` — pointer to a `TRegisterSnapshot`, or `nil` if register state is unavailable.
### registerHaltProc
```pascal
procedure registerHaltProc(proc : THaltProc);
```
Registers the architecture-specific halt procedure. Must be called before any panic can occur. If not called, a fallback infinite loop is used.
## Notes
The BSOD layout consists of a top banner (teapot TGA image beside title text) and a two-column content area. The left column contains Fault Details, CPU Registers, Process Info, and System Info cards. The right column contains the full-height Call Stack card.
The teapot image is loaded from a TGA binary linked into the kernel image via an assembly `incbin` stub (`_panic_tga_start` / `_panic_tga_size`). The image is decoded once at `init` time and stored in a pre-built LVGL image descriptor.
All text formatting in the panic path uses a set of internal buffer-writing helpers (`writeHexToBuffer`, `writeStrToBuffer`, `writeIntToBuffer`) that do not call the kernel string library, making the panic path robust against faults in those subsystems.
A compile-time switch `BSOD_ENABLE` gates the display path; if disabled, `panic` only writes to syslog and halts.
+45
View File
@@ -0,0 +1,45 @@
# core.rand
Pseudo-random number generator for the kernel.
## Overview
`core.rand` implements a linear congruential generator (LCG) using the classic glibc constants (multiplier 1103515245, increment 12345) to produce pseudo-random values of 8, 16, and 32-bit widths. A single global state variable is maintained. The unit is intended for non-cryptographic use cases such as randomised data placement, simple simulations, or test data generation.
## Dependencies
None.
## Functions and Procedures
### rand32
```pascal
function rand32 : uint32;
```
Returns a 32-bit pseudo-random value formed by combining two successive 15-bit LCG outputs in the high and low 16-bit halves.
### rand16
```pascal
function rand16 : uint16;
```
Returns a 16-bit pseudo-random value (low 16 bits of a `rand32` call).
### rand8
```pascal
function rand8 : uint8;
```
Returns an 8-bit pseudo-random value (low 8 bits of a `rand32` call).
### srand
```pascal
procedure srand(seed : uint32);
```
Seeds the generator by adding `seed` to the current internal state. The seed is added rather than assigned, so successive calls accumulate entropy rather than resetting the sequence to a fixed point.
## Notes
The generator is not cryptographically secure and must not be used for security-sensitive purposes such as key generation or nonce selection.
The internal `rand` function returns values in the range 0–32767 (15 bits), following the classic C `rand()` output convention. `rand32` combines two calls to produce a 32-bit value.
Because `srand` adds to the existing state, the output sequence cannot be exactly reproduced by setting a known seed after the generator has been called. Seed before first use for reproducible sequences.
+131
View File
@@ -0,0 +1,131 @@
# core.strings
Null-terminated string manipulation library for the kernel.
## Overview
`core.strings` provides a comprehensive set of routines for working with null-terminated (`pchar`) strings in a bare-metal environment. Because the kernel cannot use the Free Pascal runtime library string support, all allocation is performed through the kernel heap (`kalloc`/`kfree`) and all operations work on raw pointer-based C-style strings. The unit covers string creation, copying, comparison, searching, case conversion, concatenation, substring extraction, replacement, and conversion to and from integer types. A built-in `UnitTest` procedure exercises the full API and reports results via syslog.
## Dependencies
- `core.util` — `memcpy`, `memset`, `HexCharToDecimal`
- `arch.x86.util` — architecture-level utilities
- `memory.heap` — `kalloc`, `kfree`
- `core.ds.lists` — transitively required
- `io.syslog` — test output (implementation section only)
## Functions and Procedures
### stringNew
```pascal
function stringNew(size : uint32) : pchar;
```
Allocates a new zero-initialised string buffer of `size` bytes plus a null terminator. Returns a pointer to the buffer.
### stringCopy
```pascal
function stringCopy(str : pchar) : pchar;
```
Allocates and returns a heap copy of `str`.
### stringSize
```pascal
function stringSize(str : pchar) : uint32;
```
Returns the length of `str` in characters, excluding the null terminator. Returns 0 for `nil`.
### stringEquals
```pascal
function stringEquals(str1, str2 : pchar) : boolean;
```
Returns `true` if `str1` and `str2` have identical length and content.
### stringToUpper
```pascal
function stringToUpper(str : pchar) : pchar;
```
Returns a heap-allocated copy of `str` with all lowercase ASCII letters converted to uppercase.
### stringToLower
```pascal
function stringToLower(str : pchar) : pchar;
```
Returns a heap-allocated copy of `str` with all uppercase ASCII letters converted to lowercase.
### stringConcat
```pascal
function stringConcat(str1, str2 : pchar) : pchar;
```
Returns a heap-allocated string containing `str1` followed by `str2`.
### stringTrim
```pascal
function stringTrim(str : pchar; length : uint32) : pchar;
```
Returns a heap-allocated copy of `str` truncated to at most `length` characters. If `length` exceeds the string length, the full string is copied.
### stringSub
```pascal
function stringSub(str : pchar; start, size : uint32) : pchar;
```
Returns a heap-allocated substring of `str` beginning at byte offset `start` with at most `size` characters. Returns an empty string if `start` is past the end. If `start + size` exceeds the string length, the result is clamped to the end.
### stringMatchAt
```pascal
function stringMatchAt(str : pchar; pos : uint32; find : pchar) : boolean;
```
Returns `true` if `find` matches the characters in `str` starting at position `pos`. An empty `find` always returns `true`.
### stringIndexOf
```pascal
function stringIndexOf(str, find : pchar) : sint32;
```
Returns the zero-based index of the first occurrence of `find` within `str`, or `-1` if not found. An empty `find` returns `0`.
### stringContains
```pascal
function stringContains(str : pchar; sub : pchar) : boolean;
```
Returns `true` if `sub` appears anywhere within `str`.
### stringReplace
```pascal
function stringReplace(str, find, replace : pchar) : pchar;
```
Returns a heap-allocated copy of `str` with the first occurrence of `find` replaced by `replace`. If `find` is not present, a copy of `str` is returned unchanged.
### stringToInt
```pascal
function stringToInt(str : pchar) : uint32;
```
Parses a decimal integer string and returns its `uint32` value. Non-digit characters are ignored.
### intToString
```pascal
function intToString(i : uint32) : pchar;
```
Returns a heap-allocated decimal string representation of `i`.
### hexStringToInt
```pascal
function hexStringToInt(str : pchar) : uint32;
```
Parses a hexadecimal string (no `0x` prefix) and returns its `uint32` value.
### boolToString
```pascal
function boolToString(b : boolean; ext : boolean) : pchar;
```
Returns a heap-allocated string for the boolean `b`. When `ext` is `true`, returns `'true'` or `'false'`; when `false`, returns `'1'` or `'0'`.
### UnitTest
```pascal
procedure UnitTest;
```
Runs the complete string function test suite and logs a pass/fail summary to syslog under the `'STRINGS'` channel.
## Notes
All functions returning `pchar` return newly heap-allocated strings. Callers are responsible for freeing the result with `kfree` when it is no longer needed.
`stringReplace` replaces only the first occurrence of `find`. There is no bulk-replace variant.
+11
View File
@@ -0,0 +1,11 @@
# core.types
Dummy compatibility unit providing a named home for the `core.types` identifier.
## Overview
`core.types` is an intentionally empty unit whose sole purpose is to satisfy the Free Pascal unit dependency resolver when a virtual machine build environment requires a unit named `core.types` to be present. It contains no type definitions, constants, or routines. Actual shared type definitions used by Asuro modules are declared in the units that own them, or in `core.ds.types` for data structure types.
## Notes
This unit should not be used as a dependency in new code. It exists purely for VM build-system compatibility and exports no symbols.
+91
View File
@@ -0,0 +1,91 @@
# core.util
Portable data manipulation utilities with no architecture-specific dependencies.
## Overview
`core.util` provides low-level helpers that operate on raw integers and memory without relying on any x86 assembly. It covers byte and nibble extraction, endian byte-order swapping, flat memory operations (`memset`/`memcpy`), BCD-to-integer conversion, hex character parsing, and a branchless absolute value. These primitives are used throughout the kernel wherever portable, assembly-free data manipulation is required.
## Dependencies
None.
## Functions and Procedures
### hi
```pascal
function hi(b : uint8) : uint8;
```
Returns the high nibble (bits 7–4) of a byte, shifted into the low four bits of the result. Exported with the alias `util_hi`.
### lo
```pascal
function lo(b : uint8) : uint8;
```
Returns the low nibble (bits 3–0) of a byte. Exported with the alias `util_lo`.
### switchendian
```pascal
function switchendian(b : uint8) : uint8;
```
Swaps the two nibbles of a byte (equivalent to a 4-bit rotate). Exported with the alias `util_switchendian`.
### switchendian16
```pascal
function switchendian16(b : uint16) : uint16;
```
Reverses the byte order of a 16-bit value, converting between big-endian and little-endian representations.
### switchendian32
```pascal
function switchendian32(b : uint32) : uint32;
```
Reverses the byte order of a 32-bit value for endian conversion.
### getWord
```pascal
function getWord(i : uint32; hi : boolean) : uint16;
```
Extracts the high or low 16-bit word from a 32-bit value. Returns bits 31–16 when `hi` is `true`; bits 15–0 otherwise.
### getByte
```pascal
function getByte(i : uint32; index : uint8) : uint8;
```
Extracts a single byte from a 32-bit value by zero-based byte index (0 = least significant byte).
### memset
```pascal
procedure memset(location : uint32; value : uint8; size : uint32);
```
Fills `size` bytes starting at address `location` with the byte `value`. Does nothing if `size` is zero.
### memcpy
```pascal
procedure memcpy(source : uint32; dest : uint32; size : uint32);
```
Copies `size` bytes from address `source` to address `dest` byte by byte. Behaviour is undefined if the regions overlap.
### BCDToUint8
```pascal
function BCDToUint8(bcd : uint8) : uint8;
```
Converts a Binary-Coded Decimal byte to its unsigned integer equivalent. The high nibble is the tens digit; the low nibble is the units digit.
### HexCharToDecimal
```pascal
function HexCharToDecimal(hex : char) : uint8;
```
Converts a single hexadecimal character (`0`–`9`, `a`–`f`, `A`–`F`) to its decimal value 0–15. Returns 0 for unrecognised characters.
### abs
```pascal
function abs(x : sint32) : uint32;
```
Returns the absolute value of a signed 32-bit integer using a branchless arithmetic technique based on sign-extension, XOR, and subtraction. The result type is `uint32`.
## Notes
`memcpy` is a simple byte loop and does not handle overlapping source and destination regions correctly. Callers must ensure regions do not overlap, or copy in the appropriate direction manually.
The `hi`, `lo`, and `switchendian` functions carry stable C-compatible export aliases (`util_hi`, `util_lo`, `util_switchendian`) for use from assembly or interop stubs.
+62
View File
@@ -0,0 +1,62 @@
# core.version
Auto-generated kernel version and build metadata constants.
## Overview
`core.version` is a generated unit updated by the build system on every compilation. It provides string and integer constants describing the current kernel version, build toolchain versions, source statistics, and the build timestamp. Other units reference these constants for display in boot messages, the kernel panic screen, and any context where version identification is required.
## Dependencies
None.
## Constants
### VERSION
Full dotted version string with release label: `'1.1.3-alpha-176-g63b67f58'`.
### VERSION_MAJOR
Major version component string: `'1'`.
### VERSION_MINOR
Minor version component string: `'1'`.
### VERSION_SUB
Sub-version (patch) component string: `'3'`.
### REVISION
Short Git commit hash of HEAD at compile time: `'63b67f58'`.
### RELEASE
Git-describe release tag including commit distance and hash: `'alpha-176-g63b67f58'`.
### LINE_COUNT
Total source lines counted at compile time: `99538`.
### FILE_COUNT
Total source files counted at compile time: `175`.
### DRIVER_COUNT
Number of driver units counted at compile time: `69`.
### FPC_VERSION
Free Pascal Compiler version used to build the kernel: `'3.2.2'`.
### NASM_VERSION
NASM assembler version used to assemble architecture-specific stubs: `'2.16.01'`.
### MAKE_VERSION
GNU Make version used to drive the build: `'4.3'`.
### COMPILE_DATE
Compilation date in MM/DD/YY format: `'08/03/26'`.
### COMPILE_TIME
Compilation time in HH:MM:SS format: `'17:23:28'`.
### CHECKSUM
MD5 checksum of the compiled kernel image computed by the build system: `'c30f33c48e462403420808146b9075e1'`.
## Notes
This file is regenerated on every build. Manual edits will be overwritten. The unit has no implementation section.
+59
View File
@@ -0,0 +1,59 @@
# core.ds.bheap
Shared binary heap engine for min-heap, max-heap, and priority queue implementations.
## Overview
`core.ds.bheap` provides the core binary heap machinery used by `core.ds.minh`, `core.ds.maxh`, and `core.ds.prio`. It stores element data inline in a flat buffer with index-array indirection: a separate `Indices` array maps heap positions to data slot indices, so swaps during sift-up and sift-down exchange only 32-bit indices rather than copying full element data. Freed data slots are recycled via a free-slot stack, avoiding fragmentation. The buffer grows automatically by doubling when capacity is exhausted.
The heap can operate in either min-heap mode (root holds the lowest priority value) or max-heap mode (root holds the highest priority value), controlled by the `IsMinHeap` field set at creation time.
This unit is not intended to be used directly. Use the typed wrappers `core.ds.minh`, `core.ds.maxh`, or `core.ds.prio` instead.
## Dependencies
- `core.ds.types` — `TBinaryHeap`, `PBinaryHeap`
- `memory.heap` — `kalloc`, `kfree`
- `core.util` — `memcpy`, `memset`
- `arch.x86.util` — architecture utilities
## Functions and Procedures
### BHeap_New
```pascal
function BHeap_New(ElementSize : uint32; InitialCapacity : uint32;
MinHeap : boolean) : PBinaryHeap;
```
Allocates and initialises a new binary heap. `ElementSize` is the size in bytes of each data element (not including the priority field). `InitialCapacity` is the starting number of slots. `MinHeap` selects ordering: `true` for min-heap, `false` for max-heap.
### BHeap_Insert
```pascal
procedure BHeap_Insert(Heap : PBinaryHeap; Priority : uint32; Data : void);
```
Inserts a new element with the given `Priority`. The element data pointed to by `Data` is copied into the heap's internal buffer. Grows the heap automatically if capacity is exhausted.
### BHeap_ExtractRoot
```pascal
function BHeap_ExtractRoot(Heap : PBinaryHeap; OutData : void) : boolean;
```
Removes and copies the root element's data into `OutData`. The root's data slot is returned to the free-slot stack. Returns `true` if an element was extracted; `false` if the heap was empty.
### BHeap_PeekRoot
```pascal
function BHeap_PeekRoot(Heap : PBinaryHeap) : void;
```
Returns a direct pointer to the root element's data without removing it. Returns `nil` if the heap is empty. The pointer is invalidated by any subsequent insertion or extraction.
### BHeap_Free
```pascal
procedure BHeap_Free(Heap : PBinaryHeap);
```
Frees all three internal buffers (`Data`, `Indices`, `FreeSlots`) and the heap structure itself.
## Notes
The data slot layout is: `[uint32 priority][ElementSize bytes of element data]`. The `NodeStride` field equals `sizeof(uint32) + ElementSize`.
Swaps during sift-up and sift-down exchange entries in the `Indices` array only, so the cost of a swap is always O(1) regardless of element size.
When the heap is full, `BHeap_Grow` doubles all three buffers and copies existing data. This is an O(n) operation.
+65
View File
@@ -0,0 +1,65 @@
# core.ds.bloom
Probabilistic set-membership filter using double hashing.
## Overview
`core.ds.bloom` implements a Bloom filter — a space-efficient probabilistic data structure for testing whether an element is a member of a set. Insertions and membership tests run in O(k) time where k is the number of hash functions. Double hashing is used to derive k independent bit positions from two base hash functions (FNV-1a 32-bit and DJB2 32-bit), avoiding the need to store or compute k separate functions.
False positives are possible at a rate determined by the filter size and the number of hash functions. False negatives are not possible: if `Bloom_Test` returns `false`, the element was definitely not inserted.
## Dependencies
- `core.ds.types` — `TBloomFilter`, `PBloomFilter`
- `memory.heap` — `kalloc`, `kfree`
- `core.util` — `memset`
- `core.enc.fnv1a` — `Hash_FNV1a32`
- `core.enc.djb2` — `Hash_DJB2_32`
- `io.syslog` — test output
- `core.strings` — test output formatting
## Functions and Procedures
### Bloom_New
```pascal
function Bloom_New(BitCount : uint32; HashCount : uint32) : PBloomFilter;
```
Creates a new Bloom filter with `BitCount` bits and `HashCount` hash functions per element. The bit buffer is zero-initialised. Returns `nil` on allocation failure.
A common sizing guideline: `m = -n * ln(p) / (ln(2)^2)` for `n` expected elements and target false-positive rate `p`. Optimal `k = (m/n) * ln(2)`.
### Bloom_Add
```pascal
procedure Bloom_Add(Filter : PBloomFilter; Data : void; DataLen : uint32);
```
Inserts `DataLen` bytes pointed to by `Data` into the filter by setting the k bit positions derived from double hashing. Increments `Filter^.Count`.
### Bloom_Test
```pascal
function Bloom_Test(Filter : PBloomFilter; Data : void; DataLen : uint32) : boolean;
```
Tests whether `Data` (of `DataLen` bytes) was probably inserted. Returns `true` if all k bit positions are set, `false` if any bit is clear (definite non-member).
### Bloom_Clear
```pascal
procedure Bloom_Clear(Filter : PBloomFilter);
```
Resets all bits to zero and sets `Count` to zero without freeing the filter structure or bit buffer.
### Bloom_Free
```pascal
procedure Bloom_Free(Filter : PBloomFilter);
```
Frees the bit buffer and the filter structure. After this call the pointer is invalid.
### UnitTest
```pascal
procedure UnitTest;
```
Runs the Bloom filter test suite and logs a pass/fail summary to syslog under the `'BLOOM'` channel.
## Notes
The second hash `h2` is forced to be odd (`h2 := h2 or 1`) before use. This guarantees full period coverage of the bit array when stepping by `h2`, because an odd step and a power-of-two (or arbitrary) modulus are coprime.
`Bloom_Free` does not check for `nil` on the bit buffer pointer; callers should not call it on a partially initialised filter.
+78
View File
@@ -0,0 +1,78 @@
# core.ds.cfifo
Array-backed contiguous FIFO queue with lazy compaction and automatic growth.
## Overview
`core.ds.cfifo` implements a First-In First-Out queue that stores elements in a flat contiguous buffer rather than a linked list. This avoids per-element heap allocation overhead and improves cache locality. The buffer doubles in size when it becomes full. A lazy compaction strategy is used: instead of shifting elements on every dequeue, the `Head` index is simply advanced. When `Head` passes half the capacity, all remaining elements are shifted back to index 0 in a single compaction pass.
## Dependencies
- `core.ds.types` — `TCFIFOQueue`, `PCFIFOQueue`
- `memory.heap` — `kalloc`, `kfree`
- `core.util` — `memcpy`, `memset`
- `arch.x86.util` — architecture utilities
- `io.syslog` — test output (implementation only)
- `core.strings` — test output formatting (implementation only)
## Functions and Procedures
### CFIFO_New
```pascal
function CFIFO_New(ElementSize : uint32; InitialCapacity : uint32) : PCFIFOQueue;
```
Creates a new contiguous FIFO queue. `ElementSize` is the size in bytes of each element. `InitialCapacity` is the starting number of element slots; the buffer grows automatically as needed.
### CFIFO_Enqueue
```pascal
procedure CFIFO_Enqueue(Queue : PCFIFOQueue; Data : void);
```
Copies `ElementSize` bytes from `Data` into the back of the queue. Grows the buffer if all slots are consumed. Triggers a compaction pass if there is no room at the tail despite available slots (due to head advancement).
### CFIFO_Dequeue
```pascal
function CFIFO_Dequeue(Queue : PCFIFOQueue; Data : void) : boolean;
```
Copies the front element into `Data` and advances `Head`. Triggers a lazy compaction when `Head` passes half the capacity. Resets `Head` to 0 when the queue becomes empty. Returns `false` if the queue is empty.
### CFIFO_Peek
```pascal
function CFIFO_Peek(Queue : PCFIFOQueue) : void;
```
Returns a direct pointer to the front element without removing it. Returns `nil` if the queue is empty. The pointer is invalidated by any subsequent enqueue or dequeue that triggers compaction or growth.
### CFIFO_Size
```pascal
function CFIFO_Size(Queue : PCFIFOQueue) : uint32;
```
Returns the number of elements currently in the queue.
### CFIFO_IsEmpty
```pascal
function CFIFO_IsEmpty(Queue : PCFIFOQueue) : boolean;
```
Returns `true` if the queue contains no elements.
### CFIFO_Capacity
```pascal
function CFIFO_Capacity(Queue : PCFIFOQueue) : uint32;
```
Returns the current allocated capacity in number of element slots.
### CFIFO_Free
```pascal
procedure CFIFO_Free(Queue : PCFIFOQueue);
```
Frees the element buffer and the queue structure.
### UnitTest
```pascal
procedure UnitTest;
```
Runs the CFIFO test suite and logs a pass/fail summary to syslog under the `'CFIFO'` channel.
## Notes
Compaction uses `memcpy` to shift elements, which is safe here because the destination is always at a lower address than the source when `Head > 0`.
The buffer capacity never shrinks automatically. Use `CFIFO_Free` and `CFIFO_New` to reclaim memory after draining a large queue.
+79
View File
@@ -0,0 +1,79 @@
# core.ds.cfifols
Dynamic list of contiguous FIFO queue pointers.
## Overview
`core.ds.cfifols` implements a growable ordered list of `PCFIFOQueue` pointers. It is used to group and manage a variable number of related contiguous FIFO queues under a single handle. The list stores only pointer references; the referenced queues are owned and managed by the caller unless `CFIFOLS_FreeAll` is used.
## Dependencies
- `memory.heap` — `kalloc`, `kfree`
- `core.ds.types` — `TCFIFOList`, `PCFIFOList`
- `core.ds.cfifo` — `CFIFO_Free` (used by `CFIFOLS_FreeAll`)
- `core.util` — `memcpy`, `memset`
- `arch.x86.util` — architecture utilities
- `io.syslog` — test output (implementation only)
- `core.strings` — test output formatting (implementation only)
## Functions and Procedures
### CFIFOLS_New
```pascal
function CFIFOLS_New(InitialCapacity : uint32) : PCFIFOList;
```
Creates a new contiguous FIFO list with `InitialCapacity` pointer slots. The slot buffer grows automatically when the capacity is exceeded.
### CFIFOLS_Add
```pascal
procedure CFIFOLS_Add(List : PCFIFOList; Queue : PCFIFOQueue);
```
Appends the queue pointer `Queue` to the end of the list. Grows the slot buffer by doubling if capacity is exhausted.
### CFIFOLS_Get
```pascal
function CFIFOLS_Get(List : PCFIFOList; Index : uint32) : PCFIFOQueue;
```
Returns the queue pointer at zero-based `Index`. Returns `nil` if `Index` is out of range.
### CFIFOLS_Remove
```pascal
function CFIFOLS_Remove(List : PCFIFOList; Index : uint32) : boolean;
```
Removes the pointer at `Index` by shifting subsequent entries left. The referenced queue is not freed; ownership is retained by the caller. Returns `false` if `Index` is out of range.
### CFIFOLS_Count
```pascal
function CFIFOLS_Count(List : PCFIFOList) : uint32;
```
Returns the number of queue pointers currently in the list.
### CFIFOLS_IsEmpty
```pascal
function CFIFOLS_IsEmpty(List : PCFIFOList) : boolean;
```
Returns `true` if the list holds no pointers.
### CFIFOLS_Free
```pascal
procedure CFIFOLS_Free(List : PCFIFOList);
```
Frees the pointer slot buffer and the list structure. Does not free the referenced queues.
### CFIFOLS_FreeAll
```pascal
procedure CFIFOLS_FreeAll(List : PCFIFOList);
```
Calls `CFIFO_Free` on every queue in the list, then frees the slot buffer and the list structure.
### UnitTest
```pascal
procedure UnitTest;
```
Runs the CFIFOLS test suite and logs a pass/fail summary to syslog under the `'CFIFOLS'` channel.
## Notes
`CFIFOLS_Remove` shifts remaining entries using `memcpy`, which is safe because the destination is always at a lower address than the source.
The list does not track queue ownership; callers must decide whether to use `CFIFOLS_Free` (preserving queues) or `CFIFOLS_FreeAll` (destroying queues).
+78
View File
@@ -0,0 +1,78 @@
# core.ds.circ
Fixed-capacity ring-buffer queue.
## Overview
`core.ds.circ` implements a circular (ring-buffer) FIFO queue with a fixed maximum capacity set at creation time. Elements are stored in a flat pre-allocated buffer. Head and tail indices advance with modulo arithmetic to wrap around the buffer, eliminating the need for compaction or shifting. Enqueue is rejected when the buffer is full.
## Dependencies
- `memory.heap` — `kalloc`, `kfree`
- `core.ds.types` — `TCircularQueue`, `PCircularQueue`
- `core.util` — `memcpy`, `memset`
- `arch.x86.util` — architecture utilities
- `io.syslog` — test output (implementation only)
- `core.strings` — test output formatting (implementation only)
## Functions and Procedures
### circ_New
```pascal
function circ_New(Capacity : uint32; ElementSize : uint32) : PCircularQueue;
```
Creates a new circular queue with exactly `Capacity` element slots. `ElementSize` is the size in bytes of each element. The buffer is zero-initialised.
### circ_Enqueue
```pascal
function circ_Enqueue(Queue : PCircularQueue; Data : void) : boolean;
```
Copies `ElementSize` bytes from `Data` into the next free slot and advances the tail index. Returns `false` if the queue is full and the element is rejected.
### circ_Dequeue
```pascal
function circ_Dequeue(Queue : PCircularQueue; Data : void) : boolean;
```
Copies the front element into `Data` and advances the head index. Returns `false` if the queue is empty.
### circ_Peek
```pascal
function circ_Peek(Queue : PCircularQueue) : void;
```
Returns a direct pointer to the front element without removing it. Returns `nil` if the queue is empty.
### circ_Size
```pascal
function circ_Size(Queue : PCircularQueue) : uint32;
```
Returns the number of elements currently in the queue.
### circ_IsFull
```pascal
function circ_IsFull(Queue : PCircularQueue) : boolean;
```
Returns `true` if the queue has reached its maximum capacity.
### circ_IsEmpty
```pascal
function circ_IsEmpty(Queue : PCircularQueue) : boolean;
```
Returns `true` if the queue contains no elements.
### circ_Free
```pascal
procedure circ_Free(Queue : PCircularQueue);
```
Frees the element buffer and the queue structure.
### UnitTest
```pascal
procedure UnitTest;
```
Runs the circular queue test suite and logs a pass/fail summary to syslog under the `'CIRC'` channel.
## Notes
The capacity is fixed at creation. Unlike `core.ds.cfifo`, the circular queue never grows. Callers must choose a capacity sufficient for their maximum concurrent element count.
The pointer returned by `circ_Peek` is invalidated by any subsequent enqueue or dequeue that moves the head index.
+70
View File
@@ -0,0 +1,70 @@
# core.ds.fifo
Linked-list backed First-In First-Out queue.
## Overview
`core.ds.fifo` implements a FIFO queue using a singly-linked list of heap-allocated nodes. Each enqueued element is copied into a new node; each dequeue copies the data out and frees the node. The linked-list design allows unbounded growth with no compaction or shifting, at the cost of one heap allocation per element. For use cases requiring better cache locality and lower allocation overhead, see `core.ds.cfifo`.
## Dependencies
- `memory.heap` — `kalloc`, `kfree`
- `core.util` — `memcpy`
- `arch.x86.util` — architecture utilities
- `core.ds.types` — `TFIFOQueue`, `PFIFOQueue`, `TQueueNode`, `PQueueNode`
- `io.syslog` — test output (implementation only)
- `core.strings` — test output formatting (implementation only)
## Functions and Procedures
### FIFO_New
```pascal
function FIFO_New(ElementSize : uint32) : PFIFOQueue;
```
Creates and returns a new empty FIFO queue. `ElementSize` is the size in bytes of each element.
### FIFO_Enqueue
```pascal
procedure FIFO_Enqueue(Queue : PFIFOQueue; Data : void);
```
Allocates a new node, copies `ElementSize` bytes from `Data` into it, and appends it to the tail of the queue.
### FIFO_Dequeue
```pascal
function FIFO_Dequeue(Queue : PFIFOQueue; Data : void) : boolean;
```
Copies the front element's data into `Data`, removes the head node, and frees it. Returns `false` if the queue is empty.
### FIFO_Peek
```pascal
function FIFO_Peek(Queue : PFIFOQueue) : void;
```
Returns a direct pointer to the front element's data without removing the node. Returns `nil` if the queue is empty. The pointer is invalidated if the head node is dequeued.
### FIFO_Size
```pascal
function FIFO_Size(Queue : PFIFOQueue) : uint32;
```
Returns the number of elements currently in the queue.
### FIFO_IsEmpty
```pascal
function FIFO_IsEmpty(Queue : PFIFOQueue) : boolean;
```
Returns `true` if the queue contains no elements.
### FIFO_Free
```pascal
procedure FIFO_Free(Queue : PFIFOQueue);
```
Frees all nodes and their data buffers, then frees the queue structure.
### UnitTest
```pascal
procedure UnitTest;
```
Runs the FIFO queue test suite and logs a pass/fail summary to syslog under the `'FIFO'` channel.
## Notes
Each enqueue causes two heap allocations (node structure and element data buffer). For high-frequency queuing, prefer `core.ds.cfifo` which batches allocations into a single growing buffer.
+109
View File
@@ -0,0 +1,109 @@
# core.ds.hashmap
String-keyed hash map with chained collision resolution and automatic rehashing.
## Overview
`core.ds.hashmap` provides a general-purpose hash map that maps null-terminated string keys to opaque `void` pointers. Collisions are resolved by chaining (linked lists per bucket). When the load factor threshold is exceeded, the table doubles in size and all existing entries are re-distributed. Key strings are heap-copied on insertion so callers do not need to keep the original key alive.
The hash function used is FNV-1a 32-bit, replacing an earlier MD5-based scheme.
## Dependencies
- `memory.heap` — `kalloc`, `kfree`
- `core.enc.fnv1a` — `Hash_FNV1a32`
- `core.strings` — `stringEquals`, `stringCopy`, `stringSize`
- `io.syslog` — `printMap` debug output
- `debug.tracer` — call-stack tracing
- `core.util` — `memcpy`
- `arch.x86.util` — architecture utilities
## Constants
### HASHMAP_DEFAULT_SIZE
Default initial bucket count: `16`.
### HASHMAP_DEFAULT_LOADFACTOR
Default load factor threshold for rehashing: `0.75`.
## Types
### THashItem / PHashItem / DPHashItem
```pascal
THashItem = record
Next : PHashItem;
Key : pchar;
Hash : uint32;
Data : void;
end;
```
A single hash map entry. `Next` links to the next entry in the same bucket (collision chain). `Key` is a heap-allocated copy of the key string. `Hash` caches the computed key hash. `Data` is the caller-supplied value pointer.
### THashMap / PHashMap
```pascal
THashMap = record
Size : uint32;
LoadFactor : Single;
Count : uint32;
Table : DPHashItem;
end;
```
The map header. `Size` is the current bucket count. `Table` is the bucket array (an array of `PHashItem` pointers). `Count` tracks the total number of entries across all buckets.
### THashForEachCb
```pascal
THashForEachCb = procedure(key: pchar; data: void; ud: void);
```
Callback type for the `forEach` iterator. `key` is the entry's key string, `data` is the stored value, and `ud` is the caller-supplied user data pointer passed to `forEach`.
## Functions and Procedures
### new
```pascal
function new : PHashMap;
```
Creates a new hash map with `HASHMAP_DEFAULT_SIZE` buckets and `HASHMAP_DEFAULT_LOADFACTOR`.
### newEx
```pascal
function newEx(size : uint32; loadFactor : Single) : PHashMap;
```
Creates a new hash map with the specified initial bucket count and load factor.
### add
```pascal
procedure add(map : PHashMap; key : pchar; value : void);
```
Inserts or updates an entry for `key` with value `value`. If the key already exists, its value is replaced. The key string is heap-copied. Triggers a rehash if the load factor is exceeded after insertion.
### get
```pascal
function get(map : PHashMap; key : pchar) : void;
```
Returns the value associated with `key`, or `nil` if not found.
### delete
```pascal
procedure delete(map : PHashMap; key : pchar; freeItem : boolean);
```
Removes the entry for `key`. The key string's heap copy is always freed. If `freeItem` is `true`, the stored `Data` pointer is also freed with `kfree`.
### forEach
```pascal
procedure forEach(map : PHashMap; cb : THashForEachCb; ud : void);
```
Iterates over all entries in the map (in unspecified bucket order) and calls `cb` for each one. `ud` is passed through to the callback unchanged.
### printMap
```pascal
procedure printMap(map : PHashMap);
```
Writes a debug representation of all buckets and their collision chains to syslog. Intended for development use only.
## Notes
The `add` procedure increments `Count` on every call, including for key updates (overwrites). This means `Count` may overcount if the same key is added multiple times. Callers should use `get` to check for an existing key before calling `add` if accurate counting matters.
Rehashing allocates a new bucket array and re-inserts all existing items without copying their key or data — only the item pointers are moved. The old bucket array is freed.
There is no `free` procedure exported for the map. Callers managing map lifetime should iterate with `forEach` to free values, then call `kfree` on the table and the map structure directly, or arrange for the heap to be torn down wholesale.
+70
View File
@@ -0,0 +1,70 @@
# core.ds.lifo
Linked-list backed Last-In First-Out stack.
## Overview
`core.ds.lifo` implements a LIFO stack using a singly-linked list of heap-allocated nodes. Each pushed element is copied into a new node prepended to the head of the list. Each pop copies the data out and frees the top node. The linked-list design allows unbounded growth with no pre-allocation, at the cost of one heap allocation per element.
## Dependencies
- `memory.heap` — `kalloc`, `kfree`
- `core.util` — `memcpy`
- `arch.x86.util` — architecture utilities
- `core.ds.types` — `TLIFOStack`, `PLIFOStack`, `TQueueNode`, `PQueueNode`
- `io.syslog` — test output (implementation only)
- `core.strings` — test output formatting (implementation only)
## Functions and Procedures
### lifo_New
```pascal
function lifo_New(ElementSize : uint32) : PLIFOStack;
```
Creates and returns a new empty LIFO stack. `ElementSize` is the size in bytes of each element.
### lifo_Push
```pascal
procedure lifo_Push(Stack : PLIFOStack; Data : void);
```
Allocates a new node, copies `ElementSize` bytes from `Data` into it, and prepends the node to the top of the stack.
### lifo_Pop
```pascal
function lifo_Pop(Stack : PLIFOStack; Data : void) : boolean;
```
Copies the top element's data into `Data`, removes the top node, and frees it. Returns `false` if the stack is empty.
### lifo_Peek
```pascal
function lifo_Peek(Stack : PLIFOStack) : void;
```
Returns a direct pointer to the top element's data without removing the node. Returns `nil` if the stack is empty. The pointer is invalidated if the top node is popped.
### lifo_Size
```pascal
function lifo_Size(Stack : PLIFOStack) : uint32;
```
Returns the number of elements currently on the stack.
### lifo_IsEmpty
```pascal
function lifo_IsEmpty(Stack : PLIFOStack) : boolean;
```
Returns `true` if the stack contains no elements.
### lifo_Free
```pascal
procedure lifo_Free(Stack : PLIFOStack);
```
Pops and frees all nodes and their data buffers, then frees the stack structure.
### UnitTest
```pascal
procedure UnitTest;
```
Runs the LIFO stack test suite and logs a pass/fail summary to syslog under the `'LIFO'` channel.
## Notes
Each push causes two heap allocations (node structure and element data buffer). The stack does not expose an array-backed variant; if cache efficiency matters, consider using `core.ds.cfifo` reversed or a custom stack on a pre-allocated buffer.
File diff suppressed because it is too large. Load diff
+67
View File
@@ -0,0 +1,67 @@
# core.ds.maxh
Max-heap: extracts the element with the highest priority value first.
## Overview
`core.ds.maxh` is a thin typed wrapper over `core.ds.bheap` that creates a max-heap. In a max-heap, `maxh_ExtractMax` always yields the element whose `Priority` value is the largest among all inserted elements. This is suitable for applications such as scheduling where the most urgent (highest-valued) item should be processed first.
All heap mechanics (index-array indirection, free-slot recycling, automatic growth) are handled by the underlying `core.ds.bheap` engine.
## Dependencies
- `core.ds.types` — `TBinaryHeap`, `PBinaryHeap`
- `core.ds.bheap` — heap engine
- `io.syslog` — test output (implementation only)
- `core.strings` — test output formatting (implementation only)
- `memory.heap` — `kfree` (implementation only)
## Functions and Procedures
### maxh_New
```pascal
function maxh_New(ElementSize : uint32; InitialCapacity : uint32) : PBinaryHeap;
```
Creates a new max-heap. `ElementSize` is the size in bytes of each data element. `InitialCapacity` is the starting number of slots (grows automatically).
### maxh_Insert
```pascal
procedure maxh_Insert(Heap : PBinaryHeap; Priority : uint32; Data : void);
```
Inserts an element with the given priority. Higher priority values are extracted first.
### maxh_ExtractMax
```pascal
function maxh_ExtractMax(Heap : PBinaryHeap; Data : void) : boolean;
```
Removes and copies the element with the highest priority into `Data`. Returns `false` if the heap is empty.
### maxh_PeekMax
```pascal
function maxh_PeekMax(Heap : PBinaryHeap) : void;
```
Returns a direct pointer to the highest-priority element's data without removing it. Returns `nil` if the heap is empty.
### maxh_Size
```pascal
function maxh_Size(Heap : PBinaryHeap) : uint32;
```
Returns the number of elements in the heap.
### maxh_IsEmpty
```pascal
function maxh_IsEmpty(Heap : PBinaryHeap) : boolean;
```
Returns `true` if the heap contains no elements.
### maxh_Free
```pascal
procedure maxh_Free(Heap : PBinaryHeap);
```
Frees the heap and all its internal buffers.
### UnitTest
```pascal
procedure UnitTest;
```
Runs the max-heap test suite (inserts 5 elements out of order, verifies extraction in descending order) and logs a pass/fail summary to syslog under the `'MAXH'` channel.
+67
View File
@@ -0,0 +1,67 @@
# core.ds.minh
Min-heap: extracts the element with the lowest priority value first.
## Overview
`core.ds.minh` is a thin typed wrapper over `core.ds.bheap` that creates a min-heap. In a min-heap, `minh_ExtractMin` always yields the element whose `Priority` value is the smallest among all inserted elements. This is suitable for applications such as Dijkstra's algorithm or any scenario where the least-costly item should be processed first.
All heap mechanics (index-array indirection, free-slot recycling, automatic growth) are handled by the underlying `core.ds.bheap` engine.
## Dependencies
- `core.ds.types` — `TBinaryHeap`, `PBinaryHeap`
- `core.ds.bheap` — heap engine
- `io.syslog` — test output (implementation only)
- `core.strings` — test output formatting (implementation only)
- `memory.heap` — `kfree` (implementation only)
## Functions and Procedures
### minh_New
```pascal
function minh_New(ElementSize : uint32; InitialCapacity : uint32) : PBinaryHeap;
```
Creates a new min-heap. `ElementSize` is the size in bytes of each data element. `InitialCapacity` is the starting number of slots (grows automatically).
### minh_Insert
```pascal
procedure minh_Insert(Heap : PBinaryHeap; Priority : uint32; Data : void);
```
Inserts an element with the given priority. Lower priority values are extracted first.
### minh_ExtractMin
```pascal
function minh_ExtractMin(Heap : PBinaryHeap; Data : void) : boolean;
```
Removes and copies the element with the lowest priority into `Data`. Returns `false` if the heap is empty.
### minh_PeekMin
```pascal
function minh_PeekMin(Heap : PBinaryHeap) : void;
```
Returns a direct pointer to the lowest-priority element's data without removing it. Returns `nil` if the heap is empty.
### minh_Size
```pascal
function minh_Size(Heap : PBinaryHeap) : uint32;
```
Returns the number of elements in the heap.
### minh_IsEmpty
```pascal
function minh_IsEmpty(Heap : PBinaryHeap) : boolean;
```
Returns `true` if the heap contains no elements.
### minh_Free
```pascal
procedure minh_Free(Heap : PBinaryHeap);
```
Frees the heap and all its internal buffers.
### UnitTest
```pascal
procedure UnitTest;
```
Runs the min-heap test suite (basic operations plus a stress test of 50 elements inserted in reverse order and extracted in ascending order) and logs a pass/fail summary to syslog under the `'MINH'` channel.
+71
View File
@@ -0,0 +1,71 @@
# core.ds.prio
Min-heap ordered priority queue (lowest priority value dequeued first).
## Overview
`core.ds.prio` is a thin typed wrapper over `core.ds.bheap` that presents a priority queue interface. Elements are dequeued in ascending priority order: the element with the lowest `Priority` value is always at the front. This convention (low number = high urgency) is used by the Asuro process scheduler and other subsystems that assign numeric priorities to tasks.
All heap mechanics are handled by the underlying `core.ds.bheap` engine.
## Dependencies
- `core.ds.bheap` — heap engine
- `core.ds.types` — `TBinaryHeap`, `PBinaryHeap`
- `io.syslog` — test output (implementation only)
- `core.strings` — test output formatting (implementation only)
- `memory.heap` — `kfree` (implementation only)
## Functions and Procedures
### prio_New
```pascal
function prio_New(ElementSize : uint32; InitialCapacity : uint32) : PBinaryHeap;
```
Creates a new priority queue. `ElementSize` is the size in bytes of each data element. `InitialCapacity` is the starting number of slots (grows automatically).
### prio_Enqueue
```pascal
procedure prio_Enqueue(Heap : PBinaryHeap; Priority : uint32; Data : void);
```
Enqueues an element with the given `Priority`. Elements with lower priority values will be dequeued before those with higher values.
### prio_Dequeue
```pascal
function prio_Dequeue(Heap : PBinaryHeap; Data : void) : boolean;
```
Removes and copies the highest-priority (lowest-valued) element into `Data`. Returns `false` if the queue is empty.
### prio_Peek
```pascal
function prio_Peek(Heap : PBinaryHeap) : void;
```
Returns a direct pointer to the highest-priority element's data without removing it. Returns `nil` if the queue is empty.
### prio_Size
```pascal
function prio_Size(Heap : PBinaryHeap) : uint32;
```
Returns the number of elements in the priority queue.
### prio_IsEmpty
```pascal
function prio_IsEmpty(Heap : PBinaryHeap) : boolean;
```
Returns `true` if the queue contains no elements.
### prio_Free
```pascal
procedure prio_Free(Heap : PBinaryHeap);
```
Frees the priority queue and all its internal buffers.
### UnitTest
```pascal
procedure UnitTest;
```
Runs the priority queue test suite (enqueues elements with priorities 1–5 in shuffled order, verifies dequeue in priority order) and logs a pass/fail summary to syslog under the `'PRIO'` channel.
## Notes
The priority convention is inverted from common intuition: a `Priority` value of `1` is dequeued before `5`. This matches the convention used by process schedulers where priority 0 or 1 represents the most urgent task.
+106
View File
@@ -0,0 +1,106 @@
# core.ds.types
Shared type definitions for all kernel data structures.
## Overview
`core.ds.types` is a types-only unit that declares the record and pointer types used by the data structure units in the `core.ds` namespace. Centralising these definitions allows different data structure units to share types without circular dependencies. No functions or variables are defined here.
## Dependencies
None.
## Types
### TQueueNode / PQueueNode
```pascal
TQueueNode = record
Next : PQueueNode;
Data : void;
end;
```
Singly-linked node used by the linked-list FIFO (`core.ds.fifo`) and LIFO (`core.ds.lifo`) implementations. `Data` points to a heap-allocated copy of the stored element.
### TFIFOQueue / PFIFOQueue
```pascal
TFIFOQueue = record
Head : PQueueNode;
Tail : PQueueNode;
Count : uint32;
ElementSize : uint32;
end;
```
First-In First-Out queue backed by a singly-linked list. `Head` is the dequeue end; `Tail` is the enqueue end.
### TCFIFOQueue / PCFIFOQueue
```pascal
TCFIFOQueue = record
Data : void;
Head : uint32;
Count : uint32;
Capacity : uint32;
ElementSize : uint32;
end;
```
Array-backed contiguous FIFO queue with lazy compaction and automatic growth. Elements are stored contiguously starting at `Data + (Head * ElementSize)`. When `Head` advances past half the capacity, elements are shifted back to index 0. The buffer doubles when full.
### TCFIFOList / PCFIFOList
```pascal
TCFIFOList = record
Items : void;
Count : uint32;
Capacity : uint32;
end;
```
Dynamic array of `PCFIFOQueue` pointers. Used to group related contiguous FIFO queues. `Items` is a flat buffer of pointer slots that grows automatically.
### TLIFOStack / PLIFOStack
```pascal
TLIFOStack = record
Top : PQueueNode;
Count : uint32;
ElementSize : uint32;
end;
```
Last-In First-Out stack backed by a singly-linked list. `Top` points to the most recently pushed node.
### TCircularQueue / PCircularQueue
```pascal
TCircularQueue = record
Data : void;
Head : uint32;
Tail : uint32;
Count : uint32;
Capacity : uint32;
ElementSize : uint32;
end;
```
Fixed-capacity ring-buffer queue. `Head` is the index of the front element; `Tail` is the index of the next free slot. Wrap-around is handled with modulo arithmetic.
### TBinaryHeap / PBinaryHeap
```pascal
TBinaryHeap = record
Data : void;
Indices : void;
FreeSlots : void;
Count : uint32;
Capacity : uint32;
NextSlot : uint32;
FreeCount : uint32;
ElementSize : uint32;
NodeStride : uint32;
IsMinHeap : boolean;
end;
```
Array-backed binary heap with index-array indirection. Element data is stored inline in `Data` as `[Priority (uint32)][Element (ElementSize bytes)]` per slot. `Indices` maps heap positions to data slot indices, allowing O(1) swaps by exchanging indices rather than copying data. Freed data slots are recycled through `FreeSlots`/`FreeCount`. `IsMinHeap` controls whether the root holds the minimum (`true`) or maximum (`false`) priority.
### TBloomFilter / PBloomFilter
```pascal
TBloomFilter = record
Bits : void;
BitCount : uint32;
HashCount : uint32;
Count : uint32;
end;
```
Probabilistic set-membership filter. `Bits` is a flat byte buffer of `ceil(BitCount / 8)` bytes. Membership tests use `k = HashCount` independent bit positions derived from two base hashes (FNV-1a + DJB2) via double hashing: `h_i(x) = (h1(x) + i * h2(x)) mod BitCount`. False positives are possible; false negatives are not.
+56
View File
@@ -0,0 +1,56 @@
# core.enc.base64
Base64 encoding and decoding.
## Overview
`core.enc.base64` implements RFC 4648 Base64 encoding and decoding for the kernel. It operates on raw byte buffers or null-terminated strings and returns heap-allocated results. The encoder inserts a newline character every 72 output characters and appends `=` padding to complete the final group. The decoder ignores whitespace and newlines in the input.
## Dependencies
- `memory.heap` — `kalloc`, `kfree`
- `core.strings` — `stringSize`
- `debug.tracer` — call-stack tracing
- `core.util` — `memset`
- `arch.x86.util` — architecture utilities
## Constants
### base64_enc_map
A 64-element character array containing the standard Base64 alphabet (`A`–`Z`, `a`–`z`, `0`–`9`, `+`, `/`). Used by the encoder to map 6-bit values to output characters.
## Functions and Procedures
### b64_encode
```pascal
function b64_encode(src : PuInt8; len : uInt32; out_len : PuInt32) : PuInt8;
```
Encodes `len` bytes from `src` into a heap-allocated Base64 string. If `out_len` is not `nil`, the output length (including the trailing null byte) is written there. Returns `nil` if the output length calculation overflows.
### b64_decode
```pascal
function b64_decode(src : PuInt8; len : uInt32; out_len : PuInt32) : PuInt8;
```
Decodes `len` bytes of Base64 data from `src` into a heap-allocated raw byte buffer. If `out_len` is not `nil`, the decoded byte count is written there. Returns `nil` if the input is invalid or allocation fails.
### b64_encode_str
```pascal
function b64_encode_str(src : PChar) : PChar;
```
Convenience wrapper: encodes the null-terminated string `src` and returns a heap-allocated Base64 string. Pushes tracer entries on entry and return.
### b64_decode_str
```pascal
function b64_decode_str(src : PChar) : PChar;
```
Convenience wrapper: decodes the null-terminated Base64 string `src` and returns a heap-allocated decoded string. Pushes tracer entries on entry and return.
## Notes
The encoder output includes newlines after every 72 characters. Consumers that do not expect line breaks should strip them or use `b64_encode` directly and handle the output buffer themselves.
The decoder builds a 256-entry decode table on the stack at each call. Unknown characters are mapped to `$80` (the sentinel for "skip"). Padding characters (`=`) are mapped to `0` and their count is tracked to trim the output length.
If the input to `b64_decode` is not a multiple of 4 valid Base64 characters, the function currently enters an unhandled branch (silent error). Callers should validate input length before decoding.
Both `b64_encode` and `b64_decode` return heap-allocated buffers that must be freed by the caller with `kfree`.
Loaded 20 of 209 files, more files were not shown because too many files have changed in this diff. Show more