vms-40b: Alpha struct stat/sigaction layouts + stat64 wrappers - #629
Merged
Merged
Conversation
Rung A1 of the OVMX-on-Alpha epic. A0 left struct vms_stat and struct
vms_sigaction deliberately undefined for __alpha__; this defines both,
verified field-for-field (offsetof/sizeof probes compiled and run under
qemu-alpha) against the real alpha-linux-gnu kernel headers:
arch/alpha/include/uapi/asm/stat.h (`struct stat64`, what fstat64/
fstatat64 fill) and arch/alpha/include/uapi/asm/signal.h (`struct
sigaction`, handler/mask/flags order -- no sa_restorer field). Wires
vms_sys_fstat to __NR_fstat64 (427) instead of the old __NR_fstat (91,
a narrower non-stat64 struct) per the known stat64-pairing trap, and
gives vms_sys_rt_sigaction an Alpha-specific 5-arg body: Alpha's
rt_sigaction syscall takes the signal restorer as an explicit 5th
argument (SYSCALL_DEFINE5) rather than a struct field.
Proving `tests/libvmssys` under qemu-alpha (the stated gate) surfaced
four more pre-existing, unrelated Alpha ABI gaps left open by A0 --
none caused by the struct work above, all blocking before it too:
- No hardware integer divide/remainder: added __divqu/__remqu as
hand-written asm (arch/alpha/softdiv.S) implementing Alpha's
non-standard division-helper calling convention (args in $24/$25,
return address in $23, result in $27, and -- the part that cost
real debugging time -- callee must preserve $1-$8 because GCC's
div+mod fusion keeps values live across the call).
- No inline __builtin_sqrt/floor/ceil lowering on Alpha's GCC
backend (always a libcall): added freestanding implementations
(arch/alpha/softmath.c) -- schoolbook division, Newton-Raphson
sqrt, IEEE-754 mantissa-mask floor/ceil. Neither gap can pull in
glibc/libgcc (Rule 3), hence hand-rolled.
- Alpha's mmap flag bits are not the generic Linux ones (MAP_FIXED/
MAP_ANONYMOUS/MAP_NORESERVE all differ); the generic values sent a
"success" pointer that was actually a small negative errno,
segfaulting on the first write.
- No TLS thread-pointer setup in crt0 (Alpha uses PALcode rduniq/
wruniq, not a syscall); the TCB header offset (16 bytes, Variant I)
was pinned empirically since neither the toolchain headers nor
glibc's own __tls_init_tp publish it.
- Alpha's signal numbers are OSF/1, not generic Linux (SIGCHLD=20 not
17, several others renumbered); the generic VMS_SIGCHLD sent as a
clone() exit signal produced EINVAL. Also removed a stale duplicate
`#define VMS_SIGCHLD 17` elsewhere in the file that was silently
clobbering the per-arch value via macro redefinition.
Gate: all 7 tests/libvmssys suites pass under qemu-alpha (standalone
`cmake -S src/libvmssys` configure, needed enable_language(ASM) and
enable_testing() added for that path). x86_64 (full-tree ctest,
BUILD_TESTS=ON) and aarch64 (standalone cross-compile) both unchanged
and still green.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
baron-3dl
force-pushed
the
work/vms-40b-alpha-stat
branch
from
August 16, 2026 20:46
6c1c607 to
c1dcb39
Compare
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.
Summary
Rung A1 of the OVMX-on-Alpha epic (rd
vms-40b). A0 landed the Alpha freestanding backend (src/libvmssys/arch/alpha/{crt0,syscall,sigreturn}.S+ the__alpha__syscall table) but deliberately leftstruct vms_statandstruct vms_sigactionundefined for Alpha, so any code path touching them failed loud (compiler warning) rather than silently reading a wrong layout. This PR defines both, and proves the wholetests/libvmssyssuite green underqemu-alpha.Struct layouts — provenance
Both verified byte-for-byte by compiling
offsetof/sizeofprobes against the verbatim struct definitions from the real kernel headers and running them underqemu-alpha(not derived from memory):struct vms_stat←arch/alpha/include/uapi/asm/stat.h,struct stat64, Linux 6.6.52 source (same header shipped by thegcc-alpha-linux-gnu/libc6-dev-alpha-crosscross toolchain). This is whatfstat64/fstatat64fill.struct vms_sigaction←arch/alpha/include/uapi/asm/signal.h,struct sigaction(same shape in glibc's alphabits/sigaction.h). Order is handler/mask/flags — not flags-then-mask like x86_64/aarch64 — and there is nosa_restorerfield.Wrapper fixes in
vms_syscall.h:vms_sys_fstatnow calls__NR_fstat64(427) instead of the old__NR_fstat(91, a narrower non-stat64 struct) — the known trap from the rung brief.vms_sys_rt_sigactiongets an Alpha-specific 5-arg body: Alpha'srt_sigactionisSYSCALL_DEFINE5(rt_sigaction, sig, act, oact, sigsetsize, restorer)— the restorer is an explicit 5th syscall argument, not a struct field.Four more pre-existing gaps found proving the gate
None of these are caused by the struct work above — all were already blocking
tests/libvmssysunder qemu-alpha before this PR, just invisible because nothing had tried to run the suite there yet.div/idiv-equivalent; GCC calls__divqu/__remqu. Added as hand-written assembly (arch/alpha/softdiv.S) because these use a non-standard calling convention (args in$24/$25, return address in$23not$26, result in$27, and — the part that cost real debugging time — the callee must preserve$1-$8because GCC's div+mod fusion (e.g.vms_snprintf.c'suint_to_str) keeps the original dividend live across the call in an otherwise-volatile register).__builtin_sqrt/floor/ceillowering on Alpha's GCC backend — always a libcall (confirmed via-Soutput even with-mieee). Added freestanding implementations (arch/alpha/softmath.c): schoolbook division, Newton-Raphson sqrt from a bit-halved exponent guess, IEEE-754 mantissa-mask floor/ceil. Both this and authenticity: INV-1 system-identity SSOT + logical-driven login banners (vms-e652) #1 must avoid glibc/libgcc (Rule 3), hence hand-rolled rather than linked from the cross sysroot.mmapflag bits are not the generic Linux ones (arch/alpha/include/uapi/asm/mman.h):MAP_FIXED/MAP_ANONYMOUS/MAP_NORESERVEall differ. With the generic values,test_vmssys_syscall's mmap test got a small negative errno back that didn't equalVMS_MAP_FAILED, so the test dereferenced it and segfaulted.rduniq/wruniq, not a syscall). The TCB header offset (16 bytes, Variant I) isn't published in the toolchain headers, and installed glibc's own__tls_init_tpnever callswruniqat all (it assumes the kernel already set "unique" for the initial thread — an assumption our freestanding CRT can't rely on). Pinned it empirically: a probe filled a scratch buffer with a marker at a known offset, sweptwruniq()across candidate base addresses, and asked a real__threadvariable (in a separate TU, so the compiler couldn't constant-fold it away) which value it read back. Exactly one offset matched.SIGCHLD=20, not 17; several others renumbered).test_vmssys_futex's clone()-based fork emulation passed the genericVMS_SIGCHLD(17, which is Alpha's realSIGSTOP) as the clone exit signal and gotEINVALback every time; Alpha's realSIGCHLD(20) succeeds. Also found and removed a stale duplicate#define VMS_SIGCHLD 17elsewhere invms_types.hthat was silently clobbering the per-arch value via macro redefinition.Gate — qemu-alpha evidence
The Alpha "declared inside parameter list" warnings are gone (confirmed clean
-Wall -Wextra -ffreestanding -fno-builtincompile of everysrc/libvmssys/*.c).Also needed (unrelated to the struct/ABI work, but required to make the qemu-alpha gate runnable at all):
enable_language(ASM)andenable_testing()whensrc/libvmssys/CMakeLists.txtis configured standalone (cmake -S src/libvmssys), which the alpha gate does — previously only exercised by the netbsd-vax path, which needs neither.x86_64 / aarch64 unchanged
cmake -B build -DCMAKE_BUILD_TYPE=Debug -DBUILD_TESTS=ON -DBUILD_TOOLS=ONconfigures clean;ctest -R vmssys→ 7/7 pass.-DCMAKE_SYSTEM_PROCESSOR=aarch64 -DCMAKE_C_COMPILER=aarch64-linux-gnu-gcc) builds clean, no warnings.Neither arch touches
softdiv.S/softmath.c(Alpha-only in CMakeLists) or the Alpha branches ofvms_types.h/vms_syscall.h/vms_runtime_init.c.Test plan
tests/libvmssyscross-compiles for alpha-linux-gnu with zero warnings/errorstests/libvmssyssuites pass underqemu-alpha(shown above)ctest -R vmssysunaffected (7/7 pass)🤖 Generated with Claude Code