test: prove package initialization semantics

This commit is contained in:
2026-08-14 19:02:49 +09:00
parent c6bec0914d
commit 763bbc8f25
24 changed files with 2243 additions and 349 deletions

View File

@@ -24,7 +24,7 @@ categories out of the ordinary developer target.
| --- | --- |
| Arena, lexer, parser, checker, module-decl parse, narrow codegen | Six in-process C unit binaries |
| Compile success/rejection, stage-routed diagnostics, and runtime exit | `test/wcc/data/*/case.ww`, executed by `wwfixture` |
| Package semantics | `test/package` and the native package-test coordinator |
| Package semantics | `test/package`, `test/sep/sepinit_test.ww`, and the native package-test coordinator |
| Language behavior | `test/lang/*_test.ww` through the language `@test` runtime |
| Library behavior | The package coordinator's `lib/...` tree walk (`ww test -j N lib/...`) |
| Standalone library-source compilation | Three import-free real source paths named by `LIBRARY_STANDALONE_SOURCES`, compiled directly by both frontends |
@@ -236,25 +236,41 @@ qualifier remain distinct. The alias matrix covers default and explicit-only
qualification, bare function/type/def/const/variable rejection with exact
unused-before-undefined diagnostics, same-file duplicate bindings, accepted
same-path imports under distinct bindings, alias reuse across files, sibling
scope isolation, package-declaration collisions, unused aliases, and explicit
blank-alias rejection. It also pins canonical `.wwi` spelling, archive/action
ownership, stage-equal diagnostics and binaries, and clean rejection state.
scope isolation, package-declaration collisions, unused aliases, blank
side-effect imports, repeated blank/default/explicit combinations, and blank
no-binding/no-unused behavior. It also pins canonical `.wwi` spelling,
archive/action ownership, one canonical direct edge for repeated occurrences,
stage-equal diagnostics and binaries, and clean rejection state.
The declared-name observer proves imports are file-scoped while dependency
edges are the package-wide sorted union; command and
production/internal/external/generated-main variants retain canonical action
ownership; vendor expansion changes identity but not the effective qualifier;
compiler argv contains only direct `.wwi` inputs; and its named rejected
actions leave neither committed nor staged action artifacts or a published
binary. It also forces a staged multi-artifact commit to fail after the
interface rename, then proves that both stages invalidate old unit vouchers and
reconsider the importer rather than accepting a mixed warm generation. A
separate injected stamp-removal failure proves the pre-commit gate leaves all
previously committed artifacts byte-identical.
binary. It also forces a request transaction to reject after dependency work
has staged, then proves that both stages restore every prior artifact, unit,
tool record, stamp, and product rather than accepting a mixed warm generation.
Together with the existing directory, recursive, vendor,
exact-argv, command, and persistent-workdir observers, the package suite proves
archive-only link argv and exact warm/rejection-state behavior without
duplicating those broader mechanisms in this observer.
`test/sep/sepinit_test.ww` is the single focused package-initialization owner.
It generates all source trees temporarily and runs independent cold/persistent
Cstage and WWstage legs. Its matrix covers blank-only reachability; dependency,
diamond, and independent ready-task order; runtime call/allocation and aggregate
package lets; multiple init declarations and invalid forms; direct/qualified
init invisibility; initialization cycles and diagnostic order; command,
internal-test, external-test, support, and generated-main ownership; canonical
task and dispatcher symbols; deterministic one- and two-member archives;
`.wwi` exclusion; byte-identical artifacts/binaries; init-only invalidation;
warm invalid-init rollback; direct/recursive variant equivalence; exact
production, support, and generated-main task ordering; complete normalized
rejection diagnostics; dangling staging/rollback no-follow rejection; and
checked compiler-output failure/non-regular-destination rollback; and
bounded-memory allocation-failure parity under one shared ceiling supplied by
the repository-built `sep-limitexec` helper.
`ww build`, an explicit single-file `ww test -o <stem>`, and each successful
directory-package `ww test -c` build publish `<stem>.sepwork` as a caller-owned
artifact directory. The driver acquires it with one fresh `mkdir` and refuses
@@ -279,13 +295,17 @@ no hashes, every decision reproducible with `cmp` against plain files. The
driver identity covers graph construction, owner-unit composition,
direct-export argument construction, archive creation, and commit algorithms
that neither unit bytes nor compiler identity can name.
Recompiled artifacts land at staged `.new` names and commit by rename with the
unit renamed last, so an interrupted build forces a recompile rather than a
false reuse; the link always reruns. One workdir serves one invocation at a
time and may hold the complete command-global action universe for all selected
roots and isolated variants; semantic identity, rather than request shape,
controls reuse. Both driver stages implement the identical contract. This is
build staleness in the Make/mk/Go sense, not a result cache:
Recompiled artifacts, dispatcher artifacts, products, statuses, tool copies,
and the stamp land at staged `.new` names. After every requested product stages
successfully, one rollback-capable transaction installs the whole generation;
any producer or installation failure preserves the prior committed bytes and
removes remaining stages. An interrupted or rejected request therefore cannot
create false reuse or a mixed generation; a successful executable link still
reruns when required. One workdir serves one invocation at a time and may hold
the complete command-global action universe for all selected roots and isolated
variants; semantic identity, rather than request shape, controls reuse. Both
driver stages implement the identical contract. This is build staleness in the
Make/mk/Go sense, not a result cache:
tests always run, and the byte-identity and bootstrap gates keep building on
fresh scratch. `make clean` reclaims every workdir under `out/`.