nx_microscan_gate.nx
buildroot/runtime/nx_microscan_gate.nx
about
nx_microscan_gate.nx -- THE INVERSE MICRO-ANALYSER, GATED BY ROUND TRIP. Subject: nx_microscan_lib.
WHY A ROUND TRIP IS THE RIGHT REFEREE HERE, AND WHY IT NEEDS NO EXTERNAL GROUND TRUTH. The estate
already owns the FORWARD law: nx_relief_lib bakes a jittered-grid pore layer whose pitch, orifice
diameter and coverage are declared constants with a provenance ledger. So the honest test of an
INVERSE analyser is to hand it a field the shipped generator produced and ask it to recover the
number the generator was told -- WITHOUT the analyser importing any of it. nx_microscan_lib imports
nx_syscalls and nx_vecmath and nothing else; this gate imports the generator, synthesises the field,
and checks the recovered pitch against RLF_PORE_PITCH_UM. A wrong analyser cannot pass by knowing
the answer, because it has no way to see the answer.
AND IT IS CHECKED AT TWO LATTICE SCALES ON PURPOSE. A single scale can be satisfied by a constant.
T5 asserts the recovered period TRACKS the generator -- double the cell, double the answer -- which
is the property a hardcoded 800 provably cannot have.
THE TOOTH THE OPERATOR ACTUALLY ASKED FOR IS T8/T9: "does the hair come out of the pore properly".
That is a REGISTRATION question between two layers, and it is decidable today. T8 places follicles
through the generator's own centre function and must read BOUND. T9 places follicles by AREA
SAMPLING -- which is what nx_nxa_groom actually does, it samples scalp triangles by area and never
consults a pore field -- and must read DECOUPLED. Both directions, one bar, and the null is the
field's OWN measured coverage rather than an assumed rate.
THE TWO POINT SETS ARE DELIBERATELY DIFFERENT SIZES and that is the finding of the first run, not an
oversight. BOUND is a presence claim and carries on 256 points; DECOUPLED is an ABSENCE claim and
needs enough EXPECTED chance hits to have detected binding had it existed, which 256 points at a
12-permil chance rate does not provide. ms_reg_verdict abstains there, and the last neg-control
proves it abstains by handing it exactly that under-powered subset.
DECLARED RESOLUTION BAR, so no reading of this gate can be inflated into a clinical claim. The
fields here are synthetic and sampled at a texel derived from the generator's declared pitch. The
baked per-region asset carries a 50 um texel. Dermoscopic assessment of a pigmented lesion works at
roughly 10-20 um per pixel and reads COLOUR and PIGMENT NETWORK, not height. This organ measures a
height/thickness field for periodicity, layer registration and departure-from-self. It emits
candidates with scores. IT IS NOT A DIAGNOSIS OF ANYTHING and the melanoma bar is a statement of the
resolution we do not yet carry, not a capability claimed. The dermoscopy figure is SOURCE-UNPINNED
-- no reference was mirrored for this lane -- and that is stated in the verdict note too.
license_tier: ORIGINAL expect_exit: 0 No hw writes (Rule 26).
dependencies 4 imports · 0 importers
imports: nx_syscalls.nxnx_gate_verdict.nxnx_relief_lib.nxnx_microscan_lib.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
| 48 | const MG_W: i64 = 512 |
| 49 | const MG_H: i64 = 512 |
| 50 | const MG_CELL_A: i64 = 32 |
| 51 | const MG_CELL_B: i64 = 64 |
| 54 | const MG_TEXEL_A_UM: i64 = 25 |
| 55 | const MG_EXP_N_A: i64 = 256 // (MG_W / MG_CELL_A) squared |
| 56 | const MG_EXP_N_B: i64 = 64 // (MG_W / MG_CELL_B) squared |
| 58 | const MG_CAP: i64 = 4096 |
| 59 | const MG_BLK_CAP: i64 = 1024 |
| 60 | const MG_BS: i64 = 64 // anomaly block edge -> 8 x 8 = 64 blocks over the fixture |
| 61 | const MG_BW: i64 = 8 |
| 62 | const MG_PATCH_BX: i64 = 3 |
| 63 | const MG_PATCH_BY: i64 = 5 |
| 64 | const MG_PATCH_IDX: i64 = 43 // MG_PATCH_BY * MG_BW + MG_PATCH_BX |
| 67 | const MG_WALL_OK: i64 = 1000 |
| 68 | const MG_WALL_THIN: i64 = 400 |
| 69 | const MG_TEX_AMP: i64 = 20 // benign surface variation, so the robust scale is non-degenerate |
| 70 | const MG_TEX_LAT: i64 = 96 |
| 71 | const MG_K_MILLI: i64 = 3000 // three deviations |
| 76 | const MG_TOL_PERMIL: i64 = 4 |
| 79 | const MG_REG_BAR: i64 = 750 |
| 81 | const MG_HASH_X1: i64 = 101 |
| 82 | const MG_HASH_X2: i64 = 103 |
| 83 | const MG_HASH_Y1: i64 = 107 |
| 84 | const MG_HASH_Y2: i64 = 109 |
| 85 | const MG_SCATTER_SEED: i64 = 20260901 |
| 90 | const MG_AREA_STEP: i64 = 17 |
| 91 | const MG_AREA_OFF: i64 = 7 |
functions
| 93 | func mg_kv(k: *u8, v: i64) -> i64 { gv_puts(k); gv_num(v); gv_puts("\n" as *u8); return 0 } |
| 97 | func mg_fill_pore(f: *i64, cell: i64) -> i64 |
| 109 | func mg_fill_const(f: *i64, v: i64) -> i64 |
| 116 | func mg_fill_scatter(f: *i64, n: i64) -> i64 |
| 129 | func mg_fill_wall(f: *i64, textured: i64) -> i64 |
| 152 | func mg_place_bound(px: *i64, py: *i64, cell: i64) -> i64 |
| 180 | func mg_place_area(px: *i64, py: *i64) -> i64 called by 1: main |
| 196 | func main(argc: i64, argv: *i64) -> i64 |