code wiki / _hdl_build / nx_secure_token.nx
nx_secure_token.nx source
↩ module page · 45 lines · 1431 B
1// nx_secure_token.nx -- CMS ladder step 3: secure tokens. 128-bit CSPRNG hex straight from
2// /dev/urandom (L0 HAVE per the layered spec) for session ids + CSRF synchronizer tokens, plus a
3// CONSTANT-TIME comparator (no early-exit timing oracle on token checks). license_tier: ORIGINAL
4import "nx_syscalls.nx"
5
6// fill out[0..32) with lowercase hex of 16 urandom bytes; out[32]=NUL. returns 1/0.
7func st_hex128(out: *u8) -> i64 {
8 let fd: i64 = sys_openat_rd("/dev/urandom" as *u8)
9 if fd < 0 { return 0 }
10 let raw: *u8 = sys_mmap(16)
11 var got: i64 = 0
12 var go: i64 = 1
13 while go == 1 {
14 go = 0
15 if got < 16 {
16 let r: i64 = sys_read(fd, (raw + got) as *u8, 16 - got)
17 if r > 0 { got = got + r; go = 1 }
18 }
19 }
20 sys_close(fd)
21 if got < 16 { return 0 }
22 let hx: *u8 = "0123456789abcdef" as *u8
23 var i: i64 = 0
24 while i < 16 {
25 out[i*2] = hx[((raw[i] as i64) >> 4) & 15]
26 out[i*2+1] = hx[(raw[i] as i64) & 15]
27 i = i + 1
28 }
29 out[32] = 0 as u8
30 return 1
31}
32
33// constant-time equality of n bytes: examines every byte regardless of mismatches. 1/0.
34func st_eq_ct(a: *u8, b: *u8, n: i64) -> i64 {
35 var acc: i64 = 0
36 var i: i64 = 0
37 while i < n {
38 var d: i64 = (a[i] as i64) - (b[i] as i64)
39 if d < 0 { d = 0 - d }
40 acc = acc + d
41 i = i + 1
42 }
43 if acc == 0 { return 1 }
44 return 0
45}