vms-98c: lib$spawn spawns a REAL DCL subprocess (exec-drive prereq A) - #451
Merged
Merged
Conversation
…exec-drive prereq A) lib$spawn was a Rule-9 / INV-6 facade: it fork+exec'd `/bin/sh -c <command>` (the Unix Bourne shell, NOT a DCL command interpreter) and returned SS$_NORMAL for a "SHOW TIME" no DCL ever saw. Replace it with a genuine DCL subprocess: resolve SYS$SYSTEM:DCL.EXE through the VMS filespec translator (the same image JOB_CONTROL and PROVISION exec) and fork+exec it against the command via DCL's -c mode, with SYS$INPUT/SYS$OUTPUT redirection. Honest boundary (Rule 9 / INV-6): if the CLI image cannot be resolved or is not an executable regular file, return an authentic VMS error (SS$_NOSUCHFILE) and run NOTHING -- no /bin/sh fallback, never a fake success for a command that did not run. Running a real child image needs no /dev/vms. CLI$M_NOWAIT is honored (create-and-return); wait mode HIBERNATEs on the child and returns its completion status. The efn/AST completion notification, named- subprocess registration, and the persistent-subprocess + mailbox + write- attention-AST protocol MMK's build_target.c uses are prereqs B/C (vms-e0b, vms-9003) -- accepted-and-documented here, not faked. Test: tests/libvms/test_lib_spawn_dcl.c redirects SYS$SYSTEM to a private root, stages the build's own DCL image there, and drives the real lib$spawn path. Asserts (1) SHOW TIME's redirected SYS$OUTPUT carries the current year (oracle: this process's clock) -- proving a real DCL child ran it; (2) with the CLI image absent, lib$spawn fails even-status and creates nothing (no /bin/sh fallback). Hermetic, no shared /vms, no /dev/vms. 34/34 libvms tests green; Rule-9 runtime- target gate + dcl-integration green; full tree builds. No new cross-image symbol (lib$spawn already exported; helper is static), so the libvms_shr vector is unchanged. Doc pins (VSI OpenVMS, public): RTL Library (LIB$) Routines Reference Manual, LIB$SPAWN; DCL Dictionary, SPAWN / SHOW TIME. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…ixes kif_caller_census) The kif_caller_census authenticity gate went red on CI (Build & Test), not from any lib$spawn behavior regression -- test_libvms_lib_spawn_dcl itself passed on CI -- but because its CMake handed the DCL image path to the test as a quoted string compile definition (VMSDCL_PATH="$<TARGET_FILE:vmsdcl>"). That put the only backslash-escaped entry in the whole compile_commands.json, and the census reader parses compile_commands.json and does not implement backslash unescaping. Hand the path over at RUNTIME via a CTest ENVIRONMENT property (OVMX_TEST_DCL_IMAGE=$<TARGET_FILE:vmsdcl>) instead. compile_commands.json is clean again (0 backslash escapes) and the test stays hermetic against the image the build produced. If the variable is ever absent (standalone run) the test skips honestly via SKIP_RETURN_CODE 77 rather than faking a pass. Verified locally: kif_caller_census PASS, test_libvms_lib_spawn_dcl PASS, full ctest 172/172 (e2e QEMU/docker suites skipped as on CI). Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
baron-3dl
added a commit
that referenced
this pull request
Aug 13, 2026
…456) Bump OVMX_PRODUCT_VERSION V0.4-1 → V0.4-2. 10 PRs since V0.4-1, toward the 0.5 milestone: owns-kernel #450 OVMX builds its own pinned linux-6.12.103 LTS from source (byte-reproducible, boots 17/17+24/24) — vms-19e beachhead self-host #4 #446 MMK.EXE parses descrip.mms + emits TCC→LINK plan (exec-drive facilities, all proven vs real /dev/vms:) #451 lib$spawn real DCL (facade killed) · #452 mailbox IPC #453 write-attention AST · #454 exec-drive design record UX fidelity #447 DIRECTORY format+versions · #448 Ctrl-T status line #449 hierarchical HELP engine · #455 SHOW MEMORY (drop buffers+cached fabrication) + swept other threads' merged work MMK does not yet DRIVE builds (spine #4 needs async AST delivery + IO$M_NOW + DCL-mailbox-SYS$INPUT — filed vms-feb/5df/786, faithful path in flight). Co-authored-by: alice <alice@workspace.local> Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What
lib$spawnwas a Rule-9 / INV-6 facade: it fork+exec'd/bin/sh -c <command>— the Unix Bourne shell, not a DCL command interpreter — and returnedSS$_NORMALfor aSHOW TIMEthat no DCL ever saw. This replaces it with a genuine DCL subprocess.Prereq A of the vms-ec70 self-host spine #4 exec-drive (making MMK.EXE actually drive compile/link).
How the DCL child really runs the command
SYS$SYSTEM:DCL.EXEthrough the VMS filespec translator (vmsfs_to_linux_path) — the same CLI imageJOB_CONTROLandPROVISIONexec to hand a user a session, so a redefinedSYS$SYSTEMis honored.fork(), redirectSYS$INPUT/SYS$OUTPUT, thenexecl(dcl, "DCL", "-c", command)— DCL executes the one command and exits (dcl_main.c-cmode). No command → interactive DCL onSYS$INPUT.CLI$M_NOWAIThonored (create-and-return); wait mode HIBERNATEs on the child and returns its completion status.Honest boundary (Rule 9 / INV-6)
If the CLI image cannot be resolved or is not an executable regular file,
lib$spawnreturns an authenticSS$_NOSUCHFILEand runs nothing — no/bin/shfallback, never a fake success for a command that did not run. A real child image needs no/dev/vms.Test (
tests/libvms/test_lib_spawn_dcl.c)Redirects
SYS$SYSTEMto a private temp root, stages the build's own DCL image there asDCL.EXE, and drives the reallib$spawnresolve+fork+exec path (no monkeypatch, hermetic, no shared/vms, no/dev/vms):lib$spawn("SHOW TIME")withSYS$OUTPUTredirected; asserts the captured file carries the current year (oracle: this process's own clock). Captured13-AUG-2026 06:13:44.05— genuine DCLSHOW TIME./bin/sh -c "SHOW TIME"would print aSHOW: not founderror, so the pre-fix body fails this.vmsdcl -cruns without the executive (cf.test_dcl_basic.sh), so the whole spawn→DCL→SHOW TIME path is provable on a host ctest.Results
test_libvms_lib_spawn_dclPASS; 34/34 libvms tests green.runtime_target_gate+runtime_target_negctl+dcl-integrationgreen.lib$spawnalready exported; helper isstatic) →libvms_shrvector unchanged, native-link unaffected.Deferred (prereqs B/C — vms-e0b mailbox, vms-9003 write-attention AST)
The efn/AST completion notification, named-subprocess ($CREPRC) registration, and the persistent DCL subprocess + mailbox + write-attention-AST protocol MMK's
build_target.cuses (stream many commands into one long-lived DCL, read each command's full$STATUSfrom an end-of-command marker) are accepted-and-documented, not faked. This PR is the create+run primitive that rides under that protocol. Note: DCL's-cmode collapses$STATUSto shell 0/1, so full$STATUSfidelity comes via the B/C mailbox EOM markers, not this path.Clean-room (Rule 8): LIB$SPAWN semantics from the public VSI OpenVMS RTL Library (LIB$) Routines Reference Manual and the DCL Dictionary (SPAWN / SHOW TIME).
🤖 Generated with Claude Code