nx_clock_driver_sched_ar.nx
buildroot/runtime/nx_clock_driver_sched_ar.nx
about
nx_clock_sched.nx -- RENAMED FROM nx_clock.nx 2026-07-31 (lib-reconcile). PERMANENT FIX for a
two-libraries-one-name collision: runtime/nx_clock.nx is the TIMING library (nx_clock_monotonic_ns,
62 importers); THIS file is an unrelated tickless JOB SCHEDULER (clk_* registry + dispatcher) that
only shared the filename. nx_cc binds an import to the IMPORTER'S OWN DIRECTORY FIRST, so every
_hdl_build organ importing nx_clock.nx silently got the SCHEDULER -- _clk_probe.nx, whose whole
purpose is to prove nx_clock_monotonic_ns works, could not resolve it. The RENAME is the fix.
so we avoid issues ... dont have a million pulses and daemons"). Researched (knowledge/fetched/sched_*.raw:
clock-distribution = ONE oscillator -> a tree of DIVIDERS; PLL derives every frequency from ONE reference;
cron = ONE daemon reads ONE table of timed jobs; tickless = don't burn a constant tick when idle). The S-class
pattern is identical: ONE tick source + ONE durable JOB REGISTRY + ONE dispatcher. Every periodic capability
REGISTERS a job (name, interval-in-ticks) = a divider off the single clock -- it does NOT spin up its own
daemon/pulse loop. So N capabilities cost ONE loop, not N. This library is the registry + dispatcher; the single
tick source drives it (one external spark, like a crystal). license_tier: ORIGINAL
dependencies 4 imports · 1 importers
imports: nx_syscalls.nxnx_clock_driver_boundary_ar.nxnx_clock_caps.nxnx_ioadmit_lib.nx
imported by: nx_clock_driver_subject_ar.nx
structs
| none |
consts
| 18 | const CLK_MAGIC_1000000: i64 = 1000000 |
| 20 | const CLK_MAXJOBS: i64 = 512 // WAS 128 (2026-08-19): the desired plane hit 128/128 and every |
| 32 | const CLK_HOGDUTY: i64 = 9 |
| 45 | const CLK_SIGKILL: i64 = 9 |
| 46 | const CLK_DISPATCH_POLL_MS: i64 = 250 |
| 61 | const CLK_DISPATCH_DEADLINE_MS: i64 = 900000 |
| 62 | const CLK_NAMEW: i64 = CLK_CMD_CAP // bytes per name/organ slot -- DERIVED from the ONE shared |
| 74 | const CLK_ROWW: i64 = 2*CLK_NAMEW + 64 // per-row serialization budget, DERIVED, not chosen: |
| 79 | const CLK_REG: *u8 = "knowledge/sched/jobs.tsv" // RETIRED LEGACY PATH (2026-08-03, debt 1785792856): |
| 100 | const CLK_HEAVY_CONF: *u8 = "knowledge/status/clock_heavy.conf" |
| 101 | const CLK_DEFER_DIV: i64 = 4 // re-arm at interval/4: a 1800 s beat re-checks every 450 s, so a storm costs it at most 3 probes before its own next period |
| 102 | const CLK_DEFER_MIN_S: i64 = 60 // floor: the shortest re-check that is not a busy loop against /proc/stat |
| 103 | const CLK_DEFER_MAX_S: i64 = 900 // cap: half a window, the same bound CLK_DISPATCH_DEADLINE_MS already places on one job |
| 106 | const CLKRS_CONF: *u8 = "knowledge/status/clock_reserved.conf" |
| 107 | const CLKRS_NONE: i64 = 0 - 1 |
| 108 | const CLKRS_INVALID: i64 = 0 - 2 |
| 109 | const CLKRS_EINTR: i64 = 0 - 4 |
| 110 | const CLKRS_WNOHANG: i64 = 1 |
| 111 | const CLKRS_SIGNAL_EXIT_BASE: i64 = 128 // shell signal-exit convention |
| 112 | const CLKRS_DISP: i64 = 0 |
| 113 | const CLKRS_STARVED: i64 = 1 |
| 114 | const CLKRS_LATE: i64 = 2 |
| 115 | const CLKRS_MAXMISSED: i64 = 3 |
| 116 | const CLKRS_STARVIDX: i64 = 4 |
| 117 | const CLKRS_MAXEXEC: i64 = 5 |
| 118 | const CLKRS_FOREGROUND_EXEC: i64 = 6 |
| 119 | const CLKRS_ERRORS: i64 = 7 |
| 120 | const CLKRS_N: i64 = 14 |
| 121 | const CLKRS_FATAL: i64 = 8 |
| 122 | const CLKRS_LOST_INDEX: i64 = 9 |
| 123 | const CLKRS_LOST_PID: i64 = 10 |
| 124 | const CLKRS_LOST_WAIT: i64 = 11 |
| 125 | const CLKRS_FOREGROUND_DISP: i64 = 12 |
| 126 | const CLKRS_KNOWN_OWNED: i64 = 13 |
| 127 | const CLKRS_FATAL_RC: i64 = 0 - 3 |
| 128 | const CLKRS_WAIT_RUNNING: i64 = 0 |
| 129 | const CLKRS_WAIT_REAPED: i64 = 1 |
| 130 | const CLKRS_WAIT_INTERRUPTED: i64 = 2 |
| 131 | const CLKRS_WAIT_LOST: i64 = 3 |
| 132 | const CLKRS_OUT_ERRORS: i64 = 12 |
| 133 | const CLKRS_OUT_FATAL: i64 = 13 |
| 134 | const CLKRS_OUT_LOST_INDEX: i64 = 14 |
| 135 | const CLKRS_OUT_LOST_PID: i64 = 15 |
| 136 | const CLKRS_OUT_LOST_WAIT: i64 = 16 |
| 137 | const CLKRS_OUT_KNOWN_OWNED: i64 = 17 |
| 138 | const CLKRS_OUT_N: i64 = 18 |
| 760 | const CLK_EPOCH_FLOOR: i64 = 1000000000 |
| 1319 | const CFI_ECHILD: i64 = 0 - 10 |
functions
| 140 | func clk_heavy_listed(conf: *u8, n: i64, name: *u8) -> i64 |
| 167 | func clk_defer_secs(interval: i64) -> i64 called by 1: clk_run_edf_core |
| 175 | func clk_storm_defer(heavy: i64, budget: i64) -> i64 called by 1: clk_run_edf_core |
| 182 | func clk_storm_budget(ioa: *i64) -> i64 |
| 187 | func clk_slot(names: *u8, i: i64) -> *u8 { return ((names as i64) + i*CLK_NAMEW) as *u8 } |
| 188 | func clk_streq(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 } |
| 190 | func clk_find(names: *u8, n: i64, name: *u8) -> i64 { var i: i64=0; while i<n { if clk_streq(clk_slot(names,i), name)==1 { return i } i=i+1 } return 0-1 } |
| 194 | func clk_register(names: *u8, organs: *u8, intervals: *i64, next_due: *i64, np: *i64, name: *u8, organ: *u8, interval: i64) -> i64 |
| 264 | func clk_tick(intervals: *i64, next_due: *i64, n: i64, now: i64, fired: *i64) -> i64 |
| 281 | func clk_dispatch_run(organs: *u8, intervals: *i64, next_due: *i64, n: i64, now: i64, fired: *i64) -> i64 |
| 314 | func clk_run_tickless(organs: *u8, intervals: *i64, next_due: *i64, n: i64, start_tick: i64, maxbeats: i64, tick_ms: i64, out: *i64) -> i64 |
| 337 | func clk_due_in(next_due_i: i64, now: i64) -> i64 { return next_due_i - now } |
| 338 | func clk_twin_ok(organ: *u8) -> i64 { let fd: i64 = sys_openat_rd(organ); if fd < 0 { return 0 } sys_close(fd); return 1 } |
| 340 | func clk_itoa(buf: *u8, o: i64, v: i64) -> i64 { var w: i64=o; var m: i64=v; if m==0{buf[w]=48 as u8;return w+1} if m<0{buf[w]=45 as u8;w=w+1;m=0-m} let t:*u8=sys_mmap(24); var k:i64=0; while m>0{t[k]=(48+(m%10)) as u8;m=m/10;k=k+1} var j:i64=0; while j<k{buf[w]=t[k-1-j];w=w+1;j=j+1} return w } |
| 343 | func clk_msgcat(d: *u8, o: i64, s: *u8) -> i64 { var x: i64=o; var i: i64=0; while s[i]!=(0 as u8){d[x]=s[i];x=x+1;i=i+1} return x } |
| 344 | func clk_msgnum(d: *u8, o: i64, v: i64) -> i64 |
| 368 | func clk_actlog(organ: *u8, code: i64) -> i64 |
| 390 | func clk_save(path: *u8, names: *u8, organs: *u8, intervals: *i64, next_due: *i64, n: i64) -> i64 |
| 490 | func clk_load_plane(prefix: *u8, names: *u8, organs: *u8, intervals: *i64, next_due: *i64, np: *i64) -> i64 |
| 533 | func clk_save_plane(prefix: *u8, names: *u8, organs: *u8, intervals: *i64, next_due: *i64, n: i64) -> i64 |
| 581 | func clk_load_state(prefix: *u8, legacy: *u8, names: *u8, organs: *u8, intervals: *i64, next_due: *i64, np: *i64) -> i64 |
| 593 | func clk_merge_store(prefix: *u8, names: *u8, organs: *u8, intervals: *i64, next_due: *i64, np: *i64, base_tick: i64) -> i64 |
| 775 | func clk_demand_per_window(intervals: *i64, n: i64, window_secs: i64) -> i64 called by 1: main |
| 795 | func clk_edf_pick_free(deadlines: *i64, n: i64, now: i64, busy: *i64) -> i64 |
| 811 | func clk_edf_pick(deadlines: *i64, n: i64, now: i64) -> i64 called by 1: clk_run_edf_core |
| 826 | func clk_edf_next(deadlines: *i64, n: i64) -> i64 called by 1: clk_run_edf_core |
| 836 | func clk_edf_missed(deadlines: *i64, intervals: *i64, i: i64, now: i64) -> i64 |
| 845 | func clk_edf_rearm(deadlines: *i64, intervals: *i64, i: i64, now: i64) -> i64 |
| 857 | func clk_edf_migrate(deadlines: *i64, intervals: *i64, n: i64, now: i64) -> i64 called by 1: main |
| 888 | func clk_ifw(s: *u8, dst: *u8, o: i64) -> i64 { var x: i64=o; var i: i64=0; while s[i]!=(0 as u8){dst[x]=s[i];x=x+1;i=i+1} return x } called by 1: clk_inflight |
| 889 | func clk_ifn(dst: *u8, o: i64, v: i64) -> i64 { var x: i64=o; var mm: i64=v; if mm<0{dst[x]=45 as u8;x=x+1;mm=0-mm} if mm==0{dst[x]=48 as u8;return x+1} let t:*u8=sys_mmap(24); var k:i64=0; while mm>0{t[k]=(48+(mm%10)) as u8;mm=mm/10;k=k+1} var j:i64=0; while j<k{dst[x]=t[k-1-j];x=x+1;j=j+1} return x } |
| 890 | func clk_inflight(tag: *u8, organ: *u8, a: i64, b: i64) -> i64 called by 1: clk_run_edf_core calls 7: sys_mmapclk_ifwclk_ifnsys_now_realtime_secsys_openat_wrsys_write+1 |
| 903 | func clk_run_edf_core(organs: *u8, names: *u8, intervals: *i64, deadlines: *i64, n: i64, maxdispatch: i64, budget_secs: i64, tick_ms: i64, out: *i64, reserved_mode: i64) -> i64 |
| 1078 | func clk_split_argv(raw0: *u8, buf: *u8, argv: *i64, label: *u8) -> i64 |
| 1119 | func clk_dispatch_one(organs: *u8, names: *u8, i: i64) -> i64 called by 1: clk_run_edf_core calls 14: sys_mmapclk_split_argvclk_slotsys_forkclk_msgcatsys_openat_append+8 |
| 1187 | func clk_load(path: *u8, names: *u8, organs: *u8, intervals: *i64, next_due: *i64, np: *i64) -> i64 |
| 1225 | func clk_reserved_resolve(conf: *u8, cn: i64, names: *u8, organs: *u8, intervals: *i64, n: i64, heavy: *u8, hn: i64) -> i64 |
| 1282 | func clk_reserved_due(index: i64, foreground: i64, pid: i64, due: i64, now: i64, foreground_live: i64) -> i64 called by 1: clk_dispatch_reserved |
| 1292 | func clk_reserved_spawn(organs: *u8, names: *u8, i: i64) -> i64 called by 1: clk_dispatch_reserved calls 10: sys_forksys_mmapclk_split_argvclk_slotclk_msgcatsys_openat_append+4 |
| 1309 | func clk_reserved_log(organs: *u8, names: *u8, i: i64, code: i64) -> i64 |
| 1320 | func cfi_number(path: *u8) -> i64 called by 3: cfi_writeclk_reserved_wait_ownedclk_reserved_signal_owned calls 2: sys_mmapsys_read_file |
| 1326 | func cfi_write(path: *u8, value: i64) -> i64 |
| 1334 | func cfi_mode() -> i64 |
| 1340 | func cfi_fault_event() -> i64 called by 1: clk_reserved_wait_owned calls 8: sys_openat_appendsys_flocksys_closesys_mmapclk_msgcatclk_msgnum+2 |
| 1353 | func clk_reserved_wait_owned(pid: i64, status: *i64, flags: i64) -> i64 |
| 1376 | func clk_reserved_signal_owned(pid: i64, signal: i64) -> i64 |
| 1384 | func clk_reserved_wait_kind(result: i64, pid: i64) -> i64 called by 1: clk_dispatch_reserved |
| 1391 | func clk_reserved_halt_required(out: *i64) -> i64 called by 1: main |
| 1395 | func clk_reserved_lost(ro: *i64, names: *u8, i: i64, pid: i64, result: i64, other_owned: i64) -> i64 |
| 1413 | func clk_dispatch_reserved(organs: *u8, names: *u8, intervals: *i64, deadlines: *i64, i: i64, reserved: i64, deadline_ms: i64, poll_ms: i64, ro: *i64) -> i64 |
| 1505 | func clk_run_edf(organs: *u8, names: *u8, intervals: *i64, deadlines: *i64, n: i64, maxdispatch: i64, budget_secs: i64, tick_ms: i64, out: *i64) -> i64 calls 1: clk_run_edf_core |
| 1510 | func clk_run_edf_reserved(organs: *u8, names: *u8, intervals: *i64, deadlines: *i64, n: i64, maxdispatch: i64, budget_secs: i64, tick_ms: i64, out: *i64) -> i64 |