code wiki / _hdl_build / _f64_atan_gate_authored.nx

_f64_atan_gate_authored.nx source

↩ module page · 129 lines · 5574 B

1// _f64_atan_gate_authored.nx -- ME1 atan gate: TEAM-AUTHORED kernel (_pe_f64atan, 2// MATH_KERNEL/ATAN emitter) vs the LIVE sovereign bigfloat oracle 3// (nx_bigfloat120_atan -- self-anchored, no python). Pure Nishi end to end. 4// TOTAL DOMAIN: fixed edges (anchor points, fold seam at 41/16, subnormals, 5// huge, specials) + 300 banded xorshift points over the full exponent range. 6// ULP via the signed ordered map. GREEN iff max ULP <= 1. 7// Markers: ATBAD x= exp= got= ulp= / ATAN-ULP ... / ATAN-GATE verdict=GREEN|RED 8 9import "nx_syscalls.nx" 10import "nx_f64.nx" 11import "nx_f64_div.nx" 12import "nx_f64_cvt.nx" 13import "nx_bigfloat120.nx" 14import "nx_bigfloat120_div.nx" 15import "nx_bigfloat120_trig.nx" 16import "nx_bigfloat120_atan.nx" 17import "_pe_f64atan.nx" 18 19func atg_puts(s: *u8) -> i64 { var n: i64 = 0; while s[n] != (0 as u8) { n = n + 1 } sys_write(1, s, n); return 0 } 20func atg_putn(v: i64) -> i64 { let bb: *u8 = sys_mmap(28); var m: i64 = v; if m < 0 { m = 0 - m; sys_write(1, "-" as *u8, 1) }; let t: *u8 = sys_mmap(28); var k: i64 = 0; if m == 0 { t[0] = 48; k = 1 }; while m > 0 { t[k] = 48 + (m % 10); m = m / 10; k = k + 1 }; var i: i64 = 0; while i < k { bb[i] = t[k-1-i]; i = i + 1 }; sys_write(1, bb, k); return 0 } 21func atg_puthex(v: i64) -> i64 { let bb: *u8 = sys_mmap(20); var i: i64 = 0; while i < 16 { let nib: i64 = (v >> ((15 - i) * 4)) & 15; if nib < 10 { bb[i] = 48 + nib } else { bb[i] = 55 + nib } i = i + 1 } sys_write(1, bb, 16); return 0 } 22 23func atg_rng(state: *i64) -> i64 { 24 var s: i64 = state[0] 25 s = s ^ ((s >> 12) & 0x000FFFFFFFFFFFFF) 26 s = s ^ (s << 25) 27 s = s ^ ((s >> 27) & 0x0000001FFFFFFFFF) 28 state[0] = s 29 return s * 2685821657736338717 30} 31 32func atg_ord(v: i64) -> i64 { 33 if v >= 0 { return v } 34 return (1 << 63) - v 35} 36 37func atg_ulp(got: i64, want: i64) -> i64 { 38 if got == want { return 0 } 39 var u: i64 = atg_ord(got) - atg_ord(want) 40 if u < 0 { u = 0 - u } 41 return u 42} 43 44func main() -> i64 { 45 let xs: *i64 = sys_mmap(8 * 512) as *i64 46 var n: i64 = 0 47 // specials + edges 48 xs[n] = 0x7FF8000000000000; n = n + 1 // NaN 49 xs[n] = 0x7FF0000000000000; n = n + 1 // +inf 50 xs[n] = 0xFFF0000000000000; n = n + 1 // -inf 51 xs[n] = 0; n = n + 1 // +0 52 xs[n] = 1 << 63; n = n + 1 // -0 53 xs[n] = 1; n = n + 1 // min subnormal 54 xs[n] = 0x000FFFFFFFFFFFFF; n = n + 1 // max subnormal 55 xs[n] = 0x0010000000000000; n = n + 1 // min normal 56 xs[n] = 0x7FEFFFFFFFFFFFFF; n = n + 1 // max finite 57 xs[n] = 0x3FF0000000000000; n = n + 1 // 1.0 (anchor j=8) 58 xs[n] = 0xBFF0000000000000; n = n + 1 // -1.0 59 xs[n] = 0x3FEFFFFFFFFFFFFF; n = n + 1 // 1 - ulp 60 xs[n] = 0x3FF0000000000001; n = n + 1 // 1 + ulp 61 xs[n] = 0x4004800000000000; n = n + 1 // 41/16 fold seam 62 xs[n] = 0x40047FFFFFFFFFFF; n = n + 1 // seam - ulp 63 xs[n] = 0x4004800000000001; n = n + 1 // seam + ulp 64 xs[n] = 0x3FC0000000000000; n = n + 1 // 1/8 (anchor j=1) 65 xs[n] = 0x3FB0000000000000; n = n + 1 // 1/16 (j 0/1 boundary) 66 xs[n] = 0x3FD8000000000000; n = n + 1 // 3/8 (anchor j=3) 67 xs[n] = 0x4000000000000000; n = n + 1 // 2.0 (anchor j=16) 68 xs[n] = 0xC003000000000000; n = n + 1 // -2.375 (anchor j=19) 69 xs[n] = 0x3E50000000000000; n = n + 1 // 2^-26 (round-to-x zone) 70 // banded random over the full domain, random signs 71 let st: *i64 = sys_mmap(16) as *i64 72 st[0] = 16180339887498948482 73 var j: i64 = 0 74 while j < 300 { 75 var raw: i64 = atg_rng(st) 76 var efr: i64 = 0 77 let band: i64 = raw & 3 78 if band == 0 { efr = 1021 + (raw & 3) } // 0.25 .. 4: seam region 79 if band == 1 { efr = 1015 + (raw & 15) } // 2^-8 .. 2^8 80 if band == 2 { efr = 960 + (raw & 63) } // small 81 if band == 3 { efr = 1026 + (raw & 511) } // 2^3 .. 2^514: fold path 82 raw = (efr << 52) | (atg_rng(st) & 0x000FFFFFFFFFFFFF) 83 if (atg_rng(st) & 1) == 1 { raw = raw | (1 << 63) } 84 xs[n] = raw 85 n = n + 1 86 j = j + 1 87 } 88 89 var a_exact: i64 = 0 90 var a_u1: i64 = 0 91 var a_worse: i64 = 0 92 var a_max: i64 = 0 93 var i: i64 = 0 94 while i < n { 95 let x: i64 = xs[i] 96 let aw: i64 = bf_atan_f64(x) 97 let ag: i64 = nx_f64_atan(x) 98 let au: i64 = atg_ulp(ag, aw) 99 if au == 0 { a_exact = a_exact + 1 } 100 if au == 1 { a_u1 = a_u1 + 1 } 101 if au > 1 { 102 a_worse = a_worse + 1 103 if a_worse <= 20 { 104 atg_puts("ATBAD x=" as *u8); atg_puthex(x) 105 atg_puts(" exp=" as *u8); atg_puthex(aw) 106 atg_puts(" got=" as *u8); atg_puthex(ag) 107 atg_puts(" ulp=" as *u8); atg_putn(au) 108 atg_puts("\n" as *u8) 109 } 110 } 111 if au > a_max { a_max = au } 112 i = i + 1 113 } 114 115 atg_puts("ATAN-ULP total=" as *u8); atg_putn(n) 116 atg_puts(" exact=" as *u8); atg_putn(a_exact) 117 atg_puts(" ulp1=" as *u8); atg_putn(a_u1) 118 atg_puts(" worse=" as *u8); atg_putn(a_worse) 119 atg_puts(" max=" as *u8); atg_putn(a_max) 120 atg_puts("\n" as *u8) 121 if a_worse == 0 { 122 atg_puts("ATAN-GATE verdict=GREEN\n" as *u8) 123 return 0 124 } 125 atg_puts("ATAN-GATE verdict=RED\n" as *u8) 126 var rc: i64 = a_worse 127 if rc > 100 { rc = 100 } 128 return rc 129}