code wiki / _hdl_build / nx_nn_train_gate.nx

nx_nn_train_gate.nx source

↩ module page · 44 lines · 2666 B

1// nx_nn_train_gate.nx -- proves sovereign fixed-point training (nx_nn_train): batch gradient descent on a linear layer, 2// starting from zero weights, learns a known target mapping -- the MSE loss collapses and the learned weights converge 3// to the target. This is the training pipeline the neural PLC / RVQ-codebook needs, all integer, no FPU/GPU/autograd. 4import "nx_syscalls.nx" 5import "nx_gate_emit_lib.nx" 6import "nx_nn_train.nx" 7 8func g_abs(v: i64) -> i64 { if v < 0 { return 0 - v } return v } 9 10func main() -> i64 { 11 g_puts("nx_nn_train gate (sovereign fixed-point gradient descent learns a target, MEASURED)\n" as *u8) 12 var pass: i64 = 0; var total: i64 = 0 13 let I: i64 = 2; let O: i64 = 1; let T: i64 = 4; let Q: i64 = 16 // weights in Q16 so sub-unit GD steps accumulate 14 15 // target mapping W* = [1.0, -0.5] in Q16 16 let Wt: *i64 = sys_mmap(2*8) as *i64; Wt[0]=65536; Wt[1]=0-32768 17 // training inputs X[T x I] (Q8) and targets Y = (W* . X) >> Q 18 let X: *i64 = sys_mmap(T*I*8) as *i64 19 let Y: *i64 = sys_mmap(T*O*8) as *i64 20 X[0]=256; X[1]=256; X[2]=512; X[3]=128; X[4]=128; X[5]=512; X[6]=384; X[7]=256 21 var t: i64 = 0 22 while t < T { let acc: i64 = Wt[0]*X[t*I] + Wt[1]*X[t*I+1]; Y[t] = acc >> Q; t = t + 1 } 23 24 // learn from ZERO weights 25 let W: *i64 = sys_mmap(2*8) as *i64; W[0]=0; W[1]=0 26 let grad: *i64 = sys_mmap(O*I*8) as *i64 27 let pred: *i64 = sys_mmap(O*8) as *i64 28 29 let loss0: i64 = nnt_loss(X, Y, T, W, I, O, Q) 30 var it: i64 = 0 31 while it < 15000 { nnt_step(X, Y, T, W, I, O, Q, 13, grad, pred); it = it + 1 } // update_shift 13 = the learning rate 32 let lossN: i64 = nnt_loss(X, Y, T, W, I, O, Q) 33 34 g_puts(" [measure] loss: start=" as *u8); g_pn(loss0); g_puts(" after 15000 GD steps=" as *u8); g_pn(lossN) 35 g_puts(" learned W=[" as *u8); g_pn(W[0]); g_puts("," as *u8); g_pn(W[1]); g_puts("] vs target [65536,-32768] (Q16; exact convergence is fixed-point-floor-limited)\n" as *u8) 36 37 pass = pass + g_check("training collapses the loss (>= 95% reduction = it learned the mapping)" as *u8, lossN * 20 <= loss0); total=total+1 38 pass = pass + g_check("weights converge substantially toward target with correct sign (>= 60% of the way)" as *u8, (W[0] >= 39322) & (W[1] <= 0-19661)); total=total+1 39 pass = pass + g_check("started genuinely untrained (start loss > 0)" as *u8, loss0 > 0); total=total+1 40 41 g_puts("---- nn_train gate: passed " as *u8); g_pn(pass); g_puts(" / " as *u8); g_pn(total); g_puts(" ----\n" as *u8) 42 if pass == total { g_puts("verdict=GREEN\n" as *u8); sys_exit(0); return 0 } 43 g_puts("verdict=RED\n" as *u8); sys_exit(1); return 1 44}