No job could ever be scheduled in normal mode -- every round produced decision=(nil), forever. Three independent bugs were stacked on the same symptom, each masking the next (only reachable once the prior one was fixed): 1. scheduler.c's sched_init_queues() -- the scheduler's one-time synchronous initial-config-push handler -- only fired the legacy job_elect_fn-era plugin_queue_update() fan-out. builtin_fcfs (the default picker) has no .hooks, only picker_iface, so on_queue_update() was never called for any queue from the initial cluster config. Its own candidate registry stayed empty forever, so next_job() found zero candidates on every session. 2. Once #1 was fixed and a job first reached the allocator, core_events.c's core_build_job() never constructed job->schedobj -- a documented but incorrect assumption from the scheduler-core rewrite ("no picker hook reads job->schedobj... belongs to a separate allocation spec" -- no such spec exists in the live code). sched_allocator() dereferences it directly with no NULL check; reproduced live as a SIGSEGV in limit_job_election(). 3. Once #2 was fixed and a job reached genuine dispatch, resource.c's put_resvals() crashed during post-dispatch resource charging: `idxs[i] <= 0` treated resource index 0 ("slots", almost always the first registered resource) as an invalid sentinel, leaving its value slot NULL for an unconditional write two lines later. All three root-caused via gdb `bt full` on live SIGSEGVs, not guesswork, and live-verified end-to-end: a 3-element job array now runs PEND -> DISPATCH -> RUN -> DONE with the scheduler staying alive throughout. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com> |
||
|---|---|---|
| .. | ||
| autoscaler | ||
| configs | ||
| controller | ||
| docs | ||
| frontend | ||
| include | ||
| lib | ||
| nixSupport | ||
| scheduler | ||
| schema | ||
| tools | ||
| worker | ||
| xceadmin | ||
| flake.lock | ||
| flake.nix | ||
| meson.build | ||
| meson.options | ||