code wiki / (root) / nx_redteam.nx

nx_redteam.nx source

↩ module page · 84 lines · 5180 B

1// nx_redteam.nx -- automated RED-TEAM attack playbooks (census gap) driven over R0's ta_handle. Each attack asserts 2// the SECURE outcome (blocked / escaped / no-crash); a SURVIVED attack reds. Complements the invoke gate by adding the 3// hostile-INPUT classes: JSON injection via registry data, auth-bypass, malformed-body robustness, unknown-method. 4// (In-process today; a LIVE-edge playbook over nishifamily.com is the ratchet once tools/call deploys.) license_tier: ORIGINAL 5import "nx_tools_api.nx" // ta_handle_pfx + tool_register_pfx + capt_issue + TA_CAP_SECRET + ta_* (transitive) 6import "nx_gate.nx" 7const K_MAGIC_1048576: i64 = 1048576 8const K_MAGIC_4096: i64 = 4096 9 10func rt_has(o: *u8, n: i64, ndl: *u8) -> i64 { if ta_indexof(o, n, ndl) >= 0 { return 1 } return 0 } 11func rt_mark(cond: i64, p: *i64, t: *i64, lbl: *u8) -> i64 { 12 t[0] = t[0] + 1 13 if cond == 1 { p[0] = p[0] + 1; gw(" [BLOCKED] " as *u8) } else { gw(" [VULN!! ] " as *u8) } 14 gw(lbl); gw("\n" as *u8) 15 return 0 16} 17// build "POST /mcp ... <jbody>" with optional X-Nishi-Cap header. jbody passed raw (jblen bytes) so we can inject malformed. 18func rt_req(cap: *u8, caplen: i64, jbody: *u8, jblen: i64, out: *u8) -> i64 { 19 var o: i64 = ta_cat(out, 0, "POST /mcp HTTP/1.1\r\nHost: x\r\n" as *u8) 20 if caplen > 0 { o = ta_cat(out, o, "X-Nishi-Cap: " as *u8); o = ta_catb(out, o, cap, caplen); o = ta_cat(out, o, "\r\n" as *u8) } 21 o = ta_cat(out, o, "Connection: close\r\n\r\n" as *u8) 22 o = ta_catb(out, o, jbody, jblen) 23 return o 24} 25// tools/call body with `name` into buf; returns length. 26func rt_callbody(name: *u8, buf: *u8) -> i64 { 27 var o: i64 = ta_cat(buf, 0, "{\"jsonrpc\":\"2.0\",\"id\":1,\"method\":\"tools/call\",\"params\":{\"name\":\"" as *u8) 28 o = ta_cat(buf, o, name) 29 o = ta_cat(buf, o, "\"}}" as *u8) 30 return o 31} 32 33func main() -> i64 { 34 gw("=== nx_redteam: automated attack playbooks over R0 -- each attack MUST be blocked/escaped/survived-without-crash ===\n" as *u8) 35 let TP: *u8 = "knowledge/toolreg-test-rt-" as *u8 36 let secret: *u8 = TA_CAP_SECRET 37 let slen: i64 = ta_slen(secret) 38 let pbox: *i64 = sys_mmap(16) as *i64; pbox[0] = 0 39 let tbox: *i64 = sys_mmap(16) as *i64; tbox[0] = 0 40 let out: *u8 = sys_mmap(K_MAGIC_1048576) 41 let req: *u8 = sys_mmap(K_MAGIC_4096) 42 let jb: *u8 = sys_mmap(K_MAGIC_4096) 43 44 // RT1 INJECTION: register a tool whose description carries a raw `"` -> GET /api/tools MUST escape it (\" present) so 45 // it can't break out of the JSON string (no response-injection via registry data). 46 tool_register_pfx(TP, "rt_injtool" as *u8, "mal\"icious" as *u8, "x" as *u8, "gate" as *u8) 47 let r1: i64 = ta_cat(req, 0, "GET /api/tools HTTP/1.1\r\nHost: x\r\n\r\n" as *u8) 48 let n1: i64 = ta_handle_pfx(TP, req, r1, out) 49 var t1: i64 = 0; if rt_has(out, n1, "\\\"" as *u8) == 1 { t1 = 1 } 50 rt_mark(t1, pbox, tbox, "RT1 JSON-injection via registry data -> escaped (\\\" in output; string not broken)" as *u8) 51 52 // RT2 AUTH-BYPASS: tools/call with NO capability -> denied (-32001). 53 let b2: i64 = rt_callbody("nx_http_probe" as *u8, jb) 54 let r2: i64 = rt_req(0 as *u8, 0, jb, b2, req) 55 let n2: i64 = ta_handle_pfx(TP, req, r2, out) 56 var t2: i64 = 0; if rt_has(out, n2, "-32001" as *u8) == 1 { t2 = 1 } 57 rt_mark(t2, pbox, tbox, "RT2 invoke with NO capability -> DENIED (no ambient authority)" as *u8) 58 59 // RT3 FORGERY: tools/call with a garbage/forged capability -> denied. 60 let b3: i64 = rt_callbody("nx_http_probe" as *u8, jb) 61 let r3: i64 = rt_req("garbage.forged.token.zzzz" as *u8, 25, jb, b3, req) 62 let n3: i64 = ta_handle_pfx(TP, req, r3, out) 63 var t3: i64 = 0; if rt_has(out, n3, "-32001" as *u8) == 1 { t3 = 1 } 64 rt_mark(t3, pbox, tbox, "RT3 invoke with a FORGED/garbage capability -> DENIED (unforgeable)" as *u8) 65 66 // RT4 MALFORMED BODY: truncated JSON-RPC -> graceful (no crash; a non-empty response comes back). 67 let mal: *u8 = "{\"jsonrpc\":\"2.0\",\"id\":1,\"method\":" as *u8 68 let r4: i64 = rt_req(0 as *u8, 0, mal, ta_slen(mal), req) 69 let n4: i64 = ta_handle_pfx(TP, req, r4, out) 70 var t4: i64 = 0; if n4 > 0 { t4 = 1 } 71 rt_mark(t4, pbox, tbox, "RT4 malformed/truncated body -> handled gracefully (no crash, response returned)" as *u8) 72 73 // RT5 UNKNOWN METHOD: -> -32601 (not found), no crash. 74 let b5: i64 = ta_cat(jb, 0, "{\"jsonrpc\":\"2.0\",\"id\":1,\"method\":\"admin/deleteEverything\"}" as *u8) 75 let r5: i64 = rt_req(0 as *u8, 0, jb, b5, req) 76 let n5: i64 = ta_handle_pfx(TP, req, r5, out) 77 var t5: i64 = 0; if rt_has(out, n5, "-32601" as *u8) == 1 { t5 = 1 } 78 rt_mark(t5, pbox, tbox, "RT5 unknown/hostile method -> -32601 not-found (no crash, no unintended action)" as *u8) 79 80 gw("\n=== nx_redteam " as *u8); gn(pbox[0]); gw("/" as *u8); gn(tbox[0]); gw(" attacks blocked ===\n" as *u8) 81 if pbox[0] == tbox[0] { gw("RED-TEAM GREEN -- every attack in the playbook was blocked/escaped/survived. No vuln found.\n" as *u8); sys_exit(0); return 0 } 82 gw("RED-TEAM RED -- an attack SUCCEEDED. That is a vulnerability -> bank it (nx_regress_bank) + fix.\n" as *u8) 83 sys_exit(1); return 1 84}