code wiki / _hdl_build / nx_apistack_metrics_gate.nx

nx_apistack_metrics_gate.nx source

↩ module page · 51 lines · 3166 B

1// nx_apistack_metrics_gate.nx -- hermetic gate for CAP-API-METRICS. Proves integer counters increment/add, stay 2// independent, and serialize to Prometheus-style text. Sovereign: nx_syscalls + nx_apistack_metrics. expect_exit: 0 3import "nx_syscalls.nx" 4import "nx_apistack_metrics.nx" 5import "nx_gate_verdict.nx" 6 7func gp(s: *u8) -> i64 { var n: i64=0; while s[n]!=(0 as u8){n=n+1} sys_write(1,s,n); return 0 } 8func gn(v: i64) -> i64 { var t: i64=v; if t<0{sys_write(1,"-" as *u8,1);t=0-t} let tm:*u8=sys_mmap(24); var k:i64=0; if t==0{tm[0]=48 as u8;k=1} while t>0{tm[k]=(48+(t%10)) as u8;t=t/10;k=k+1} let b:*u8=sys_mmap(24); var j:i64=0; while j<k{b[j]=tm[k-1-j];j=j+1} sys_write(1,b,k); return 0 } 9func g_slen(s: *u8) -> i64 { var n: i64=0; while s[n]!=(0 as u8){n=n+1} return n } 10func g_contains(hay: *u8, hlen: i64, needle: *u8) -> i64 { 11 let nl: i64 = g_slen(needle); var i: i64 = 0 12 while i + nl <= hlen { var j: i64=0; var m: i64=1; while j<nl { if hay[i+j]!=needle[j] { m=0; j=nl } else { j=j+1 } } if m==1 { return 1 } i=i+1 } 13 return 0 14} 15 16func main(argc: i64, argv: *i64) -> i64 { 17 gp("=== nx_apistack_metrics_gate (deterministic integer counters) ===\n" as *u8) 18 let c: *i64 = sys_mmap(64) as *i64 19 let names: *i64 = sys_mmap(64) as *i64 20 names[0] = "api_deploys_total" as *u8 as i64 21 names[1] = "api_restarts_total" as *u8 as i64 22 var pass: i64 = 0; var fail: i64 = 0 23 24 // T1 inc x3 25 mx_inc(c, 0); mx_inc(c, 0); mx_inc(c, 0) 26 if mx_get(c, 0) == 3 { pass=pass+1; gp(" T1 inc x3 -> 3 PASS\n" as *u8) } else { fail=fail+1; gp(" T1 FAIL=" as *u8); gn(mx_get(c,0)); gp("\n" as *u8) } 27 28 // T2 independent counters 29 mx_inc(c, 1) 30 if mx_get(c, 1) == 1 { if mx_get(c, 0) == 3 { pass=pass+1; gp(" T2 independent counters PASS\n" as *u8) } else { fail=fail+1; gp(" T2 FAIL c0 changed\n" as *u8) } } else { fail=fail+1; gp(" T2 FAIL c1\n" as *u8) } 31 32 // T3 add delta 33 mx_add(c, 0, 10) 34 if mx_get(c, 0) == 13 { pass=pass+1; gp(" T3 add 10 -> 13 PASS\n" as *u8) } else { fail=fail+1; gp(" T3 FAIL\n" as *u8) } 35 36 // T4 emit Prometheus-style 37 let out: *u8 = sys_mmap(4096); let n: i64 = mx_emit(c, names, 2, out) 38 gp(" EMIT: " as *u8); sys_write(1, out, n) 39 if g_contains(out, n, "api_deploys_total 13" as *u8) == 1 { if g_contains(out, n, "api_restarts_total 1" as *u8) == 1 { pass=pass+1; gp(" T4 emit serializes both PASS\n" as *u8) } else { fail=fail+1; gp(" T4 FAIL restarts\n" as *u8) } } else { fail=fail+1; gp(" T4 FAIL deploys\n" as *u8) } 40 41 gp("RESULT pass=" as *u8); gn(pass); gp(" fail=" as *u8); gn(fail) 42 // MIGRATED onto nx_gate_verdict by nx_gate_dry_apply (D001, minimal form): every check 43 // row above is untouched, so the PASS/FAIL vector cannot change; only the hand-rolled 44 // verdict emission is replaced by the ONE shared base class. Proven by nx_gate_migrate verify. 45 let ctr__dry: *i64 = gv_ctr() 46 ctr__dry[0] = pass 47 ctr__dry[1] = pass + fail 48 let rc__dry: i64 = gv_verdict("APISTACK-METRICS-GATE" as *u8, ctr__dry, "teeth unchanged; verdict emission migrated onto the shared base class" as *u8) 49 sys_exit(rc__dry) 50 return rc__dry 51}