nx_qwen_extract.nx source
↩ module page · 135 lines · 6558 B
1// nx_qwen_extract.nx -- R5: the pretrained sovereign Qwen as the RESEARCHER'S EXTRACTION stage (importable by
2// nx_qabench). qwx_load() boots the model ONCE (like rd_load); qwx_extract(g, para, pred) reads paragraph `para`'s
3// sentences + the question (qabench g[] slots) and greedy-generates an answer IN-PROCESS (nsv_generate, no HTTP),
4// writing the first-line answer into pred (db_setpred convention: <=250 chars + NUL). Opt-in: qabench calls these
5// only in qwen-reader mode. PROVEN standalone: nx_qwen_reader_bench_gate measured Qwen-as-reader >> mechanical 251.
6// Sovereign: nx_nofloat_serve_core. ⚠tk_bpe_encode overflows g_nsv_ids past 192 tok BEFORE its length check ->
7// the QWX_MAXPROMPT char guard is MANDATORY (SIGSEGV otherwise). license_tier: ORIGINAL
8import "nx_syscalls.nx"
9import "nx_nofloat_serve_core.nx"
10
11const QWX_MODEL: *u8 = "/home/elderwesto/nx_stage/nx_real_model.gguf"
12const QWX_CTXCAP: i64 = 500 // s0-window context cap; 253(1-shot)+500+140(Q+cues)=893 < MAXPROMPT. ⚠2-shot@380 was REVERTED: measured on-protocol SQuAD 427 < 1-shot@500 510 (surface benefit null under multi-alias; 380 clips real retrieved paras). See arc memory.
13const QWX_MAXPROMPT: i64 = 900 // hard char guard at the PROVEN-SAFE band: 900/2.5-worst-bpe = 360 tok + 16 gen = 376 < NSV_MAXT=384 (1000 allowed ~400 tok worst-case = g_nsv_ids overflow risk)
14const QWX_MAXNEW: i64 = 16
15const QWX_MODE: i64 = 0 // 0 = i32 lossless (faithful default; i8 also verified working at NSV_MAXT=384)
16
17static g_qwx_ready: i64 // 0 until nsv_init succeeds (BSS-zero, safe to read pre-init)
18static g_qwx_pr: *u8 // preallocated prompt/out/meta/gp (no per-question mmap accumulation)
19static g_qwx_out: *u8
20static g_qwx_meta: *i64
21static g_qwx_gp: *i64
22
23// boot the model once (idempotent). returns 0 on success (or if already loaded), else the nsv_init rc.
24// model path: knowledge/index/qwen_model_path.txt overrides QWX_MODEL when present (config over hardcode --
25// NAS-exec has no /home/elderwesto; one trimmed line, kept in a persistent mmap so nsv_init's pointer stays valid).
26func qwx_load() -> i64 {
27 if g_qwx_ready == 1 { return 0 }
28 var mp: *u8 = QWX_MODEL
29 let pfd: i64 = sys_openat_rd("knowledge/index/qwen_model_path.txt" as *u8)
30 if pfd >= 0 {
31 let pb: *u8 = sys_mmap(512)
32 let pn: i64 = sys_read(pfd, pb, 511)
33 sys_close(pfd)
34 var pe: i64 = pn
35 var trim: i64 = 1
36 while trim == 1 {
37 trim = 0
38 if pe > 0 {
39 let c: i64 = pb[pe-1] as i64
40 if c == 10 { pe=pe-1; trim=1 } else { if c == 13 { pe=pe-1; trim=1 } else { if c == 32 { pe=pe-1; trim=1 } } }
41 }
42 }
43 if pe > 0 { pb[pe] = 0 as u8; mp = pb }
44 }
45 let rc: i64 = nsv_init(mp)
46 if rc != 0 { return rc }
47 g_qwx_pr = sys_mmap(2048)
48 g_qwx_out = sys_mmap(4096)
49 g_qwx_meta = sys_mmap(8*8) as *i64
50 g_qwx_gp = sys_mmap(12*8) as *i64
51 g_qwx_ready = 1
52 return 0
53}
54func qwx_ready() -> i64 { return g_qwx_ready }
55
56func qwx_cat(dst: *u8, off: i64, s: *u8, n: i64, cap: i64) -> i64 {
57 var i: i64 = 0
58 var o: i64 = off
59 while i < n { if o < cap { dst[o]=s[i]; o=o+1 } i=i+1 }
60 return o
61}
62func qwx_cats(dst: *u8, off: i64, s: *u8, cap: i64) -> i64 {
63 var i: i64 = 0
64 var o: i64 = off
65 while s[i] != (0 as u8) { if o < cap { dst[o]=s[i]; o=o+1 } i=i+1 }
66 return o
67}
68
69// extract an answer for the question in g[4] into pred, giving Qwen a context window CENTERED on the retrieved
70// best sentence s0 (NOT the paragraph start -- a long SQuAD paragraph truncated from the start hides the answer).
71// Reads qabench sentence slots g[15]/16/17/18, g[19]=ns. returns 1 if generated, 0 if not-ready/too-long/empty.
72func qwx_extract(g: *i64, s0: i64, pred: *u8) -> i64 {
73 if g_qwx_ready == 0 { return 0 }
74 if s0 < 0 { return 0 }
75 let q: *u8 = g[4] as *u8
76 let sb: *u8 = g[15] as *u8
77 let so: *i64 = g[16] as *i64
78 let sl: *i64 = g[17] as *i64
79 let sp: *i64 = g[18] as *i64
80 let ns: i64 = g[19]
81 let para: i64 = sp[s0] // the paragraph containing the retrieved best sentence
82 let pr: *u8 = g_qwx_pr
83 var po: i64 = 0
84 po = qwx_cats(pr, po, "Extract the answer as the shortest exact phrase from the context, not a sentence.\n\nContext: The Eiffel Tower was completed in 1889 and stands in the city of Paris.\nQuestion: In what city is the Eiffel Tower?\nAnswer: Paris\n\nContext: " as *u8, 2048)
85 var s: i64 = s0 - 1 // s0-CENTERED WINDOW (s0 +/- 1 neighbor, same para): the
86 if s < 0 { s = 0 } // retrieved best sentence + coreference support. MEASURED
87 var send: i64 = s0 + 1 // (bench D-v2 vs whole-para): tight relevant window is
88 if send >= ns { send = ns - 1 } // non-inferior on F1, sends fewer tokens (faster), and
89 var ctxlen: i64 = 0 // defuses the 1-shot+whole-para guard-skip on long paras.
90 while s <= send {
91 if sp[s] == para { if ctxlen < QWX_CTXCAP {
92 var take: i64 = sl[s]
93 if ctxlen + take > QWX_CTXCAP { take = QWX_CTXCAP - ctxlen }
94 po = qwx_cat(pr, po, (sb as i64 + so[s]) as *u8, take, 2048)
95 po = qwx_cat(pr, po, " " as *u8, 1, 2048)
96 ctxlen = ctxlen + take + 1
97 } }
98 s = s + 1
99 }
100 po = qwx_cats(pr, po, "\n\nQuestion: " as *u8, 2048)
101 var qc: i64 = 0
102 while q[qc] != (0 as u8) { qc = qc + 1 }
103 if qc > 120 { qc = 120 }
104 po = qwx_cat(pr, po, q, qc, 2048)
105 po = qwx_cats(pr, po, "\nAnswer:" as *u8, 2048)
106 if po > QWX_MAXPROMPT { return 0 } // MANDATORY guard: never let nprompt exceed the 192-tok window
107
108 let out: *u8 = g_qwx_out
109 let gp: *i64 = g_qwx_gp
110 gp[0]=pr as i64
111 gp[1]=po
112 gp[2]=QWX_MAXNEW
113 gp[3]=QWX_MODE
114 gp[4]=out as i64
115 gp[5]=4096
116 gp[6]=g_qwx_meta as i64
117 gp[7]=0-1
118 gp[8]=0
119 gp[9]=0
120 gp[10]=0
121 gp[11]=0
122 let tlen: i64 = nsv_generate(gp)
123 if tlen <= 0 { return 0 }
124 var el: i64 = tlen
125 var i2: i64 = 0
126 var nlf: i64 = 0
127 while i2 < tlen { if nlf==0 { if (out[i2] as i64)==10 { el=i2; nlf=1 } } i2=i2+1 }
128 var st: i64 = 0
129 if el > 0 { if (out[0] as i64)==32 { st=1 } } // trim the model's leading space (" Von Miller")
130 var w: i64 = 0
131 var k: i64 = st
132 while k < el { if w < 250 { pred[w]=out[k]; w=w+1 } k=k+1 }
133 pred[w] = 0 as u8
134 return 1
135}