code wiki / (root) / nx_fieldfit_verified_canonical_gate_t333.nx

nx_fieldfit_verified_canonical_gate_t333.nx source

↩ module page · 292 lines · 17497 B

1// nx_fieldfit_gate.nx -- THE FIELD-FIT MACHINERY (nx_fieldfit_lib) ON A SYNTHETIC ORACLE WITH A KNOWN ANSWER 2// (anatomy AN17, 2026-09-19). The oracle is a point sphere of radius FG_R centred (FG_CX, FG_CY, FG_CZ), sampled on a 3// 10-degree lattice; the field is a sphere whose centre and radius are stations 0..3 of a five-station vector, with 4// station 4 a DECOY the field never reads and the live mask retires. Started from a wrong vector, the descent must 5// recover the centre and the radius to FG_TOL mm, must leave the decoy untouched, and must not move from the true 6// vector (a move accepted at the optimum is a broken accept rule). The fit file's prefix contract and the spatial 7// hash are held to exact answers. NEG-CONTROL: the two-sided objective must charge a shrunken sphere MORE than the 8// true one (a one-sided objective is gamed by deleting geometry; this is the tooth that cannot pass on one side). 9// license_tier: ORIGINAL. No hw writes (Rule 26). 10import "nx_syscalls.nx" 11import "nx_gate_verdict.nx" 12import "nx_sdfprim_lib.nx" 13import "nx_fieldfit_lib.nx" 14 15const FG_NP: i64 = 5 16const FG_NREG: i64 = 8 // the octants 17const FG_CAP: i64 = 4096 18const FG_EXT: i64 = 60 // the sphere (centre 8, radius 40) fits in +/- 60 19const FG_DIM: i64 = 12 20const FG_LAT: i64 = 6 21const FG_R: i64 = 40 22const FG_CX: i64 = 5 23const FG_CY: i64 = 0-3 24const FG_CZ: i64 = 8 25const FG_DECOY: i64 = 777 26const FG_WRONG_DX: i64 = 12 // the wrong start: centre x shifted, radius shrunk 27const FG_WRONG_R: i64 = 25 28const FG_SHRUNK_R: i64 = 20 // the neg-control's deleted geometry 29const FG_PASSES: i64 = 6 30const FG_STEP0: i64 = 8 31const FG_TOL: i64 = 2 // mm: the reverse lattice at 6 mm bounds the placement 32const FG_STEP_DEG: i64 = 10 33const FG_FILE: *u8 = "/tmp/nx_fieldfit_gate.fit" 34const FG_FILE3: *u8 = "/tmp/nx_fieldfit_gate.fit3" 35const FG_FILE2: *u8 = "/tmp/nx_fieldfit_gate.fit2" 36const FG_ABSENT: *u8 = "/tmp/nx_fieldfit_gate.absent" 37const FG_MODE644: i64 = 420 38 39func fg_field(px: i64, py: i64, pz: i64, a: i64, b: i64, P: *i64) -> i64 { 40 let dx: i64 = px - P[0] 41 let dy: i64 = py - P[1] 42 let dz: i64 = pz - P[2] 43 return (sp_isqrt(dx*dx + dy*dy + dz*dz) - P[3])*SP_FQ 44} 45func fg_region(x: i64, y: i64, z: i64) -> i64 { 46 var r: i64 = 0 47 if x >= 0 { r = r + 1 } 48 if y >= 0 { r = r + 2 } 49 if z >= 0 { r = r + 4 } 50 return r 51} 52func fg_live(k: i64) -> i64 { if k == 4 { return 0 } return 1 } 53const FG_EXTRA: i64 = 900 54func fg_extra(P: *i64) -> i64 { return FG_EXTRA } 55func fg_abs(v: i64) -> i64 { if v < 0 { return 0 - v } return v } 56// the oracle: points on the sphere at every 10 degrees of polar and azimuthal angle 57func fg_oracle(c: *FfCtx) -> i64 { 58 var n: i64 = 0 59 var th: i64 = 0 60 while th <= 180 { 61 var ph: i64 = 0 62 while ph < 360 { 63 let s: i64 = sp_isin(th) 64 let cth: i64 = sp_icos(th) 65 var cph: i64 = sp_icos(ph) 66 var sph: i64 = sp_isin(ph) 67 if ph > 180 { cph = 0 - sp_icos(ph - 180); sph = 0 - sp_isin(ph - 180) } 68 c.RX[n] = FG_CX + FG_R*s/SP_PERMILLE*cph/SP_PERMILLE 69 c.RY[n] = FG_CY + FG_R*s/SP_PERMILLE*sph/SP_PERMILLE 70 c.RZ[n] = FG_CZ + FG_R*cth/SP_PERMILLE 71 n = n + 1 72 ph = ph + FG_STEP_DEG 73 } 74 th = th + FG_STEP_DEG 75 } 76 c.n = n 77 return n 78} 79func fg_write(path: *u8, s: *u8) -> i64 { 80 var n: i64 = 0 81 while s[n] != (0 as u8) { n = n + 1 } 82 let fd: i64 = sys_openat_wr(path, FG_MODE644) 83 if fd < 0 { return 0 - 1 } 84 sys_write(fd, s, n) 85 sys_close(fd) 86 return n 87} 88 89 90func fg_valid(P: *i64, np: i64) -> i64 { if np != FG_NP { return 0 } if P[3] <= 0 { return 0 } return 1 } 91func fg_contract() -> *FfFitContract { 92 let C: *FfFitContract = sys_mmap(32) as *FfFitContract 93 C.header = "NXFFIT2 schema=sphere5 frame=xyz-mm producer=fixture reference=sphere-known objective=two-sided-v1\n" as *u8 94 C.header_bytes = 99 95 C.np = FG_NP; C.valid = fg_valid 96 return C 97} 98 99 100static FG_BAD_TRIAL: i64 101func fg_decoy_live(k: i64) -> i64 { if k == 4 { return 1 } return 0 } 102func fg_bound_valid(P: *i64, np: i64) -> i64 { if P[4] < 0 { FG_BAD_TRIAL = FG_BAD_TRIAL + 1; return 0 } return fg_valid(P, np) } 103 104 105const FG_REPEAT_LOADS: i64 = 100 106const FG_STATUS_BYTES: i64 = 4096 107func fg_vm_kb(b: *u8) -> i64 { 108 let fd: i64=sys_openat_rd("/proc/self/status" as *u8) 109 if fd < 0 { return 0 - 1 } 110 let n: i64=sys_read(fd,b,FG_STATUS_BYTES);sys_close(fd) 111 let key: *u8="VmSize:" as *u8 112 var i: i64=0 113 while i+7<n { 114 var k: i64=0;var same: i64=1 115 while k<7 { if b[i+k]!=key[k] { same=0 } k=k+1 } 116 if same==1 { i=i+7; while i<n { if b[i]>=48 && b[i]<=57 { var v: i64=0;while i<n { if b[i]<48 || b[i]>57 { return v } v=v*10+(b[i] as i64)-48;i=i+1 } return v } i=i+1 } return 0-1 } 117 i=i+1 118 } 119 return 0-1 120} 121 122func main(argc: i64, argv: *i64) -> i64 { 123 gv_head("nx_fieldfit_gate: the field-fit machinery recovers a known sphere from a wrong start, honours the live mask, and keeps the fit-file prefix contract" as *u8) 124 let ctr: *i64 = gv_ctr() 125 let C: *FfCtx = ff_ctx_new(FG_NP, FG_NREG, FG_CAP, FG_EXT, FG_DIM, FG_LAT, SP_FQ) 126 C.field = fg_field 127 C.region = fg_region 128 C.live = fg_live 129 let n: i64 = fg_oracle(C) 130 gv_check("oracle-sampled-a-nonempty-sphere" as *u8, (n > 100) as i64, ctr) 131 ff_bin(C) 132 ff_regions(C) 133 // every octant is populated: the balance has eight regions to balance 134 var reg_ok: i64 = 1 135 var r: i64 = 0 136 while r < FG_NREG { 137 var seen: i64 = 0 138 var i: i64 = 0 139 while i < n { if C.RG[i] == r { seen = 1 } i = i + 1 } 140 if seen == 0 { reg_ok = 0 } 141 r = r + 1 142 } 143 gv_check("every-region-holds-oracle-samples" as *u8, reg_ok, ctr) 144 // ---- the spatial hash ---- 145 gv_check_eq("nearest-oracle-sample-to-a-sample-is-itself" as *u8, ff_near(C, C.RX[0], C.RY[0], C.RZ[0]), 0, ctr) 146 gv_check_eq("nearest-sample-7mm-radially-outside-the-pole-reads-7" as *u8, ff_near(C, FG_CX, FG_CY, FG_CZ + FG_R + 7), 7, ctr) 147 gv_check_eq("live-count-excludes-the-decoy" as *u8, ff_live_count(C), FG_NP - 1, ctr) 148 // ---- the objective ---- 149 let T: *i64 = sys_mmap(FG_NP*FF_I64) as *i64 150 T[0] = FG_CX; T[1] = FG_CY; T[2] = FG_CZ; T[3] = FG_R; T[4] = FG_DECOY 151 let s_true: i64 = ff_score2(C, T) 152 let W: *i64 = sys_mmap(FG_NP*FF_I64) as *i64 153 W[0] = FG_CX; W[1] = FG_CY; W[2] = FG_CZ; W[3] = FG_SHRUNK_R; W[4] = FG_DECOY 154 let s_shrunk: i64 = ff_score2(C, W) 155 gv_check("true-vector-scores-under-one-lattice-step" as *u8, (s_true < FG_LAT*FF_CENTI) as i64, ctr) 156 gv_bite("neg-control-a-shrunken-sphere-is-charged-more-than-the-true-one" as *u8, (s_shrunk > s_true) as i64, (s_true > s_true) as i64, ctr) 157 // the forward side alone reads the shrink as its whole depth: the two-sided mean must exceed the forward side of the truth 158 // the fixture's own radius, MEASURED: integer point generation lands the samples a few mm inside the nominal sphere, 159 // so the shrink is read against the mean radius the points actually have, never against the number typed above 160 var rsum: i64 = 0 161 var ri: i64 = 0 162 while ri < n { 163 let ddx: i64 = C.RX[ri] - FG_CX 164 let ddy: i64 = C.RY[ri] - FG_CY 165 let ddz: i64 = C.RZ[ri] - FG_CZ 166 rsum = rsum + sp_isqrt(ddx*ddx + ddy*ddy + ddz*ddz) 167 ri = ri + 1 168 } 169 let mean_r: i64 = rsum / n 170 let fwd_shrunk: i64 = ff_score_fwd(C, W) 171 gv_check_near("shrunken-forward-term-reads-the-measured-shrink-in-centi-mm" as *u8, fwd_shrunk, (mean_r - FG_SHRUNK_R)*FF_CENTI, FF_CENTI, ctr) 172 // ---- the descent from a wrong start ---- 173 let P: *i64 = sys_mmap(FG_NP*FF_I64) as *i64 174 P[0] = FG_CX + FG_WRONG_DX; P[1] = FG_CY; P[2] = FG_CZ; P[3] = FG_WRONG_R; P[4] = FG_DECOY 175 let s_start: i64 = ff_score2(C, P) 176 let best: i64 = ff_descend(C, P, FG_PASSES, FG_STEP0, 0) 177 gv_check("descent-lowered-the-measured-objective" as *u8, (best < s_start) as i64, ctr) 178 gv_check_near("descent-recovered-the-centre-x" as *u8, P[0], FG_CX, FG_TOL, ctr) 179 gv_check_near("descent-recovered-the-centre-y" as *u8, P[1], FG_CY, FG_TOL, ctr) 180 gv_check_near("descent-recovered-the-centre-z" as *u8, P[2], FG_CZ, FG_TOL, ctr) 181 gv_check_near("descent-recovered-the-radius" as *u8, P[3], FG_R, FG_TOL, ctr) 182 gv_check_eq("descent-left-the-retired-decoy-untouched" as *u8, P[4], FG_DECOY, ctr) 183 gv_check_eq("best-is-the-objective-of-the-vector-returned" as *u8, ff_score2(C, P) - best, 0, ctr) 184 // ---- neg-control: from the truth, nothing moves ---- 185 let Q: *i64 = sys_mmap(FG_NP*FF_I64) as *i64 186 Q[0] = FG_CX; Q[1] = FG_CY; Q[2] = FG_CZ; Q[3] = FG_R; Q[4] = FG_DECOY 187 let b2: i64 = ff_descend(C, Q, 2, FG_STEP0, 0) 188 gv_check("neg-control-descent-from-the-truth-stays-within-a-millimetre" as *u8, ((fg_abs(Q[0]-FG_CX) <= 1) * (fg_abs(Q[3]-FG_R) <= 1)) as i64, ctr) 189 gv_check("neg-control-descent-from-the-truth-does-not-raise-the-objective" as *u8, (b2 <= s_true) as i64, ctr) 190 // ---- the optional third term: a constant extra of 900 centi folds in as the three-way mean ---- 191 C.extra = fg_extra 192 C.has_extra = 1 193 let s3: i64 = ff_score2(C, T) 194 let f3: i64 = ff_score_fwd(C, T) 195 let r3: i64 = ff_score_rev(C, T) 196 gv_check_eq("extra-term-folds-in-as-the-three-way-mean" as *u8, s3, (f3 + r3 + FG_EXTRA)/3, ctr) 197 C.has_extra = 0 198 gv_check_eq("extra-term-off-restores-the-two-way-mean" as *u8, ff_score2(C, T), (f3 + r3)/2, ctr) 199 // ---- the fit file ---- 200 gv_check_eq("absent-fit-file-applies-nothing" as *u8, ff_load_prefix(FG_ABSENT, Q, FG_NP, 3), 0, ctr) 201 let wrote: i64 = ff_save(FG_FILE, P, FG_NP) 202 gv_check("save-wrote-bytes" as *u8, (wrote > 0) as i64, ctr) 203 let R: *i64 = sys_mmap(FG_NP*FF_I64) as *i64 204 R[0] = 1; R[1] = 2; R[2] = 3; R[3] = 4; R[4] = 5 205 gv_check_eq("save-then-load-applies-the-whole-vector" as *u8, ff_load_prefix(FG_FILE, R, FG_NP, 3), FG_NP, ctr) 206 gv_check_eq("save-then-load-round-trips-every-station" as *u8, (R[0]-P[0]) + (R[1]-P[1]) + (R[2]-P[2]) + (R[3]-P[3]) + (R[4]-P[4]), 0, ctr) 207 fg_write(FG_FILE3, "11\n-22\n33\n" as *u8) 208 R[0] = 0; R[1] = 0; R[2] = 0; R[3] = 4; R[4] = 5 209 gv_check_eq("a-three-int-file-applies-a-prefix-of-three" as *u8, ff_load_prefix(FG_FILE3, R, FG_NP, 3), 3, ctr) 210 gv_check_eq("the-prefix-lands-with-its-sign" as *u8, R[1], 0-22, ctr) 211 gv_check_eq("stations-past-the-prefix-keep-their-defaults" as *u8, R[3] + R[4], 9, ctr) 212 fg_write(FG_FILE2, "11\n22\n" as *u8) 213 R[0] = 0; R[1] = 0 214 gv_check_eq("a-file-shorter-than-minlen-applies-nothing" as *u8, ff_load_prefix(FG_FILE2, R, FG_NP, 3), 0, ctr) 215 gv_check_eq("a-refused-short-file-leaves-the-vector-unchanged" as *u8, R[0] + R[1], 0, ctr) 216 217 var VC: *FfFitContract = fg_contract() 218 gv_check_eq("verified-reader-classifies-legacy-without-applying" as *u8, ff_load_verified(FG_FILE, R, VC), FF_FIT_LEGACY_UNVERIFIED, ctr) 219 gv_check("verified-save-positive-domain" as *u8, (ff_save_verified(FG_FILE, P, VC) > 0) as i64, ctr) 220 gv_check_eq("verified-roundtrip-exact-vector" as *u8, ff_load_verified(FG_FILE, R, VC), FG_NP, ctr) 221 gv_check_eq("verified-roundtrip-radius" as *u8, R[3], P[3], ctr) 222 let bad: i64 = R[3] 223 R[3] = 0 - 9 224 gv_check_eq("negative-radius-save-refused" as *u8, ff_save_verified(FG_FILE2, R, VC), FF_FIT_INVALID, ctr) 225 gv_check_eq("negative-initial-descent-refused" as *u8, ff_descend_checked(C, R, 1, 8, 0, fg_valid), FF_FIT_INVALID, ctr) 226 gv_check_eq("invalid-descent-preserves-input" as *u8, R[3], 0 - 9, ctr) 227 R[3] = bad 228 let vbest: i64 = ff_descend_checked(C, R, 1, 8, 0, fg_valid) 229 gv_check("checked-descent-keeps-domain" as *u8, fg_valid(R, FG_NP), ctr) 230 gv_check_eq("checked-descent-returns-real-objective" as *u8, vbest, ff_score2(C, R), ctr) 231 VC.header = "NXFFIT2 schema=sphere5 frame=zyx-mm producer=fixture reference=sphere-known objective=two-sided-v1\n" as *u8 232 gv_check_eq("wrong-coordinate-frame-refused" as *u8, ff_load_verified(FG_FILE, R, VC), FF_FIT_CONTRACT_MISMATCH, ctr) 233 VC = fg_contract() 234 fg_write(FG_FILE2, "NXFFIT2 schema=sphere5 frame=xyz-mm producer=fixture reference=sphere-known objective=two-sided-v1\n1\n2\n3\n" as *u8) 235 gv_check_eq("verified-truncated-refused" as *u8, ff_load_verified(FG_FILE2, R, VC), FF_FIT_MALFORMED, ctr) 236 fg_write(FG_FILE2, "NXFFIT2 schema=sphere5 frame=xyz-mm producer=fixture reference=sphere-known objective=two-sided-v1\n1\n2\n3\n4\n5\n6\n" as *u8) 237 gv_check_eq("verified-extra-refused" as *u8, ff_load_verified(FG_FILE2, R, VC), FF_FIT_MALFORMED, ctr) 238 fg_write(FG_FILE2, "NXFFIT2 schema=sphere5 frame=xyz-mm producer=fixture reference=sphere-known objective=two-sided-v1\n1\n2\n3\n4x\n5\n" as *u8) 239 gv_check_eq("verified-garbage-refused" as *u8, ff_load_verified(FG_FILE2, R, VC), FF_FIT_MALFORMED, ctr) 240 fg_write(FG_FILE2, "NXFFIT2 schema=sphere5 frame=xyz-mm producer=fixture reference=sphere-known objective=two-sided-v1\n1\n2\n3\n9223372036854775808\n5\n" as *u8) 241 gv_check_eq("verified-overflow-refused" as *u8, ff_load_verified(FG_FILE2, R, VC), FF_FIT_MALFORMED, ctr) 242 fg_write(FG_FILE2, "NXFFIT2 schema=sphere5 frame=xyz-mm producer=fixture reference=sphere-known objective=two-sided-v1\n1\n2\n3\n-9\n5\n" as *u8) 243 gv_check_eq("verified-negative-radius-refused" as *u8, ff_load_verified(FG_FILE2, R, VC), FF_FIT_INVALID, ctr) 244 245 gv_check_eq("refused-files-preserve-vector-x" as *u8, R[0], P[0], ctr) 246 gv_check_eq("refused-files-preserve-vector-y" as *u8, R[1], P[1], ctr) 247 gv_check_eq("refused-files-preserve-vector-z" as *u8, R[2], P[2], ctr) 248 gv_check_eq("refused-files-preserve-vector-radius" as *u8, R[3], P[3], ctr) 249 gv_check_eq("refused-files-preserve-vector-decoy" as *u8, R[4], P[4], ctr) 250 R[4] = FF_FIT_I64_POS_LIMIT 251 C.live = fg_decoy_live; FG_BAD_TRIAL = 0 252 let overflow_best: i64 = ff_descend_checked(C, R, 1, 8, 0, fg_bound_valid) 253 gv_check_eq("overflow-trial-never-reaches-validator" as *u8, FG_BAD_TRIAL, 0, ctr) 254 gv_check_eq("overflow-trial-keeps-vector" as *u8, R[4], FF_FIT_I64_POS_LIMIT, ctr) 255 gv_check_eq("overflow-trial-keeps-actual-objective" as *u8, overflow_best, ff_score2(C, R), ctr) 256 C.live = fg_live; R[4] = P[4] 257 gv_check_eq("negative-step-refused" as *u8, ff_descend_checked(C, R, 1, 0 - 8, 0, fg_valid), FF_FIT_INVALID, ctr) 258 fg_write(FG_FILE2, "NXFFIT2 schema=sphere5 frame=xyz-mm producer=fixture reference=sphere-known objective=two-sided-v1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n1\n" as *u8) 259 gv_check_eq("oversized-file-refused-before-file-sized-allocation" as *u8, ff_load_verified(FG_FILE2, R, VC), FF_FIT_MALFORMED, ctr) 260 261 let keep_np: i64 = VC.np 262 VC.np = FF_FIT_I64_POS_LIMIT 263 gv_check_eq("overflowing-contract-count-refused" as *u8, ff_load_verified(FG_FILE, R, VC), FF_FIT_CONTRACT_MISMATCH, ctr) 264 VC.np = keep_np 265 let keep_header: i64 = VC.header_bytes 266 VC.header_bytes = FF_FIT_I64_POS_LIMIT 267 gv_check_eq("overflowing-header-plus-sentinel-refused" as *u8, ff_load_verified(FG_FILE, R, VC), FF_FIT_CONTRACT_MISMATCH, ctr) 268 VC.header_bytes = keep_header 269 gv_check_eq("atomic-fit-crash-before-rename-preserves-published-file" as *u8, ar_crashwrite(FG_FILE, "torn" as *u8, 4), 0, ctr) 270 gv_check_eq("atomic-fit-old-file-still-valid-after-staging-crash" as *u8, ff_load_verified(FG_FILE, R, VC), FG_NP, ctr) 271 gv_check_eq("atomic-fit-old-radius-still-intact" as *u8, R[3], P[3], ctr) 272 273 let vmb: *u8=sys_mmap(FG_STATUS_BYTES) 274 fg_write(FG_FILE2, "NXFFIT2 schema=sphere5 frame=xyz-mm producer=fixture reference=sphere-known objective=two-sided-v1\n1\n2\n3\n-9\n5\n" as *u8) 275 let vm_before: i64=fg_vm_kb(vmb) 276 var rep: i64=0;var load_ok: i64=1 277 while rep<FG_REPEAT_LOADS { if ff_load_verified(FG_FILE,R,VC)!=FG_NP { load_ok=0 } if ff_load_verified(FG_FILE2,R,VC)!=FF_FIT_INVALID { load_ok=0 } rep=rep+1 } 278 let vm_after: i64=fg_vm_kb(vmb) 279 gv_check("repeated-valid-and-refused-loads-return-correct-status" as *u8,load_ok,ctr) 280 gv_check("process-vmsize-readable" as *u8,(vm_before>0 && vm_after>0) as i64,ctr) 281 gv_check_eq("repeated-reader-success-refusal-retains-no-mappings" as *u8,vm_after,vm_before,ctr) 282 gv_values_head() 283 gv_kv("oracle_samples" as *u8, n) 284 gv_kv("score_true_centi" as *u8, s_true) 285 gv_kv("score_shrunk_centi" as *u8, s_shrunk) 286 gv_kv("score_shrunk_fwd_centi" as *u8, fwd_shrunk) 287 gv_kv("fixture_mean_radius_mm" as *u8, mean_r) 288 gv_kv("score_start_centi" as *u8, s_start) 289 gv_kv("score_best_centi" as *u8, best) 290 gv_kv("recovered_cx" as *u8, P[0]); gv_kv("recovered_cy" as *u8, P[1]); gv_kv("recovered_cz" as *u8, P[2]); gv_kv("recovered_r" as *u8, P[3]) 291 return gv_verdict("nx_fieldfit_gate" as *u8, ctr, "one optimiser and one two-sided region-balanced objective for every anatomy field, proven on a sphere with a known answer" as *u8) 292}