code wiki / (root) / nx_5wh_log.nx

nx_5wh_log.nx source

↩ module page · 402 lines · 14964 B

1// nx_5wh_log.nx -- unified 5W+H+GLP ledger. 2// 3// The bridge between top-down measurement (nx_monte_carlo, 4// nx_multivariate, nx_patch_attribution, nx_knn, nx_closed_loop, 5// nx_quality_grade) and bottom-up attribution (nx_attribution, 6// nx_activation_steer). Both axes emit Nx5whRecord into ONE 7// queryable causal DAG. 8// 9// Schema (canonical 9-field tuple per COMPETITIVE_POSITION.md:60): 10// who -- actor id (caller / tensor / weight) 11// what -- sealed enum: MEASUREMENT / VERDICT / ATTRIBUTION ... 12// when -- monotonic step counter 13// where -- sealed where-kind + 3 indices (layer/head/pos) 14// why_parent -- record_id of the record this one was caused by 15// (or -1 for root); forms the causal DAG 16// how -- algorithm tag (FNV-1a of algo name) 17// genealogy -- research-paper id hash (Welford 1962 etc.) 18// lineage -- data-checkpoint id hash (W matrix hash etc.) 19// performance -- one numeric: latency_us | err_bound | share_q10 20// (interpretation depends on what_kind) 21// 22// JPL Power of 10 Rule 2: bounded capacity; ring overflow drops 23// oldest with NX_5WH_DROPPED verdict returned on emit. 24// 25// genealogy_id: substrate_5wh_log_v1 26// lineage_id: competitive_position_md_line_60 27 28import "nx_syscalls.nx" 29import "nx_runtime.nx" 30import "nx_tier.nx" 31 32// ===== sealed enum: what_kind ===================================== 33 34const NX_5WH_WHAT_MEASUREMENT: nx_int = 0 35const NX_5WH_WHAT_VERDICT: nx_int = 1 36const NX_5WH_WHAT_ATTRIBUTION: nx_int = 2 37const NX_5WH_WHAT_CONTRIBUTION: nx_int = 3 38const NX_5WH_WHAT_OP_BEGIN: nx_int = 4 39const NX_5WH_WHAT_OP_END: nx_int = 5 40const NX_5WH_WHAT_ALLOC: nx_int = 6 41const NX_5WH_WHAT_STEER: nx_int = 7 42const NX_5WH_WHAT_ADJUST: nx_int = 8 43const NX_5WH_WHAT_REROLL: nx_int = 9 44const NX_5WH_WHAT_GATE: nx_int = 10 45const NX_5WH_WHAT_N_KINDS: nx_int = 11 46 47func nx_5wh_what_is_valid(k: nx_int) -> nx_int { 48 if k < 0 { return 0 } 49 if k >= NX_5WH_WHAT_N_KINDS { return 0 } 50 return 1 51} 52 53// ===== sealed enum: where_kind ==================================== 54 55const NX_5WH_WHERE_NONE: nx_int = 0 56const NX_5WH_WHERE_TRANSFORMER_LAYER: nx_int = 1 57const NX_5WH_WHERE_ATTN_HEAD: nx_int = 2 58const NX_5WH_WHERE_MLP_BLOCK: nx_int = 3 59const NX_5WH_WHERE_EMBED: nx_int = 4 60const NX_5WH_WHERE_UNEMBED: nx_int = 5 61const NX_5WH_WHERE_UNET_BLOCK: nx_int = 6 62const NX_5WH_WHERE_VAE_BLOCK: nx_int = 7 63const NX_5WH_WHERE_SAMPLER: nx_int = 8 64const NX_5WH_WHERE_DECODER: nx_int = 9 65const NX_5WH_WHERE_RASTER: nx_int = 10 66const NX_5WH_WHERE_MESH: nx_int = 11 67const NX_5WH_WHERE_HARDWARE: nx_int = 12 68const NX_5WH_WHERE_EXTERNAL: nx_int = 13 69const NX_5WH_WHERE_N_KINDS: nx_int = 14 70 71func nx_5wh_where_is_valid(k: nx_int) -> nx_int { 72 if k < 0 { return 0 } 73 if k >= NX_5WH_WHERE_N_KINDS { return 0 } 74 return 1 75} 76 77// ===== emit verdict ================================================= 78 79const NX_5WH_OK: nx_int = 0 80const NX_5WH_DROPPED: nx_int = 1 81const NX_5WH_INVALID: nx_int = 2 82 83// ===== sentinel root for why_parent ================================ 84 85const NX_5WH_NO_PARENT: nx_int = -1 86 87// ===== record struct =============================================== 88 89struct Nx5whRecord { 90 who: nx_int, 91 what: nx_int, 92 when_step: nx_int, 93 where_kind: nx_int, 94 where_idx_a: nx_int, 95 where_idx_b: nx_int, 96 where_idx_c: nx_int, 97 why_parent_id: nx_int, 98 how: nx_int, 99 genealogy: nx_int, 100 lineage: nx_int, 101 performance: nx_int, 102} 103 104const NX_5WH_RECORD_BYTES: nx_size = 96 // 12 fields x 8 bytes 105 106// ===== ledger struct =============================================== 107 108struct Nx5whLedger { 109 records: *Nx5whRecord, 110 capacity: nx_int, 111 head: nx_int, // next slot to write 112 n_emitted: nx_int, // total emits since alloc (monotone) 113 n_dropped: nx_int, // total dropped due to overflow 114 step: nx_int, // when-counter 115} 116 117const NX_5WH_LEDGER_BYTES: nx_size = 48 118const NX_5WH_DEFAULT_CAP: nx_int = 4096 119const NX_5WH_MAX_CAP: nx_int = 1048576 120 121// ===== alloc ======================================================= 122 123func nx_5wh_log_alloc(capacity: nx_int) -> *Nx5whLedger { 124 var cap: nx_int = capacity 125 if cap <= 0 { cap = NX_5WH_DEFAULT_CAP } 126 if cap > NX_5WH_MAX_CAP { cap = NX_5WH_MAX_CAP } 127 let bytes_records: nx_size = (cap as nx_size) * NX_5WH_RECORD_BYTES 128 let recs_ptr: *u8 = sys_mmap(bytes_records) 129 let ledger_ptr: *u8 = sys_mmap(NX_5WH_LEDGER_BYTES) 130 let ledger: *Nx5whLedger = ledger_ptr as *Nx5whLedger 131 ledger.records = recs_ptr as *Nx5whRecord 132 ledger.capacity = cap 133 ledger.head = 0 134 ledger.n_emitted = 0 135 ledger.n_dropped = 0 136 ledger.step = 0 137 return ledger 138} 139 140// ===== bounded ring-buffer slot picker ============================ 141 142func _5wh_advance(ledger: *Nx5whLedger) -> nx_int { 143 let slot: nx_int = ledger.head 144 ledger.head = ledger.head + 1 145 if ledger.head >= ledger.capacity { 146 ledger.head = 0 147 ledger.n_dropped = ledger.n_dropped + 1 148 } 149 return slot 150} 151 152// ===== emit ======================================================== 153 154func nx_5wh_emit(ledger: *Nx5whLedger, 155 who: nx_int, what: nx_int, 156 where_kind: nx_int, 157 where_idx_a: nx_int, where_idx_b: nx_int, where_idx_c: nx_int, 158 why_parent_id: nx_int, 159 how: nx_int, genealogy: nx_int, lineage: nx_int, 160 performance: nx_int) -> nx_int { 161 if nx_5wh_what_is_valid(what) == 0 { return 0 - 1 } 162 if nx_5wh_where_is_valid(where_kind) == 0 { return 0 - 1 } 163 let slot: nx_int = _5wh_advance(ledger) 164 let rec: *Nx5whRecord = (ledger.records as *u8 + (slot as nx_size) * NX_5WH_RECORD_BYTES) as *Nx5whRecord 165 rec.who = who 166 rec.what = what 167 rec.when_step = ledger.step 168 rec.where_kind = where_kind 169 rec.where_idx_a = where_idx_a 170 rec.where_idx_b = where_idx_b 171 rec.where_idx_c = where_idx_c 172 rec.why_parent_id = why_parent_id 173 rec.how = how 174 rec.genealogy = genealogy 175 rec.lineage = lineage 176 rec.performance = performance 177 ledger.step = ledger.step + 1 178 ledger.n_emitted = ledger.n_emitted + 1 179 return slot 180} 181 182// ===== record fetch ================================================ 183 184func nx_5wh_record_at(ledger: *Nx5whLedger, slot: nx_int) -> *Nx5whRecord { 185 if slot < 0 { return 0 as *Nx5whRecord } 186 if slot >= ledger.capacity { return 0 as *Nx5whRecord } 187 return (ledger.records as *u8 + (slot as nx_size) * NX_5WH_RECORD_BYTES) as *Nx5whRecord 188} 189 190// ===== query: filterable scan ====================================== 191// 192// what_kind_mask: bitmask -- bit i set means "include records where 193// what==i". Pass -1 (all bits) to match all. Pass 0 to skip filter. 194// where_kind_mask: same shape over where_kind values. 195// min_step / max_step: when-window; pass -1 to disable bound. 196// out_ids[]: caller-provided output array; out_cap entries. 197// Returns number of matching records written (clamped to out_cap). 198 199func _5wh_bit_test(mask: nx_int, bit: nx_int) -> nx_int { 200 if mask == 0 - 1 { return 1 } 201 if mask == 0 { return 1 } 202 if bit < 0 { return 0 } 203 if bit >= 64 { return 0 } 204 let shifted: nx_int = mask >> bit 205 let lsb: nx_int = shifted & 1 206 return lsb 207} 208 209func nx_5wh_query(ledger: *Nx5whLedger, 210 what_mask: nx_int, where_mask: nx_int, 211 min_step: nx_int, max_step: nx_int, 212 out_ids: *nx_int, out_cap: nx_int) -> nx_int { 213 var count: nx_int = 0 214 var i: nx_int = 0 215 let cap: nx_int = ledger.capacity 216 let emitted: nx_int = ledger.n_emitted 217 var scan_n: nx_int = emitted 218 if scan_n > cap { scan_n = cap } 219 while i < scan_n { 220 if count >= out_cap { return count } 221 let rec: *Nx5whRecord = nx_5wh_record_at(ledger, i) 222 let what_hit: nx_int = _5wh_bit_test(what_mask, rec.what) 223 let where_hit: nx_int = _5wh_bit_test(where_mask, rec.where_kind) 224 var ok: nx_int = 1 225 if what_hit == 0 { ok = 0 } 226 if where_hit == 0 { ok = 0 } 227 if min_step >= 0 { 228 if rec.when_step < min_step { ok = 0 } 229 } 230 if max_step >= 0 { 231 if rec.when_step > max_step { ok = 0 } 232 } 233 if ok == 1 { 234 out_ids[count] = i 235 count = count + 1 236 } 237 i = i + 1 238 } 239 return count 240} 241 242// ===== lineage walk: follow why_parent_id back to root ============= 243// 244// Returns recorded chain in out_ids[] from the seed record back 245// toward root (NX_5WH_NO_PARENT). Bounded by out_cap and 246// JPL Rule 2 max-depth NX_5WH_MAX_WALK to refuse cycles. 247 248const NX_5WH_MAX_WALK: nx_int = 1024 249 250func nx_5wh_walk_lineage(ledger: *Nx5whLedger, seed_id: nx_int, 251 out_ids: *nx_int, out_cap: nx_int) -> nx_int { 252 var count: nx_int = 0 253 var cur: nx_int = seed_id 254 var safety: nx_int = 0 255 while safety < NX_5WH_MAX_WALK { 256 if cur < 0 { return count } 257 if count >= out_cap { return count } 258 let rec: *Nx5whRecord = nx_5wh_record_at(ledger, cur) 259 if rec == (0 as *Nx5whRecord) { return count } 260 out_ids[count] = cur 261 count = count + 1 262 cur = rec.why_parent_id 263 safety = safety + 1 264 } 265 return count 266} 267 268// ===== summary counts ============================================== 269 270func nx_5wh_count_by_what(ledger: *Nx5whLedger, what: nx_int) -> nx_int { 271 if nx_5wh_what_is_valid(what) == 0 { return 0 - 1 } 272 var count: nx_int = 0 273 var i: nx_int = 0 274 let cap: nx_int = ledger.capacity 275 let emitted: nx_int = ledger.n_emitted 276 var scan_n: nx_int = emitted 277 if scan_n > cap { scan_n = cap } 278 while i < scan_n { 279 let rec: *Nx5whRecord = nx_5wh_record_at(ledger, i) 280 if rec.what == what { count = count + 1 } 281 i = i + 1 282 } 283 return count 284} 285 286func nx_5wh_n_emitted(ledger: *Nx5whLedger) -> nx_int { 287 return ledger.n_emitted 288} 289 290func nx_5wh_n_dropped(ledger: *Nx5whLedger) -> nx_int { 291 return ledger.n_dropped 292} 293 294// ===== self-test ==================================================== 295// 296// Verifies: 297// - emit returns ascending slot ids 298// - record fetch returns identical fields 299// - query filters work (what_mask + where_mask + step range) 300// - lineage walk follows why_parent back to root 301// - bounded ring drops oldest correctly 302// - sealed-enum validators refuse out-of-range 303 304func main() -> nx_int { 305 let ledger: *Nx5whLedger = nx_5wh_log_alloc(8) 306 if ledger.capacity != 8 { return 1 } 307 if ledger.n_emitted != 0 { return 2 } 308 309 // Emit a chain: MEASUREMENT (root) -> VERDICT (caused by m0) 310 // -> ATTRIBUTION (caused by v0). 311 let m0: nx_int = nx_5wh_emit(ledger, 312 100, NX_5WH_WHAT_MEASUREMENT, 313 NX_5WH_WHERE_SAMPLER, 0, 0, 0, 314 NX_5WH_NO_PARENT, 315 200, 300, 400, 950) 316 if m0 != 0 { return 3 } 317 let v0: nx_int = nx_5wh_emit(ledger, 318 101, NX_5WH_WHAT_VERDICT, 319 NX_5WH_WHERE_SAMPLER, 0, 0, 0, 320 m0, 321 201, 301, 401, 1) 322 if v0 != 1 { return 4 } 323 let a0: nx_int = nx_5wh_emit(ledger, 324 102, NX_5WH_WHAT_ATTRIBUTION, 325 NX_5WH_WHERE_TRANSFORMER_LAYER, 5, 2, 128, 326 v0, 327 202, 302, 402, 768) 328 if a0 != 2 { return 5 } 329 330 // Fetch + verify fields. 331 let rec_m0: *Nx5whRecord = nx_5wh_record_at(ledger, m0) 332 if rec_m0.who != 100 { return 10 } 333 if rec_m0.what != NX_5WH_WHAT_MEASUREMENT { return 11 } 334 if rec_m0.why_parent_id != NX_5WH_NO_PARENT { return 12 } 335 if rec_m0.performance != 950 { return 13 } 336 337 let rec_a0: *Nx5whRecord = nx_5wh_record_at(ledger, a0) 338 if rec_a0.where_kind != NX_5WH_WHERE_TRANSFORMER_LAYER { return 20 } 339 if rec_a0.where_idx_a != 5 { return 21 } 340 if rec_a0.where_idx_b != 2 { return 22 } 341 if rec_a0.where_idx_c != 128 { return 23 } 342 if rec_a0.why_parent_id != v0 { return 24 } 343 344 // Query: all VERDICTs anywhere -> should find exactly v0. 345 let q_buf: *nx_int = (sys_mmap(64)) as *nx_int 346 let verdict_mask: nx_int = 1 << NX_5WH_WHAT_VERDICT 347 let n_v: nx_int = nx_5wh_query(ledger, verdict_mask, 0, -1, -1, q_buf, 8) 348 if n_v != 1 { return 30 } 349 if q_buf[0] != v0 { return 31 } 350 351 // Query: all records at TRANSFORMER_LAYER -> should find a0. 352 let xform_mask: nx_int = 1 << NX_5WH_WHERE_TRANSFORMER_LAYER 353 let n_x: nx_int = nx_5wh_query(ledger, 0, xform_mask, -1, -1, q_buf, 8) 354 if n_x != 1 { return 32 } 355 if q_buf[0] != a0 { return 33 } 356 357 // Query: step-window 1..2 -> v0 + a0. 358 let n_win: nx_int = nx_5wh_query(ledger, 0, 0, 1, 2, q_buf, 8) 359 if n_win != 2 { return 34 } 360 if q_buf[0] != v0 { return 35 } 361 if q_buf[1] != a0 { return 36 } 362 363 // Lineage walk from a0 -> a0, v0, m0. 364 let walk_buf: *nx_int = (sys_mmap(64)) as *nx_int 365 let n_walk: nx_int = nx_5wh_walk_lineage(ledger, a0, walk_buf, 8) 366 if n_walk != 3 { return 40 } 367 if walk_buf[0] != a0 { return 41 } 368 if walk_buf[1] != v0 { return 42 } 369 if walk_buf[2] != m0 { return 43 } 370 371 // Counts. 372 if nx_5wh_count_by_what(ledger, NX_5WH_WHAT_MEASUREMENT) != 1 { return 50 } 373 if nx_5wh_count_by_what(ledger, NX_5WH_WHAT_VERDICT) != 1 { return 51 } 374 if nx_5wh_count_by_what(ledger, NX_5WH_WHAT_ATTRIBUTION) != 1 { return 52 } 375 if nx_5wh_count_by_what(ledger, NX_5WH_WHAT_OP_BEGIN) != 0 { return 53 } 376 377 // Sealed-enum validators refuse out-of-range. 378 if nx_5wh_what_is_valid(0 - 1) != 0 { return 60 } 379 if nx_5wh_what_is_valid(NX_5WH_WHAT_N_KINDS) != 0 { return 61 } 380 if nx_5wh_where_is_valid(0 - 1) != 0 { return 62 } 381 if nx_5wh_where_is_valid(NX_5WH_WHERE_N_KINDS) != 0 { return 63 } 382 383 // Invalid emit refused. 384 let bad: nx_int = nx_5wh_emit(ledger, 385 0, 999, NX_5WH_WHERE_NONE, 0, 0, 0, 386 NX_5WH_NO_PARENT, 0, 0, 0, 0) 387 if bad != 0 - 1 { return 64 } 388 389 // Ring overflow: fill cap=8 more emits, head should wrap. 390 var k: nx_int = 0 391 while k < 10 { 392 nx_5wh_emit(ledger, 393 500 + k, NX_5WH_WHAT_OP_BEGIN, 394 NX_5WH_WHERE_HARDWARE, 0, 0, 0, 395 NX_5WH_NO_PARENT, 396 600 + k, 700 + k, 800 + k, k) 397 k = k + 1 398 } 399 if ledger.n_dropped < 1 { return 70 } 400 401 return 0 402}