GPT-2 grade on a single RTX 5090 in 41 hours — recipe, Blackwell gotcha, and an open question about sliding windows #819
carey-bunks
started this conversation in
Show and tell
Replies: 0 comments
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
GPT-2 grade on a single RTX 5090 in 41 hours — recipe, Blackwell gotcha, and an open question about sliding windows
Not a leaderboard entry — the leaderboard measures wall-clock on 8×H100 and this is one consumer card. Posting because the README points sub-80GB users at
--device-batch-sizeand leaves them to it, and there were a few more things to get right than that.Result
Data: 170 ClimbMix shards downloaded, 131 consumed,
epoch: 1throughout. Tokenizer 4.74 chars/token. Cost: electricity (approx. £6.64 or $8.95).The Blackwell gotcha (this one is mandatory)
On sm_120 the FA3 loader reports success and then dies at the first attention call:
_load_flash_attention_3()only special-casesmajor == 9for Hopper; Blackwell falls through tokernels-community/flash-attn3, andhas_kernel()returnsTruefor a kernel with no sm_120 image. One-line fix innanochat/flash_attention.py, right after the capability check:Verify:
(Filed separately as an issue.)
Full recipe
Notes on each deviation
--device-batch-size=2→ 256 gradient accumulation steps. Peak was 21 GB torch-reported (~29.5 GB innvidia-smi, the difference being allocator reservation). 4 does not fit for d24 on 32 GB.base_evalat 16 is fine — no optimizer state.--window-pattern L— forced, not chosen. Sliding windows need FA3; without it_sdpa_attentionhas to build an explicit mask, which disables the fused kernel, andbase_train.pywarns about this directly. WithLatTq == Tk == 2048the SDPA path returns viaF.scaled_dot_product_attention(..., is_causal=True)with no mask, so you stay on torch's own fused flash backend, which does support sm_120.--fp8works on Blackwell — 145/158 linear layers converted, no issues across 41 hours.Use
torchruneven on one GPU. Barepython -m scripts.base_trainhung before argparse and was unresponsive to SIGINT on this setup. The--separator is required when going through torchrun.Don't run
runs/speedrun.sh— it hardcodesNANOCHAT_BASE_DIR, 8 GPUs, device-batch 16, and the default window pattern.--save-everydefaults to −1, i.e. checkpoints only at the end. I gambled and got away with it; on a 41-hour run you probably want--save-every=500. If you're on a consumer card, also check your case thermals rather than just the GPU — I had a prior kernel panic at 12 hours under sustained load at stock 575 W. Ran this one capped at 500 W, ~78 °C, with extra airflow, and step time held at 27.1 s for the full run with zero drift.Reading the log:
bf16_mfushows ~17% but real utilisation is ~100%.Estimated FLOPs per tokenfor d24 prints 9.06e8, which appears to count only the attention term — the matmul term is missing, true value ≈ 5.28e9. (38,800 tok/s × 5.28e9 = 2.05e14 FLOP/s against the card's 2.10e14 bf16 peak.) Trust theetafield, which is wall-clock derived.An open question about sliding windows
My CORE came in above the ClimbMix leaderboard entry (0.2702 vs 0.2571) at essentially identical val_bpb (0.7188 in-training vs 0.71854). I want to be clear that this is not evidence for anything — I'm on master four months after that entry, at d24 rather than d26, ratio 8 rather than 8.25, device-batch 2 with 256 accumulation steps rather than 8×16, FP8 on a different hardware path, one seed, and I'm not certain whether leaderboard CORE figures come from the capped in-training eval or the full standalone one (that gap alone is 0.0101 for me).
But it does raise a question I can't answer from one run: what does the
SSSLsliding-window pattern cost in quality? It's there to save compute, and on H100s with FA3 it clearly does. Whether the local-attention inductive bias is free, mildly positive, or mildly negative at fixed step count doesn't seem to have been isolated anywhere I could find.That's a clean d12 A/B —
LvsSSSL, everything else held — and cheap on 8×H100 at the ~5 min/run scale the README recommends for iteration. I can run it on the 5090 (slowly, sinceSSSLwill be on the unfused SDPA path here), but someone with the reference hardware would get a much cleaner answer, and paired val_bpb + CORE would settle it. Happy to be told this has already been measured.Other small things
nvidia-smioverstates memory considerably vs the torch-reported peak; don't size batches from it-wto 2 if you see failuresteewithoutPYTHONUNBUFFERED=1gives a 0-byte log for several minutes and looks exactly like a hang--run=without a wandb account errors;WANDB_RUN=dummy+--run=dummyHappy to share the full training log or eval CSV if useful.
Disclosure per repo AI policy: this post was drafted with LLM assistance. The run, configuration, logs and numbers are my own.
All reactions