code wiki / _hdl_build / nx_seat_drive_gate.nx

nx_seat_drive_gate.nx source

↩ module page · 217 lines · 9225 B

1// nx_seat_drive_gate.nx -- GATE for the S2 seat-protocol driver (6 teeth, 3 negative controls). 2// PREREQ: stage the elfs first (banked /tmp-wipe + fork-budget laws): 3// nx_sov_build_run nx_seat_drive / nx_fix_ok / nx_fix_fail -> cp /tmp/<n>.sov.elf _offc/<n>.elf 4// Run from nxc2 root. SELF-EXEC CHAIN (one driver fork per process, counters ride argv -- 5// the proven WSL fork-budget pattern): argv = [self] [stage] [pass]. 6// Teeth: T1 happy e2e (DONE frame + both artifacts) | T2 NEG work-fail refused | T3 NEG lane-gate 7// RED refused | T4 NEG checkin refused fail-closed (work never ran) | T5 NEG artifact-lie refused 8// (rc0 work without its declared artifact) | T6 journal is append-only across reruns (DONE x2). 9// Verdict: NX-SEAT-DRIVE-GATE pass=N/6 verdict=GREEN|RED (exit 0 iff 6/6). 10// license_tier: ORIGINAL No hw writes (Rule 26). 11import "nx_seg_store.nx" 12import "nx_deploy_lib.nx" 13import "nx_syscalls.nx" 14 15const SG_JCAP: i64 = 65536 16 17func sg_w(s: *u8) -> i64 { 18 var n: i64 = 0 19 while s[n] != (0 as u8) { n = n + 1 } 20 sys_write(1, s, n) 21 return 0 22} 23 24func sg_len(s: *u8) -> i64 { 25 var n: i64 = 0 26 while s[n] != (0 as u8) { n = n + 1 } 27 return n 28} 29 30func sg_atoi(s: *u8) -> i64 { 31 var v: i64 = 0 32 var i: i64 = 0 33 while s[i] != (0 as u8) { 34 let c: i64 = s[i] as i64 35 if c >= 48 { if c <= 57 { v = v * 10 + (c - 48) } } 36 i = i + 1 37 } 38 return v 39} 40 41func sg_itoa(dst: *u8, v: i64) -> i64 { 42 var m: i64 = v 43 let t: *u8 = sys_mmap(24) 44 var k: i64 = 0 45 if m == 0 { t[0] = 48 as u8; k = 1 } 46 while m > 0 { t[k] = (48 + (m % 10)) as u8; m = m / 10; k = k + 1 } 47 var i: i64 = 0 48 while i < k { dst[i] = t[k - 1 - i]; i = i + 1 } 49 dst[k] = 0 as u8 50 return k 51} 52 53func sg_count(buf: *u8, n: i64, needle: *u8) -> i64 { 54 var cnt: i64 = 0 55 var p: i64 = 0 56 while p < n { 57 var ki: i64 = 0 58 var hit: i64 = 1 59 var scanning: i64 = 1 60 while scanning == 1 { 61 let kc: i64 = needle[ki] as i64 62 if kc == 0 { scanning = 0 } else { 63 var bc: i64 = 0 64 if p + ki < n { bc = buf[p + ki] as i64 } 65 if bc == kc { ki = ki + 1 } else { hit = 0; scanning = 0 } 66 } 67 } 68 if hit == 1 { cnt = cnt + 1 } 69 p = p + 1 70 } 71 return cnt 72} 73 74// journal-frame count: reads path fresh each call, one fixed callee chain 75func sg_jcount(path: *u8, needle: *u8) -> i64 { 76 let buf: *u8 = sys_mmap(SG_JCAP) 77 let n: i64 = dp_read(path, buf, SG_JCAP) 78 return sg_count(buf, n, needle) 79} 80 81// non-empty file probe (artifact-truth): 1 iff path exists with >0 bytes 82func sg_nonempty(path: *u8) -> i64 { 83 let buf: *u8 = sys_mmap(64) 84 let n: i64 = dp_read(path, buf, 32) 85 if n > 0 { return 1 } 86 return 0 87} 88 89// run the driver on a lane file; returns driver exit code (-1 on signal death) 90func sg_drive(lanep: *u8, outp: *u8) -> i64 { 91 let av: *i64 = sys_mmap(32) as *i64 92 av[0] = lanep as i64 93 return dep_run_capture("_offc/nx_seat_drive.elf" as *u8, av, 1, outp) 94} 95 96func main(argc: i64, argv: *i64) -> i64 { 97 var stage: i64 = 1 98 var pass: i64 = 0 99 if argc >= 2 { let ss: *u8 = argv[1] as *u8; stage = sg_atoi(ss) } 100 if argc >= 3 { let ps: *u8 = argv[2] as *u8; pass = sg_atoi(ps) } 101 if stage < 1 { stage = 1 } 102 103 if stage == 1 { 104 sys_unlinkat("/tmp/sdg_t1.jrnl" as *u8) 105 sys_unlinkat("/tmp/sdg_t1.marker" as *u8) 106 sys_unlinkat("/tmp/sdg_t1.gmarker" as *u8) 107 let lane: *u8 = "ws=sdg-t1\nactor=gatefix\njournal=/tmp/sdg_t1.jrnl\nworkelf=_offc/nx_fix_ok.elf\nworkarg1=/tmp/sdg_t1.marker\nworkartifact=/tmp/sdg_t1.marker\ngateelf=_offc/nx_fix_ok.elf\ngatearg1=/tmp/sdg_t1.gmarker\n" as *u8 108 ss_writefile("/tmp/sdg_t1.lane" as *u8, lane, sg_len(lane)) 109 let rc: i64 = sg_drive("/tmp/sdg_t1.lane" as *u8, "/tmp/sdg_t1.out" as *u8) 110 let done: i64 = sg_jcount("/tmp/sdg_t1.jrnl" as *u8, "DONE" as *u8) 111 let ma: i64 = sg_nonempty("/tmp/sdg_t1.marker" as *u8) 112 let ga: i64 = sg_nonempty("/tmp/sdg_t1.gmarker" as *u8) 113 var ok: i64 = 1 114 if rc != 0 { ok = 0 } 115 if done != 1 { ok = 0 } 116 if ma != 1 { ok = 0 } 117 if ga != 1 { ok = 0 } 118 if ok == 1 { sg_w("T1 happy-e2e PASS\n" as *u8); pass = pass + 1 } else { sg_w("T1 happy-e2e FAIL\n" as *u8) } 119 } 120 if stage == 2 { 121 sys_unlinkat("/tmp/sdg_t2.jrnl" as *u8) 122 sys_unlinkat("/tmp/sdg_t2.marker" as *u8) 123 let lane: *u8 = "ws=sdg-t2\nactor=gatefix\njournal=/tmp/sdg_t2.jrnl\nworkelf=_offc/nx_fix_fail.elf\nworkarg1=/tmp/sdg_t2.marker\nworkartifact=/tmp/sdg_t2.marker\ngateelf=_offc/nx_fix_ok.elf\n" as *u8 124 ss_writefile("/tmp/sdg_t2.lane" as *u8, lane, sg_len(lane)) 125 let rc: i64 = sg_drive("/tmp/sdg_t2.lane" as *u8, "/tmp/sdg_t2.out" as *u8) 126 let wf: i64 = sg_jcount("/tmp/sdg_t2.jrnl" as *u8, "WORKFAIL" as *u8) 127 let done: i64 = sg_jcount("/tmp/sdg_t2.jrnl" as *u8, "DONE" as *u8) 128 var ok: i64 = 1 129 if rc != 4 { ok = 0 } 130 if wf != 1 { ok = 0 } 131 if done != 0 { ok = 0 } 132 if ok == 1 { sg_w("T2 neg-workfail PASS\n" as *u8); pass = pass + 1 } else { sg_w("T2 neg-workfail FAIL\n" as *u8) } 133 } 134 if stage == 3 { 135 sys_unlinkat("/tmp/sdg_t3.jrnl" as *u8) 136 sys_unlinkat("/tmp/sdg_t3.marker" as *u8) 137 let lane: *u8 = "ws=sdg-t3\nactor=gatefix\njournal=/tmp/sdg_t3.jrnl\nworkelf=_offc/nx_fix_ok.elf\nworkarg1=/tmp/sdg_t3.marker\nworkartifact=/tmp/sdg_t3.marker\ngateelf=_offc/nx_fix_fail.elf\n" as *u8 138 ss_writefile("/tmp/sdg_t3.lane" as *u8, lane, sg_len(lane)) 139 let rc: i64 = sg_drive("/tmp/sdg_t3.lane" as *u8, "/tmp/sdg_t3.out" as *u8) 140 let gr: i64 = sg_jcount("/tmp/sdg_t3.jrnl" as *u8, "GATERED" as *u8) 141 let done: i64 = sg_jcount("/tmp/sdg_t3.jrnl" as *u8, "DONE" as *u8) 142 var ok: i64 = 1 143 if rc != 5 { ok = 0 } 144 if gr != 1 { ok = 0 } 145 if done != 0 { ok = 0 } 146 if ok == 1 { sg_w("T3 neg-gatered PASS\n" as *u8); pass = pass + 1 } else { sg_w("T3 neg-gatered FAIL\n" as *u8) } 147 } 148 if stage == 4 { 149 sys_unlinkat("/tmp/sdg_t4.jrnl" as *u8) 150 sys_unlinkat("/tmp/sdg_t4.marker" as *u8) 151 let lane: *u8 = "ws=sdg-t4\nactor=gatefix\njournal=/tmp/sdg_t4.jrnl\nworkelf=_offc/nx_fix_ok.elf\nworkarg1=/tmp/sdg_t4.marker\nworkartifact=/tmp/sdg_t4.marker\ngateelf=_offc/nx_fix_ok.elf\ncheckinelf=_offc/nx_fix_fail.elf\n" as *u8 152 ss_writefile("/tmp/sdg_t4.lane" as *u8, lane, sg_len(lane)) 153 let rc: i64 = sg_drive("/tmp/sdg_t4.lane" as *u8, "/tmp/sdg_t4.out" as *u8) 154 let cr: i64 = sg_jcount("/tmp/sdg_t4.jrnl" as *u8, "CHECKIN-REFUSED" as *u8) 155 let ma: i64 = sg_nonempty("/tmp/sdg_t4.marker" as *u8) 156 var ok: i64 = 1 157 if rc != 3 { ok = 0 } 158 if cr != 1 { ok = 0 } 159 if ma != 0 { ok = 0 } 160 if ok == 1 { sg_w("T4 neg-checkin-failclosed PASS\n" as *u8); pass = pass + 1 } else { sg_w("T4 neg-checkin-failclosed FAIL\n" as *u8) } 161 } 162 if stage == 5 { 163 sys_unlinkat("/tmp/sdg_t5.jrnl" as *u8) 164 sys_unlinkat("/tmp/sdg_t5.marker" as *u8) 165 sys_unlinkat("/tmp/sdg_t5.other" as *u8) 166 let lane: *u8 = "ws=sdg-t5\nactor=gatefix\njournal=/tmp/sdg_t5.jrnl\nworkelf=_offc/nx_fix_ok.elf\nworkarg1=/tmp/sdg_t5.other\nworkartifact=/tmp/sdg_t5.marker\ngateelf=_offc/nx_fix_ok.elf\n" as *u8 167 ss_writefile("/tmp/sdg_t5.lane" as *u8, lane, sg_len(lane)) 168 let rc: i64 = sg_drive("/tmp/sdg_t5.lane" as *u8, "/tmp/sdg_t5.out" as *u8) 169 let na: i64 = sg_jcount("/tmp/sdg_t5.jrnl" as *u8, "NOARTIFACT" as *u8) 170 var ok: i64 = 1 171 if rc != 6 { ok = 0 } 172 if na != 1 { ok = 0 } 173 if ok == 1 { sg_w("T5 neg-artifact-lie PASS\n" as *u8); pass = pass + 1 } else { sg_w("T5 neg-artifact-lie FAIL\n" as *u8) } 174 } 175 if stage == 6 { 176 // NO cleanup -- T6 proves the journal is append-only across reruns of the T1 lane 177 let rc: i64 = sg_drive("/tmp/sdg_t1.lane" as *u8, "/tmp/sdg_t6.out" as *u8) 178 let done: i64 = sg_jcount("/tmp/sdg_t1.jrnl" as *u8, "DONE" as *u8) 179 var ok: i64 = 1 180 if rc != 0 { ok = 0 } 181 if done != 2 { ok = 0 } 182 if ok == 1 { sg_w("T6 journal-append-only PASS\n" as *u8); pass = pass + 1 } else { sg_w("T6 journal-append-only FAIL\n" as *u8) } 183 } 184 185 if stage >= 6 { 186 sg_w("NX-SEAT-DRIVE-GATE pass=" as *u8) 187 let pb: *u8 = sys_mmap(24) 188 sg_itoa(pb, pass) 189 sg_w(pb) 190 if pass == 6 { 191 sg_w("/6 verdict=GREEN\n" as *u8) 192 sys_exit(0) 193 return 0 194 } 195 sg_w("/6 verdict=RED\n" as *u8) 196 sys_exit(1) 197 return 1 198 } 199 200 // SELF-EXEC CHAIN: one driver fork per process; counters ride argv 201 let self: *u8 = argv[0] as *u8 202 let sb: *u8 = sys_mmap(24) 203 sg_itoa(sb, stage + 1) 204 let pb2: *u8 = sys_mmap(24) 205 sg_itoa(pb2, pass) 206 let nav: *i64 = sys_mmap(40) as *i64 207 nav[0] = self as i64 208 nav[1] = sb as i64 209 nav[2] = pb2 as i64 210 nav[3] = 0 211 let envp: *i64 = sys_mmap(16) as *i64 212 envp[0] = 0 213 sys_execve(self, nav, envp) 214 sg_w("SDG-EXEC-FAIL\n" as *u8) 215 sys_exit(1) 216 return 1 217}