code wiki / _hdl_build / nx_skincube_anim_gate.nx
nx_skincube_anim_gate.nx source
↩ module page · 117 lines · 6380 B
1// nx_skincube_anim_gate.nx -- CAP-SKELETAL-ANIM rung-3: the lit skinned cube ANIMATES over time. Sweeps the
2// skinned-normal-lit cube through a FULL oscillation cycle (frame 0..120 -> joint bend 0->+50->0->-50->0 via
3// the sin-driven joint in mv_render_skincube_lit) IN OUR wasm VM, and proves the animation PLAYS as a real
4// loop: motion at the extremes, RETURNS TO REST each half-cycle (oscillation, not a one-way ramp), continuous
5// frame-to-frame, deterministic. Builds mv.wasm via the SOVEREIGN chain (nx_compile_wat -> nx_wat_compiler,
6// no Emscripten) like nx_meshview_wasm_gate; no wasm-source change (mv_render_skincube_lit already takes frame).
7// expect_exit: 0 license_tier: ORIGINAL
8import "nx_syscalls.nx"
9import "nx_wasm_vm.nx"
10
11const CWAT_ELF: *u8 = "/tmp/nx_compile_wat.sov.elf"
12const WATC_ELF: *u8 = "/tmp/nx_wat_compiler.sov.elf"
13const SRC_NX: *u8 = "/mnt/c/Users/elder/nishi-core/nxc2/runtime/nx_meshview_wasm.nx"
14const OUT_WAT: *u8 = "/tmp/mv.wat"
15const OUT_WASM: *u8 = "/tmp/mv.wasm"
16const O_FB: i64 = 0
17const MV_N: i64 = 4096
18const BG: i64 = 4280295456
19
20func g_puts(s: *u8) -> i64 { var n: i64=0; while s[n]!=(0 as u8){n=n+1} sys_write(1,s,n); return 0 }
21func g_pn(v: i64) -> i64 { let b: *u8=sys_mmap(28); var x: i64=v; if x<0{b[0]=45 as u8;sys_write(1,b,1);x=0-x} if x==0{b[0]=48 as u8;sys_write(1,b,1);return 0} var d: i64=0; var y: i64=x; while y>0{d=d+1;y=y/10} var i: i64=d-1; y=x; while i>=0{b[i]=(48+(y%10)) as u8;y=y/10;i=i-1} sys_write(1,b,d); return 0 }
22func ck(name: *u8, c: i64) -> i64 { if c==1 { g_puts(" PASS " as *u8) } else { g_puts(" FAIL " as *u8) } g_puts(name); g_puts("\n" as *u8); return c }
23func run_elf(elf: *u8, a1: *u8, a2: *u8) -> i64 {
24 let pid: i64 = sys_fork()
25 if pid == 0 {
26 let argv: *i64 = sys_mmap(64) as *i64
27 argv[0] = elf as i64
28 var ai: i64 = 1
29 if (a1 as i64) != 0 { argv[ai] = a1 as i64; ai = ai + 1 }
30 if (a2 as i64) != 0 { argv[ai] = a2 as i64; ai = ai + 1 }
31 argv[ai] = 0
32 let envp: *i64 = sys_mmap(16) as *i64
33 envp[0] = "PATH=/usr/bin:/bin" as *u8 as i64
34 envp[1] = 0
35 sys_execve(elf, argv, envp)
36 sys_exit(127)
37 }
38 let st: *i64 = sys_mmap(16) as *i64
39 sys_wait4(pid, st, 0)
40 return (st[0] >> 8) & 0xff
41}
42
43func main() -> i64 {
44 g_puts("nx_skincube_anim_gate (CAP-SKELETAL-ANIM rung-3: the lit skinned cube ANIMATES a full cycle in OUR wasm VM)\n" as *u8)
45 let rc1: i64 = run_elf(CWAT_ELF, SRC_NX, OUT_WAT)
46 g_puts(" [build] nx_compile_wat rc="); g_pn(rc1); g_puts("\n" as *u8)
47 let rc2: i64 = run_elf(WATC_ELF, OUT_WAT, OUT_WASM)
48 g_puts(" [build] nx_wat_compiler rc="); g_pn(rc2); g_puts("\n" as *u8)
49
50 let box: *i64 = sys_mmap(16) as *i64
51 let wasm: *u8 = sys_read_file(OUT_WASM, box)
52 if (wasm as i64) == 0 { g_puts(" FAIL cannot read mv.wasm\nverdict=RED\n" as *u8); sys_exit(1); return 1 }
53 let mod: *WasmMod = wm_new(wasm, box[0])
54 if wm_parse(mod) != 0 { g_puts(" FAIL wasm parse\nverdict=RED\n" as *u8); sys_exit(1); return 1 }
55 mod.mem = sys_mmap(131072) as *u8
56 let fbp: *i64 = (mod.mem as i64 + O_FB) as *i64
57
58 let STEP: i64 = 15
59 let NSTEP: i64 = 9 // frames 0,15,..,120 = one full sin cycle (0->+50->0->-50->0 deg)
60 let snap0: *i64 = sys_mmap(MV_N*8) as *i64
61 let snapPrev: *i64 = sys_mmap(MV_N*8) as *i64
62 let d0arr: *i64 = sys_mmap(16*8) as *i64
63
64 var all_render: i64 = 1
65 var all_move: i64 = 1
66 var s: i64 = 0
67 var i: i64 = 0
68 var cov: i64 = 0
69 var d0: i64 = 0
70 var dp: i64 = 0
71 var frame: i64 = 0
72 var drawn: i64 = 0
73 var px: i64 = 0
74 while s < NSTEP {
75 frame = s * STEP
76 drawn = wm_run(mod, "mv_render_skincube_lit" as *u8, frame, 0, 0, 0, 0, 1)
77 cov = 0; d0 = 0; dp = 0; i = 0
78 while i < MV_N {
79 px = fbp[i]
80 if px != BG { cov = cov + 1 }
81 if s > 0 { if px != snap0[i] { d0 = d0 + 1 } if px != snapPrev[i] { dp = dp + 1 } }
82 i = i + 1
83 }
84 if drawn <= 0 { all_render = 0 }
85 if cov <= 100 { all_render = 0 }
86 if s > 0 { if dp <= 0 { all_move = 0 } }
87 d0arr[s] = d0
88 if s == 0 { i = 0; while i < MV_N { snap0[i] = fbp[i]; i = i + 1 } }
89 i = 0; while i < MV_N { snapPrev[i] = fbp[i]; i = i + 1 }
90 g_puts(" frame "); g_pn(frame); g_puts(": cov="); g_pn(cov); g_puts(" diff_from_rest="); g_pn(d0); g_puts(" diff_from_prev="); g_pn(dp); g_puts("\n" as *u8)
91 s = s + 1
92 }
93
94 // determinism + teeth: render frame 45 twice -> must be pixel-identical (proves the diffs above are REAL motion)
95 drawn = wm_run(mod, "mv_render_skincube_lit" as *u8, 45, 0, 0, 0, 0, 1)
96 i = 0; while i < MV_N { snapPrev[i] = fbp[i]; i = i + 1 }
97 drawn = wm_run(mod, "mv_render_skincube_lit" as *u8, 45, 0, 0, 0, 0, 1)
98 var det_diff: i64 = 0
99 i = 0; while i < MV_N { if fbp[i] != snapPrev[i] { det_diff = det_diff + 1 } i = i + 1 }
100
101 var pass: i64 = 0; var t: i64 = 0
102 pass = pass + ck("T1: all 9 frames of the cycle render (drawn>0, coverage>100)" as *u8, all_render); t = t + 1
103 var t2: i64 = 0; if d0arr[2] > 100 { if d0arr[6] > 100 { t2 = 1 } }
104 pass = pass + ck("T2 (MEASURED motion): both bend extremes (frame30=+50deg, frame90=-50deg) change >100 px vs rest" as *u8, t2); t = t + 1
105 var t3: i64 = 0; if d0arr[4] < d0arr[2]/2 { if d0arr[8] < d0arr[2]/2 { t3 = 1 } }
106 pass = pass + ck("T3 (OSCILLATION): frame60 + frame120 RETURN to ~rest (diff << peak) = a real looping animation, not a one-way ramp" as *u8, t3); t = t + 1
107 pass = pass + ck("T4 (CONTINUOUS): every sampled frame differs from the previous = smooth motion across the whole cycle" as *u8, all_move); t = t + 1
108 var t5: i64 = 0; if det_diff == 0 { t5 = 1 }
109 pass = pass + ck("T5 (DETERMINISTIC + teeth): the same frame rendered twice is pixel-identical (the per-frame diffs are REAL motion)" as *u8, t5); t = t + 1
110
111 var okall: i64 = 0; if pass == t { okall = 1 }
112 g_puts("---- nx_skincube_anim_gate: passed "); g_pn(pass); g_puts(" / "); g_pn(t); g_puts(" ----\n" as *u8)
113 if okall == 1 {
114 g_puts("verdict=GREEN -- the lit skinned cube ANIMATES (a full sin-driven bend cycle) in OUR wasm VM: skeletal animation PLAYS, sovereign\n" as *u8); sys_exit(0); return 0
115 }
116 g_puts("verdict=RED\n" as *u8); sys_exit(1); return 1
117}