nano-rope
nano-vllm/nanovllm/layers/rotary_embedding.py · bb823b3 · L6–50 · 固定 commit 上游
这是固定版本源码的只读摘录;可在线阅读,也可通过上游链接查看原文件。
6def apply_rotary_emb(
7 x: torch.Tensor,
8 cos: torch.Tensor,
9 sin: torch.Tensor,
10) -> torch.Tensor:
11 x1, x2 = torch.chunk(x.float(), 2, dim=-1)
12 y1 = x1 * cos - x2 * sin
13 y2 = x2 * cos + x1 * sin
14 return torch.cat((y1, y2), dim=-1).to(x.dtype)
15
16
17class RotaryEmbedding(nn.Module):
18
19 def __init__(
20 self,
21 head_size: int,
22 rotary_dim: int,
23 max_position_embeddings: int,
24 base: float,
25 ) -> None:
26 super().__init__()
27 self.head_size = head_size
28 assert rotary_dim == head_size
29 inv_freq = 1.0 / (base**(torch.arange(0, rotary_dim, 2, dtype=torch.float) / rotary_dim))
30 t = torch.arange(max_position_embeddings, dtype=torch.float)
31 freqs = torch.einsum("i,j -> ij", t, inv_freq)
32 cos = freqs.cos()
33 sin = freqs.sin()
34 cache = torch.cat((cos, sin), dim=-1).unsqueeze_(1)
35 self.register_buffer("cos_sin_cache", cache, persistent=False)
36
37 @torch.compile
38 def forward(
39 self,
40 positions: torch.Tensor,
41 query: torch.Tensor,
42 key: torch.Tensor,
43 ) -> tuple[torch.Tensor, torch.Tensor]:
44 cos_sin = self.cos_sin_cache[positions]
45 cos, sin = cos_sin.chunk(2, dim=-1)
46 query = apply_rotary_emb(query, cos, sin)
47 key = apply_rotary_emb(key, cos, sin)
48 return query, key
49
50