nx_import_qualified_gate.nx
buildroot/runtime/nx_import_qualified_gate.nx
about
nx_import_qualified_gate.nx -- LN14 QUALIFIED IMPORTS: the referee for
runtime/nx_import.nx's `import "m.nx" as ns` / `ns::name` rung.
WHAT IT PROVES, and the shape of the proof:
1. THE CENSUS IS MEASURED, NOT INHERITED. The matrix row this rung hangs off
cites "22 shadow collisions found 2026-06-23". That number is a
measurement with a date on it, so this gate RE-TAKES it every run over the
full population of runtime/ and runtime/_hdl_build/ (composing
nx_janitor_dupname, the organ that already owns that walk -- there is no
second ruler here) and prints what it finds, with the SHADOW/COPY/
UNREADABLE partition reconciled against the total.
2. A REAL COLLISION FROM THAT CENSUS IS THE FIXTURE. The gate picks the first
collision whose two copies genuinely DIFFER and which declares at least one
top-level name in BOTH copies, then compiles two programs that import both
copies: one plainly, one with the _hdl_build copy qualified. Plain must
fail; qualified must build clean. The candidate is checked for solo
buildability FIRST, so a RED cannot be a red for some unrelated reason.
3. TWO REAL COMPILERS, NOT A SYNTHESISED MUTANT. Every fixture is built with
the CHALLENGER passed in argv AND with the live baseline
_offc/nx_cc_sovereign.elf. The qualified program must build under the
challenger and must be REFUSED by the baseline: that pair is the bite, and
neither half is available to a gate that only ever sees one compiler.
4. EVERY REFUSAL NAMES ITS RULE. The three neg-controls do not merely check
"was it refused" -- each greps the compiler's own stderr for the exact
rule token nx_import.nx emits (ALIAS-UNKNOWN-NAMESPACE,
ALIAS-NO-SUCH-EXPORT, ALIAS-MODULE-ALREADY-IMPORTED). A mutant that
disabled one check but still refused for a different reason passes a
"was it refused" suite and fails this one.
5. POSITIVE CONTROLS, BECAUSE A GUARD THAT REFUSES EVERYTHING PASSES EVERY
NEGATIVE TEST. An ordinary unaliased fixture must BUILD AND RUN under both
compilers, and the shipping resolver must still resolve every import edge
in the compiler's own closure, bound to the count of files it spliced.
Without those, a noexec mount or a missing assembler reads as a verdict
about the language.
dependencies 5 imports · 0 importers
imports: nx_syscalls.nxnx_gate_verdict.nxnx_ccbuild_lib.nxnx_import.nxnx_janitor_dupname.nx
imported by: nobody (leaf or entry point)
call flow from main pre-order; caps 40 nodes / depth 6 declared; ↻ = already shown
structs
| none |
consts
| 92 | const IQ_JDN_MAXK: i64 = 30000 |
| 94 | const IQ_NAME_MAX: i64 = 256 |
| 97 | const IQ_EXPAND_CAP: i64 = 4194304 |
| 100 | const IQ_PAIR_CAP: i64 = 4194304 |
| 103 | const IQ_FIXTURE_CAP: i64 = 4096 |
| 104 | const IQ_PATH_CAP: i64 = 1024 |
| 105 | const IQ_MODE_644: i64 = 420 |
| 106 | const IQ_MODE_755: i64 = 493 |
| 108 | const IQ_STATUS_SHIFT: i64 = 256 |
| 109 | const IQ_BYTE: i64 = 256 |
functions
| 116 | func iq_slen(s: *u8) -> i64 { var n: i64 = 0; while s[n] != (0 as u8) { n = n + 1 } return n } called by 1: iq_contains |
| 118 | func iq_cat(d: *u8, o: i64, s: *u8) -> i64 |
| 124 | func iq_catb(d: *u8, o: i64, b: i64) -> i64 { d[o] = b as u8; return o + 1 } |
| 130 | func iq_imp(d: *u8, o: i64, name: *u8) -> i64 |
| 138 | func iq_imp_as(d: *u8, o: i64, name: *u8, ns: *u8) -> i64 |
| 151 | func iq_put(path: *u8, body: *u8, n: i64) -> i64 |
| 162 | func iq_contains(path: *u8, needle: *u8) -> i64 |
| 186 | func iq_join(out: *u8, a: *u8, b: *u8) -> i64 |
| 193 | func iq_exit_code(st: i64) -> i64 called by 1: main |
| 198 | func iq_kv(k: *u8, v: i64) -> i64 |
| 210 | func iq_build(cc: *u8, src: *u8, tag: *u8, envp: *i64, elf_out: *u8, cclog: *u8) -> i64 |
| 236 | func iq_shared_syms(ctx: *ExpandCtx, k: i64, j: i64) -> i64 |
| 251 | func main(argc: i64, argv: *i64) -> i64 |