mirror of
https://github.com/Comfy-Org/comfy-kitchen.git
synced 2026-11-04 23:37:42 +00:00
[PR #254] Vectorize HIP rms_adaln and split-half rms_rope #259
Labels
No labels
pull-request
No milestone
No project
No assignees
1 participant
Notifications
Due date
No due date set.
Dependencies
No dependencies set.
Reference
Comfy-Org/comfy-kitchen#259
Loading…
Add table
Add a link
Reference in a new issue
No description provided.
Delete branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
📋 Pull Request Information
Original PR: https://github.com/Comfy-Org/comfy-kitchen/pull/254
Author: @qweqweewqe7-create
Created: 10/17/2026
Status: 🔄 Open
Base:
main← Head:moss-hip-adaln-rope-vectorize📝 Commits (2)
7c01dd2Vectorize HIP rms_adaln and split-half rms_rope8a3e749Copy rms_adaln/rms_rope vector packs with memcpy📊 Changes
2 files changed (+318 additions, -0 deletions)
View changed files
📝
comfy_kitchen/backends/hip/ops/adaln.hip(+159 -0)📝
comfy_kitchen/backends/hip/ops/rms_rope.hip(+159 -0)📄 Description
Summary
Vectorized HIP fast paths for two memory-bound kernels used by modulated DiT blocks (MOSS-Image, among others):
rms_adaln/adaln: half/bf16 rows withD % 8 == 0andD <= 4096. Each thread keeps up to four 16-byte chunks of the row in registers, soxis read once instead of twice; scale/shift are loaded 8 at a time; the reductions use wave shuffles.rms_rope: half/bf16q/kwith a contiguous head dim of 64, 128 or 256, full rotation and contiguous fp32[.., rot/2, 2, 2]freqs.head_dim / 8lanes share a row and each holds four(p, p + head_dim/2)pairs ofqandk, so both are read once; the norm reduces with shuffles. The in-place variant stays safe, since every lane loads its elements before storing them.Every other dtype, layout and size keeps the existing kernels. The per-element math and rounding are the existing kernels'; only the order of the fp32 sums differs.
Performance
RX 9070 XT (gfx1201), PyTorch
2.16.0a0+rocm10.2.0a20261015, HIP event timing, 50 iterations after 10 warmups:rms_adalnbf16 6304x3072, broadcast scale/shiftrms_adalnfp16 1000x3072, per-row fp32 scale/shiftrms_adalnbf16 4097x1536rms_adalnbf16 2048x4096rms_rope_split_halfbf16 qkv slice, 6304 x 24 x 128rms_rope_split_halffp16 3001 x 16 x 64rms_rope_split_halfbf16 1003 x 8 x 256, fp32 scalerms_rope_split_half_bf16 in place, 2051 x 24 x 128A device-to-device copy measures 618 GB/s on the same card. MOSS-Image 1024x1536 DiT forward: 584 -> 554 ms.
Correctness
tests/test_adaln.py tests/test_rms_rope.pyand the HIP dispatch/WMMA/INT8 files on RX 9070 XT (gfx1201) and RX 9060 XT (gfx1200): same results as unmodifiedmain. The only failures (18 triton cases andtest_int8_linear_correctness[hip]) fail identically onmain.Update: rebased onto v0.2.40, compared with #259's wave32 rms_rope
Rebased onto
main(f8b7e97, v0.2.40). #259 addedrms_rope_wave32_128_kernel, which now handles every head_dim=128 call on wave32, split-half included. The vectorized split-half path here is checked first and only takes the cases it supports. Everything else goes through #259's dispatch. The interleavedrms_ropeis unchanged and gives the same output hash asmain.RX 9070 XT (gfx1201) and RX 9060 XT (gfx1200), PyTorch
2.16.0a0+rocm10.3.0a20261023, HIP 7.17.26423. Timings are wall-clock medians over windows of 50 calls, averaged over two alternating runs. MOSS-Image 1024x1536 shapes (6304 tokens, D=3072, 24 heads x 128, BHND):rms_adalnbf16 6304 x 3072adalnbf16 6304 x 3072rms_rope_split_halfbf16rms_rope(interleaved, unchanged)The split-half path is still about 1.5-1.6x faster than #259's wave32 kernel.
rms_adalnandadalnare about 2x faster.Tests on both GPUs (
test_hip_wmma,test_hip_dispatch,test_gemm_bias_contract,test_int8*,test_adaln,test_rms_rope,test_int8_attention,test_sol_attn,test_convrot_unpacked_quantization,test_w4a8_mma,test_w6a8) show the same failures as unmodifiedmain: 18 triton rope cases andtest_int8_linear_correctness[hip].🤖 Generated with Claude Code
🔄 This issue represents a GitHub Pull Request. It cannot be merged through Gitea due to API limitations.