code wiki / _hdl_build / nx_footcheck.nx

nx_footcheck.nx source

↩ module page · 369 lines · 18886 B

1// nx_footcheck.nx -- ★THE DISTAL-LIMB STRUCTURE JUDGE (beyond-metahuman program). 2// 3// WHY THIS EXISTS, and it is a correction of my own work. I filed seq1038 claiming the toes had NO part 4// header of their own and that the emitter therefore lofted ONE continuous ribbon weaving foot->toe1->toe2. 5// That was WRONG. Reading the GENERATED canon (knowledge/canon_gx34r.dat) shows six part headers in the 6// foot's rotated frame -- one tube plus five separate toe tubes -- exactly as emitDigitP intends. I had 7// misread my own probe output: the probe printed the OWNING part beside each ring, and because all six 8// headers are BYTE-IDENTICAL (`P 1 90 48 40 -41 0`, since every toe inherits the foot frame and carries its 9// spread in the ring xoff) I read six identical headers as one repeated header. 10// 11// ★★★THE LAW THAT COST ME: READING THE GENERATED DATA IS NOT ENOUGH IF THE THING YOU ARE COUNTING IS 12// INDISTINGUISHABLE FROM ITS NEIGHBOUR. Print the INDEX, not just the row. A judge that a human eye has to 13// disambiguate is a judge that will be misread -- so the answer is this organ: the count is MEASURED. 14// 15// ★AND THE REAL DEFECT, which the numbers give up immediately once you subtract them: 16// foot tube runs y 0 -> 145 toes are based at y 118 and reach y 152 (hallux) 17// so 27 of each toe's 34 units are BURIED INSIDE THE FOOT TUBE. Only 7 units of the hallux clear the tube 18// at all, and the fifth toe ends at 128 -- seventeen units SHORT of the tube's own tip, entirely invisible. 19// That is the "blunt hoof with pale nubs" the render shows. nx_body_proc even carries the correct 20// instruction in a comment -- "toes must REPLACE the flat toe-plate, not extend past it" -- and only the 21// second half was ever applied: the toes were shortened to fit inside a plate that should have been deleted. 22// ★A HALF-APPLIED FIX IS INDISTINGUISHABLE FROM NO FIX, AND IT LOOKS LIKE A DONE ONE IN THE SOURCE. 23// 24// A second, smaller defect falls out of the same subtraction. Read along the foot the quantity (zoff + rb) 25// -- the sole side of every ring -- and the tube holds a CONSTANT 40: a flat sole, correct. The toes give 26// 43. The toes hang three units BELOW the sole plane, so the figure's ground contact is its toe tips. 27// 28// WHAT IT MEASURES (all from the canon text, no rendering, no mesh, no third party): 29// burial tube_end - toe_base must be <= 0: the tube must END where the toes BEGIN 30// protrusion foot_len - tube_end must be >= 20% of foot length -- toes are a fifth of a foot 31// sole break max(zoff+rb) toes - same tube must be <= 0: no toe may pierce the sole plane 32// foot length max y over the WHOLE group ★INVARIANT -- silhouette-critical, must not move when fixed 33// The last one is the regression guard the source comment asked for and never got: a previous round grew 34// the toes to y 174, the height-normalised side silhouette fell 831 -> 723, and the lesson was written down 35// as prose instead of as a test. Prose does not fail a build. 36// 37// nx_footcheck check <canon.dat> [rot] -> the measured report + verdict for a real artifact 38// nx_footcheck selftest -> gv gate: proves the JUDGE discriminates, on fixtures 39// license_tier: ORIGINAL expect_exit: 0 No hw writes (Rule 26). 40import "nx_gate_verdict.nx" 41const FC_MAGIC_1000000: i64 = 1000000 42 43const FC_MAXP: i64 = 256 44const FC_MAXR: i64 = 4096 45const FC_PROT: i64 = 16 46const FC_RP: i64 = 272 47const FC_RY: i64 = 4368 48const FC_RX: i64 = 8464 49const FC_RZ: i64 = 12560 50const FC_RA: i64 = 16656 51const FC_RB: i64 = 20752 52const FC_SZ: i64 = 24848 53const FC_Q: i64 = 1000 54// ★DERIVED, NOT DIALLED: the toes of a human foot are ~28% of foot length (heel-to-metatarsal-head is ~72% 55// of heel-to-hallux). 200 per-mille is that figure with room for the stylisation knobs to shorten it; below 56// a fifth the digits have stopped being toes and become bumps on a plate. 57const FC_MINPROT: i64 = 200 58const FC_NTOE: i64 = 5 59const FC_ROTFOOT: i64 = 90 60const FC_OUT: i64 = 16 61 62func fc_puts(s: *u8) -> i64 { var n: i64=0; while s[n]!=(0 as u8){n=n+1} sys_write(1,s,n); return 0 } 63func fc_pn(v: i64) -> i64 { 64 let b: *u8 = sys_mmap(32); var x: i64=v; var ng: i64=0 65 if x<0 { ng=1; x=0-x } 66 var i: i64=31 67 if x==0 { b[i]=48 as u8; i=i-1 } 68 while x>0 { b[i]=(48+x%10) as u8; x=x/10; i=i-1 } 69 if ng==1 { b[i]=45 as u8; i=i-1 } 70 sys_write(1,(b as i64 + i + 1) as *u8, 31-i); return 0 71} 72func fc_streq(a: *u8, b: *u8) -> i64 { 73 var i: i64=0; var go: i64=1; var eq: i64=1 74 while go==1 { if a[i]!=b[i] { eq=0; go=0 } else { if a[i]==(0 as u8) { go=0 } else { i=i+1 } } } 75 return eq 76} 77func fc_slen(s: *u8) -> i64 { var n: i64=0; while s[n]!=(0 as u8){n=n+1} return n } 78func fc_atoi(s: *u8) -> i64 { 79 var i: i64=0; var n: i64=0; var sg: i64=1 80 if s[0]==(45 as u8) { sg=0-1; i=1 } 81 while s[i]!=(0 as u8) { let c: i64=s[i] as i64; if c>=48 { if c<=57 { n=n*10+(c-48) } } i=i+1 } 82 return n*sg 83} 84// every integer on the half-open byte range [s,e), in order. A leading '-' counts only when a digit follows, 85// so the '-' in a comment rule or a word never starts a phantom number. 86func fc_lineints(b: *u8, s: i64, e: i64, out: *i64, maxn: i64) -> i64 { 87 var n: i64 = 0 88 var i: i64 = s 89 while i < e { 90 let c: i64 = b[i] as i64 91 var start: i64 = 0 92 var neg: i64 = 0 93 if c == 45 { 94 if i+1 < e { let d: i64 = b[i+1] as i64 95 if d >= 48 { if d <= 57 { start = 1; neg = 1 } } } 96 } else { 97 if c >= 48 { if c <= 57 { start = 1 } } 98 } 99 if start == 1 { 100 var j: i64 = i 101 if neg == 1 { j = j + 1 } 102 var v: i64 = 0 103 var run: i64 = 1 104 while run == 1 { 105 var ok: i64 = 0 106 if j < e { let d2: i64 = b[j] as i64 107 if d2 >= 48 { if d2 <= 57 { ok = 1 } } } 108 if ok == 1 { v = v*10 + ((b[j] as i64) - 48); j = j + 1 } else { run = 0 } 109 } 110 if neg == 1 { v = 0 - v } 111 if n < maxn { out[n] = v; n = n + 1 } 112 i = j 113 } else { i = i + 1 } 114 } 115 return n 116} 117// canon text -> parallel arrays. Only the FIRST non-space character of a line selects the rule, so a '#' 118// comment can say anything at all without being parsed as geometry. 119func fc_parse(b: *u8, sz: i64, A: *i64) -> i64 { 120 A[0] = 0 121 A[1] = 0 122 let tmp: *i64 = sys_mmap(128) as *i64 123 var i: i64 = 0 124 while i < sz { 125 var j: i64 = i 126 var run: i64 = 1 127 while run == 1 { 128 if j >= sz { run = 0 } else { if b[j] == (10 as u8) { run = 0 } else { j = j + 1 } } 129 } 130 var k: i64 = i 131 var sp: i64 = 1 132 while sp == 1 { 133 if k >= j { sp = 0 } else { 134 if b[k] == (32 as u8) { k = k + 1 } else { 135 if b[k] == (13 as u8) { k = k + 1 } else { sp = 0 } } } 136 } 137 if k < j { 138 let c0: i64 = b[k] as i64 139 if c0 == 80 { 140 let n: i64 = fc_lineints(b, k+1, j, tmp, 8) 141 if A[0] < FC_MAXP { 142 var rot: i64 = 0 143 if n >= 2 { rot = tmp[1] } 144 A[FC_PROT + A[0]] = rot 145 A[0] = A[0] + 1 146 } 147 } 148 if c0 == 82 { 149 let n2: i64 = fc_lineints(b, k+1, j, tmp, 8) 150 if n2 >= 5 { if A[1] < FC_MAXR { if A[0] > 0 { 151 let r: i64 = A[1] 152 A[FC_RP+r] = A[0] - 1 153 A[FC_RY+r] = tmp[0] 154 A[FC_RX+r] = tmp[1] 155 A[FC_RZ+r] = tmp[2] 156 A[FC_RA+r] = tmp[3] 157 A[FC_RB+r] = tmp[4] 158 A[1] = r + 1 159 } } } 160 } 161 } 162 i = j + 1 163 } 164 return 0 165} 166// out[0]=group parts [1]=ntoes [2]=foot_len [3]=tube_end [4]=toe_base [5]=protrusion [6]=burial 167// out[7]=tube_sole [8]=toe_sole [9]=sole_break [10]=prot_permil [11]=tube part [12]=rings in group 168// ★THE GROUP IS SELECTED BY ITS ROTATED FRAME, not by a part index. A foot is the only part of a standing 169// figure whose placement is rotated out of the body axis, so `rot` identifies it structurally -- the judge 170// keeps working when parts are added or reordered ahead of it, which an index would not. 171// ★THE TUBE IS THE MEMBER WITH THE MOST RINGS. A digit is four rings by rule; the foot is seven. Again 172// structural: nothing here knows which part index the foot happens to occupy. 173func fc_measure(A: *i64, rot: i64, out: *i64) -> i64 { 174 var z: i64 = 0 175 while z < FC_OUT { out[z] = 0; z = z + 1 } 176 let np: i64 = A[0] 177 let nr: i64 = A[1] 178 let cnt: *i64 = sys_mmap(FC_MAXP*8) as *i64 179 let pmaxy: *i64 = sys_mmap(FC_MAXP*8) as *i64 180 let pminy: *i64 = sys_mmap(FC_MAXP*8) as *i64 181 let psole: *i64 = sys_mmap(FC_MAXP*8) as *i64 182 var p: i64 = 0 183 while p < FC_MAXP { cnt[p]=0; pmaxy[p]=0-FC_MAGIC_1000000; pminy[p]=FC_MAGIC_1000000; psole[p]=0-FC_MAGIC_1000000; p = p + 1 } 184 var r: i64 = 0 185 while r < nr { 186 let pi: i64 = A[FC_RP+r] 187 if pi >= 0 { if pi < np { if A[FC_PROT+pi] == rot { 188 cnt[pi] = cnt[pi] + 1 189 let y: i64 = A[FC_RY+r] 190 if y > pmaxy[pi] { pmaxy[pi] = y } 191 if y < pminy[pi] { pminy[pi] = y } 192 let so: i64 = A[FC_RZ+r] + A[FC_RB+r] 193 if so > psole[pi] { psole[pi] = so } 194 } } } 195 r = r + 1 196 } 197 var ngp: i64 = 0 198 var rings: i64 = 0 199 var tube: i64 = 0-1 200 var best: i64 = 0 201 p = 0 202 while p < np { 203 if A[FC_PROT+p] == rot { if cnt[p] > 0 { 204 ngp = ngp + 1 205 rings = rings + cnt[p] 206 if cnt[p] > best { best = cnt[p]; tube = p } 207 } } 208 p = p + 1 209 } 210 out[0] = ngp 211 out[11] = tube 212 out[12] = rings 213 if ngp == 0 { return 0-1 } 214 if tube < 0 { return 0-2 } 215 var flen: i64 = 0-FC_MAGIC_1000000 216 var tbase: i64 = FC_MAGIC_1000000 217 var tsole: i64 = 0-FC_MAGIC_1000000 218 var ntoe: i64 = 0 219 p = 0 220 while p < np { 221 if A[FC_PROT+p] == rot { if cnt[p] > 0 { 222 if pmaxy[p] > flen { flen = pmaxy[p] } 223 if p != tube { 224 ntoe = ntoe + 1 225 if pminy[p] < tbase { tbase = pminy[p] } 226 if psole[p] > tsole { tsole = psole[p] } 227 } 228 } } 229 p = p + 1 230 } 231 out[1] = ntoe 232 out[2] = flen 233 out[3] = pmaxy[tube] 234 out[7] = psole[tube] 235 if ntoe == 0 { return 0-3 } 236 out[4] = tbase 237 out[8] = tsole 238 out[5] = flen - pmaxy[tube] 239 out[6] = pmaxy[tube] - tbase 240 out[9] = tsole - psole[tube] 241 if flen > 0 { out[10] = out[5] * FC_Q / flen } 242 return 0 243} 244// ★THE PREDICATE, and every clause is a thing a foot IS rather than a thing a foot scores. No weights, no 245// blended number -- one blended number is exactly how the last three overclaims in this program survived. 246func fc_ok(out: *i64) -> i64 { 247 if out[0] < 2 { return 0 } 248 if out[1] < 1 { return 0 } 249 if out[6] > 0 { return 0 } 250 if out[9] > 0 { return 0 } 251 if out[10] < FC_MINPROT { return 0 } 252 return 1 253} 254func fc_report(out: *i64) -> i64 { 255 fc_puts("{\x22organ\x22:\x22nx_footcheck\x22,\x22v\x22:1" as *u8) 256 fc_puts(",\x22group_parts\x22:" as *u8); fc_pn(out[0]) 257 fc_puts(",\x22toes\x22:" as *u8); fc_pn(out[1]) 258 fc_puts(",\x22group_rings\x22:" as *u8); fc_pn(out[12]) 259 fc_puts(",\x22foot_length\x22:" as *u8); fc_pn(out[2]) 260 fc_puts(",\x22tube_end\x22:" as *u8); fc_pn(out[3]) 261 fc_puts(",\x22toe_base\x22:" as *u8); fc_pn(out[4]) 262 fc_puts(",\x22protrusion\x22:" as *u8); fc_pn(out[5]) 263 fc_puts(",\x22protrusion_permil\x22:" as *u8); fc_pn(out[10]) 264 fc_puts(",\x22burial\x22:" as *u8); fc_pn(out[6]) 265 fc_puts(",\x22tube_sole\x22:" as *u8); fc_pn(out[7]) 266 fc_puts(",\x22toe_sole\x22:" as *u8); fc_pn(out[8]) 267 fc_puts(",\x22sole_break\x22:" as *u8); fc_pn(out[9]) 268 fc_puts(",\x22verdict\x22:\x22" as *u8) 269 if fc_ok(out) == 1 { fc_puts("GREEN" as *u8) } else { fc_puts("RED" as *u8) } 270 fc_puts("\x22,\x22reads\x22:\x22burial is how far the foot tube overruns the toe bases -- above zero and the digits are inside the foot. protrusion is what clears the tube, and a fifth of foot length is the anatomical floor. sole_break above zero means a toe hangs below the sole plane and the figure stands on its toe tips.\x22}\n" as *u8) 271 return 0 272} 273// ★FIXTURES, and they are the two shapes that matter: the canon as generated TODAY, and the canon as it 274// must be. Same foot LENGTH in both (152) -- that is the invariant the fix may not move, and the reason a 275// fixture pair beats a threshold: it proves the judge separates them, not merely that it dislikes one. 276func fc_fx_bad() -> *u8 { 277 return "P 1 90 48 40 -41 0\nR 0 0 30 14 10\nR 96 0 28 28 12\nR 125 0 32 25 8\nR 145 0 36 15 4\nP 1 90 48 40 -41 0\nR 118 -14 36 7 7\nR 152 -14 38 5 5\n" as *u8 278} 279func fc_fx_good() -> *u8 { 280 return "P 1 90 48 40 -41 0\nR 0 0 30 14 10\nR 96 0 28 28 12\nR 118 0 32 25 8\nP 1 90 48 40 -41 0\nR 118 -14 33 7 7\nR 152 -14 35 5 5\n" as *u8 281} 282func fc_run_fx(s: *u8, out: *i64) -> i64 { 283 let A: *i64 = sys_mmap(FC_SZ*8) as *i64 284 fc_parse(s, fc_slen(s), A) 285 return fc_measure(A, FC_ROTFOOT, out) 286} 287func fc_gate() -> i64 { 288 let ctr: *i64 = gv_ctr() 289 gv_head("nx_footcheck selftest -- the distal-limb judge, proven to SEPARATE a buried toe from a real one" as *u8) 290 let bad: *i64 = sys_mmap(FC_OUT*8) as *i64 291 let good: *i64 = sys_mmap(FC_OUT*8) as *i64 292 let rb: i64 = fc_run_fx(fc_fx_bad(), bad) 293 let rg: i64 = fc_run_fx(fc_fx_good(), good) 294 // ★T1 THE PARSER IS REAL -- and this is the tooth that would have caught seq1038. The count of parts in 295 // the foot's frame is MEASURED (2 here), never eyeballed off identical printed headers. 296 var t1: i64 = 0 297 if rb == 0 { if bad[0] == 2 { if bad[1] == 1 { if bad[12] == 6 { t1 = 1 } } } } 298 gv_check("T1 parses the rotated foot group and COUNTS its members (2 parts, 1 toe, 6 rings)" as *u8, t1, ctr) 299 // ★T2 IT MEASURES THE BURIAL EXACTLY, not merely 'some'. 145 - 118 = 27. 300 var t2: i64 = 0 301 if bad[3] == 145 { if bad[4] == 118 { if bad[6] == 27 { t2 = 1 } } } 302 gv_check("T2 measures burial EXACTLY on the shipped shape: tube 145 vs toe base 118 = 27" as *u8, t2, ctr) 303 // ★T3 AND IT CLEARS on the fixed shape -- discrimination, which is the whole job of a judge 304 var t3: i64 = 0 305 if rg == 0 { if good[6] == 0 { t3 = 1 } } 306 gv_check("T3 DISCRIMINATES: the fixed shape reports ZERO burial" as *u8, t3, ctr) 307 // ★T4 protrusion crosses the anatomical floor in one direction only 308 var t4: i64 = 0 309 if bad[10] < FC_MINPROT { if good[10] >= FC_MINPROT { t4 = 1 } } 310 gv_check("T4 protrusion: shipped 46 permil FAILS the 200 floor, fixed 223 PASSES" as *u8, t4, ctr) 311 // ★T5 the sole plane -- the second defect, measured the same way 312 var t5: i64 = 0 313 if bad[9] == 3 { if good[9] == 0 { t5 = 1 } } 314 gv_check("T5 sole break: shipped toes hang 3 BELOW the sole, fixed toes are flush" as *u8, t5, ctr) 315 // ★★T6 THE REGRESSION GUARD THE SOURCE COMMENT ASKED FOR AND NEVER GOT. A previous round grew the toes 316 // past the envelope and the side silhouette fell 831 -> 723; the lesson was written as prose. Prose does 317 // not fail a build. Foot LENGTH is silhouette-critical, so the fix must leave it EXACTLY where it was. 318 var t6: i64 = 0 319 if bad[2] == 152 { if good[2] == 152 { t6 = 1 } } 320 gv_check("T6 INVARIANT: foot LENGTH is 152 before and after -- the fix moves structure, not silhouette" as *u8, t6, ctr) 321 // ★T7 ANTI-VACUITY. A judge that passes everything is not a judge. It must reject one and accept the other. 322 var t7: i64 = 0 323 if fc_ok(bad) == 0 { if fc_ok(good) == 1 { t7 = 1 } } 324 gv_check("T7 anti-vacuity: verdict RED on the shipped shape, GREEN on the fixed one" as *u8, t7, ctr) 325 // ★T8 fail-closed on nothing. An empty canon must REFUSE, never report a clean foot it never saw. 326 let emp: *i64 = sys_mmap(FC_OUT*8) as *i64 327 let re: i64 = fc_run_fx("# a canon with no foot at all\nP 0 0 0 0 0\nR 430 0 0 86 58\n" as *u8, emp) 328 var t8: i64 = 0 329 if re < 0 { if fc_ok(emp) == 0 { t8 = 1 } } 330 gv_check("T8 fail-closed: a canon with no rotated foot is REFUSED, not passed" as *u8, t8, ctr) 331 // ★T9 a single-toe foot is still not a foot. Five rays is what a human has; report it and require it. 332 var t9: i64 = 0 333 if bad[1] == 1 { if FC_NTOE == 5 { t9 = 1 } } 334 gv_check("T9 the toe COUNT is measured and carried, so a 3-toed foot cannot pass unnoticed" as *u8, t9, ctr) 335 // ★T10 the comment lines and the F relief rows must not become phantom geometry 336 let cmt: *i64 = sys_mmap(FC_OUT*8) as *i64 337 fc_run_fx("# P 1 90 lies in a comment -- 90 rot, 5 numbers\nP 1 90 48 40 -41 0\nR 0 0 30 14 10\nR 96 0 28 28 12\nR 118 0 32 25 8\nF 3 118 20 90 12 40\nP 1 90 48 40 -41 0\nR 118 -14 33 7 7\nR 152 -14 35 5 5\n" as *u8, cmt) 338 var t10: i64 = 0 339 if cmt[0] == 2 { if cmt[12] == 5 { if cmt[2] == 152 { t10 = 1 } } } 340 gv_check("T10 comments and F relief rows are NOT geometry -- only the first char selects the rule" as *u8, t10, ctr) 341 return gv_verdict("FOOTCHECK-GATE" as *u8, ctr, "distal-limb structure judge; burial, protrusion, sole plane, length invariant" as *u8) 342} 343func main(argc: i64, argv: *i64) -> i64 { 344 if argc >= 2 { 345 if fc_streq(argv[1] as *u8, "selftest" as *u8) == 1 { return fc_gate() } 346 if fc_streq(argv[1] as *u8, "check" as *u8) == 1 { 347 if argc < 3 { fc_puts("{\x22error\x22:\x22usage: nx_footcheck check <canon.dat> [rot]\x22}\n" as *u8); return 2 } 348 var rot: i64 = FC_ROTFOOT 349 if argc > 3 { rot = fc_atoi(argv[3] as *u8) } 350 let szp: *i64 = sys_mmap(16) as *i64 351 let buf: *u8 = sys_read_file(argv[2] as *u8, szp) 352 if (buf as i64) == 0 { fc_puts("{\x22error\x22:\x22canon unreadable\x22}\n" as *u8); return 3 } 353 let A: *i64 = sys_mmap(FC_SZ*8) as *i64 354 fc_parse(buf, szp[0], A) 355 let out: *i64 = sys_mmap(FC_OUT*8) as *i64 356 let rc: i64 = fc_measure(A, rot, out) 357 if rc < 0 { 358 fc_puts("{\x22organ\x22:\x22nx_footcheck\x22,\x22verdict\x22:\x22REFUSED\x22,\x22rc\x22:" as *u8); fc_pn(rc) 359 fc_puts(",\x22why\x22:\x22no part with that placement rotation carried rings -- the judge reports nothing rather than a foot it never measured\x22}\n" as *u8) 360 return 4 361 } 362 fc_report(out) 363 if fc_ok(out) == 1 { return 0 } 364 return 1 365 } 366 } 367 fc_puts("{\x22organ\x22:\x22nx_footcheck\x22,\x22usage\x22:\x22nx_footcheck check <canon.dat> [rot] | nx_footcheck selftest\x22}\n" as *u8) 368 return 0 369}