@@ -44,6 +44,29 @@ def test_rotary_transform():
4444 assert torch .equal (comp_rot_expected , comp_rot )
4545
4646
47+ def test_rotary_transform_computes_frequencies_in_fp32_for_bf16_inputs (monkeypatch ):
48+ operand_and_result_dtypes = []
49+ original_einsum = torch .einsum
50+
51+ def recording_einsum (equation , * operands ):
52+ result = original_einsum (equation , * operands )
53+ operand_and_result_dtypes .append ((* [operand .dtype for operand in operands ], result .dtype ))
54+ return result
55+
56+ monkeypatch .setattr (torch , "einsum" , recording_einsum )
57+
58+ rotary_transform = RotaryTransform (n_embd = 128 , n_head = 2 )
59+ q = torch .randn (1 , 2 , 16 , 64 , dtype = torch .bfloat16 )
60+ k = torch .randn_like (q )
61+ v = torch .randn_like (q )
62+
63+ q_rot , k_rot , _ = rotary_transform (q = q , k = k , v = v )
64+
65+ assert operand_and_result_dtypes == [(torch .float32 , torch .float32 , torch .float32 )]
66+ assert q_rot .dtype == torch .bfloat16
67+ assert k_rot .dtype == torch .bfloat16
68+
69+
4770def _apply_rotary (x : torch .Tensor , cos_cached : torch .Tensor , sin_cached : torch .Tensor ) -> torch .Tensor :
4871 cos_local = cos_cached [:, :, : x .shape [- 2 ], :]
4972 sin_local = sin_cached [:, :, : x .shape [- 2 ], :]
@@ -61,7 +84,7 @@ def _assert_yarn_outputs_match_reference(
6184 seq_length : int ,
6285) -> None :
6386 t = torch .arange (seq_length , device = q .device , dtype = torch .float32 )
64- freqs = torch .einsum ("i,j->ij" , t , rotary_transform .inv_freq .to ( q . dtype ))
87+ freqs = torch .einsum ("i,j->ij" , t , rotary_transform .inv_freq .float ( ))
6588 emb = torch .cat ((freqs , freqs ), dim = - 1 )
6689 cos = (emb .cos () * rotary_transform .attention_scaling )[None , None , :, :].to (q .dtype )
6790 sin = (emb .sin () * rotary_transform .attention_scaling )[None , None , :, :].to (q .dtype )
0 commit comments