code wiki / _hdl_build / nx_write.nx

nx_write.nx source

↩ module page · 489 lines · 22110 B

1// nx_write.nx -- W-BB-1: THE WRITE LANE'S BACKBONE. The organ that actually WRITES. 2// 3// u2605u2605u2605u2605u2605u2605THE GAP THIS CLOSES, AND IT IS EMBARRASSING IN THE RIGHT WAY. The write lane had a ruler 4// (nx_writebench, 625 permil), a panel-reliability bound, a real-person gate, a greeting-structure 5// grader, a campaign continuity checker and a per-turn dialogue meter -- and NO GENERATOR. 6// `nx_writer_run` is 9 functions that emit scaffolding and contain no inference call whatsoever: no 7// engine, no model, no HTTP. Meanwhile the local engine answers /v1/chat/completions in ~1.4s and 8// has all along; the gen lane has been using it for images and chat for weeks. 9// u21d2 WE HAD BUILT GRADERS FOR A THING THAT COULD NOT PRODUCE. 10// u2605u2605u2605u2605u2605u2605A LANE WITH RULERS AND NO PRODUCER MEASURES NOTHING -- COVERAGE ON AN EMPTY LANE IS A 11// NUMBER ABOUT THE RULER, NOT ABOUT A CAPABILITY. 12// 13// WHAT THIS IS: prompt -> real prose, on the local engine, for every mode in the registry -- 14// the writing equivalent of what nx_gen is for images. 15// 16// u2605THE SEAM IS ENFORCED BY CONSTRUCTION, NOT BY POLICY TEXT. write_modes.tsv declares per mode a 17// REGISTER (sfw|mixed|explicit) and a LANE (tutor|local). An `explicit` mode may only run on the 18// `local` lane -- it never leaves this machine. That is a routing fact checked here before a single 19// byte is sent, so it cannot be forgotten by a caller or argued away by a prompt. 20// 21// u2605ENDPOINT FROM THE SWARM SSOT, never a literal: se_addr("gpu-image") -- the same single source the 22// gen daemon resolves per request, so a DHCP move heals both lanes at once (the 6-hardcoded-sites 23// outage is not repeated here). 24// 25// nx_write <mode> <prompt...> -- generate; prose to stdout 26// nx_write modes -- list the registry 27// license_tier: ORIGINAL expect_exit: 0 28// module: nishi-core.write.backbone 29import "nx_syscalls.nx" 30import "nx_estate_path.nx" 31import "nx_connect.nx" 32import "nx_swarm_endpoint_lib.nx" 33import "nx_store_seed_lib.nx" 34import "nx_lane_conf.nx" 35const W_MAGIC_4096: i64 = 4096 36// THE MODE REGISTRY IS A SEG-STORE PLANE (info-plane doctrine 2026-08-01: registries are planes, 37// never TSVs). Seed/refresh via `nx_write migrate` (reads the tombstoned tsv one more time and 38// re-seeds); every lookup reads the plane and FAILS CLOSED if it is unseeded -- a silent tsv 39// fallback here would be a forked SSOT wearing a convenience. 40const W_PLANE: *u8 = "knowledge/store/writemode-" 41 42const W_BUF: i64 = 1048576 43const W_REQ: i64 = 262144 44// u26a0the three below are ABSENT-CONF FALLBACKS ONLY (rule 11): the live values are rows in 45// knowledge/write_lane.conf, hot-read via nx_lane_conf -- edit the conf, never these. 46const W_TMO_SEC: i64 = 300 47const W_MAXTOK: i64 = 1200 48const W_LEN_MIN: i64 = 200 49const W_LEN_MAX: i64 = 8000 50 51func ww(s: *u8) -> i64 { var n: i64 = 0; while s[n] != (0 as u8) { n = n + 1 } sys_write(1, s, n); return 0 } 52func we(s: *u8) -> i64 { var n: i64 = 0; while s[n] != (0 as u8) { n = n + 1 } sys_write(2, s, n); return 0 } 53func w_len(s: *u8) -> i64 { var n: i64 = 0; while s[n] != (0 as u8) { n = n + 1 } return n } 54func w_cat(d: *u8, o: i64, s: *u8) -> i64 { var i: i64 = 0; var a: i64 = o; while s[i] != (0 as u8) { d[a] = s[i]; a = a + 1; i = i + 1 } return a } 55func w_catn(d: *u8, o: i64, v: i64) -> i64 { 56 let t: *u8 = sys_mmap(32) 57 var m: i64 = v; var k: i64 = 0 58 if m < 0 { d[o] = 45 as u8; o = o + 1; m = 0 - m } 59 if m == 0 { t[0] = 48 as u8; k = 1 } 60 while m > 0 { t[k] = (48 + (m % 10)) as u8; m = m / 10; k = k + 1 } 61 var a: i64 = o; var j: i64 = k - 1 62 while j >= 0 { d[a] = t[j]; a = a + 1; j = j - 1 } 63 return a 64} 65// JSON-escape into dst 66func w_jesc(d: *u8, o: i64, s: *u8) -> i64 { 67 var a: i64 = o; var i: i64 = 0 68 while s[i] != (0 as u8) { 69 let c: i64 = s[i] & 0xff 70 if c == 34 { d[a] = 92 as u8; a = a + 1; d[a] = 34 as u8; a = a + 1 } 71 else { if c == 92 { d[a] = 92 as u8; a = a + 1; d[a] = 92 as u8; a = a + 1 } 72 else { if c == 10 { d[a] = 92 as u8; a = a + 1; d[a] = 110 as u8; a = a + 1 } 73 else { if c < 32 { d[a] = 32 as u8; a = a + 1 } else { d[a] = s[i]; a = a + 1 } } } } 74 i = i + 1 75 } 76 return a 77} 78func w_slurp(path: *u8, buf: *u8, cap: i64) -> i64 { 79 let fd: i64 = ep_open_rd(path) 80 if fd < 0 { return 0 - 1 } 81 var t: i64 = 0 82 var r: i64 = 1 83 while r > 0 { 84 if t >= cap { r = 0 } else { r = sys_read(fd, ((buf as i64) + t) as *u8, cap - t); if r > 0 { t = t + r } } 85 } 86 sys_close(fd) 87 return t 88} 89func w_streq(a: *u8, b: *u8) -> i64 { 90 var i: i64 = 0 91 while a[i] != (0 as u8) { if a[i] != b[i] { return 0 } i = i + 1 } 92 if b[i] != (0 as u8) { return 0 } 93 return 1 94} 95// copy field <idx> (tab-separated) of row [s,e) into out; returns length 96func w_field(buf: *u8, s: i64, e: i64, idx: i64, out: *u8, cap: i64) -> i64 { 97 var p: i64 = s 98 var f: i64 = 0 99 while f < idx { 100 var go: i64 = 1 101 while go == 1 { 102 if p >= e { go = 0 } else { if buf[p] == (9 as u8) { p = p + 1; go = 0 } else { p = p + 1 } } 103 } 104 f = f + 1 105 } 106 if p >= e { out[0] = 0 as u8; return 0 } 107 var k: i64 = 0 108 while p < e { 109 if buf[p] == (9 as u8) { p = e } else { 110 if k < cap - 1 { out[k] = buf[p]; k = k + 1 } 111 p = p + 1 112 } 113 } 114 out[k] = 0 as u8 115 return k 116} 117 118// parse unsigned digits from s starting at pi[0]; advances pi past them. 0 if none. 119func w_atoi(s: *u8, pi: *i64) -> i64 { 120 var i: i64 = pi[0] 121 var v: i64 = 0 122 var run: i64 = 1 123 while run == 1 { 124 if s[i] < (48 as u8) { run = 0 } else { 125 if s[i] > (57 as u8) { run = 0 } else { v = v*10 + ((s[i] as i64) - 48); i = i + 1 } 126 } 127 } 128 pi[0] = i 129 return v 130} 131 132// look up a mode row -> register/lane/structure (+ optional col5 max_tokens, col6 arc). 133// Old 5-column rows stay valid: missing fields come back empty -> caller defaults. 1 = found. 134func w_mode_lookup(mode: *u8, reg: *u8, lane: *u8, structure: *u8, mtok: *u8, arc: *u8) -> i64 { 135 let buf: *u8 = sys_mmap(W_BUF) 136 let n: i64 = sts_load(W_PLANE, buf, W_BUF) 137 if n <= 0 { return 0 - 1 } 138 let nm: *u8 = sys_mmap(128) 139 var p: i64 = 0 140 while p < n { 141 var e: i64 = n 142 var q: i64 = p 143 var go: i64 = 1 144 while go == 1 { 145 if q >= n { e = n; go = 0 } else { if buf[q] == (10 as u8) { e = q; go = 0 } else { q = q + 1 } } 146 } 147 if e > p { 148 if buf[p] != (35 as u8) { // skip comments 149 w_field(buf, p, e, 0, nm, 128) 150 if w_streq(nm, mode) == 1 { 151 w_field(buf, p, e, 1, reg, 64) 152 w_field(buf, p, e, 2, lane, 64) 153 w_field(buf, p, e, 3, structure, 64) 154 w_field(buf, p, e, 5, mtok, 16) 155 w_field(buf, p, e, 6, arc, 16) 156 return 1 157 } 158 } 159 } 160 p = e + 1 161 } 162 return 0 163} 164 165func w_list_modes() -> i64 { 166 let buf: *u8 = sys_mmap(W_BUF) 167 let n: i64 = sts_load(W_PLANE, buf, W_BUF) 168 if n <= 0 { we("nx_write: writemode- plane unseeded -- run `nx_write migrate` once\n\x00" as *u8); return 1 } 169 ww("# writemode- plane (SSOT; columns: mode register lane structure description [max_tokens] [arc])\n" as *u8) 170 sys_write(1, buf, n) 171 return 0 172} 173 174// one-time (re)seed: read the tombstoned tsv, keep DATA rows only, sts_seed the plane, report parity. 175func w_migrate() -> i64 { 176 let raw: *u8 = sys_mmap(W_BUF) 177 let n: i64 = w_slurp("knowledge/registry/write_modes.tsv" as *u8, raw, W_BUF) 178 if n <= 0 { we("nx_write migrate: write_modes.tsv unreadable\n\x00" as *u8); return 1 } 179 let clean: *u8 = sys_mmap(W_BUF) 180 var co: i64 = 0 181 var tsvrows: i64 = 0 182 var p: i64 = 0 183 while p < n { 184 var e: i64 = p 185 var go: i64 = 1 186 while go == 1 { 187 if e >= n { go = 0 } else { if raw[e] == (10 as u8) { go = 0 } else { e = e + 1 } } 188 } 189 if e > p { if raw[p] != (35 as u8) { 190 var q: i64 = p 191 while q < e { clean[co] = raw[q]; co = co + 1; q = q + 1 } 192 clean[co] = 10 as u8; co = co + 1 193 tsvrows = tsvrows + 1 194 } } 195 p = e + 1 196 } 197 let seeded: i64 = sts_seed(W_PLANE, clean, co) 198 ww("WRITEMODE-MIGRATE tsv_rows=" as *u8) 199 let nb: *u8 = sys_mmap(32) 200 var nn: i64 = w_catn(nb, 0, tsvrows) 201 sys_write(1, nb, nn) 202 ww(" plane_rows=" as *u8) 203 nn = w_catn(nb, 0, seeded) 204 sys_write(1, nb, nn) 205 if seeded == tsvrows { ww(" PARITY-OK (plane is now the SSOT; tsv is a tombstone)\n" as *u8); return 0 } 206 ww(" PARITY-FAIL -- do not tombstone, investigate\n" as *u8) 207 return 1 208} 209 210// system prompt per STRUCTURE -- the registry's own column drives it, so adding a mode is a row edit. 211// arc column: "complete" = carry the piece through its FULL arc (the fade-out class: a scene prompt 212// that says "end on a beat that invites what comes next" plus a token ceiling reads as coy 213// truncation -- for modes that declare complete, the ending is part of the deliverable). 214func w_system_for(structure: *u8, arc: *u8, out: *u8) -> i64 { 215 var o: i64 = w_cat(out, 0, "You are a skilled prose writer. Write the piece itself with no preamble, no meta-commentary, and no headings unless the form requires them. " as *u8) 216 if w_streq(structure, "scene" as *u8) == 1 { 217 o = w_cat(out, o, "Write a scene: establish who is present and where, let something happen, and end on a beat that invites what comes next. Concrete sensory detail over summary." as *u8) 218 } else { if w_streq(structure, "scenario" as *u8) == 1 { 219 o = w_cat(out, o, "Open a scenario the reader can step into. Three beats: introduce the speaker, establish the situation already in motion, then address the reader directly and hand them the move." as *u8) 220 } else { if w_streq(structure, "panel" as *u8) == 1 { 221 o = w_cat(out, o, "Write a page script as numbered PANEL blocks. Each panel: one line of visual description, then any dialogue." as *u8) 222 } else { if w_streq(structure, "tone" as *u8) == 1 { 223 o = w_cat(out, o, "Match the requested voice closely. Keep sentence rhythm and diction consistent throughout." as *u8) 224 } else { if w_streq(structure, "imrad" as *u8) == 1 { 225 o = w_cat(out, o, "Use IMRaD structure: Introduction, Methods, Results, Discussion. Be precise and cite nothing you cannot support." as *u8) 226 } else { if w_streq(structure, "convo" as *u8) == 1 { 227 o = w_cat(out, o, "Write a natural back-and-forth conversation that keeps the topic moving." as *u8) 228 } else { 229 o = w_cat(out, o, "Write clearly and vividly in the form the request implies." as *u8) 230 } } } } } } 231 if w_streq(arc, "complete" as *u8) == 1 { 232 o = w_cat(out, o, " Carry the piece through its FULL arc to an actual conclusion: the events themselves happen on the page, rendered at the same sensory depth as the rest -- never summarize past them, never fade out, never stop short. The piece ends only after its climax and a brief settling beat." as *u8) 233 } 234 out[o] = 0 as u8 235 return o 236} 237 238// POST /v1/chat/completions to a.b.c.d:port; response into resp. returns length, -1 on failure. 239func w_engine_call(a: i64, b: i64, c: i64, d: i64, port: i64, req: *u8, reqlen: i64, resp: *u8, cap: i64) -> i64 { 240 let fd: i64 = sys_socket(2, 1, 0) 241 if fd < 0 { return 0 - 1 } 242 sys_set_socket_timeout(fd, W_TMO_SEC) 243 let sa: *u8 = sys_mmap(16) 244 sa[0] = 2 as u8; sa[1] = 0 as u8 245 sa[2] = ((port >> 8) & 0xff) as u8; sa[3] = (port & 0xff) as u8 246 sa[4] = a as u8; sa[5] = b as u8; sa[6] = c as u8; sa[7] = d as u8 247 var z: i64 = 8 248 while z < 16 { sa[z] = 0 as u8; z = z + 1 } 249 if nx_connect_bounded(fd, sa, 16, NX_CONN_DEFAULT_MS) != 0 { sys_close(fd); return 0 - 1 } 250 sys_write(fd, req, reqlen) 251 var t: i64 = 0 252 var r: i64 = 1 253 while r > 0 { 254 if t >= cap { r = 0 } else { r = sys_read(fd, ((resp as i64) + t) as *u8, cap - t); if r > 0 { t = t + r } } 255 } 256 sys_close(fd) 257 return t 258} 259 260// try-connect only: 0 = reachable, nonzero = not. Bounded like every other connect here, so an 261// absent/firewalled brain costs one connect window, never a read timeout. 262func w_probe(a: i64, b: i64, c: i64, d: i64, port: i64) -> i64 { 263 let fd: i64 = sys_socket(2, 1, 0) 264 if fd < 0 { return 0 - 1 } 265 let sa: *u8 = sys_mmap(16) 266 sa[0] = 2 as u8; sa[1] = 0 as u8 267 sa[2] = ((port >> 8) & 0xff) as u8; sa[3] = (port & 0xff) as u8 268 sa[4] = a as u8; sa[5] = b as u8; sa[6] = c as u8; sa[7] = d as u8 269 var z: i64 = 8 270 while z < 16 { sa[z] = 0 as u8; z = z + 1 } 271 let rc: i64 = nx_connect_bounded(fd, sa, 16, NX_CONN_DEFAULT_MS) 272 sys_close(fd) 273 if rc != 0 { return 0 - 1 } 274 return 0 275} 276 277// pull the assistant text out of {"choices":[{"message":{"content":"..."}}]} and unescape it. 278func w_extract(resp: *u8, n: i64) -> i64 { 279 let key: *u8 = "\"content\":\"" as *u8 280 let kl: i64 = w_len(key) 281 var i: i64 = 0 282 var s: i64 = 0 - 1 283 while i + kl <= n { 284 var j: i64 = 0 285 var same: i64 = 1 286 while j < kl { if resp[i + j] != key[j] { same = 0; j = kl } else { j = j + 1 } } 287 if same == 1 { s = i + kl; i = n } else { i = i + 1 } 288 } 289 if s < 0 { return 0 - 1 } 290 let out: *u8 = sys_mmap(W_BUF) 291 var o: i64 = 0 292 var p: i64 = s 293 var go: i64 = 1 294 while go == 1 { 295 if p >= n { go = 0 } else { 296 let ch: i64 = resp[p] & 0xff 297 if ch == 34 { go = 0 } 298 else { 299 if ch == 92 { 300 let nx: i64 = resp[p + 1] & 0xff 301 if nx == 110 { out[o] = 10 as u8; o = o + 1; p = p + 2 } 302 else { if nx == 116 { out[o] = 9 as u8; o = o + 1; p = p + 2 } 303 else { out[o] = resp[p + 1]; o = o + 1; p = p + 2 } } 304 } else { out[o] = resp[p]; o = o + 1; p = p + 1 } 305 } 306 } 307 } 308 sys_write(1, out, o) 309 ww("\n\x00" as *u8) 310 return o 311} 312 313// parse "a.b.c.d:port" into w[0..4]; 1 = ok 314func w_parse_addr(s: *u8, w: *i64) -> i64 { 315 var i: i64 = 0 316 var f: i64 = 0 317 while f < 5 { 318 var v: i64 = 0 319 var dig: i64 = 0 320 var scan: i64 = 1 321 while scan == 1 { 322 let c: i64 = s[i] as i64 323 if c < 48 { scan = 0 } else { if c > 57 { scan = 0 } else { v = v * 10 + (c - 48); dig = dig + 1; i = i + 1 } } 324 } 325 if dig == 0 { return 0 } 326 w[f] = v 327 f = f + 1 328 if f < 5 { i = i + 1 } // skip the '.' or ':' 329 } 330 return 1 331} 332 333func main(argc: i64, argv: *i64) -> i64 { 334 ep_anchor() 335 if argc < 2 { 336 ww("usage: nx_write <mode> <prompt...> | nx_write modes\n\x00" as *u8) 337 return 1 338 } 339 let mode: *u8 = argv[1] as *u8 340 if w_streq(mode, "modes" as *u8) == 1 { return w_list_modes() } 341 if w_streq(mode, "migrate" as *u8) == 1 { return w_migrate() } 342 if argc < 3 { we("nx_write: needs a prompt\n\x00" as *u8); return 2 } 343 344 let reg: *u8 = sys_mmap(64) 345 let lane: *u8 = sys_mmap(64) 346 let structure: *u8 = sys_mmap(64) 347 let mtok: *u8 = sys_mmap(16) 348 let arc: *u8 = sys_mmap(16) 349 let found: i64 = w_mode_lookup(mode, reg, lane, structure, mtok, arc) 350 if found < 0 { we("nx_write: writemode- plane unseeded/unreadable (the plane is the SSOT; nothing is guessed) -- run `nx_write migrate`\n\x00" as *u8); return 3 } 351 if found == 0 { 352 we("nx_write: unknown mode -- run `nx_write modes` for the registry\n\x00" as *u8) 353 return 4 354 } 355 356 // u2605THE SEAM, CHECKED BEFORE A BYTE IS SENT: an explicit register may only run on the local lane. 357 if w_streq(reg, "explicit" as *u8) == 1 { 358 if w_streq(lane, "local" as *u8) == 0 { 359 we("nx_write REFUSED: mode is register=explicit but lane=\x00" as *u8); we(lane) 360 we(" -- an explicit register may only run on the local lane. Fix the registry row, not this call.\n\x00" as *u8) 361 return 5 362 } 363 } 364 365 // SPOKE-YIELD ADMISSION (operator 2026-08-05): if the spoke's sentinel reports an interactive 366 // GPU tenant (a game), the swarm YIELDS -- interactive sessions outrank batch generation. The 367 // hub is not brought down and nothing is lost: the writer's async lane keeps the request as a 368 // durable .req and the sweeper runs it when the GPU frees. Conf-driven (gpu_yield_to_games). 369 if lc_write_lane("gpu_yield_to_games" as *u8, 1) == 1 { 370 let gb: *u8 = sys_mmap(256) 371 let gn: i64 = w_slurp("knowledge/status/gpu_avail.conf" as *u8, gb, 250) 372 if gn > 0 { 373 let gp: *i64 = sys_mmap(16) as *i64 374 gp[0] = 0 375 let gep: i64 = w_atoi(gb, gp) 376 let nowt: *i64 = sys_mmap(16) as *i64 377 nowt[0] = 0 378 sys_clock_gettime_real(nowt) 379 if nowt[0] - gep < lc_write_lane("gpu_avail_max_age_sec" as *u8, 180) { 380 var gi: i64 = 0 381 var isgame: i64 = 0 382 while gi + 5 < gn { 383 if gb[gi]==(103 as u8) { if gb[gi+1]==(97 as u8) { if gb[gi+2]==(109 as u8) { if gb[gi+3]==(101 as u8) { if gb[gi+4]==(61 as u8) { 384 if gb[gi+5]==(110 as u8) { if gb[gi+6]==(111 as u8) { if gb[gi+7]==(110 as u8) { if gb[gi+8]==(101 as u8) { isgame = 0-1 } } } } 385 if isgame == 0 { isgame = 1 } 386 gi = gn 387 } } } } } 388 gi = gi + 1 389 } 390 if isgame == 1 { 391 ww("NX-WRITE-DEFERRED gpu yielded to interactive session (sentinel: game present); queued jobs run when the gpu frees\n" as *u8) 392 return 0 393 } 394 } 395 } 396 } 397 398 // endpoint from the swarm SSOT -- prefer the dedicated write brain (gpu-write, llama-server), 399 // fall back to the image engine's chat lane (gpu-image). Both rows live in knowledge/swarm_nodes.conf; 400 // adding/moving a brain is a ROW EDIT, never a code edit. u2605RESOLVE IS NOT REACHABLE (the swarm 401 // co_usable lesson): the preferred role must also PROBE-CONNECT, else a firewalled brain wedges 402 // the lane that a healthy fallback could serve. 403 var addr: *u8 = se_addr("gpu-write" as *u8) 404 if (addr as i64) != 0 { 405 let wp: *i64 = sys_mmap(64) as *i64 406 if w_parse_addr(addr, wp) == 1 { 407 if w_probe(wp[0], wp[1], wp[2], wp[3], wp[4]) != 0 { addr = 0 as *u8 } 408 } else { addr = 0 as *u8 } 409 } 410 if (addr as i64) == 0 { addr = se_addr("gpu-image" as *u8) } 411 if (addr as i64) == 0 { 412 we("nx_write: neither gpu-write nor gpu-image resolvable in knowledge/swarm_nodes.conf (fail-closed; no fabricated endpoint)\n\x00" as *u8) 413 return 6 414 } 415 let w4: *i64 = sys_mmap(64) as *i64 416 if w_parse_addr(addr, w4) == 0 { we("nx_write: malformed endpoint row\n\x00" as *u8); return 6 } 417 418 // length: registry col5 (per mode) -> conf default; a leading len=<N> prompt token 419 // overrides per call, clamped to the conf min/max. 420 var toks: i64 = lc_write_lane("write_default_max_tokens" as *u8, W_MAXTOK) 421 let lmin: i64 = lc_write_lane("write_len_min" as *u8, W_LEN_MIN) 422 let lmax: i64 = lc_write_lane("write_len_max" as *u8, W_LEN_MAX) 423 if mtok[0] != (0 as u8) { 424 let mp: *i64 = sys_mmap(16) as *i64 425 mp[0] = 0 426 let mv: i64 = w_atoi(mtok, mp) 427 if mv > 0 { toks = mv } 428 } 429 // len=<N> may arrive as its OWN argv token (CLI) or as the PREFIX of a single prompt string 430 // (the /write daemon passes the whole body as one arg) -- handle both. 431 var ai: i64 = 2 432 var a2off: i64 = 0 433 let a2: *u8 = argv[2] as *u8 434 if a2[0] == (108 as u8) { if a2[1] == (101 as u8) { if a2[2] == (110 as u8) { if a2[3] == (61 as u8) { 435 let lp: *i64 = sys_mmap(16) as *i64 436 lp[0] = 4 437 let lv: i64 = w_atoi(a2, lp) 438 if lv >= lmin { if lv <= lmax { 439 toks = lv 440 if a2[lp[0]] == (0 as u8) { ai = 3 } else { 441 if a2[lp[0]] == (32 as u8) { a2off = lp[0] + 1 } 442 } 443 } } 444 } } } } 445 if ai >= argc { if a2off == 0 { we("nx_write: needs a prompt after len=\n\x00" as *u8); return 2 } } 446 447 // assemble the prompt from argv[ai..] (a2off skips a consumed len= prefix inside argv[2]) 448 let user: *u8 = sys_mmap(W_REQ) 449 var uo: i64 = 0 450 while ai < argc { 451 if uo > 0 { user[uo] = 32 as u8; uo = uo + 1 } 452 if ai == 2 { uo = w_cat(user, uo, ((a2 as i64) + a2off) as *u8) } else { uo = w_cat(user, uo, argv[ai] as *u8) } 453 ai = ai + 1 454 } 455 user[uo] = 0 as u8 456 457 let sysp: *u8 = sys_mmap(W_MAGIC_4096) 458 w_system_for(structure, arc, sysp) 459 460 let body: *u8 = sys_mmap(W_REQ) 461 var bo: i64 = w_cat(body, 0, "{\"model\":\"local\",\"max_tokens\":" as *u8) 462 bo = w_catn(body, bo, toks) 463 bo = w_cat(body, bo, ",\"messages\":[{\"role\":\"system\",\"content\":\"" as *u8) 464 bo = w_jesc(body, bo, sysp) 465 bo = w_cat(body, bo, "\"},{\"role\":\"user\",\"content\":\"" as *u8) 466 bo = w_jesc(body, bo, user) 467 bo = w_cat(body, bo, "\"}]}" as *u8) 468 469 let req: *u8 = sys_mmap(W_REQ) 470 var ro: i64 = w_cat(req, 0, "POST /v1/chat/completions HTTP/1.1\r\nHost: engine\r\nConnection: close\r\nContent-Type: application/json\r\nContent-Length: " as *u8) 471 ro = w_catn(req, ro, bo) 472 ro = w_cat(req, ro, "\r\n\r\n" as *u8) 473 var bi: i64 = 0 474 while bi < bo { req[ro] = body[bi]; ro = ro + 1; bi = bi + 1 } 475 476 let resp: *u8 = sys_mmap(W_BUF) 477 let rn: i64 = w_engine_call(w4[0], w4[1], w4[2], w4[3], w4[4], req, ro, resp, W_BUF) 478 if rn <= 0 { 479 we("nx_write: engine unreachable at \x00" as *u8); we(addr) 480 we(" -- is the local engine up? (nishi_elara_engine_keeper.ps1)\n\x00" as *u8) 481 return 7 482 } 483 if w_extract(resp, rn) < 0 { 484 we("nx_write: engine replied but no content field -- raw response follows on stderr\n\x00" as *u8) 485 sys_write(2, resp, rn) 486 return 8 487 } 488 return 0 489}