@@ -155,6 +155,9 @@ def forward(ctx: Any,
155155 cpu_offloading = True ):
156156
157157 do_save = layernorm_output .requires_grad
158+ # The all-to-all partitions by KV group, and only the caller knows that count: the
159+ # gather-direction and backward calls below see an already-sharded head dim.
160+ num_kv_heads = kv_projection_size // hidden_size_per_attention_head
158161
159162 if rotary_pos_emb is not None :
160163 pos_emb_cos , pos_emb_sin = rotary_pos_emb [0 ].permute (1 , 0 , 2 , 3 ), rotary_pos_emb [1 ].permute (1 , 0 , 2 , 3 )
@@ -180,6 +183,7 @@ def forward(ctx: Any,
180183 ctx .dtype = layernorm_output .dtype
181184 ctx .projection_size = projection_size
182185 ctx .kv_projection_size = kv_projection_size
186+ ctx .num_kv_heads = num_kv_heads
183187
184188 global_q = []
185189 global_k = []
@@ -206,7 +210,7 @@ def forward(ctx: Any,
206210 q_chunk = qkv_chunk [:, :, :projection_size ].contiguous ().reshape (
207211 qkv_chunk .shape [0 ], qkv_chunk .shape [1 ], - 1 ,
208212 hidden_size_per_attention_head ).permute (1 , 0 , 2 , 3 ).contiguous () # b, l, nh, hd
209- q_chunk = single_all_to_all (q_chunk , scatter_idx , gather_idx , 0 , spg )
213+ q_chunk = single_all_to_all (q_chunk , scatter_idx , gather_idx , 0 , spg , num_kv_heads = num_kv_heads )
210214 global_q_chunk_len = q_chunk .shape [1 ]
211215 if rotary_pos_emb is not None :
212216 q_chunk = apply_rotary_pos_emb (q_chunk ,
@@ -217,7 +221,7 @@ def forward(ctx: Any,
217221 k_chunk = qkv_chunk [:, :, projection_size :projection_size + kv_projection_size ].contiguous ().reshape (
218222 qkv_chunk .shape [0 ], qkv_chunk .shape [1 ], - 1 ,
219223 hidden_size_per_attention_head ).permute (1 , 0 , 2 , 3 ).contiguous () # b, l, nh, hd
220- k_chunk = single_all_to_all (k_chunk , scatter_idx , gather_idx , 0 , spg )
224+ k_chunk = single_all_to_all (k_chunk , scatter_idx , gather_idx , 0 , spg , num_kv_heads = num_kv_heads )
221225 if rotary_pos_emb is not None :
222226 k_chunk = apply_rotary_pos_emb (k_chunk ,
223227 pos_emb_cos [:, global_q_chunk_len * i :global_q_chunk_len * (i + 1 )],
@@ -227,7 +231,7 @@ def forward(ctx: Any,
227231 v_chunk = qkv_chunk [:, :, projection_size + kv_projection_size :].contiguous ().reshape (
228232 qkv_chunk .shape [0 ], qkv_chunk .shape [1 ], - 1 ,
229233 hidden_size_per_attention_head ).permute (1 , 0 , 2 , 3 ).contiguous () # b, l, nh, hd
230- v_chunk = single_all_to_all (v_chunk , scatter_idx , gather_idx , 0 , spg )
234+ v_chunk = single_all_to_all (v_chunk , scatter_idx , gather_idx , 0 , spg , num_kv_heads = num_kv_heads )
231235 global_v .append (v_chunk )
232236
233237 for k_i in range (len (global_k )):
@@ -276,7 +280,12 @@ def forward(ctx: Any,
276280
277281 for i in range (num_chunks ):
278282 global_lse [i ] = global_lse [i ][:, :, :, 0 ].permute (0 , 2 , 1 ).contiguous ()
279- output [i ] = single_all_to_all (global_o [i ].to (ctx .dtype ).contiguous (), gather_idx , scatter_idx , 0 , spg )
283+ output [i ] = single_all_to_all (global_o [i ].to (ctx .dtype ).contiguous (),
284+ gather_idx ,
285+ scatter_idx ,
286+ 0 ,
287+ spg ,
288+ num_kv_heads = num_kv_heads )
280289 output = torch .cat (output , dim = 1 )
281290
282291 head_dim = output .shape [- 1 ]
@@ -312,6 +321,7 @@ def backward(ctx, grad_output):
312321
313322 projection_size = ctx .projection_size
314323 kv_projection_size = ctx .kv_projection_size
324+ num_kv_heads = ctx .num_kv_heads
315325
316326 layernorm_output = ctx .saved_tensors [0 ]
317327
@@ -338,7 +348,12 @@ def backward(ctx, grad_output):
338348 st = chunk_size * i
339349 ed = st + chunk_size
340350 grad_global_attn_output .append (
341- single_all_to_all (grad_output [:, st :ed ].contiguous (), scatter_idx , gather_idx , 0 , spg ))
351+ single_all_to_all (grad_output [:, st :ed ].contiguous (),
352+ scatter_idx ,
353+ gather_idx ,
354+ 0 ,
355+ spg ,
356+ num_kv_heads = num_kv_heads ))
342357
343358 del grad_output
344359
@@ -440,8 +455,8 @@ def backward(ctx, grad_output):
440455 else :
441456 dk [i ] = dk [i ].to (dtype )
442457 dv [i ] = dv [i ].to (dtype )
443- dk [i ] = single_all_to_all (dk [i ].contiguous (), gather_idx , scatter_idx , 0 , spg )
444- dv [i ] = single_all_to_all (dv [i ].contiguous (), gather_idx , scatter_idx , 0 , spg )
458+ dk [i ] = single_all_to_all (dk [i ].contiguous (), gather_idx , scatter_idx , 0 , spg , num_kv_heads = num_kv_heads )
459+ dv [i ] = single_all_to_all (dv [i ].contiguous (), gather_idx , scatter_idx , 0 , spg , num_kv_heads = num_kv_heads )
445460
446461 input_st = i * input_chunk_size
447462 input_ed = input_st + input_chunk_size
@@ -474,7 +489,12 @@ def backward(ctx, grad_output):
474489 ctx .pos_emb_sin [:, dq_seq_len * i :dq_seq_len * (i + 1 )])
475490 else :
476491 dq [i ] = dq [i ].to (dtype )
477- dq [i ] = single_all_to_all (dq [i ].to (dtype ).contiguous (), gather_idx , scatter_idx , 0 , spg )
492+ dq [i ] = single_all_to_all (dq [i ].to (dtype ).contiguous (),
493+ gather_idx ,
494+ scatter_idx ,
495+ 0 ,
496+ spg ,
497+ num_kv_heads = num_kv_heads )
478498
479499 input_chunk = layernorm_output [:input_chunk_size ].reshape (- 1 , layernorm_output .shape [- 1 ])
480500 layernorm_output = layernorm_output [input_chunk_size :]
@@ -565,6 +585,9 @@ def forward(ctx: Any,
565585 cpu_offloading = True ):
566586
567587 do_save = layernorm_output .requires_grad
588+ # The all-to-all partitions by KV group, and only the caller knows that count: the
589+ # gather-direction and backward calls below see an already-sharded head dim.
590+ num_kv_heads = kv_projection_size // hidden_size_per_attention_head
568591
569592 if rotary_pos_emb is not None :
570593 pos_emb_cos , pos_emb_sin = rotary_pos_emb [0 ].permute (1 , 0 , 2 , 3 ), rotary_pos_emb [1 ].permute (1 , 0 , 2 , 3 )
@@ -590,6 +613,7 @@ def forward(ctx: Any,
590613 ctx .dtype = layernorm_output .dtype
591614 ctx .projection_size = projection_size
592615 ctx .kv_projection_size = kv_projection_size
616+ ctx .num_kv_heads = num_kv_heads
593617
594618 global_q = []
595619 global_k = []
@@ -628,18 +652,18 @@ def forward(ctx: Any,
628652 q_chunk = qkv_chunk [:, :, :projection_size ].contiguous ().reshape (
629653 qkv_chunk .shape [0 ], qkv_chunk .shape [1 ], - 1 ,
630654 hidden_size_per_attention_head ).permute (1 , 0 , 2 , 3 ).contiguous () # b, l, nh, hd
631- q_chunk = single_all_to_all (q_chunk , scatter_idx , gather_idx , 0 , spg )
655+ q_chunk = single_all_to_all (q_chunk , scatter_idx , gather_idx , 0 , spg , num_kv_heads = num_kv_heads )
632656 global_q_chunk_len = q_chunk .shape [1 ]
633657
634658 k_chunk = qkv_chunk [:, :, projection_size :projection_size + kv_projection_size ].contiguous ().reshape (
635659 qkv_chunk .shape [0 ], qkv_chunk .shape [1 ], - 1 ,
636660 hidden_size_per_attention_head ).permute (1 , 0 , 2 , 3 ).contiguous () # b, l, nh, hd
637- k_chunk = single_all_to_all (k_chunk , scatter_idx , gather_idx , 0 , spg )
661+ k_chunk = single_all_to_all (k_chunk , scatter_idx , gather_idx , 0 , spg , num_kv_heads = num_kv_heads )
638662
639663 v_chunk = qkv_chunk [:, :, projection_size + kv_projection_size :].contiguous ().reshape (
640664 qkv_chunk .shape [0 ], qkv_chunk .shape [1 ], - 1 ,
641665 hidden_size_per_attention_head ).permute (1 , 0 , 2 , 3 ).contiguous () # b, l, nh, hd
642- v_chunk = single_all_to_all (v_chunk , scatter_idx , gather_idx , 0 , spg )
666+ v_chunk = single_all_to_all (v_chunk , scatter_idx , gather_idx , 0 , spg , num_kv_heads = num_kv_heads )
643667
644668 dist .barrier ()
645669
@@ -739,8 +763,12 @@ def forward(ctx: Any,
739763 global_q [q_compute_chunk_idx ].offload ()
740764 q_compute_chunk_idx += 1
741765
742- all2all_output = single_all_to_all (
743- cur_attn_output .to (ctx .dtype ).contiguous (), gather_idx , scatter_idx , 0 , spg )
766+ all2all_output = single_all_to_all (cur_attn_output .to (ctx .dtype ).contiguous (),
767+ gather_idx ,
768+ scatter_idx ,
769+ 0 ,
770+ spg ,
771+ num_kv_heads = num_kv_heads )
744772 final_output .append (all2all_output )
745773 with get_accelerator ().stream (general_offload_stream ):
746774 global_o .append (SequenceChunk (cur_attn_output .to (ctx .dtype )))
@@ -783,6 +811,7 @@ def backward(ctx, grad_output):
783811
784812 projection_size = ctx .projection_size
785813 kv_projection_size = ctx .kv_projection_size
814+ num_kv_heads = ctx .num_kv_heads
786815
787816 layernorm_output = ctx .layernorm_output
788817
@@ -821,8 +850,12 @@ def backward(ctx, grad_output):
821850 device = qkv_linear_weight .device ,
822851 dtype = torch .float )
823852
824- grad_global_attn_output_chunk = single_all_to_all (grad_output [:, :chunk_size ].contiguous (), scatter_idx ,
825- gather_idx , 0 , spg )
853+ grad_global_attn_output_chunk = single_all_to_all (grad_output [:, :chunk_size ].contiguous (),
854+ scatter_idx ,
855+ gather_idx ,
856+ 0 ,
857+ spg ,
858+ num_kv_heads = num_kv_heads )
826859 get_accelerator ().synchronize ()
827860 grad_output = grad_output [:, chunk_size :]
828861
@@ -931,7 +964,11 @@ def backward(ctx, grad_output):
931964
932965 if grad_global_attn_output [next_q_compute_chunk_idx ] is None :
933966 grad_global_attn_output_chunk = single_all_to_all (grad_output [:, :chunk_size ].contiguous (),
934- scatter_idx , gather_idx , 0 , spg )
967+ scatter_idx ,
968+ gather_idx ,
969+ 0 ,
970+ spg ,
971+ num_kv_heads = num_kv_heads )
935972 dist .barrier ()
936973 grad_output = grad_output [:, chunk_size :]
937974 grad_global_attn_output [next_q_compute_chunk_idx ] = SequenceChunk (
@@ -976,9 +1013,24 @@ def backward(ctx, grad_output):
9761013 dk_accum = dk_accum .to (dtype )
9771014 dv_accum = dv_accum .to (dtype )
9781015
979- dq_accum = single_all_to_all (dq_accum .contiguous (), gather_idx , scatter_idx , 0 , spg )
980- dk_accum = single_all_to_all (dk_accum .contiguous (), gather_idx , scatter_idx , 0 , spg )
981- dv_accum = single_all_to_all (dv_accum .contiguous (), gather_idx , scatter_idx , 0 , spg )
1016+ dq_accum = single_all_to_all (dq_accum .contiguous (),
1017+ gather_idx ,
1018+ scatter_idx ,
1019+ 0 ,
1020+ spg ,
1021+ num_kv_heads = num_kv_heads )
1022+ dk_accum = single_all_to_all (dk_accum .contiguous (),
1023+ gather_idx ,
1024+ scatter_idx ,
1025+ 0 ,
1026+ spg ,
1027+ num_kv_heads = num_kv_heads )
1028+ dv_accum = single_all_to_all (dv_accum .contiguous (),
1029+ gather_idx ,
1030+ scatter_idx ,
1031+ 0 ,
1032+ spg ,
1033+ num_kv_heads = num_kv_heads )
9821034
9831035 general_offload_stream .synchronize ()
9841036 compute_stream .wait_stream (general_offload_stream )
0 commit comments