code wiki / (root) / nx_service_test.nx

nx_service_test.nx source

↩ module page · 164 lines · 8529 B

1// nx_service_test.nx -- gate for the service base. The JSON writer is checked 2// BYTE-FOR-BYTE against expected output (a wire format that drifts is a broken 3// API), escaping is proven to neutralise an injection attempt, and the 4// overflow flag is proven to trip rather than corrupt. 5// expect_exit: 0 license_tier: ORIGINAL 6import "nx_syscalls.nx" 7import "nx_service.nx" 8 9func t_puts(s: *u8) -> i64 { var n: i64 = 0; while s[n] != (0 as u8) { n = n + 1 } sys_write(1, s, n); return 0 } 10func t_putn(v: i64) -> i64 { let bb: *u8 = sys_mmap(28); var m: i64 = v; if m < 0 { m = 0 - m; sys_write(1, "-" as *u8, 1) } let t: *u8 = sys_mmap(28); var k: i64 = 0; if m == 0 { t[0] = 48 as u8; k = 1 } while m > 0 { t[k] = (48 + (m % 10)) as u8; m = m / 10; k = k + 1 } var i: i64 = 0; while i < k { bb[i] = t[k - 1 - i]; i = i + 1 } sys_write(1, bb, k); return 0 } 11 12// Compare j's buffer against a NUL-terminated expected string, byte for byte. 13func j_matches(j: *NxJson, want: *u8) -> i64 { 14 var n: i64 = 0 15 while want[n] != (0 as u8) { n = n + 1 } 16 if j.off != n { return 0 } 17 let b: *u8 = j.buf 18 var i: i64 = 0 19 while i < n { 20 if b[i] != want[i] { return 0 } 21 i = i + 1 22 } 23 return 1 24} 25 26func main() -> i64 { 27 var pass: i64 = 0 28 var total: i64 = 0 29 30 // --- T1 integers, including negatives and zero --- 31 total = total + 1 32 let j1: *NxJson = nx_json_new(256) 33 nj_puti(j1, 0) 34 nj_putc(j1, 44) 35 nj_puti(j1, 42) 36 nj_putc(j1, 44) 37 nj_puti(j1, 0 - 1045) 38 let ok1: i64 = j_matches(j1, "0,42,-1045" as *u8) 39 t_puts("T1 integer emit '0,42,-1045': " as *u8) 40 if ok1 == 1 { pass = pass + 1; t_puts("PASS\n" as *u8) } else { t_puts("FAIL got '" as *u8); sys_write(1, j1.buf, j1.off); t_puts("'\n" as *u8) } 41 42 // --- T2 a key/value object, byte-exact --- 43 total = total + 1 44 let j2: *NxJson = nx_json_new(256) 45 nj_putc(j2, 123) 46 nj_kv_int(j2, "dose_mg" as *u8, 600) 47 nj_comma(j2) 48 nj_kv_str(j2, "name" as *u8, "Ashwagandha" as *u8) 49 nj_comma(j2) 50 nj_kv_bool(j2, "lawful" as *u8, 1) 51 nj_putc(j2, 125) 52 let ok2: i64 = j_matches(j2, "{\"dose_mg\":600,\"name\":\"Ashwagandha\",\"lawful\":true}" as *u8) 53 t_puts("T2 kv object byte-exact: " as *u8) 54 if ok2 == 1 { pass = pass + 1; t_puts("PASS\n" as *u8) } else { t_puts("FAIL got '" as *u8); sys_write(1, j2.buf, j2.off); t_puts("'\n" as *u8) } 55 56 // --- T3 ESCAPING neutralises an injection attempt --- 57 // A claim sentence carrying a quote and a backslash must not break out of 58 // its string. This is the boundary defence, proven. 59 total = total + 1 60 let j3: *NxJson = nx_json_new(256) 61 nj_putstr(j3, "he said \"cure\" \\ done" as *u8) 62 let ok3: i64 = j_matches(j3, "\"he said \\\"cure\\\" \\\\ done\"" as *u8) 63 t_puts("T3 injection-safe escaping: " as *u8) 64 if ok3 == 1 { pass = pass + 1; t_puts("PASS\n" as *u8) } else { t_puts("FAIL got '" as *u8); sys_write(1, j3.buf, j3.off); t_puts("'\n" as *u8) } 65 66 // --- T4 the OK envelope, open + data + close --- 67 total = total + 1 68 let j4: *NxJson = nx_json_new(512) 69 nsvc_ok_open(j4, "gtm" as *u8, "ingredient.class" as *u8) 70 nj_kv_int(j4, "class" as *u8, 1) 71 j4.ov = 0 72 nsvc_ok_close(j4) 73 let ok4: i64 = j_matches(j4, "{\"v\":1,\"svc\":\"gtm\",\"verb\":\"ingredient.class\",\"ok\":true,\"data\":{\"class\":1},\"truncated\":false}" as *u8) 74 t_puts("T4 ok envelope byte-exact: " as *u8) 75 if ok4 == 1 { pass = pass + 1; t_puts("PASS\n" as *u8) } else { t_puts("FAIL got '" as *u8); sys_write(1, j4.buf, j4.off); t_puts("'\n" as *u8) } 76 77 // --- T5 the ERROR envelope, with machine-readable code + HTTP status --- 78 total = total + 1 79 let j5: *NxJson = nx_json_new(512) 80 nsvc_error(j5, "gtm" as *u8, "bogus.verb" as *u8, NSVC_ERR_UNKNOWN_VERB, "no such verb" as *u8) 81 let ok5: i64 = j_matches(j5, "{\"v\":1,\"svc\":\"gtm\",\"verb\":\"bogus.verb\",\"ok\":false,\"error\":{\"code\":\"UNKNOWN_VERB\",\"status\":404,\"detail\":\"no such verb\"}}" as *u8) 82 t_puts("T5 error envelope byte-exact: " as *u8) 83 if ok5 == 1 { pass = pass + 1; t_puts("PASS\n" as *u8) } else { t_puts("FAIL got '" as *u8); sys_write(1, j5.buf, j5.off); t_puts("'\n" as *u8) } 84 85 // --- T6 error status + slug tables --- 86 total = total + 1 87 var ok6: i64 = 1 88 if nsvc_err_status(NSVC_ERR_BAD_ARGS) != 400 { ok6 = 0 } 89 if nsvc_err_status(NSVC_ERR_REFUSED) != 422 { ok6 = 0 } 90 if nsvc_err_status(NSVC_ERR_INTERNAL) != 500 { ok6 = 0 } 91 if nsvc_streq(nsvc_err_slug(NSVC_ERR_REFUSED), "REFUSED" as *u8) != 1 { ok6 = 0 } 92 t_puts("T6 error status 400/422/500 + slug: " as *u8) 93 if ok6 == 1 { pass = pass + 1; t_puts("PASS\n" as *u8) } else { t_puts("FAIL\n" as *u8) } 94 95 // --- T7 TRUNCATION IS MARKED, NEVER SILENT --- 96 // A tiny buffer overflows; ov must trip and the envelope must SAY so. 97 total = total + 1 98 let j7: *NxJson = nx_json_new(8) 99 nj_puts(j7, "this string is definitely longer than eight bytes" as *u8) 100 let ov: i64 = j7.ov 101 let len: i64 = j7.off 102 t_puts("T7 overflow flag=" as *u8); t_putn(ov); t_puts(" len=" as *u8); t_putn(len); t_puts(" cap=8 (flag set, bounded): " as *u8) 103 var ok7: i64 = 1 104 if ov != 1 { ok7 = 0 } 105 if len != 8 { ok7 = 0 } 106 if ok7 == 1 { pass = pass + 1; t_puts("PASS\n" as *u8) } else { t_puts("FAIL\n" as *u8) } 107 108 // --- T8 argv helpers: bounds-safe access + integer parse --- 109 total = total + 1 110 let av: *i64 = sys_mmap(32) 111 av[0] = "prog" as i64 112 av[1] = "verb" as i64 113 av[2] = "-42" as i64 114 let a1: *u8 = nsvc_arg(3, av, 1) 115 let a_oob: *u8 = nsvc_arg(3, av, 9) 116 let ai: i64 = nsvc_arg_int(3, av, 2) 117 let eq: i64 = nsvc_streq(a1, "verb" as *u8) 118 let oob_empty: i64 = a_oob[0] as i64 119 t_puts("T8 arg[1]='verb'=" as *u8); t_putn(eq); t_puts(" arg[2] parsed=" as *u8); t_putn(ai); t_puts(" oob-is-empty=" as *u8); t_putn(oob_empty); t_puts(": " as *u8) 120 var ok8: i64 = 1 121 if eq != 1 { ok8 = 0 } 122 if ai != 0 - 42 { ok8 = 0 } 123 if oob_empty != 0 { ok8 = 0 } 124 if ok8 == 1 { pass = pass + 1; t_puts("PASS\n" as *u8) } else { t_puts("FAIL\n" as *u8) } 125 126 // --- T9 atoi edge cases --- 127 total = total + 1 128 let z: i64 = nsvc_atoi("\x00" as *u8) 129 let big: i64 = nsvc_atoi("39990" as *u8) 130 let neg: i64 = nsvc_atoi("-7" as *u8) 131 t_puts("T9 atoi empty=" as *u8); t_putn(z); t_puts(" '39990'=" as *u8); t_putn(big); t_puts(" '-7'=" as *u8); t_putn(neg); t_puts(": " as *u8) 132 var ok9: i64 = 1 133 if z != 0 { ok9 = 0 } 134 if big != 39990 { ok9 = 0 } 135 if neg != 0 - 7 { ok9 = 0 } 136 if ok9 == 1 { pass = pass + 1; t_puts("PASS\n" as *u8) } else { t_puts("FAIL\n" as *u8) } 137 138 // --- T10 the GROUNDING TRAILER: nsvc_ok_close_g emits the evidence tier, 139 // the verified flag, and the meaning -- byte-exact --- 140 total = total + 1 141 let jg: *NxJson = nx_json_new(512) 142 nsvc_ok_open(jg, "gtm" as *u8, "ethics.rank" as *u8) 143 nj_kv_int(jg, "cpi" as *u8, 90) 144 jg.ov = 0 145 nsvc_ok_close_g(jg, GND_ASSERTED) 146 let okg: i64 = j_matches(jg, "{\"v\":1,\"svc\":\"gtm\",\"verb\":\"ethics.rank\",\"ok\":true,\"data\":{\"cpi\":90,\"grounding\":\"ASSERTED\",\"verified\":false,\"grounding_note\":\"domain-knowledge constant; no in-system external check\"},\"truncated\":false}" as *u8) 147 t_puts("T10 grounding trailer (ASSERTED, verified:false) byte-exact: " as *u8) 148 if okg == 1 { pass = pass + 1; t_puts("PASS\n" as *u8) } else { t_puts("FAIL got '" as *u8); sys_write(1, jg.buf, jg.off); t_puts("'\n" as *u8) } 149 150 // --- T11 an ANCHORED datum reports verified:true --- 151 total = total + 1 152 let ja: *NxJson = nx_json_new(512) 153 nsvc_ok_open(ja, "labsci" as *u8, "x" as *u8) 154 nj_kv_int(ja, "mass" as *u8, 10455345) 155 ja.ov = 0 156 nsvc_ok_close_g(ja, GND_ANCHORED) 157 let oka: i64 = j_matches(ja, "{\"v\":1,\"svc\":\"labsci\",\"verb\":\"x\",\"ok\":true,\"data\":{\"mass\":10455345,\"grounding\":\"ANCHORED\",\"verified\":true,\"grounding_note\":\"independent method + external literature agree\"},\"truncated\":false}" as *u8) 158 t_puts("T11 ANCHORED datum reports verified:true byte-exact: " as *u8) 159 if oka == 1 { pass = pass + 1; t_puts("PASS\n" as *u8) } else { t_puts("FAIL got '" as *u8); sys_write(1, ja.buf, ja.off); t_puts("'\n" as *u8) } 160 161 t_puts("SERVICE-BASE-GATE passed " as *u8); t_putn(pass); t_puts("/" as *u8); t_putn(total) 162 if pass == total { t_puts(" verdict=GREEN\n" as *u8); sys_exit(0); return 0 } 163 t_puts(" verdict=RED\n" as *u8); sys_exit(1); return 1 164}