code wiki / _hdl_build / nx_train_triage_sweep.nx

nx_train_triage_sweep.nx source

↩ module page · 136 lines · 6018 B

1// nx_train_triage_sweep.nx -- the CONDUCTOR's pulse step that closes the triage wiring callout: 2// every training report on file is diagnosed EVERY BEAT, and a verdict CHANGE auto-files a 3// PM-ESCALATION row (the sentinel pattern) so a sick training lane becomes backlog work without 4// Claude in the loop. Idempotent by construction (law 10): the PM row is filed ONLY when the 5// verdict differs from the LAST swept verdict for that report (read back from the triage log). 6// Conf-driven (law 11): knowledge/status/train_reports.conf rows "R <path>" -- adding a training 7// lane = adding a row, never code. Recovery to CONVERGED-HEALTHY logs but does not escalate. 8// BROKEN-REPORT escalates AND exits nonzero (the emitting lane itself is the defect -> pulse 9// ATTENTION). argv overrides (conf, triage-log, pm-log) = the Engineer's gate lane. 10// license_tier: ORIGINAL 11import "nx_train_triage.nx" 12 13func tsw_cat(dst: *u8, off: i64, s: *u8) -> i64 { var i: i64 = 0; while s[i] != (0 as u8) { dst[off+i] = s[i]; i = i + 1 } dst[off+i] = 0 as u8; return off + i } 14 15// last swept verdict for a report: scan tlog for the LAST "TRIAGESWEEP report=<path> verdict=" 16// row and copy its verdict token into out (NUL-terminated); returns 1 if found 17func tsw_prev_verdict(tlog: *u8, rpath: *u8, out: *u8) -> i64 { 18 let lenp: *i64 = sys_mmap(16) as *i64 19 let b: *u8 = sys_read_file(tlog, lenp) 20 let n: i64 = lenp[0] 21 if n <= 0 { return 0 } 22 let pre: *u8 = sys_mmap(256) 23 var o: i64 = 0 24 o = tsw_cat(pre, o, "TRIAGESWEEP report=" as *u8) 25 o = tsw_cat(pre, o, rpath) 26 o = tsw_cat(pre, o, " verdict=" as *u8) 27 var found: i64 = 0 28 var ls: i64 = 0 29 while ls < n { 30 var le: i64 = ls 31 var stop: i64 = 0 32 while stop == 0 { 33 if le >= n { stop = 1 } else { if b[le] == (10 as u8) { stop = 1 } else { le = le + 1 } } 34 } 35 if tt_match(b, ls, le, pre) == 1 { 36 var p: i64 = ls + o 37 var k: i64 = 0 38 var stop2: i64 = 0 39 while stop2 == 0 { 40 if p >= le { stop2 = 1 } else { if b[p] == (32 as u8) { stop2 = 1 } else { 41 if k < 40 { out[k] = b[p]; k = k + 1 } 42 p = p + 1 43 } } 44 } 45 out[k] = 0 as u8 46 found = 1 47 } 48 ls = le + 1 49 } 50 return found 51} 52func tsw_streq(a: *u8, b: *u8) -> i64 { 53 var i: i64 = 0 54 while a[i] != (0 as u8) { 55 if a[i] != b[i] { return 0 } 56 i = i + 1 57 } 58 if b[i] == (0 as u8) { return 1 } 59 return 0 60} 61 62func main(argc: i64, argv: *i64) -> i64 { 63 var conf: *u8 = "knowledge/status/train_reports.conf" as *u8 64 var tlog: *u8 = "knowledge/status/train_triage.log" as *u8 65 var pmlog: *u8 = "knowledge/status/pm_plan_durable.log" as *u8 66 if argc >= 2 { conf = argv[1] as *u8 } 67 if argc >= 3 { tlog = argv[2] as *u8 } 68 if argc >= 4 { pmlog = argv[3] as *u8 } 69 tt_w(1, "=== TRAIN-TRIAGE SWEEP (Conductor: diagnose every training report; escalate verdict CHANGES) ===\n" as *u8) 70 let lenp: *i64 = sys_mmap(16) as *i64 71 let b: *u8 = sys_read_file(conf, lenp) 72 let n: i64 = lenp[0] 73 if n <= 0 { tt_w(1, " conf missing/empty: " as *u8); tt_w(1, conf); tt_w(1, "\n" as *u8); sys_exit(1); return 1 } 74 var swept: i64 = 0 75 var escalated: i64 = 0 76 var broken: i64 = 0 77 var ls: i64 = 0 78 while ls < n { 79 var le: i64 = ls 80 var stop: i64 = 0 81 while stop == 0 { 82 if le >= n { stop = 1 } else { if b[le] == (10 as u8) { stop = 1 } else { le = le + 1 } } 83 } 84 if tt_match(b, ls, le, "R " as *u8) == 1 { 85 let rpath: *u8 = sys_mmap(256) 86 var k: i64 = 0 87 var p: i64 = ls + 2 88 var stop2: i64 = 0 89 while stop2 == 0 { 90 if p >= le { stop2 = 1 } else { if b[p] == (32 as u8) { stop2 = 1 } else { 91 if k < 200 { rpath[k] = b[p]; k = k + 1 } 92 p = p + 1 93 } } 94 } 95 rpath[k] = 0 as u8 96 if k > 0 { 97 let id: i64 = tt_diagnose(rpath) 98 let cur: *u8 = tt_name(id) 99 let prev: *u8 = sys_mmap(64) 100 let hadprev: i64 = tsw_prev_verdict(tlog, rpath, prev) 101 var changed: i64 = 1 102 if hadprev == 1 { if tsw_streq(cur, prev) == 1 { changed = 0 } } 103 tt_w(1, " report=" as *u8); tt_w(1, rpath) 104 tt_w(1, " verdict=" as *u8); tt_w(1, cur) 105 if changed == 1 { tt_w(1, " (CHANGED)\n" as *u8) } else { tt_w(1, " (steady)\n" as *u8) } 106 let lfd: i64 = sys_openat_append(tlog, 0x1a4) 107 if lfd >= 0 { 108 tt_w(lfd, "TRIAGESWEEP report=" as *u8); tt_w(lfd, rpath) 109 tt_w(lfd, " verdict=" as *u8); tt_w(lfd, cur) 110 tt_w(lfd, " epoch=" as *u8); tt_wn(lfd, sys_now_realtime_sec()); tt_w(lfd, "\n" as *u8) 111 sys_close(lfd) 112 } 113 if changed == 1 { if id != TT_HEALTHY { 114 let pfd: i64 = sys_openat_append(pmlog, 0x1a4) 115 if pfd >= 0 { 116 tt_w(pfd, "PM-ESCALATION source=train-triage report=" as *u8); tt_w(pfd, rpath) 117 tt_w(pfd, " verdict=" as *u8); tt_w(pfd, cur) 118 tt_w(pfd, " :: fix=" as *u8); tt_w(pfd, tt_fix(id)); tt_w(pfd, "\n" as *u8) 119 sys_close(pfd) 120 escalated = escalated + 1 121 } 122 } } 123 if id == TT_BROKEN { broken = broken + 1 } 124 swept = swept + 1 125 } 126 } 127 ls = le + 1 128 } 129 tt_w(1, " SWEEP: reports=" as *u8); tt_wn(1, swept) 130 tt_w(1, " escalated=" as *u8); tt_wn(1, escalated) 131 tt_w(1, " broken=" as *u8); tt_wn(1, broken); tt_w(1, "\n" as *u8) 132 if swept == 0 { sys_exit(1); return 1 } 133 if broken > 0 { sys_exit(1); return 1 } 134 sys_exit(0) 135 return 0 136}