code wiki / (root) / nx_help.nx

nx_help.nx source

↩ module page · 252 lines · 8120 B

1// nx_help.nx -- substrate-native S-class help / search engine. 2// 3// User mandate 2026-05-13: 'this should allow nishilang to have its 4// own native search engine of itself a true s class help'. 5// 6// Single entry point that unifies search across: 7// - nx_jargon terminology + cross-discipline aliases 8// - nx_qed_db theorem entries with verify_status 9// - nx_question_genealogy why-chains 10// - (queued) theorem cards from THEOREM_CATALOG 11// 12// Sealed result kinds; tier-appropriate answers; no external network; 13// no AI hallucination. Every result cites a primary source from 14// nishi-library/seeds/formal_math/. 15// 16// genealogy_id: knuth_taocp + dewey_decimal + library_science 17// lineage_id: unified_search + faceted_query 18// axioms: NX_AX_LOGIC_IDENTITY (a result IS its content) 19 20// nx_safety_envelope: 21// intended_use: AUTO_APPLIED -- primitive-specific tuning queued 22// sil_target: SIL1 23// evidence: [bulk_applied_2026-05-16, see-file-comment-for-detail] 24// verdict: NOT_YET_EVALUATED 25 26import "syscalls.nx" 27import "nx_axioms.nx" 28import "nx_jargon.nx" 29import "nx_qed_db.nx" 30import "nx_question_genealogy.nx" 31 32// ===== sealed result kinds ============================================= 33 34const NX_HELP_KIND_NONE: i64 = 0 35const NX_HELP_KIND_JARGON_DEFINITION: i64 = 1 36const NX_HELP_KIND_THEOREM_CARD: i64 = 2 37const NX_HELP_KIND_QUESTION_NARRATIVE: i64 = 3 38const NX_HELP_KIND_AMBIGUOUS: i64 = 4 // multiple matches 39 40// ===== unified result ================================================= 41 42struct HelpResult { 43 kind: i64, // sealed NX_HELP_KIND_* 44 primary_id: i64, // index into the matching DB 45 secondary_id: i64, // for cross-references 46 tier: i64, // NX_TIER_BEGINNER / INTERMEDIATE / EXPERT 47 text: *u8, // best-match explanation 48 n_alternates: i64, // count of other matches 49} 50 51const NX_HELP_RESULT_BYTES: i64 = 48 52 53func nx_help_result_alloc() -> *HelpResult { 54 let raw: *u8 = sys_mmap(NX_HELP_RESULT_BYTES) 55 let r: *HelpResult = raw as *HelpResult 56 r.kind = NX_HELP_KIND_NONE 57 r.primary_id = -1 58 r.secondary_id = -1 59 r.tier = NX_TIER_BEGINNER 60 r.text = "" as *u8 61 r.n_alternates = 0 62 return r 63} 64 65// ===== unified search ================================================ 66// 67// Searches each substrate DB in turn: 68// 1. Jargon (term + discipline + tier) 69// 2. QED theorem name 70// 3. Question genealogy (text contains query) 71// Returns first match; counts other potential matches in n_alternates. 72 73func nx_help_str_starts_with(haystack: *u8, needle: *u8) -> i64 { 74 var i: i64 = 0 75 while i < 128 { 76 if needle[i] == 0 { return 1 } 77 if haystack[i] == 0 { return 0 } 78 if needle[i] != haystack[i] { return 0 } 79 i = i + 1 80 } 81 return 0 82} 83 84// Search jargon DB. Returns matching entry index per (term, discipline, tier). 85func nx_help_search_jargon(jd: *JargonDb, query: *u8, 86 discipline: i64, tier: i64, 87 result: *HelpResult) -> i64 { 88 let idx: i64 = nx_jargon_lookup(jd, query, discipline, tier) 89 if idx < 0 { return 0 } 90 let e: *JargonEntry = nx_jargon_entry_at(jd, idx) 91 result.kind = NX_HELP_KIND_JARGON_DEFINITION 92 result.primary_id = idx 93 result.tier = tier 94 result.text = e.explanation 95 return 1 96} 97 98// Search QED DB by name. 99func nx_help_search_qed(qd: *QedDb, query: *u8, 100 result: *HelpResult) -> i64 { 101 let qid: i64 = nx_qed_find_by_name(qd, query) 102 if qid <= 0 { return 0 } 103 // Find the entry with that qed_id. 104 var i: i64 = 0 105 while i < qd.n_entries { 106 let e: *QedEntry = nx_qed_entry_at(qd, i) 107 if e.qed_id == qid { 108 result.kind = NX_HELP_KIND_THEOREM_CARD 109 result.primary_id = i 110 result.secondary_id = qid 111 result.text = e.name 112 return 1 113 } 114 i = i + 1 115 } 116 return 0 117} 118 119// Search question genealogy by substring match on question text. 120// Returns node index of first node whose question_text starts with query. 121func nx_help_search_qg(qt: *QuestionTree, query: *u8, 122 result: *HelpResult) -> i64 { 123 var i: i64 = 0 124 while i < qt.n_nodes { 125 let n: *QuestionNode = nx_qg_node_at(qt, i) 126 if nx_help_str_starts_with(n.question_text, query) == 1 { 127 result.kind = NX_HELP_KIND_QUESTION_NARRATIVE 128 result.primary_id = i 129 result.tier = n.tier 130 result.text = n.question_text 131 return 1 132 } 133 i = i + 1 134 } 135 return 0 136} 137 138// Top-level: search ALL substrate DBs, return best match. 139func nx_help_query(jd: *JargonDb, qd: *QedDb, qt: *QuestionTree, 140 query: *u8, discipline: i64, tier: i64, 141 result: *HelpResult) -> i64 { 142 // Try jargon first (most likely query). 143 if nx_help_search_jargon(jd, query, discipline, tier, result) == 1 { 144 // Count alternates: same query at other tiers / disciplines. 145 var alts: i64 = 0 146 var t: i64 = 0 147 while t < 3 { 148 if t != tier { 149 if nx_jargon_lookup(jd, query, discipline, t) >= 0 { 150 alts = alts + 1 151 } 152 } 153 t = t + 1 154 } 155 result.n_alternates = alts 156 return 1 157 } 158 // Try theorem DB. 159 if nx_help_search_qed(qd, query, result) == 1 { 160 return 1 161 } 162 // Try question genealogy. 163 if nx_help_search_qg(qt, query, result) == 1 { 164 return 1 165 } 166 result.kind = NX_HELP_KIND_NONE 167 return 0 168} 169 170// ===== narrative emission ============================================= 171 172func hp_putc(fd: i64, c: i64) -> i64 { 173 let buf: *u8 = sys_mmap(1) 174 buf[0] = c & 0xFF 175 sys_write(fd, buf, 1) 176 return 0 177} 178 179func hp_str(fd: i64, s: *u8, n: i64) -> i64 { 180 sys_write(fd, s, n) 181 return 0 182} 183 184func hp_strz(fd: i64, s: *u8) -> i64 { 185 var i: i64 = 0 186 while s[i] != 0 { i = i + 1 } 187 sys_write(fd, s, i) 188 return i 189} 190 191func hp_i64(fd: i64, n: i64) -> i64 { 192 if n < 0 { 193 hp_putc(fd, 45) 194 return hp_i64(fd, -n) 195 } 196 if n == 0 { 197 hp_putc(fd, 48) 198 return 0 199 } 200 let digits: *u8 = sys_mmap(32) 201 var d: i64 = 0 202 var v: i64 = n 203 while v > 0 { 204 digits[d] = (v % 10) + 48 205 v = v / 10 206 d = d + 1 207 } 208 while d > 0 { 209 d = d - 1 210 hp_putc(fd, digits[d]) 211 } 212 return 0 213} 214 215func nx_help_emit_result(fd: i64, r: *HelpResult, query: *u8) -> i64 { 216 hp_str(fd, "[nx_help] query: ", 17) 217 hp_strz(fd, query) 218 hp_str(fd, "\n", 1) 219 if r.kind == NX_HELP_KIND_NONE { 220 hp_str(fd, " no match found. queue an IMPROVEMENT_OPP entry to add this term.\n", 67) 221 return 0 222 } 223 if r.kind == NX_HELP_KIND_JARGON_DEFINITION { 224 hp_str(fd, " kind: jargon definition\n tier: ", 34) 225 if r.tier == NX_TIER_BEGINNER { hp_str(fd, "BEGINNER", 8) } 226 if r.tier == NX_TIER_INTERMEDIATE { hp_str(fd, "INTERMEDIATE", 12) } 227 if r.tier == NX_TIER_EXPERT { hp_str(fd, "EXPERT", 6) } 228 hp_str(fd, "\n explanation: ", 16) 229 hp_strz(fd, r.text) 230 hp_str(fd, "\n alternates at other tiers: ", 30) 231 hp_i64(fd, r.n_alternates) 232 hp_str(fd, "\n", 1) 233 return 0 234 } 235 if r.kind == NX_HELP_KIND_THEOREM_CARD { 236 hp_str(fd, " kind: theorem card\n qed_id: ", 31) 237 hp_i64(fd, r.secondary_id) 238 hp_str(fd, "\n name: ", 9) 239 hp_strz(fd, r.text) 240 hp_str(fd, "\n", 1) 241 return 0 242 } 243 if r.kind == NX_HELP_KIND_QUESTION_NARRATIVE { 244 hp_str(fd, " kind: question narrative\n node: ", 35) 245 hp_i64(fd, r.primary_id) 246 hp_str(fd, "\n question: ", 13) 247 hp_strz(fd, r.text) 248 hp_str(fd, "\n", 1) 249 return 0 250 } 251 return 0 252}