Repository navigation
GLM-5.3-Flash on two CUDA ranks: the native family, its kernels (fused EXL3 prompt kernel), DFlash2, -Dglm - #855
BobClawblaw wants to merge 28 commits into
Conversation
….cu) and the ranks' control link (tp_link.zig): small gathers as RDMA writes over both halves of the port, after b12x's exchange; NCCL carries the rest
…wer: batched prompt passes (prefill_many, addStreams), a backend's refusals for a memory guard, follow() for a tensor-parallel rank 1, shared-pool admission fields, image and video inputs for the native server (vision_inputs, media_fetch, qwen_image, stb_image)
…glm_cuda), its kernels (zig/kernels/cuda/glm: the dense matmul at 4/6/8/16 bits, the EXL3 trellis experts with the fused prompt kernel, latent attention, the indexer, KDA, the hyper-connections, the vision tower's helpers, DFlash2), tf-cuda-test glm-batch/glm-prof/glm-tf, -Dglm (cherry picked from commit 611959f15964cda97ecd12d0e459ea4ac0e84f78)
…h), no include across families
…prefill, sample) and no Flash Next test commands
…meration, kernel parameter info, virtual memory)
|
@BobClawblaw thanks for the CUDA GLM work. Here are test results for Setup. 2× DGX Spark (GB10), one direct ConnectX-7 cable, with two HCAs configured in Checkpoint: Engine test.
These are direct engine tests, separate from the server benchmarks below. Both ranks printed the pass line, but rank 0 was still alive about 22 minutes later, with Server tests.
All measured runs had matching token and output hashes across the three modes. The drafted measurements reused prompt state; the undrafted measurements reported zero cached tokens. With DFlash2 and Median aggregate decode throughput at level 4 was 97.4 tok/s for These are TensorFold's benchmark-tool prompts, so the rates are not directly comparable with the recipe's prose/code/structured/list results. DFlash2's observed throughput was 6.3% higher than MTP on Prompt TTFT. MTP,
The server counted 2,040–32,762 prompt tokens. These are TTFT-derived rates on different prompts and lengths, rather than a reproduction of the recipe's prefill benchmark. Rank 0's startup report labelled 85.65 GiB as model allocation with DFlash2 loaded. Its Not tested: |
|
Thank you for the independent run, that is exactly the check this PR needed. The decode gap against the recipe's numbers is settings, not hardware: the recipe serves with Rank 0 alive after "glm-batch passed": known and not yet fixed in this branch; our harness kills the test binaries on the pass line, which is no answer. The hang is in the test's teardown, after the pass line: NCCL's communicator abort and the library's unload with its service threads still live. The fix lands as a commit here shortly: each "no prompt cache" at startup while responses report cached tokens: the startup line describes the lane core's prompt cache, which this family does not use; the family keeps its own prompt states (what the The 1M-context configuration is measured in the recipe's evidence ( |
|
Both fixes are on the branch as 8f99433: |
…ardown hung in NCCL's service threads under the library's unload, reported on PR 855); the startup line says a family keeps its own prompt states instead of 'no prompt cache'
3c6ed00 to
87ef757
Compare
…cel; lean rule and zig fmt setup() returned cancel()'s true for a background warm pass that yields to a newer request, so the caller launched the job cancel() had just finished (SEGV in lane_host_warm_test). It now returns false, as for a drop. Comments one line each; lean_check skips zig/vendor/ (stb_image.h, as on ashhart#726). lane_host.zig and lanes/engine.zig stay under 600 lines: the batched prompt pass moves to lane_host_admit.zig (many, one) and lanes/open.zig (addStreams, adoptPrefilled), aliased where they were.
…ders in docs/glm-cuda-notes.md Splits move code unchanged (only imports, aliases and pub change): kern.zig into kern_attn, kern_kda and kern_moe; weights.zig into ckpt, experts_load and qpack; dflash.zig into dflash_load and dflash_select; native.zig into native_draft, native_prompt, native_follow and native_env; exl3.cu's transposed prompt design into exl3_transposed.cuh; tf-cuda-test glm-tf and glm-prof into glm_forward_run.zig.
…cs/roce-gather.md, zig fmt
…rozen words (the errors/content-image golden)
|
CI fix. This branch now carries #852's and #853's fixes (merged in), including #853's warm-pass crash fix and the golden refusal. Its own changes, in
Locally: |
…nsorfold-native takes memcpy from libSystem again (zig build test on macOS)
|
Hello @BobClawblaw, Thank you for GLM-5.3-Flash on two CUDA ranks. DFlash2, the history-copy draft, the vision tower, the kept prompt states, and the EXL3 routed path move into #804, the one GLM CUDA family. The two-rank link and the small RoCE gather move into the one transport. A sampled prompt returns the token from drawRows and skips the RoCE check (decode.zig:222, decode.zig:90). readPicks calls it (decode.zig:31). A timed-out gather writes nothing and returns success (roce_gather.cu:99), so the token can be the previous request's candidates. Call check after every sync that then reads a gather, including DFlash2 (dflash.zig:626). fits still uses this rank's unrounded max_bytes (roce.zig:453). The handshake compared only the rounded slots (roce.zig:213). Startup agrees only that the drafter is on both ranks (native.zig:381). Each rank reads its own prompt chunk (forward.zig:31, decode.zig:174), TF_GLM_MIX (native.zig:337, native.zig:781), and the DFlash2 split (dflash.zig:321, dflash.zig:718). Agree those before the first collective, or refuse the pair. The image frame goes out before the prompt is admitted (native.zig:576, native.zig:517). Rank 1 keeps the features and attaches them to the next prefill (native.zig:952). If admission fails, a later text prompt on rank 1 can take the previous image. Bind the features to that prefill, and drop them if it never arrives. release sends keep before the retained prefix exists (native.zig:913). If the allocation fails, rank 0 drops the sequence and rank 1 keeps it (native.zig:1003). Allocate first, or send an eviction when the keep fails. Thank you again. |
…eports; images wait for the shared decoder; no refused hook - prompt_cache: Entry.pins, Store.pin/unpin. victimBut passes pinned entries over, so a later job's lookup in admit.many (or a keep during the batched pass) no longer frees a state an earlier job has yet to restore; a keep with nothing evictable fails instead of unwrapping null. LaneHost.setup pins, reported and requeue unpin. - vision: zig/vendor/stb dropped and no longer compiled. qwen_image.decode refuses by name (NoDecoder) until the shared runtime decoder (pinned libjpeg-turbo) lands; lean_check's vendor exemption goes with it. - lanes: Backend.VTable.refused, Engine.refused, cuda_bound's forwarding and the fake's stray refusedFn removed; nothing consumed them.
…; fits tests the smaller on both), its host test in the cuda tests
… reads a gather (sampled draws, the full row, DFlash2), the ranks' settings agreed before the first collective, an image frame bound to its prefill by request id, a kept state allocated before rank 1 hears the keep
|
Thank you, @BobClawblaw, for continuing the two-rank GLM work. At Three blockers and one should-fix are still open:
Please close these paths before it lands. Posted by Ash's AI Assistant Synthena |
|
Thank you, @ashhart. All four are closed in
Checked on our pair at TP=2 with the recipe's settings (EXL3, DFlash2, dense 4 bits):
Not run yet: the image path itself. Our server build refuses image inputs before admission (it lacks the shared JPEG and PNG decoder), so the request-id binding is checked by build and review only, not by a live image request. |
…eed only at its last unpin; a job reports resumed before it unpins
|
@ashhart Two updates, in
|
|
Thank you, @BobClawblaw, for addressing all four failure schedules and carrying the later #853 lifetime fix. At c525ea9, Please include the settings-mismatch and failed-image-admission/retry cases in the two-rank integration checks once the common image decoder is connected. Posted by Ash's AI Assistant Synthena |
|
@BobClawblaw thanks for the fixes. Here is a rerun of Build.
Those rates are 4.0–4.4% below the Settings check. I started Server,
Token and output hashes matched across the three modes and both commits. As before, the drafted runs reused prompt state and the undrafted ones reported zero cached tokens. With DFlash2 and Cold prompt TTFT with MTP,
These TTFT-based rates are within 0.5% of the earlier run. Not tested: image inputs (so neither the request-id binding nor a failed image admission), sampled decoding, a transport failure, a failed keep, and the recipe's |
|
@SvangenStudios thanks for rerunning On the 4–7% gap, I reran
Single runs drop by 7–17% at random on either commit, more than the gap between your two runs. The medians agree within noise, so I don't see a regression. @ashhart thanks for closing the four findings. Now that 1.0.12 and #804 are on main, I'm moving this work where you asked: the RoCE gather and the ranks' link into the transport on main (
I'll update this PR when the ported head passes them on our pair, and rerun |
|
@ashhart a question before I bring this onto 1.0.12, since #804 landed GLM-5.3-Flash on CUDA from the NVFP4 checkpoint. The two families overlap:
I'll hold this branch until you say. |
GLM-5.3-Flash on two CUDA ranks
The native family (
zig/src/families/glm_cuda), registered with-Dglm, on top of #853 (lane core and host) and #852 (the RoCE all-gather); the branch contains both:zig/kernels/cuda/glm): the dense matmul at 4/6/8/16 bits, the EXL3 trellis experts with a fused prompt kernel after Mia's AI Lab's transposed design (gate and up with the SwiGLU as the epilogue, the down projection with its own: 7.2 s for 32K tokens' experts where the grouped kernel took 87 s), latent attention, the indexer, KDA, the hyper-connections, DFlash2.tf-cuda-test glm-batch(16 streams together equal to each alone, serial and drafted, resumed equal to fresh),glm-prof(a prompt's kernels),glm-tf(teacher-forced agreement).Measured on two DGX Sparks (GB10) at TP=2, 1M context: cold prefill 991 / 1,001 / 957 tok/s on 6K / 30K / 114K-token prompts, one-stream decode 45 / 69 / 56 / 55 tok/s (prose / code / structured / list), 16 streams 131-173 tok/s aggregate. Evidence and the quality suite (GSM8K 244/250, MMLU 292/342, HumanEval 156/164, MGSM 223/240) in https://github.com/BobClawblaw/glm53-flash-exl3-2x-dgx-sparks.
The Flash Next CUDA family that shares the vision tower is not in this PR.