Skip to content

Commit 62e45e7

Browse files
committed
Ledger (61): the analytic-IC pre_process trap, the bracket-free MPI-wait split (4 reps), GPU-ladder provenance
1 parent f123623 commit 62e45e7

1 file changed

Lines changed: 68 additions & 0 deletions

File tree

docs/documentation/amr_action_plan.md

Lines changed: 68 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -226,6 +226,74 @@ possible while AMR aborts on the target machine at 1 rank, and every increment b
226226
on a compiler that does not reproduce it. It also means the ladder should add a CCE arm as soon as one
227227
exists, or the same class of breakage will keep accumulating undetected.
228228

229+
## 2026-09-03 (61) — A FAKE NaN REGRESSION (the analytic-IC pre_process trap), the bracket-free MPI-wait instrument, and where Phase 2 stands at the end of the day
230+
231+
**The NaN.** The first run of the new `[mpiwait]` instrument on the 400^3 deck aborted with "NaN(s) in timestep output" at
232+
step 40 (the second regrid) on the merged tree with rdma_mpi=T; the same deck had run clean all afternoon on 230ed4eb with
233+
rdma_mpi=T. I bisected it as a Task 11 / Task 6 / rdma interaction (two GPU builds, one rdma=F control) — and the control was
234+
worthless, because it used the campaign's pinned pre_process. The implementer found the discriminator: **the NaN follows the
235+
pre_process binary**, not the simulation. The 400^3 deck's density is an ANALYTIC expression compiled into pre_process
236+
(pre_process.inp carries `alpha_rho(1) = 0d0` as the placeholder); a pre_process built generically (`mfc.sh build` without
237+
the case) initializes zero density, identical grids, different `lustre_0.dat`, and the flow reaches a NaN at the step-40
238+
regrid. Every simulation binary (17706ebb, 230edeb, instrumented or not, rdma T or F) is clean with the case-built
239+
pre_process. **No code regression.** The standing rule (amr-tooling-accelerants: never an analytic IC in a benchmark deck)
240+
was violated by the deck itself; the next campaign deck uses a built-in patch geometry, and until then every new simulation
241+
binary pairs with the pinned pre_process (bin/pre_process, sha 2d8c235a). Cost: ~1 h of the hold and two unneeded builds.
242+
243+
**Task 6 wall gate, first pair (np64, one node k003-003, cap-0 deck, job 404113):** old1 8264.0 s, new1 8444.8 s (+2.2%).
244+
Pre-registered expectation was wall-neutral; +2.2% on one pair is inside this deck's rep spread (ledger 53: 0.5-0.8% at
245+
np512 but ~5% at np64 single-node) and is not a verdict; old2/new2 read when they land. The np512 pair (404112) has no arm
246+
finished yet. Neither A/B is on the cap-64 operating point of ledger 53 (the guard forced cap 0 before Task 11 landed).
247+
248+
**Provenance finding on the GPU ladder (ledger 57's np8 -> np16 = 1.33x).** The multi-node GPU harness (qgpu_multi.sh)
249+
pinned its binary from a hard-coded path in the `mfc-amr-build` worktree, which is DIRTY (d4edbce2 plus 70 modified files;
250+
binary 1169b6fd built 09-01 15:04). The np8/np16 rungs therefore ran code of unknown provenance, and the np32 rung
251+
(404066) died in 5 s because the harness excluded only one of the six sick nodes and drew k004-002. Both fixed in the
252+
script (TREE parameter recorded per job; full exclude list). The 1.33x stands only as indicative; the GPU ladder is redone
253+
on up/mega (np8/16/32, one job per rung, same binary, [mpiwait] regrid row included) before statement 1 cites it.
254+
255+
**The instrument (task10/waitinst 9de1fbe4, +146/-3, NOT merged yet).** 28 two-line MPI_Wtime brackets around the exchange
256+
families' WAITALL/RECV/SENDRECV sites (no GPU_WAIT, no new MPI calls in the step loop; one gather at finalize), printed as a
257+
`[mpiwait]` table with per-rank vectors under rank_time_wrt. Gates: 70/70 AMR goldens; rank_time_wrt T vs F byte-identical on
258+
two np=2 decks; [amr-xa] counts identical to an uninstrumented binary. First 40-step table (growth window, rdma=T): total MPI
259+
wait 7.45 s mean / 9.95 max (rank 7) / 4.79 min (rank 0) = 0.19 s/step mean, 57% of it in the base halo SENDRECV with rank 0
260+
the late arriver. The steady-state 60-40 split and the pre-registered decision (>= 0.7 s/step -> skew; <= 0.3 -> host work
261+
-> batched advance) are read here from the rerun with the case-built pre_process (prof_wi_oldpre.out; amr_{40,60}_wi/sim_r{1,2}.log).
262+
263+
**THE SPLIT (steps 41-60, MPI wait per step; four reps = prof_wi_oldpre + prof_wi2; per-rank differencing, then mean /
264+
max / min over the 8 ranks; reviewed and recomputed 2026-09-03 after a first version combined already-aggregated columns):**
265+
| family group | rep 1 (window 2.63 s/step) | rep 2 (3.20) | rep 3 (2.85) | rep 4 (2.78) |
266+
| base grid (halo + b:halo + rg:halo) | 0.02 / 0.10 / -0.02 | 0.09 / 0.21 / 0.04 | 0.06 / 0.21 / 0.01 | 0.03 / 0.14 / -0.01 |
267+
| gather + pgather (F1/F2) | 0.03 / 0.05 / 0.02 | 0.05 / 0.08 / 0.02 | 0.06 / 0.08 / 0.02 | 0.05 / 0.06 / 0.03 |
268+
| seam (F6) | 0.06 / 0.13 / 0.01 | 0.06 / 0.14 / 0.02 | 0.07 / 0.14 / 0.02 | 0.06 / 0.14 / 0.01 |
269+
| reflux (F5) | 0.12 / 0.22 / -0.03 | 0.13 / 0.21 / 0.06 | 0.19 / 0.33 / 0.04 | 0.14 / 0.24 / 0.01 |
270+
| restr (F7) | 0.05 / 0.08 / 0.00 | 0.07 / 0.10 / 0.03 | 0.06 / 0.10 / 0.02 | 0.07 / 0.10 / 0.03 |
271+
| **exchange families, total** | **0.28** / 0.43 / 0.11 | **0.41** / 0.53 / 0.24 | **0.43** / 0.64 / 0.23 | **0.35** / 0.51 / 0.14 |
272+
| regrid (one regrid in the window) | 0.21 / 0.28 / 0.01 | 0.53 / 0.66 / 0.03 | 0.21 / 0.28 / 0.01 | 0.20 / 0.28 / 0.02 |
273+
| TOTAL | 0.48 / 0.66 / 0.12 | 0.94 / 1.18 / 0.35 | 0.64 / 0.89 / 0.24 | 0.56 / 0.78 / 0.15 |
274+
| rank 0 only, TOTAL | 0.65 | 1.15 | 0.89 | 0.78 |
275+
Rank 3 is the least-waiting rank in TOTAL, in regrid, and in seam in all four reps, and in reflux in three; it is the
276+
MOST-waiting rank in gather+pgather (0.05-0.08) in two reps — so it is the overall straggler the others wait for at the
277+
regrid and the reflux/seam syncs, not uniformly. Its fine_work is the largest (+2.7% over the mean). At the one regrid in
278+
the window the other seven ranks wait 3.9-5.7 s each (13 s in rep 2, whose regrid was 2.5x slower across the board) while
279+
rank 3 waits 0.2-0.7 s. The window moved 22% between reps 1 and 2 (2.63 vs 3.20 s/step, same binary, same deck, back to
280+
back under the lock; reps 3-4 at 2.85/2.78) — the rep spread of this deck at 8 GPUs exceeds any single family's wait, so
281+
per-family numbers are ranges. The table excludes collectives (ALLREDUCE/ALLGATHER in the regrid and the rb:xchg flag are
282+
not bracketed), so TOTAL is a lower bound on MPI wait.
283+
284+
**Decision-rule outcome (pre-registered in task-10-step2-brief.md): IN BETWEEN.** Exchange-family MPI wait is 0.28-0.43
285+
s/step (rank mean), neither >= 0.7 (skew would be the program) nor <= 0.3 (host work would be). Rank-0 accounting of the
286+
window, with the GPU-side term CARRIED from ledger 60's separate 2.87 s/step steady arm (kernels 1.03 + descriptor copies
287+
0.17 = 1.20; not remeasured here): window 2.63 / 3.20 / 2.85 / 2.78 minus 1.20 minus rank-0 MPI wait 0.65 / 1.15 / 0.89 /
288+
0.78 = **host-only work between launches 0.78 / 0.85 / 0.75 / 0.81 s/step** (plan building, per-box host loops, 1,256
289+
launches' API latency) — the largest single term after the kernels, and the one the batched advance / fused launches
290+
attack. Ordering for Phase 2, final for today: (1) launch-count reduction — batched fine advance (row 6) and fused packs
291+
(2b) on top of the parked 2a pools, ceiling ~0.8-1.0 s/step (host work + dispatch tax), A/B by bracket-free 240-step walls;
292+
(2) reflux/seam waits (0.2 s/step) via the M1 one-message-per-peer families (Task 5); (3) the regrid straggler
293+
(0.2-0.5 s/step, one rank) belongs to Tasks 4/9 — the `[mpiwait] regrid` row IS the per-rank regrid-skew instrument Task 4
294+
set out to build, and its np256/512 rungs should read it. The instrument branch goes to review for merge (it is +146 lines
295+
of MPI_Wtime bookkeeping, gated on rank_time_wrt, byte-identical T vs F).
296+
229297
## 2026-09-03 (60) — PHASE 2 FIRST RESULTS: rdma_mpi=T legal under OpenMP (-4% wall); device pools buy NOTHING (falsifier confirmed on 240-step arms); the per-DISPATCH tax measured (21,000 tiny D2D copies/step); Task 6 (batch-4) merged; GPU_LOCK protocol
230298

231299
**Increment 0 (amr-bench/notes/phase2_batched_advance.md, "Increment 0 RESULT").** The `rdma_mpi` checker gate predated the

0 commit comments

Comments
 (0)