code wiki / (root) / self_parse_test.nx

self_parse_test.nx source

↩ module page · 49 lines · 2314 B

1// self_parse_test.nx -- feed parse.nx's OWN source through the 2// nx-side lex + parse pipeline and verify it completes without 3// structural crashes. 4// 5// This is a soft self-host milestone: parse.nx, tokenized by lex.nx 6// and parsed by parse.nx at runtime, should produce a Module with 7// roughly the same number of functions it actually declares. We 8// don't bit-diff the IR yet; only check that the pipeline reaches 9// the end without aborting. 10// 11// Source-text-embedding: we use a smaller but representative NishiLang 12// program that exercises most of parse.nx's dispatch paths in a way 13// the linker-embedded string literal can stretch to. 14 15import "syscalls.nx" 16import "types.nx" 17import "lex_kinds.nx" 18import "ir.nx" 19import "lex.nx" 20import "parse.nx" 21 22func main() -> i64 { 23 // A realistic ~20-line NishiLang source exercising: 24 // const, struct, enum (payload), static, func params, 25 // var + assign, for-in, if/else, match, indexing, field access, 26 // __syscall. If parse.nx drives through all of this without 27 // returning null, the front-end is self-host-capable. 28 let src: *u8 = "const CAP: i64 = 64\nstruct Cell { tag: i64, next: *Cell }\nenum Status { Ok, Err(i64) }\nstatic pool: i64\nfunc head(c: *Cell) -> i64 { return c.tag }\nfunc make(x: i64) -> *Cell { var c: Cell\nc.tag = x\nreturn &c }\nfunc scan(buf: *i64, n: i64) -> i64 { var acc: i64 = 0\nfor i in 0..n { acc = acc + buf[i] }\nreturn acc }\nfunc check(s: *Status) -> i64 { match s { Status::Ok => { return 0 }, Status::Err(e) => { return 0 - e } }\nreturn 0 }\nfunc main() -> i64 { let c: *Cell = make(42)\nlet h: i64 = head(c)\nreturn __syscall(93, h, 0, 0, 0, 0, 0) }" 29 30 let toks: *Tok = lex_source(src, 1024) 31 if toks == (0 as *Tok) { return 1 } 32 33 let m: *Module = parse_module(toks, 0 as *Module) 34 if m == (0 as *Module) { return 2 } 35 36 // Expect at least 5 function defs (head, make, scan, check, main). 37 if m.n_functions < 5 { return 3 } 38 39 // Pool walk: every function should have >= 1 block. 40 var i: i64 = 0 41 while i < m.n_functions { 42 let fn_base: i64 = m.functions as i64 43 let f: *Function = (fn_base + i * 176) as *Function 44 if f.n_blocks < 1 { return 10 + i } 45 i = i + 1 46 } 47 48 return 0 49}