Console login creates a real interactive VMS process another process can see (vms-72c) - #40
Merged
Merged
Conversation
…can see (vms-72c)
Measured the gap on a real QEMU boot before changing anything: SHOW SYSTEM/
SHOW PROCESS already read the executive process table honestly (vms-8019),
and SHOW TERMINAL/job-terminal binding already worked (vms-d0b) -- but three
real facades remained.
1. Authentication was vacuous. distro/rootfs/.../SYSUAF.DAT shipped every
account with an EMPTY password hash, and sysuaf_authenticate() treats an
empty hash as "no password required" -- so any password, including a
deliberately wrong one, authenticated successfully. Reproduced directly
against a real QEMU boot (SYSTEM + a wrong password reached a DCL prompt).
Fixed by giving SYSTEM and GUEST (the accounts the UAT actually drives)
real SHA256 hashes; refusal message ("User authorization failure") pinned
to a public OpenVMS documentation transcript since the ~/vax lab was
mid-use for an unrelated cluster experiment for the whole of this item.
2. The login session had no VMS process name. tools/vms_login.c never
called vms_kif_setprn() (which already existed and already had a
product caller for $CREPRC), so SHOW PROCESS printed Process name: ""
for a real, authenticated, terminal-owning session. Closed by calling
vms_kif_setprn(rec->username) after identity is stamped, pinned to the
VAX1 oracle capture showing the interactive SYSTEM session named
literally SYSTEM (docs/oracle/vax73-show-system-process.md Section 1).
Distinct from vms-d0e's still-open, broader question (default naming
for a bare $CREPRC with no explicit prcnam).
3. SHOW USERS was a per-process facade. Its terminal-allocation-table
reader (vms_term_list()) had had its only writer deleted by vms-fb9,
so the table was permanently empty and the "no entries" branch
fabricated a row from the CALLING process's own context -- getpid(),
not the VMS pid. Measured: SHOW USERS printed PID 00000049 for the
same session SHOW PROCESS reported as VMS pid 10000003. Rewritten to
read the executive process table via vms_kif_procscan(), the same
source SHOW SYSTEM/SHOW PROCESS already use; the dead file-based
reader is deleted along with its now-unused writer-less table.
4. The LOGINOUT-exec-fails fallback to raw, unauthenticated DCL is
deleted (Rule 10): LOGINOUT.EXE is a required, always-provisioned
system file, so the condition is made unreachable rather than handled
by a plausible-looking degraded shell.
Extended tests/uat/vms_session_qemu.sh (not weakened): a wrong-password
negative test with anchored refusal/non-grant checks, a SHOW USERS
assertion cross-checked against the session's own real VMS pid, and the
vms-d0e known-divergence tripwire for SHOW PROCESS's Process name field
converted to a real VMS-matching assertion now that this item lands it
for the login path. 52/52 UAT checks pass (up from 47), reproduced twice.
A cross-process $GETJPI-by-name UAT check (SPAWN a second time in the
same session) was written, built, and run against a real boot -- and hit
a pre-existing, unrelated DCL defect instead: the second SPAWN in a
session fails outright (%DCL-E-CREPRC) regardless of command content,
reproduced three ways including a minimal isolated probe. Not this item's
to fix; reported as a finding. The cross-process $GETJPI-by-name
mechanism itself is proven at the kernel-executive layer independent of
DCL/SPAWN (tests/qemu/test_syssvc_procnam.c, pre-existing).
Verified: host ctest 50/50, QEMU kernel-executive test suite 28/28
suites, executive-absent negative control (3 passed / 25 failed exactly
as its own harness expects), product-boot UAT 52/52 (x2).
Co-Authored-By: Claude Opus 5 <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.
distro/rootfs/.../SYSUAF.DATshipped every account with an empty password hash, andsysuaf_authenticate()treats an empty hash as "no password required."Measured on the unmodified image, not inferred: booting
origin/mainand logging in asSYSTEMwitha deliberately wrong password reached
Welcome to OVMXand a$prompt.SYSTEMandGUESTnow carry real SHA256 hashes, and the refusal messageUser authorization failureis pinned to public OpenVMS documentation (VMS Help "Login", Example 6) — the
~/vaxlab wasmid-experiment for
vms-760for this item's entire duration, checked viaps auxand never touched.The other two facades
The login session had no VMS process name.
tools/vms_login.cnever calledvms_kif_setprn()— awrapper that already existed and already had a product caller. Now called after identity is stamped,
pinned to the VAX1 oracle capture showing an interactive
SYSTEMsession's ownSHOW SYSTEMrow namedliterally
SYSTEM.SHOW USERSwas a per-process fabrication. Its terminal-table reader had its only writer deleted byvms-fb9, so the table was permanently empty and the "no entries" branch invented a row from thecalling process's
getpid(). Measured:SHOW USERSprinted PID00000049for the same session whoseSHOW PROCESS, one command earlier, reported VMS pid10000003. It now reads the executive processtable through
vms_kif_procscan()— the same sourceSHOW SYSTEMandSHOW PROCESSalready use — andthe dead file-based reader is deleted.
Rule 10
The "LOGINOUT failed to exec" path fell back to a raw, unauthenticated DCL shell.
LOGINOUT.EXEis arequired, always-provisioned system file, so the condition is made unreachable rather than degraded into
a shell — the same illegal-third-answer shape as the empty-hash default.
The UAT was extended, not weakened
52/52, up from 47, reproduced twice for determinism. A wrong-password negative test with an anchored
refusal; a
SHOW USERSassertion cross-checked against the session's own real VMS pid extracted fromits
SHOW PROCESSresponse rather than re-typed as a literal; and the pre-existingvms-d0edivergencetripwire converted into a real VMS-matching assertion now that the login-session case is answered.
Verification
ctest 50/50 · QEMU 28 suites / 0 failed · executive-absent control red for the right reason · product-boot
UAT 52/52 twice.
Filed, not fixed:
vms-d0f5— SPAWN fails on the second invocation in a session regardless of commandcontent, proven by a minimal probe (three
SPAWN SHOW TIME: #1 succeeds, #2 and #3 fail identically).That blocked a cross-process
$GETJPI-by-name check at the command layer; the mechanism is proven insteadat the executive layer by
test_syssvc_procnam.c.Closes vms-72c.
🤖 Generated with Claude Code