mirror of
https://github.com/subhobhai943/SUB-OS.git
synced 2026-10-25 16:52:29 +00:00
feat(sched): Weave tiered scheduler with real kernel-thread context switching
Replace the state-relabel-only round-robin with the SUB-OS "Weave" scheduler backed by a genuine callee-saved context switch. Threads now actually run on their own kernel stacks instead of merely having their state field rewritten. What was implemented: - sub_ctx_switch(): per-arch assembly (arch/x86_64/cpu/switch.asm, arch/aarch64/cpu/switch.S, arch/armv8i/cpu/switch.S) that saves/restores the callee-saved register set (+ flags on x86_64) on each thread's own stack, plus a first-run trampoline (sub_thread_trampoline) that launches a freshly forged thread frame with entry/arg in callee-saved registers. - task_forge_frame(): builds the initial saved-context frame per arch so the very first switch into a new thread lands on the trampoline; task_t gains a pointer-sized ctx_sp so the same struct works on 64- and 32-bit. - Weave policy (kernel/sched.c): WEAVE_NLANES priority lanes, always dispatch the lowest non-empty lane round-robin; a task that yields voluntarily is woven UP a lane (interactive), one preempted after burning its quantum is woven DOWN (CPU-bound). Cooperative switching (sched_yield / task_exit) is always live; timer-driven preemption is gated behind sched_set_preempt() and left disarmed for now. - task_exit() now switches to the next runnable thread via sched_exit_current() instead of spinning/halting. - Boot-time weave_selftest() (x86_64) and sched_dump() diagnostics. How it was verified: - Builds clean for all three targets: x86_64 (CROSS_COMPILE=x86_64-linux-gnu-, RUSTC="rustc --target x86_64-unknown-none"), aarch64, armv8i. No new warnings; the new x86_64 asm carries a .note.GNU-stack section. - Booted x86_64 under QEMU (TCG): the self-test runs three cooperative kernel threads to completion on separate stacks with the expected 1->2->3 round-robin interleave, reports "20 real context switches, 3/3 workers exited", returns cleanly to the boot thread, and boot proceeds normally to ring-3 init and the shell. No fault/panic. Left unverified: - The aarch64/armv8i sub_ctx_switch frames build and link but are not yet boot-tested on their QEMU targets (tracked in docs/AUTODEV_ROADMAP.md). - Timer preemption path is implemented but disarmed; exited kernel threads currently leak their stack (reaper is next in the backlog). Co-Authored-By: Claude Opus 4.8 <[email protected]> Claude-Session: https://claude.ai/code/session_01Jk6K69yGS7zYgvoWd6nJxQ
This commit is contained in:
10 files changed
+570
-58
No files matched your search
@@ -0,0 +1,67 @@
|
||||
# SUB-OS Autonomous Development Roadmap
|
||||
|
||||
This file is the cross-run memory for the continuous-development effort. Each
|
||||
run: read it, pick the single highest-value NEXT item achievable in one
|
||||
session, implement + verify it, then move it to DONE with a one-line result and
|
||||
refine the backlog.
|
||||
|
||||
## Known-good build invocations (this host)
|
||||
|
||||
- **Toolchain setup:** `apt-get install -y nasm gcc-aarch64-linux-gnu
|
||||
binutils-aarch64-linux-gnu gcc-arm-linux-gnueabihf binutils-arm-linux-gnueabihf
|
||||
qemu-system-x86 qemu-system-arm`; for Rust: `rustup target add x86_64-unknown-none`.
|
||||
- **x86_64:** `make x86_64_defconfig && make CROSS_COMPILE=x86_64-linux-gnu-
|
||||
CXX=x86_64-linux-gnu-g++ RUSTC="rustc --target x86_64-unknown-none"`
|
||||
- **aarch64:** `make aarch64_defconfig && make`
|
||||
- **armv8i:** `make armv8i_defconfig && make`
|
||||
- **Boot (x86_64, headless):** `qemu-system-x86_64 -drive format=raw,file=SUB-OS.img
|
||||
-m 256M -netdev user,id=net0 -device e1000,netdev=net0 -serial stdio -display none`
|
||||
(slow under TCG; the shell waits on input, so a timeout at the prompt is normal).
|
||||
|
||||
## DONE
|
||||
|
||||
- **Weave scheduler + real kernel-thread context switching** (2026-08-25):
|
||||
Replaced the state-relabel-only round-robin with the SUB-OS "Weave" tiered
|
||||
scheduler backed by a genuine callee-saved context switch (`sub_ctx_switch`,
|
||||
per-arch assembly for x86_64/aarch64/armv8i) and a first-run trampoline.
|
||||
Threads run on their own kernel stacks; a task's lane floats on behaviour
|
||||
(voluntary yield → woven up, quantum-burn → woven down). Verified on x86_64
|
||||
under QEMU: a boot-time self-test runs 3 cooperative kernel threads to
|
||||
completion (20 real context switches, correct 1→2→3 round-robin interleave,
|
||||
clean return to the boot thread, then boot proceeds to ring-3 init + shell).
|
||||
ARM switch asm builds on both targets but is not yet boot-tested.
|
||||
|
||||
## NEXT (prioritized backlog)
|
||||
|
||||
1. **Preemptive Weave scheduling from the timer tick.** The plumbing exists
|
||||
(`sched_set_preempt`, `sched_tick` charges the quantum). Arm it *after* boot
|
||||
completes, make the PIT ISR path re-entrancy-safe (switch on IRQ return, not
|
||||
mid-handler), and add a preemption self-test showing a CPU-bound thread being
|
||||
woven down while an interactive one stays in lane 0. Needs an IRQ-context
|
||||
switch (save the full trap frame, not just callee-saved state).
|
||||
2. **Thread reaping / zombie cleanup.** Exited kernel threads currently leak
|
||||
their 16 KB stack + task_t. Add a reaper (per-CPU dead list drained by the
|
||||
idle thread) so `task_exit` hands the corpse to it instead of leaking.
|
||||
3. **Boot-test the ARM context switch.** Wire a `weave_selftest()` call into the
|
||||
aarch64/armv8i boot paths and boot under `qemu-system-aarch64`/`-arm` to
|
||||
confirm the AArch64/AArch32 `sub_ctx_switch` frames are correct.
|
||||
4. **fork/exec/wait for the ring-3 userland.** Build on the existing ELF64
|
||||
loader + per-process page tables so `sh` can spawn and reap real children,
|
||||
not just the single builtin init.
|
||||
5. **An original capability-based IPC channel** ("sub-ports"): typed,
|
||||
capability-addressed message endpoints distinct from the SysV msg/pipe/shm
|
||||
set already present in `ipc/` — leaning into the "object-first" identity.
|
||||
6. **SMP bring-up (x86_64):** AP boot trampoline, per-CPU run lanes, and making
|
||||
the Weave lanes per-CPU with work-stealing between them.
|
||||
7. **GUI (feat/gui-desktop):** compositor damage tracking, a VFS-backed file
|
||||
manager, a text editor, and a settings panel over the toolkit widgets.
|
||||
|
||||
## Notes / gotchas
|
||||
|
||||
- `.S` files are run through cpp: no nested `/* ... */` comments.
|
||||
- `printk`/vsprintf supports only `c s d i u o x X p %` — no length modifiers
|
||||
(`l`, `ll`) and no field width; cast to `int`/`unsigned`/`void*`.
|
||||
- `list_del()` NULLs both links, so `list_empty()` is not a reliable "is this
|
||||
node queued?" test after a delete — check the links directly.
|
||||
- During `subos_modular_core_boot()` step 13, hardware interrupts are still
|
||||
masked (enabled at step 14), so cooperative in-boot tests are deterministic.
|
||||
Reference in new issue
Block a user