code wiki / _hdl_build / nx_organ_callers.nx

nx_organ_callers.nx source

↩ module page · 149 lines · 9185 B

1// nx_organ_callers.nx -- SOVEREIGN caller-finder: given an organ basename, walk the .nx tree and list every 2// file that REFERENCES it (by name, import, or path). This is the missing tool that makes a rename SAFE -- you 3// can SEE all callers before touching a name, instead of a blind rename (#19 contract stability) or a grep that 4// times out on this tree. It is the prerequisite for resolving the 22 shadow collisions nx_janitor_dupname found. 5// Bounded BFS getdents walk; reads each .nx into a REUSED buffer + sys_munmap (no 4GB-per-call reserve, no leak, 6// no timeout) -- the proven nx_janitor_sprawl walk shape. Match = substring of the needle with a LEFT word 7// boundary so "nx_grep" is not matched inside "nx_grep_test" (over-reporting a caller is safe; this avoids it). 8// READ-ONLY (never-brick). Sovereign. license_tier: ORIGINAL 9import "nx_syscalls.nx" 10 11const OC_PATH_SLOT: i64 = 768 12const OC_QUEUE_CAP: i64 = 16384 13const OC_DENT_BUF: i64 = 65536 14const OC_FILE_CAP: i64 = 4194304 15const OC_MAX_HITS: i64 = 4096 16const OC_HIT_ARENA: i64 = 3145728 // bytes for the caller-path list 17 18func oc_slen(s: *u8) -> i64 { var n: i64=0; while s[n]!=(0 as u8){n=n+1} return n } 19func oc_eq(a: *u8, b: *u8) -> i64 { var i: i64=0; while a[i]!=(0 as u8){ if a[i]!=b[i]{return 0} i=i+1 } if b[i]!=(0 as u8){return 0} return 1 } 20func oc_ends(path: *u8, pl: i64, ext: *u8) -> i64 { let el: i64=oc_slen(ext); if el>pl { return 0 } var i: i64=0; while i<el { if path[pl-el+i]!=ext[i] { return 0 } i=i+1 } return 1 } 21func oc_is_ident(c: i64) -> i64 { if c>=48 { if c<=57 { return 1 } } if c>=65 { if c<=90 { return 1 } } if c>=97 { if c<=122 { return 1 } } if c==95 { return 1 } return 0 } 22// is `pat` referenced in buf[0..n) with a LEFT word boundary? 23func oc_referenced(buf: *u8, n: i64, pat: *u8) -> i64 { 24 let pl: i64=oc_slen(pat); if pl==0 { return 0 } 25 var i: i64=0 26 while i+pl<=n { 27 var j: i64=0; var ok: i64=1 28 while j<pl { if buf[i+j]!=pat[j] { ok=0; j=pl } else { j=j+1 } } 29 if ok==1 { var b: i64=1; if i>0 { if oc_is_ident(buf[i-1] as i64)==1 { b=0 } } if b==1 { return 1 } } 30 i=i+1 31 } 32 return 0 33} 34func oc_join(dst: *u8, dir: *u8, name: *u8) -> i64 { var o: i64=0; var i: i64=0; while dir[i]!=(0 as u8){ dst[o]=dir[i]; o=o+1; i=i+1 } dst[o]=47 as u8; o=o+1; i=0; while name[i]!=(0 as u8){ dst[o]=name[i]; o=o+1; i=i+1 } dst[o]=0 as u8; return o } 35func oc_getdents(fd: i64, buf: *u8, count: i64) -> i64 { return __syscall(SYS_GETDENTS64, fd, buf, count, 0, 0, 0) } 36func oc_isdir(path: *u8, st: *u8) -> i64 { let r: i64=__syscall(262, 0-100, path, st, 0, 0, 0); if r<0 { return 0-1 } let mode: i64=(st[24] as i64)|((st[25] as i64)<<8)|((st[26] as i64)<<16)|((st[27] as i64)<<24); if (mode & 0xF000)==0x4000 { return 1 } return 0 } 37func oc_read(path: *u8, buf: *u8, cap: i64) -> i64 { let fd: i64=sys_openat_rd(path); if fd<0 { return 0-1 } var total: i64=0; var nrd: i64=sys_read(fd, buf, cap); while nrd>0 { total=total+nrd; if total>=cap { nrd=0 } else { nrd=sys_read(fd, ((buf as i64)+total) as *u8, cap-total) } } sys_close(fd); return total } 38 39// SOVEREIGN GREP: find `needle` in EVERY file under `root` (any extension, not just .nx), skipping files larger 40// than `maxsize` (build scripts/configs are small; this avoids slurping huge binaries). The ecosystem's answer 41// to the 3rd-party grep that times out on this tree. Records each matching path into hits/hitoff; returns count. 42func oc_grep(root: *u8, needle: *u8, maxsize: i64, hits: *u8, hitoff: *i64, maxh: i64) -> i64 { 43 let qbuf: *u8=sys_mmap(OC_PATH_SLOT*OC_QUEUE_CAP) 44 let gbuf: *u8=sys_mmap(OC_DENT_BUF) 45 let stbuf: *u8=sys_mmap(256) 46 let fbuf: *u8=sys_mmap(OC_FILE_CAP) 47 let child: *u8=sys_mmap(OC_PATH_SLOT) 48 var qh: i64=0; var qt: i64=0 49 var ri: i64=0; while root[ri]!=(0 as u8){ qbuf[ri]=root[ri]; ri=ri+1 } qbuf[ri]=0 as u8; qt=1 50 var nh: i64=0; hitoff[0]=0 51 while qh<qt { 52 let dir: *u8=((qbuf as i64)+qh*OC_PATH_SLOT) as *u8; qh=qh+1 53 let fd: i64=sys_openat_rd(dir) 54 if fd<0 { } else { 55 var nread: i64=oc_getdents(fd, gbuf, OC_DENT_BUF) 56 while nread>0 { 57 var off: i64=0 58 while off<nread { 59 let reclen: i64=(gbuf[off+16] as i64)|((gbuf[off+17] as i64)<<8) 60 if reclen<=0 { off=nread } else { 61 let name: *u8=((gbuf as i64)+off+19) as *u8 62 var skip: i64=0 63 if oc_eq(name, "." as *u8)==1 { skip=1 } 64 if oc_eq(name, ".." as *u8)==1 { skip=1 } 65 if skip==0 { 66 oc_join(child, dir, name) 67 let isd: i64=oc_isdir(child, stbuf) 68 if isd==1 { 69 var vend: i64=0 70 if oc_eq(name, "node_modules" as *u8)==1 { vend=1 } 71 if oc_eq(name, ".git" as *u8)==1 { vend=1 } 72 if oc_eq(name, ".alelane" as *u8)==1 { vend=1 } 73 if vend==0 { if qt<OC_QUEUE_CAP { let dst: *u8=((qbuf as i64)+qt*OC_PATH_SLOT) as *u8; var c: i64=0; while child[c]!=(0 as u8){ dst[c]=child[c]; c=c+1 } dst[c]=0 as u8; qt=qt+1 } } 74 } else { if isd==0 { 75 let fn: i64=oc_read(child, fbuf, OC_FILE_CAP) 76 if fn>0 { if fn<=maxsize { if oc_referenced(fbuf, fn, needle)==1 { if nh<maxh { 77 let st: i64=hitoff[nh]; var k: i64=0; while child[k]!=(0 as u8){ hits[st+k]=child[k]; k=k+1 } hits[st+k]=0 as u8; hitoff[nh+1]=st+k+1; nh=nh+1 78 } } } } 79 } } 80 } 81 off=off+reclen 82 } 83 } 84 nread=oc_getdents(fd, gbuf, OC_DENT_BUF) 85 } 86 sys_close(fd) 87 } 88 } 89 sys_munmap(qbuf, OC_PATH_SLOT*OC_QUEUE_CAP); sys_munmap(gbuf, OC_DENT_BUF); sys_munmap(fbuf, OC_FILE_CAP) 90 return nh 91} 92 93// FIND callers of `needle` under `root` (skip the file whose basename == self_skip, e.g. the organ itself). 94// records each caller path into hits/hitoff; returns caller count. 95func oc_find(root: *u8, needle: *u8, self_skip: *u8, hits: *u8, hitoff: *i64, maxh: i64) -> i64 { 96 let qbuf: *u8=sys_mmap(OC_PATH_SLOT*OC_QUEUE_CAP) 97 let gbuf: *u8=sys_mmap(OC_DENT_BUF) 98 let stbuf: *u8=sys_mmap(256) 99 let fbuf: *u8=sys_mmap(OC_FILE_CAP) 100 let child: *u8=sys_mmap(OC_PATH_SLOT) 101 var qh: i64=0; var qt: i64=0 102 var ri: i64=0; while root[ri]!=(0 as u8){ qbuf[ri]=root[ri]; ri=ri+1 } qbuf[ri]=0 as u8; qt=1 103 var nh: i64=0; hitoff[0]=0 104 while qh<qt { 105 let dir: *u8=((qbuf as i64)+qh*OC_PATH_SLOT) as *u8; qh=qh+1 106 let fd: i64=sys_openat_rd(dir) 107 if fd<0 { } else { 108 var nread: i64=oc_getdents(fd, gbuf, OC_DENT_BUF) 109 while nread>0 { 110 var off: i64=0 111 while off<nread { 112 let reclen: i64=(gbuf[off+16] as i64)|((gbuf[off+17] as i64)<<8) 113 if reclen<=0 { off=nread } else { 114 let name: *u8=((gbuf as i64)+off+19) as *u8 115 var skip: i64=0 116 if oc_eq(name, "." as *u8)==1 { skip=1 } 117 if oc_eq(name, ".." as *u8)==1 { skip=1 } 118 if skip==0 { 119 oc_join(child, dir, name) 120 let isd: i64=oc_isdir(child, stbuf) 121 if isd==1 { 122 var vend: i64=0 123 if oc_eq(name, "node_modules" as *u8)==1 { vend=1 } 124 if oc_eq(name, ".git" as *u8)==1 { vend=1 } 125 if oc_eq(name, ".alelane" as *u8)==1 { vend=1 } 126 if vend==0 { if qt<OC_QUEUE_CAP { let dst: *u8=((qbuf as i64)+qt*OC_PATH_SLOT) as *u8; var c: i64=0; while child[c]!=(0 as u8){ dst[c]=child[c]; c=c+1 } dst[c]=0 as u8; qt=qt+1 } } 127 } else { if isd==0 { 128 let pl: i64=oc_slen(child) 129 if oc_ends(child, pl, ".nx" as *u8)==1 { if oc_eq(name, self_skip)==0 { 130 let fn: i64=oc_read(child, fbuf, OC_FILE_CAP) 131 if fn>0 { if oc_referenced(fbuf, fn, needle)==1 { if nh<maxh { 132 let st: i64=hitoff[nh]; var k: i64=0; while child[k]!=(0 as u8){ hits[st+k]=child[k]; k=k+1 } hits[st+k]=0 as u8; hitoff[nh+1]=st+k+1; nh=nh+1 133 } } } 134 } } 135 } } 136 } 137 off=off+reclen 138 } 139 } 140 nread=oc_getdents(fd, gbuf, OC_DENT_BUF) 141 } 142 sys_close(fd) 143 } 144 } 145 sys_munmap(qbuf, OC_PATH_SLOT*OC_QUEUE_CAP) 146 sys_munmap(gbuf, OC_DENT_BUF) 147 sys_munmap(fbuf, OC_FILE_CAP) 148 return nh 149}