nx_par_matmul.nx source
↩ module page · 96 lines · 4311 B
1// nx_par_matmul.nx -- SOVEREIGN CPU parallelism: matmul across all cores via fork + shared memory, NO 3rd
2// party (operator: "no 3rd party, nishi ecosystem from the hardware rung up"). Pure syscalls -- sys_fork +
3// sys_mmap_shared (children write row-slices of C into shared mem) + sys_wait4 (parent joins). Inner MAC =
4// sovereign SSE (__f32_mul/__f32_add, nx_f32_hw). This is the tractable sovereign speed lever for the forward
5// (the matmul is the bottleneck): serial vs N-worker parallel, measured, bit-verified. license_tier: ORIGINAL
6import "nx_syscalls.nx"
7import "nx_f32.nx"
8import "nx_f32_hw.nx"
9
10const PM_M: i64 = 384
11const PM_K: i64 = 384
12const PM_N: i64 = 384
13const PM_NW: i64 = 8 // worker forks (>= cores -> measures effective parallelism)
14
15func pm_puts(s: *u8) -> i64 { var n: i64 = 0; while s[n] != (0 as u8) { n = n + 1 } sys_write(1, s, n); return 0 }
16func pm_putn(v: i64) -> i64 {
17 if v == 0 { sys_write(1, "0" as *u8, 1); return 0 }
18 var m: i64 = v
19 if m < 0 { sys_write(1, "-" as *u8, 1); m = 0 - m }
20 let d: *u8 = sys_mmap(24); var k: i64 = 0
21 while m > 0 { d[k] = (48 + (m % 10)) as u8; m = m / 10; k = k + 1 }
22 var j: i64 = k - 1
23 while j >= 0 { sys_write(1, ((d as i64)+j) as *u8, 1); j = j - 1 }
24 return 0
25}
26
27// C[lo..hi) rows = A[MxK] * B[KxN], sovereign SSE inner. (each worker owns a disjoint row range -> no races)
28func matmul_rows(A: *i64, B: *i64, C: *i64, K: i64, N: i64, lo: i64, hi: i64) -> i64 {
29 var i: i64 = lo
30 while i < hi {
31 var j: i64 = 0
32 while j < N {
33 var acc: i64 = 0
34 var k: i64 = 0
35 while k < K { acc = __f32_add(acc, __f32_mul(A[i * K + k], B[k * N + j])); k = k + 1 }
36 C[i * N + j] = acc
37 j = j + 1
38 }
39 i = i + 1
40 }
41 return 0
42}
43
44func main() -> i64 {
45 let A: *i64 = sys_mmap(PM_M * PM_K * 8) as *i64
46 let B: *i64 = sys_mmap(PM_K * PM_N * 8) as *i64
47 var i: i64 = 0
48 while i < PM_M * PM_K { A[i] = f32_of((i % 5) - 2); i = i + 1 }
49 i = 0
50 while i < PM_K * PM_N { B[i] = f32_of((i % 7) - 3); i = i + 1 }
51
52 // ---- SERIAL (one core) ----
53 let Cser: *i64 = sys_mmap(PM_M * PM_N * 8) as *i64
54 let t0: i64 = sys_now_ms()
55 matmul_rows(A, B, Cser, PM_K, PM_N, 0, PM_M)
56 let serial_ms: i64 = sys_now_ms() - t0
57
58 // ---- PARALLEL (fork PM_NW workers, each a row-slice, into SHARED C) ----
59 let Cpar: *i64 = sys_mmap_shared(PM_M * PM_N * 8) as *i64
60 let t1: i64 = sys_now_ms()
61 var w: i64 = 0
62 while w < PM_NW {
63 let pid: i64 = sys_fork()
64 if pid == 0 {
65 let lo: i64 = (w * PM_M) / PM_NW
66 let hi: i64 = ((w + 1) * PM_M) / PM_NW
67 matmul_rows(A, B, Cpar, PM_K, PM_N, lo, hi)
68 sys_exit(0)
69 }
70 w = w + 1
71 }
72 let stp: *i64 = sys_mmap(8) as *i64
73 var d: i64 = 0
74 while d < PM_NW { sys_wait4(0 - 1, stp, 0); d = d + 1 }
75 let par_ms: i64 = sys_now_ms() - t1
76
77 // ---- verify bit-identical ----
78 var mism: i64 = 0
79 i = 0
80 while i < PM_M * PM_N { if Cpar[i] != Cser[i] { mism = mism + 1 } i = i + 1 }
81
82 pm_puts("=== nx_par_matmul: SOVEREIGN fork-parallel matmul (no 3rd party; fork+shared-mem+SSE) ===\n")
83 pm_puts(" "); pm_putn(PM_M); pm_puts("x"); pm_putn(PM_K); pm_puts("x"); pm_putn(PM_N)
84 pm_puts(" matmul, "); pm_putn(PM_NW); pm_puts(" fork-workers\n")
85 pm_puts(" serial = "); pm_putn(serial_ms); pm_puts(" ms\n")
86 pm_puts(" parallel= "); pm_putn(par_ms); pm_puts(" ms\n")
87 if par_ms > 0 { pm_puts(" speedup = "); pm_putn((serial_ms * 100) / par_ms); pm_puts(" /100x ("); pm_putn(serial_ms / par_ms); pm_puts("x)\n") }
88 pm_puts(" mismatches vs serial = "); pm_putn(mism); pm_puts(" (0 = bit-identical)\n")
89
90 var pass: i64 = 0
91 if mism == 0 { pm_puts(" T1 parallel result bit-identical to serial: PASS\n"); pass = pass + 1 } else { pm_puts(" T1: FAIL\n") }
92 if par_ms < serial_ms { pm_puts(" T2 parallel faster than serial (real sovereign speedup): PASS\n"); pass = pass + 1 } else { pm_puts(" T2: FAIL\n") }
93 pm_puts("\n PASS="); pm_putn(pass); pm_puts("/2 ")
94 if pass == 2 { pm_puts("VERDICT=GREEN (sovereign multicore speedup, no 3rd party -- fork+shared-mem+SSE)\n"); sys_exit(0); return 0 }
95 pm_puts("VERDICT=RED\n"); sys_exit(1); return 1
96}