15 KiB
Birthing Plan: Child VMs Born of Hera
Status: DRAFT — requires Captain Bob approval before any implementation begins
Branch: birthing (off lithosananke)
Authors: Claude Code + Captain Bob
Date: 2026-05-24
1. Vision
Three named VMs form the initial constellation of LithosAnanke:
| VM Name | Role |
|---|---|
| Hera | Mama VM — orchestrates all other VMs; runs capsules/init.4th |
| Hermes | Messaging stratum — pub/sub between VMs; runs capsules/hermes/init.4th |
| Artemis | Storage and memory manager; runs capsules/artemis/init.4th |
Hades remains the kernel + HAL substrate beneath all of them.
For now, Hera's job is simply: birth, start, stop, and kill VM instances. Concurrent scheduling, inter-VM messaging, and storage management are later milestones.
Every VM — including Hermes and Artemis — carries the same lifecycle primitives. A VM can birth and manage other VMs. The infrastructure is uniform.
2. Hard Constraints
Fixed by the execution model. Hera's implementation is not constrained — she expands as the design requires.
| Constraint | Implication |
|---|---|
| Same process as Hera | No fork(), no pthread_create() |
| No threads | Scheduling is cooperative, inside the interpreter loop |
| No OS processes | VMs share Hera's address space |
ANSI C99, -Wall -Werror |
No GNU extensions |
| Hades is the substrate | All I/O, timing, and memory from Hades (kernel+HAL) |
3. VM Identity and Naming
3.1 Every VM Has a Name
The current VMRegistryEntry tracks VMs by numeric ID only. This must be extended with a
symbolic name field. A VM's name:
- Is set at birth (derived from the capsule namespace — see §5)
- Is displayed in every log line emitted by that VM
- Is the argument to all lifecycle words:
S" Artemis" BIRTH,S" Artemis" KILL, etc. - Is unique within a session (no two live VMs share a name)
- Is case-preserved but case-insensitive for lookup
3.2 VM Registry Extension
VMRegistryEntry needs a name field (at minimum char name[64]). The name is:
- Set by
BIRTHat VM creation time - Cleared on
KILL(slot becomes reusable) - Logged in every parity record alongside the numeric VM ID
3.3 Log Prefix — Critical
Every line of console output emitted by a VM is prefixed with its name:
[Hera] ok
[Hermes] pub/sub ready
[Artemis] storage initialized
[Hera] 2 VMs alive
This applies to EMIT, TYPE, ., .S, CR, and all I/O words. The prefix is injected
at the HAL console layer — the VM does not format it; Hades prints it automatically based
on the current active VM context.
4. The Five Primitive Forth Words
These words are built-in C primitives registered in every VM's dictionary at startup. They are not defined in Forth — they are part of the base word set, available to all VMs.
Stack signatures use the counted-string convention: ( c-addr u -- )
BIRTH ( c-addr u -- )
Birth a new VM from the capsule whose namespace matches the given name.
Mapping: S" Artemis" → lowercase "artemis" → capsule name artemis:init.4th
(the standard capsule for a named VM is <name>:init.4th).
Sequence:
- Lowercase the name string
- Construct capsule name:
<name>:init.4th - Look up capsule in the directory by name
- Verify capsule is
FLAG_PRODUCTION+FLAG_ACTIVEand notFLAG_REVOKED - Allocate a new VM context (full VM — Hera expands her pool as needed)
- Execute the capsule init (via existing
capsule_exec_initpath) - Register VM under the symbolic name in the extended
VMRegistryEntry - Log parity record:
PARITY:BIRTH name=Artemis vm_id=N capsule_id=X - On success: push 0; on failure: push error code
If a VM named "Artemis" is already alive: check its health. If healthy, skip the birth and log the fact. Do not error, do not replace. BIRTH is idempotent for healthy VMs.
KILL ( c-addr u -- )
Destroy a named VM. The VM's resources are freed and its registry slot is cleared.
Sequence:
- Look up VM by name in registry
- If not found: push error code, return
- Forcibly terminate any pending execution in that VM
- Free the VM's stacks, dictionary, and memory
- Clear registry slot (name + state = DEAD)
- Log parity record:
PARITY:KILL name=Artemis vm_id=N - Push 0 on success
Note: KILL is unconditional. It does not wait for the VM to reach a yield point. At this phase (no concurrent execution), the VM is idle when KILL is called.
START ( c-addr u -- )
Begin or resume execution of a named VM.
At this phase: START runs the VM to completion (or until it calls STOP on itself)
before returning control to the caller. Concurrent interleaved execution is a later milestone.
Sequence:
- Look up VM by name
- If state is EMBRYO or STOPPED: set state to LIVE, transfer execution
- If state is LIVE: error (already running)
- On VM completion or self-STOP: return control to the calling VM
- Push 0 on success
STOP ( c-addr u -- )
Suspend a named VM. Its execution state is preserved; START will resume it.
Any VM can STOP any other. Authority comes from identity — a VM may assume another identity for failsafe and recovery. The identity assumption mechanism is a future milestone; in Phase 1, cross-VM STOP is permitted without restriction.
Sequence:
- Verify name matches the current VM
- Save execution state (IP, stacks)
- Set state to STOPPED
- Return control to the VM that called
START
USE ( c-addr u -- )
Make a named VM the active console target. Subsequent REPL input and output is directed
to and from that VM until another USE call or the VM dies.
S" Hermes" USE \ REPL now talks to Hermes
: send-test S" hello" PUBLISH ;
S" Hera" USE \ REPL returns to Hera
USE is system-wide — it is not scoped to a capsule or identity. All REPL input and
output redirects to the named VM until the next USE call. The [Name] prefix in the
console reflects the active USE target.
Sequence:
- Look up VM by name in registry
- Set as the active system-wide REPL/console VM
- Console prefix changes to
[VMName] - Stack unchanged (no return value)
5. Capsule Namespace Convention
5.1 Directory Structure
Each named VM owns a subdirectory under capsules/:
capsules/
├── init.4th ← Hera's capsule ONLY (root level, no subdir)
├── hermes/
│ └── init.4th ← Hermes' capsule
└── artemis/
└── init.4th ← Artemis' capsule
capsules/init.4th is Hera's exclusive init. No other VM uses the root-level init.
Do not place general capsules there. Do not recreate the old conf/ directory.
5.2 How mkcapsule Names Capsules
tools/mkcapsule.c scans capsules/ recursively. It encodes relative paths by replacing
/ with :. So:
| File path | Capsule name |
|---|---|
capsules/init.4th |
init.4th |
capsules/hermes/init.4th |
hermes:init.4th |
capsules/artemis/init.4th |
artemis:init.4th |
5.3 BIRTH Name → Capsule Name Mapping
BIRTH lowercases the VM name and appends :init.4th:
| Forth call | Capsule looked up |
|---|---|
S" Hera" BIRTH |
init.4th (special case — root) |
S" Hermes" BIRTH |
hermes:init.4th |
S" Artemis" BIRTH |
artemis:init.4th |
S" MyWorker" BIRTH |
myworker:init.4th |
The root-level init.4th is a special case: S" Hera" BIRTH is how a future VM would
re-birth Hera; at bootstrap, Hera boots from it automatically.
5.4 mkcapsule Flag Mapping
The capsule flag (FLAG_PRODUCTION vs FLAG_EXPERIMENT) is determined by the directory
prefix — not the file name. Under the current mkcapsule logic:
capsules/hermes/init.4th→ does not matchproduction:*,core:*, ordomains:*→ currently getsFLAG_EXPERIMENT
All capsules carry both FLAG_PRODUCTION and FLAG_EXPERIMENT. Birth eligibility is
not gated on the flag type — any capsule can be used for any identity. mkcapsule will be
updated to set both flags on every capsule it generates. The distinction between production
and experiment remains in the flags for audit/logging purposes but does not block BIRTH.
6. Capsule Content (Stubs)
Hermes and Artemis capsule directories exist but are empty (.gitkeep only). They need
init.4th stubs before the system can BIRTH them.
capsules/hermes/init.4th (stub)
Should:
- Print
[Hermes] initializing(or similar boot message) - Define Hermes' pub/sub vocabulary (placeholder for now)
- Leave Hermes in a known state (not just empty)
capsules/artemis/init.4th (stub)
Should:
- Print
[Artemis] initializing - Define Artemis' storage/memory vocabulary (placeholder)
These stubs must be written before make -f Makefile.starkernel is run, because
mkcapsule runs at build time and produces capsule_generated.c from whatever is in
capsules/ at that moment.
7. VM Lifecycle Model
(capsule exists in directory)
│
▼
[BIRTH]
│
▼
EMBRYO ──────────────────[KILL]──────► DEAD
│ ▲
[START] │
│ [KILL]
▼ │
LIVE/RUNNING ──────────[STOP]──► STOPPED─┘
│
(completes)
│
▼
DEAD (natural)
States:
- EMBRYO — VM born (capsule executed) but
STARTnot yet called - LIVE — executing (at this phase: running synchronously inside
START) - STOPPED — suspended; state saved; resumable via
START - DEAD — killed or naturally completed; slot reclaimable
8. Scheduling Model (Phase 1)
At this phase, scheduling is sequential and explicit:
STARTruns a VM synchronously — the calling VM suspends while the started VM runs- No round-robin, no time-slicing, no preemption
- The REPL is always in exactly one VM's context at a time
USEswitches the REPL/console target
This is intentionally simple. Cooperative concurrent scheduling (multiple VMs interleaved in the interpreter loop) is a future milestone, designed separately after the basic lifecycle works.
9. Dictionary and Namespace
The five lifecycle words (BIRTH, KILL, START, STOP, USE) are C primitives in every VM's base dictionary. They are registered at VM initialization, before any capsule init runs.
A child VM born by Hermes or Artemis also has these words — all VMs can manage other VMs.
Dictionary isolation: Each VM has its own dictionary. Words defined by Artemis's
init.4th do not appear in Hera's dictionary or Hermes' dictionary. VMs communicate
through the messaging layer (Hermes), not shared dictionary state.
10. Hades Interface
All VMs access Hades through the same HAL interface. At this phase:
- No capability bitmask enforcement
- All VMs can call any HAL function (I/O, memory, time)
- The log prefix (
[VMName]) is injected by the HAL console layer based on the currently executing VM context — not by the VM itself
Capability enforcement (limiting what a child VM can do in Hades) is a future milestone.
11. Physics / SSM Integration
Each VM has its own independent SSM/L8 Jacquard state — this is already the natural
consequence of each VM being a full VM instance with its own VM struct. No shared physics.
The heartbeat runs per-VM. Hera's SSM does not observe Hermes' or Artemis' execution.
12. Decisions — RESOLVED
| # | Decision | Resolution |
|---|---|---|
| D1 | BIRTH name collision | Idempotent — check health of existing VM; if healthy, skip and log. No error, no replace. |
| D2 | Production flag | All capsules carry both FLAG_PRODUCTION and FLAG_EXPERIMENT. Birth eligibility is not gated on flag type. mkcapsule updated accordingly. |
| D3 | BIRTH return value |
Nothing — BIRTH is a pure side-effect word, leaves stack clean. |
| D4 | USE scope |
REPL only, but system-wide. Not bound to any specific capsule or identity. All REPL I/O redirects to the named VM. |
| D5 | STOP across VMs | Any VM may assume another identity for failsafe and recovery purposes, enabling cross-VM STOP. Identity assumption mechanism is a future milestone; Phase 1 allows any VM to STOP any other. |
| D6 | Max named VMs | Dynamic — Hera allocates as needed. No fixed ceiling. |
| D7 | Log prefix format | [Name] — e.g., [Hera], [Hermes], [Artemis] |
13. What This Is NOT
- Not a thread scheduler. No preemption. Sequential execution at this phase.
- Not a process model. VMs share Hera's address space.
- Not a security boundary yet. No capability enforcement in this phase.
- Not constrained by Hera's current implementation. Hera expands as the design requires.
14. Implementation Phases
No code until Captain Bob approves the plan.
| Phase | Scope | Deliverable |
|---|---|---|
| 0 | Design approval | This document, signed off |
| 1 | VM registry naming | Add name[64] to VMRegistryEntry; name lookup functions |
| 2 | Log prefix | HAL console layer emits [VMName] prefix per active VM |
| 3 | Capsule stubs | Write capsules/hermes/init.4th, capsules/artemis/init.4th |
| 4 | mkcapsule flag update | Set both FLAG_PRODUCTION and FLAG_EXPERIMENT on all capsules |
| 5 | BIRTH word | C primitive; name→capsule lookup; health-check idempotence; full VM alloc |
| 6 | KILL word | C primitive; teardown; registry clear |
| 7 | START word | C primitive; synchronous execution hand-off |
| 8 | STOP word | C primitive; cross-VM; state save; return to caller |
| 9 | USE word | C primitive; system-wide REPL/console redirect |
| 10 | Hera init.4th update | Use new words to birth Hermes and Artemis at boot |
| 11 | Integration test | Boot sequence: Hera → BIRTH Hermes → BIRTH Artemis → [Name] in logs |
15. Mythological Framing Reference
| Name | Role |
|---|---|
| Hades | Kernel + HAL — the underworld substrate |
| Hera | Mama VM — queen, orchestrator, eternal; capsules/init.4th |
| Hermes | Messenger — pub/sub stratum; capsules/hermes/init.4th |
| Artemis | Hunter/keeper — storage and memory; capsules/artemis/init.4th |
| BIRTH | The word that brings a new VM into being |
| KILL | The word that destroys a VM |
| START | The word that gives a VM its first breath (or resumes it) |
| STOP | The word that suspends a VM |
| USE | The word that shifts the speaker's attention to a VM |
This document is a planning artifact only. No code changes have been made.
Captain Bob's approval of the open decisions in §12 is required before Phase 1 begins.