Naphon commited on
Commit
92907e4
·
verified ·
1 Parent(s): 9f15582

Upload 2 files

Browse files
Files changed (2) hide show
  1. configuration_iii.py +178 -0
  2. modeling_iii.py +2072 -0
configuration_iii.py ADDED
@@ -0,0 +1,178 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ # Licensed to the Apache Software Foundation (ASF) under one
2
+ # or more contributor license agreements. See the NOTICE file
3
+ # distributed with this work for additional information
4
+ # regarding copyright ownership. The ASF licenses this file
5
+ # to you under the Apache License, Version 2.0 (the
6
+ # "License"); you may not use this file except in compliance
7
+ # with the License. You may obtain a copy of the License at
8
+
9
+ # http://www.apache.org/licenses/LICENSE-2.0
10
+
11
+ # Unless required by applicable law or agreed to in writing,
12
+ # software distributed under the License is distributed on an
13
+ # "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
14
+ # KIND, either express or implied. See the License for the
15
+ # specific language governing permissions and limitations
16
+ # under the License.
17
+
18
+
19
+ from transformers.configuration_utils import PretrainedConfig
20
+
21
+
22
+ class IIIConfig(PretrainedConfig):
23
+ model_type = "iii"
24
+ keys_to_ignore_at_inference = ["past_key_values"]
25
+
26
+ def __init__(
27
+ self,
28
+ vocab_size=30000,
29
+ hidden_dim=2048,
30
+ lora_dim=512,
31
+ intermediate_dim=5120,
32
+ n_layers=40,
33
+ n_heads=16,
34
+ max_position_embedding=100000,
35
+ rms_norm_eps=1e-6,
36
+ use_cache=True,
37
+ pad_token_id=None,
38
+ bos_token_id=0,
39
+ eos_token_id=1,
40
+ tie_word_embedding=False,
41
+ rope_theta=10000.0,
42
+ rope_scaling=None,
43
+ attention_bias=False,
44
+ layer_window_sizes=(
45
+ 3, 5, 7, 11, 0,
46
+ 3, 5, 7, 11, 0,
47
+ 3, 5, 7, 11, 0,
48
+ 3, 5, 7, 11, 0,
49
+ 3, 5, 7, 11, 0,
50
+ 3, 5, 7, 11, 0,
51
+ 3, 5, 7, 11, 0,
52
+ 3, 5, 7, 11, 0,
53
+ ),
54
+ layer_dilation_size=(
55
+ 1, 3, 5, 7, 0,
56
+ 1, 3, 5, 7, 0,
57
+ 1, 3, 5, 7, 0,
58
+ 1, 3, 5, 7, 0,
59
+ 1, 3, 5, 7, 0,
60
+ 1, 3, 5, 7, 0,
61
+ 1, 3, 5, 7, 0,
62
+ 1, 3, 5, 7, 0,
63
+ ),
64
+ **kwargs,
65
+ ):
66
+ self.vocab_size = vocab_size
67
+ self.hidden_dim = hidden_dim
68
+ self.lora_dim = lora_dim
69
+ self.intermediate_dim = intermediate_dim
70
+
71
+ self.n_layers = n_layers
72
+ self.n_heads = n_heads
73
+
74
+ self.max_position_embedding = (
75
+ max_position_embedding
76
+ )
77
+
78
+ self.rms_norm_eps = rms_norm_eps
79
+ self.use_cache = use_cache
80
+
81
+ self.pad_token_id = pad_token_id
82
+ self.bos_token_id = bos_token_id
83
+ self.eos_token_id = eos_token_id
84
+
85
+ self.tie_word_embedding = tie_word_embedding
86
+
87
+ self.rope_theta = rope_theta
88
+ self.rope_scaling = rope_scaling
89
+
90
+ self.attention_bias = attention_bias
91
+
92
+ self.layer_window_sizes = tuple(
93
+ layer_window_sizes
94
+ )
95
+ self.num_hidden_layers = self.n_layers
96
+ self.hidden_size = self.hidden_dim
97
+ self.num_attention_heads = self.n_heads
98
+
99
+ self.layer_dilation_size = tuple(
100
+ layer_dilation_size
101
+ )
102
+
103
+ # ----------------------------------------------------
104
+ # Validation
105
+ # ----------------------------------------------------
106
+
107
+ if hidden_dim <= 0:
108
+ raise ValueError(
109
+ "hidden_dim must be > 0."
110
+ )
111
+
112
+ if lora_dim <= 0:
113
+ raise ValueError(
114
+ "lora_dim must be > 0."
115
+ )
116
+
117
+ if lora_dim % n_heads != 0:
118
+ raise ValueError(
119
+ f"lora_dim ({lora_dim}) must be divisible "
120
+ f"by n_heads ({n_heads})."
121
+ )
122
+
123
+ if len(self.layer_window_sizes) != n_layers:
124
+ raise ValueError(
125
+ "layer_window_sizes must contain exactly "
126
+ f"{n_layers} entries, got "
127
+ f"{len(self.layer_window_sizes)}."
128
+ )
129
+
130
+ if len(self.layer_dilation_size) != n_layers:
131
+ raise ValueError(
132
+ "layer_dilation_size must contain exactly "
133
+ f"{n_layers} entries, got "
134
+ f"{len(self.layer_dilation_size)}."
135
+ )
136
+
137
+ for layer_id, (
138
+ window,
139
+ dilation,
140
+ ) in enumerate(
141
+ zip(
142
+ self.layer_window_sizes,
143
+ self.layer_dilation_size,
144
+ )
145
+ ):
146
+ if window == 0:
147
+ if dilation != 0:
148
+ raise ValueError(
149
+ f"Layer {layer_id} is attention "
150
+ "but has non-zero dilation."
151
+ )
152
+ else:
153
+ if window < 1:
154
+ raise ValueError(
155
+ f"Layer {layer_id}: "
156
+ "CNN window must be >= 1."
157
+ )
158
+
159
+ if dilation < 1:
160
+ raise ValueError(
161
+ f"Layer {layer_id}: "
162
+ "CNN dilation must be >= 1."
163
+ )
164
+
165
+ if not any(
166
+ window == 0
167
+ for window in self.layer_window_sizes
168
+ ):
169
+ raise ValueError(
170
+ "III requires at least one attention layer."
171
+ )
172
+
173
+ super().__init__(
174
+ pad_token_id=pad_token_id,
175
+ bos_token_id=bos_token_id,
176
+ eos_token_id=eos_token_id,
177
+ **kwargs,
178
+ )
modeling_iii.py ADDED
@@ -0,0 +1,2072 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ # Licensed to the Apache Software Foundation (ASF) under one
2
+ # or more contributor license agreements. See the NOTICE file
3
+ # distributed with this work for additional information
4
+ # regarding copyright ownership. The ASF licenses this file
5
+ # to you under the Apache License, Version 2.0 (the
6
+ # "License"); you may not use this file except in compliance
7
+ # with the License. You may obtain a copy of the License at
8
+
9
+ # http://www.apache.org/licenses/LICENSE-2.0
10
+
11
+ # Unless required by applicable law or agreed to in writing,
12
+ # software distributed under the License is distributed on an
13
+ # "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
14
+ # KIND, either express or implied. See the License for the
15
+ # specific language governing permissions and limitations
16
+ # under the License.
17
+
18
+
19
+ from typing import Optional
20
+
21
+ import torch
22
+ import torch.nn.functional as F
23
+
24
+ from torch import Tensor
25
+
26
+ from torch.nn import (
27
+ Module,
28
+ Parameter,
29
+ Linear,
30
+ SiLU,
31
+ Conv1d,
32
+ Embedding,
33
+ )
34
+
35
+ from transformers.cache_utils import (
36
+ Cache,
37
+ DynamicCache,
38
+ )
39
+
40
+ from transformers.modeling_outputs import (
41
+ BaseModelOutputWithPast,
42
+ CausalLMOutputWithPast,
43
+ )
44
+
45
+ from transformers.modeling_utils import (
46
+ PreTrainedModel,
47
+ )
48
+
49
+ from transformers.generation import GenerationMixin
50
+
51
+ from transformers.pytorch_utils import (
52
+ ALL_LAYERNORM_LAYERS,
53
+ )
54
+
55
+ from .configuration_iii import IIIConfig
56
+
57
+
58
+ _CONFIG_FOR_DOC = "IIIConfig"
59
+
60
+
61
+ # ============================================================
62
+ # RMSNorm
63
+ # ============================================================
64
+
65
+ class IIIRMSNorm(Module):
66
+ def __init__(
67
+ self,
68
+ dim,
69
+ eps=1e-6,
70
+ ):
71
+ super().__init__()
72
+
73
+ self.weight = Parameter(
74
+ torch.ones(dim)
75
+ )
76
+
77
+ self.epsilon = eps
78
+
79
+ def forward(
80
+ self,
81
+ tensor,
82
+ ):
83
+ input_dtype = tensor.dtype
84
+
85
+ tensor = tensor.to(
86
+ torch.float32
87
+ )
88
+
89
+ variance = tensor.pow(2).mean(
90
+ -1,
91
+ keepdim=True,
92
+ )
93
+
94
+ tensor = tensor * torch.rsqrt(
95
+ variance + self.epsilon
96
+ )
97
+
98
+ return (
99
+ self.weight
100
+ * tensor.to(input_dtype)
101
+ )
102
+
103
+
104
+ ALL_LAYERNORM_LAYERS.append(
105
+ IIIRMSNorm
106
+ )
107
+
108
+
109
+ # ============================================================
110
+ # RoPE
111
+ # ============================================================
112
+
113
+ class IIIRoPE(Module):
114
+ def __init__(
115
+ self,
116
+ dim,
117
+ max_position_embeddings=100000,
118
+ theta=10000.0,
119
+ device=None,
120
+ ):
121
+ super().__init__()
122
+
123
+ self.dim = dim
124
+ self.max_position_embeddings = (
125
+ max_position_embeddings
126
+ )
127
+ self.theta = theta
128
+
129
+ inv_freq = 1.0 / (
130
+ theta
131
+ ** (
132
+ torch.arange(
133
+ 0,
134
+ dim,
135
+ 2,
136
+ device=device,
137
+ dtype=torch.float32,
138
+ )
139
+ / dim
140
+ )
141
+ )
142
+
143
+ self.register_buffer(
144
+ "inv_freq",
145
+ inv_freq,
146
+ persistent=False,
147
+ )
148
+
149
+ self.max_seq_len_cached = 0
150
+
151
+ self._set_cos_sin_cache(
152
+ seq_len=max_position_embeddings,
153
+ device=self.inv_freq.device,
154
+ dtype=torch.get_default_dtype(),
155
+ )
156
+
157
+ def _set_cos_sin_cache(
158
+ self,
159
+ seq_len,
160
+ device,
161
+ dtype,
162
+ ):
163
+ self.max_seq_len_cached = seq_len
164
+
165
+ t = torch.arange(
166
+ seq_len,
167
+ device=device,
168
+ dtype=self.inv_freq.dtype,
169
+ )
170
+
171
+ freqs = torch.outer(
172
+ t,
173
+ self.inv_freq.to(t.device),
174
+ )
175
+
176
+ # Half-split RoPE:
177
+ #
178
+ # [f0 f1 ... fn f0 f1 ... fn]
179
+ #
180
+ # This matches rotate_half().
181
+ emb = torch.cat(
182
+ (
183
+ freqs,
184
+ freqs,
185
+ ),
186
+ dim=-1,
187
+ )
188
+
189
+ self.register_buffer(
190
+ "cos_cached",
191
+ emb.cos().to(dtype),
192
+ persistent=False,
193
+ )
194
+
195
+ self.register_buffer(
196
+ "sin_cached",
197
+ emb.sin().to(dtype),
198
+ persistent=False,
199
+ )
200
+
201
+ def forward(
202
+ self,
203
+ x,
204
+ seq_len=None,
205
+ ):
206
+ if seq_len is None:
207
+ seq_len = x.shape[-2]
208
+
209
+ if (
210
+ seq_len
211
+ > self.max_seq_len_cached
212
+ ):
213
+ self._set_cos_sin_cache(
214
+ seq_len=seq_len,
215
+ device=x.device,
216
+ dtype=x.dtype,
217
+ )
218
+
219
+ return (
220
+ self.cos_cached[
221
+ :seq_len
222
+ ].to(
223
+ device=x.device,
224
+ dtype=x.dtype,
225
+ ),
226
+ self.sin_cached[
227
+ :seq_len
228
+ ].to(
229
+ device=x.device,
230
+ dtype=x.dtype,
231
+ ),
232
+ )
233
+
234
+
235
+ def rotate_half(x):
236
+ x1 = x[
237
+ ...,
238
+ : x.shape[-1] // 2,
239
+ ]
240
+
241
+ x2 = x[
242
+ ...,
243
+ x.shape[-1] // 2 :,
244
+ ]
245
+
246
+ return torch.cat(
247
+ (
248
+ -x2,
249
+ x1,
250
+ ),
251
+ dim=-1,
252
+ )
253
+
254
+
255
+ def apply_rotary_pos_emb(
256
+ q,
257
+ k,
258
+ cos,
259
+ sin,
260
+ position_ids,
261
+ unsqueeze_dim=1,
262
+ ):
263
+ cos = cos[
264
+ position_ids
265
+ ].unsqueeze(
266
+ unsqueeze_dim
267
+ )
268
+
269
+ sin = sin[
270
+ position_ids
271
+ ].unsqueeze(
272
+ unsqueeze_dim
273
+ )
274
+
275
+ q_embed = (
276
+ q * cos
277
+ + rotate_half(q) * sin
278
+ )
279
+
280
+ k_embed = (
281
+ k * cos
282
+ + rotate_half(k) * sin
283
+ )
284
+
285
+ return q_embed, k_embed
286
+
287
+
288
+ # ============================================================
289
+ # SwiGLU-style MLP
290
+ # ============================================================
291
+
292
+ class IIIMLP(Module):
293
+ def __init__(
294
+ self,
295
+ config,
296
+ dim=None,
297
+ intermediate_dim=None,
298
+ ):
299
+ super().__init__()
300
+
301
+ self.config = config
302
+
303
+ self.dim = (
304
+ config.hidden_dim
305
+ if dim is None
306
+ else dim
307
+ )
308
+
309
+ self.intermediate_dim = (
310
+ config.intermediate_dim
311
+ if intermediate_dim is None
312
+ else intermediate_dim
313
+ )
314
+
315
+ self.gate = Linear(
316
+ self.dim,
317
+ self.intermediate_dim,
318
+ bias=False,
319
+ )
320
+
321
+ self.up = Linear(
322
+ self.dim,
323
+ self.intermediate_dim,
324
+ bias=False,
325
+ )
326
+
327
+ self.down = Linear(
328
+ self.intermediate_dim,
329
+ self.dim,
330
+ bias=False,
331
+ )
332
+
333
+ self.activation = SiLU()
334
+
335
+ def forward(self, x):
336
+ value = self.up(x)
337
+
338
+ gate = self.activation(
339
+ self.gate(x)
340
+ )
341
+
342
+ return self.down(
343
+ gate * value
344
+ )
345
+
346
+
347
+ # ============================================================
348
+ # Attention
349
+ # ============================================================
350
+
351
+ class IIIAttention(Module):
352
+ def __init__(
353
+ self,
354
+ config,
355
+ layer_id=None,
356
+ ):
357
+ super().__init__()
358
+
359
+ self.config = config
360
+ self.layer_id = layer_id
361
+
362
+ self.hidden_dim = config.hidden_dim
363
+ self.lora_dim = config.lora_dim
364
+ self.num_heads = config.n_heads
365
+
366
+ if self.lora_dim % self.num_heads != 0:
367
+ raise ValueError(
368
+ f"lora_dim ({self.lora_dim}) "
369
+ f"must be divisible by "
370
+ f"n_heads ({self.num_heads})."
371
+ )
372
+
373
+ self.head_dim = self.lora_dim // self.num_heads
374
+
375
+ # ----------------------------------------------------
376
+ # QKV
377
+ # ----------------------------------------------------
378
+
379
+ self.qkv = Linear(
380
+ self.hidden_dim,
381
+ self.lora_dim * 3,
382
+ bias=config.attention_bias,
383
+ )
384
+
385
+ self.o = Linear(
386
+ self.lora_dim,
387
+ self.hidden_dim,
388
+ bias=config.attention_bias,
389
+ )
390
+
391
+ # ----------------------------------------------------
392
+ # Q/K normalization
393
+ # ----------------------------------------------------
394
+
395
+ self.q_norm = IIIRMSNorm(
396
+ self.head_dim,
397
+ eps=config.rms_norm_eps,
398
+ )
399
+
400
+ self.k_norm = IIIRMSNorm(
401
+ self.head_dim,
402
+ eps=config.rms_norm_eps,
403
+ )
404
+
405
+ # ----------------------------------------------------
406
+ # RoPE
407
+ # ----------------------------------------------------
408
+
409
+ self.rotary_emb = IIIRoPE(
410
+ dim=self.head_dim,
411
+ max_position_embeddings=config.max_position_embedding,
412
+ theta=config.rope_theta,
413
+ )
414
+
415
+ # ============================================================
416
+ # Causal mask
417
+ # ============================================================
418
+
419
+ def _make_causal_mask(
420
+ self,
421
+ q_len,
422
+ kv_len,
423
+ device,
424
+ ):
425
+ """
426
+ Returns a boolean causal mask of shape:
427
+
428
+ [1, 1, q_len, kv_len]
429
+
430
+ True = attention is allowed
431
+ False = attention is blocked
432
+
433
+ Works for both:
434
+
435
+ 1. Full sequence
436
+ q_len = kv_len = S
437
+
438
+ 2. KV-cache decoding
439
+ q_len < kv_len
440
+
441
+ Example:
442
+ q_len=1, kv_len=5
443
+
444
+ [1 1 1 1 1]
445
+
446
+ Example:
447
+ q_len=2, kv_len=5
448
+
449
+ [1 1 1 1 0]
450
+ [1 1 1 1 1]
451
+ """
452
+
453
+ q_positions = torch.arange(
454
+ kv_len - q_len,
455
+ kv_len,
456
+ device=device,
457
+ )
458
+
459
+ k_positions = torch.arange(
460
+ kv_len,
461
+ device=device,
462
+ )
463
+
464
+ causal = (
465
+ k_positions.unsqueeze(0)
466
+ <= q_positions.unsqueeze(1)
467
+ )
468
+
469
+ return causal.unsqueeze(0).unsqueeze(0)
470
+
471
+ # ============================================================
472
+ # Prepare user attention mask
473
+ # ============================================================
474
+
475
+ def _prepare_attention_mask(
476
+ self,
477
+ attention_mask,
478
+ device,
479
+ ):
480
+ """
481
+ Converts attention_mask into an attention-compatible shape.
482
+
483
+ Supported input shapes:
484
+
485
+ [B, KV]
486
+ [B, Q, KV]
487
+ [B, 1, Q, KV]
488
+
489
+ Boolean masks:
490
+ True = allowed
491
+ False = blocked
492
+
493
+ Integer masks:
494
+ 1 = allowed
495
+ 0 = blocked
496
+
497
+ Float masks:
498
+ treated as additive attention bias.
499
+ """
500
+
501
+ if attention_mask is None:
502
+ return None
503
+
504
+ # --------------------------------------------------------
505
+ # [B, KV]
506
+ # --------------------------------------------------------
507
+
508
+ if attention_mask.dim() == 2:
509
+ if attention_mask.dtype == torch.bool:
510
+ return attention_mask[
511
+ :, None, None, :
512
+ ].to(device)
513
+
514
+ # Integer 0/1 attention masks
515
+ if not torch.is_floating_point(attention_mask):
516
+ return (
517
+ attention_mask != 0
518
+ )[:, None, None, :].to(device)
519
+
520
+ # Float mask.
521
+ # Hugging Face commonly uses 0 for valid tokens
522
+ # and a large negative value for masked tokens.
523
+ return attention_mask[
524
+ :, None, None, :
525
+ ].to(device)
526
+
527
+ # --------------------------------------------------------
528
+ # [B, Q, KV]
529
+ # --------------------------------------------------------
530
+
531
+ if attention_mask.dim() == 3:
532
+ return attention_mask[
533
+ :, None, :, :
534
+ ].to(device)
535
+
536
+ # --------------------------------------------------------
537
+ # [B, 1, Q, KV]
538
+ # --------------------------------------------------------
539
+
540
+ if attention_mask.dim() == 4:
541
+ return attention_mask.to(device)
542
+
543
+ raise ValueError(
544
+ "attention_mask must be "
545
+ "2D, 3D, or 4D."
546
+ )
547
+
548
+ # ============================================================
549
+ # Combine causal + attention mask
550
+ # ============================================================
551
+
552
+ def _combine_masks(
553
+ self,
554
+ attention_mask,
555
+ q_len,
556
+ kv_len,
557
+ device,
558
+ dtype,
559
+ ):
560
+ """
561
+ Combines the user's attention/padding mask with the
562
+ causal mask.
563
+
564
+ This is the important part.
565
+
566
+ We NEVER allow an attention_mask to replace causality.
567
+
568
+ Returns:
569
+ bool mask OR additive float mask
570
+
571
+ suitable for SDPA with is_causal=False.
572
+ """
573
+
574
+ causal_mask = self._make_causal_mask(
575
+ q_len=q_len,
576
+ kv_len=kv_len,
577
+ device=device,
578
+ )
579
+
580
+ # --------------------------------------------------------
581
+ # No user mask
582
+ # --------------------------------------------------------
583
+
584
+ if attention_mask is None:
585
+ return causal_mask
586
+
587
+ mask = self._prepare_attention_mask(
588
+ attention_mask,
589
+ device,
590
+ )
591
+
592
+ # --------------------------------------------------------
593
+ # Boolean mask
594
+ # --------------------------------------------------------
595
+
596
+ if mask.dtype == torch.bool:
597
+ return mask & causal_mask
598
+
599
+ # --------------------------------------------------------
600
+ # Integer mask
601
+ # --------------------------------------------------------
602
+
603
+ if not torch.is_floating_point(mask):
604
+ mask = mask != 0
605
+ return mask & causal_mask
606
+
607
+ # --------------------------------------------------------
608
+ # Additive float mask
609
+ #
610
+ # Typical form:
611
+ #
612
+ # valid -> 0
613
+ # masked -> -inf / large negative
614
+ #
615
+ # We impose causality by setting all future positions
616
+ # to the minimum representable value.
617
+ # --------------------------------------------------------
618
+
619
+ min_value = torch.finfo(dtype).min
620
+
621
+ # Convert causal mask to additive form.
622
+ causal_bias = torch.zeros(
623
+ (1, 1, q_len, kv_len),
624
+ dtype=dtype,
625
+ device=device,
626
+ )
627
+
628
+ causal_bias = causal_bias.masked_fill(
629
+ ~causal_mask,
630
+ min_value,
631
+ )
632
+
633
+ # Make sure the supplied mask has the correct dtype.
634
+ mask = mask.to(dtype)
635
+
636
+ return mask + causal_bias
637
+
638
+ # ============================================================
639
+ # Forward
640
+ # ============================================================
641
+
642
+ def forward(
643
+ self,
644
+ hidden_states,
645
+ attention_mask=None,
646
+ position_ids=None,
647
+ kv_cache: Optional[Cache] = None,
648
+ use_cache=False,
649
+ output_attentions=False,
650
+ ):
651
+ batch_size, seq_len, _ = hidden_states.shape
652
+
653
+ # --------------------------------------------------------
654
+ # Validate cache usage
655
+ # --------------------------------------------------------
656
+
657
+ if (
658
+ use_cache
659
+ and kv_cache is not None
660
+ and self.layer_id is None
661
+ ):
662
+ raise ValueError(
663
+ "layer_id must be set when "
664
+ "using KV cache."
665
+ )
666
+
667
+ # --------------------------------------------------------
668
+ # QKV
669
+ # --------------------------------------------------------
670
+
671
+ qkv = self.qkv(hidden_states)
672
+
673
+ q, k, v = qkv.chunk(
674
+ 3,
675
+ dim=-1,
676
+ )
677
+
678
+ # --------------------------------------------------------
679
+ # Heads
680
+ # --------------------------------------------------------
681
+
682
+ q = q.view(
683
+ batch_size,
684
+ seq_len,
685
+ self.num_heads,
686
+ self.head_dim,
687
+ ).transpose(1, 2)
688
+
689
+ k = k.view(
690
+ batch_size,
691
+ seq_len,
692
+ self.num_heads,
693
+ self.head_dim,
694
+ ).transpose(1, 2)
695
+
696
+ v = v.view(
697
+ batch_size,
698
+ seq_len,
699
+ self.num_heads,
700
+ self.head_dim,
701
+ ).transpose(1, 2)
702
+
703
+ # --------------------------------------------------------
704
+ # Q/K RMSNorm
705
+ # --------------------------------------------------------
706
+
707
+ q = self.q_norm(q)
708
+ k = self.k_norm(k)
709
+
710
+ # --------------------------------------------------------
711
+ # Cache length
712
+ # --------------------------------------------------------
713
+
714
+ if (
715
+ kv_cache is not None
716
+ and kv_cache.get_seq_length(
717
+ self.layer_id
718
+ ) > 0
719
+ ):
720
+ past_len = kv_cache.get_seq_length(
721
+ self.layer_id
722
+ )
723
+ else:
724
+ past_len = 0
725
+
726
+ # --------------------------------------------------------
727
+ # Position IDs
728
+ # --------------------------------------------------------
729
+
730
+ if position_ids is None:
731
+ position_ids = torch.arange(
732
+ past_len,
733
+ past_len + seq_len,
734
+ device=hidden_states.device,
735
+ )
736
+
737
+ position_ids = (
738
+ position_ids
739
+ .unsqueeze(0)
740
+ .expand(
741
+ batch_size,
742
+ -1,
743
+ )
744
+ )
745
+
746
+ max_position = (
747
+ int(position_ids.max().item())
748
+ + 1
749
+ )
750
+
751
+ # --------------------------------------------------------
752
+ # RoPE
753
+ # --------------------------------------------------------
754
+
755
+ cos, sin = self.rotary_emb(
756
+ q,
757
+ seq_len=max_position,
758
+ )
759
+
760
+ q, k = apply_rotary_pos_emb(
761
+ q,
762
+ k,
763
+ cos,
764
+ sin,
765
+ position_ids,
766
+ )
767
+
768
+ # --------------------------------------------------------
769
+ # Update KV cache
770
+ # --------------------------------------------------------
771
+
772
+ if (
773
+ use_cache
774
+ and kv_cache is not None
775
+ ):
776
+ k, v = kv_cache.update(
777
+ k,
778
+ v,
779
+ self.layer_id,
780
+ )
781
+
782
+ # --------------------------------------------------------
783
+ # Actual attention sizes
784
+ # --------------------------------------------------------
785
+
786
+ kv_len = k.shape[-2]
787
+ q_len = q.shape[-2]
788
+
789
+ # ========================================================
790
+ # Build combined mask
791
+ # ========================================================
792
+
793
+ mask = self._combine_masks(
794
+ attention_mask=attention_mask,
795
+ q_len=q_len,
796
+ kv_len=kv_len,
797
+ device=hidden_states.device,
798
+ dtype=q.dtype,
799
+ )
800
+
801
+ # We explicitly constructed the causal mask above,
802
+ # so don't also ask SDPA to construct another one.
803
+ #
804
+ # This is also necessary because SDPA does not allow
805
+ # simultaneously supplying an attn_mask and is_causal=True.
806
+ is_causal = False
807
+
808
+ # ========================================================
809
+ # Attention
810
+ # ========================================================
811
+
812
+ attention_weights = None
813
+
814
+ # --------------------------------------------------------
815
+ # Debug / visualization path
816
+ # --------------------------------------------------------
817
+
818
+ if output_attentions:
819
+ scale = self.head_dim ** -0.5
820
+
821
+ scores = torch.matmul(
822
+ q,
823
+ k.transpose(-2, -1),
824
+ ) * scale
825
+
826
+ # ----------------------------------------------------
827
+ # Boolean mask
828
+ # ----------------------------------------------------
829
+
830
+ if mask.dtype == torch.bool:
831
+ scores = scores.masked_fill(
832
+ ~mask,
833
+ torch.finfo(
834
+ scores.dtype
835
+ ).min,
836
+ )
837
+
838
+ # ----------------------------------------------------
839
+ # Additive mask
840
+ # ----------------------------------------------------
841
+
842
+ else:
843
+ scores = scores + mask.to(
844
+ scores.dtype
845
+ )
846
+
847
+ attention_weights = torch.softmax(
848
+ scores,
849
+ dim=-1,
850
+ )
851
+
852
+ attn_output = torch.matmul(
853
+ attention_weights,
854
+ v,
855
+ )
856
+
857
+ # --------------------------------------------------------
858
+ # SDPA path
859
+ # --------------------------------------------------------
860
+
861
+ else:
862
+ attn_output = (
863
+ F.scaled_dot_product_attention(
864
+ q,
865
+ k,
866
+ v,
867
+ attn_mask=mask,
868
+ dropout_p=0.0,
869
+ is_causal=is_causal,
870
+ )
871
+ )
872
+
873
+ # ========================================================
874
+ # Merge heads
875
+ # ========================================================
876
+
877
+ attn_output = (
878
+ attn_output
879
+ .transpose(1, 2)
880
+ .contiguous()
881
+ .view(
882
+ batch_size,
883
+ seq_len,
884
+ self.lora_dim,
885
+ )
886
+ )
887
+
888
+ # ========================================================
889
+ # Output
890
+ # ========================================================
891
+
892
+ attn_output = self.o(
893
+ attn_output
894
+ )
895
+
896
+ return (
897
+ attn_output,
898
+ kv_cache,
899
+ attention_weights,
900
+ )
901
+
902
+
903
+ # ============================================================
904
+ # Gated Causal CNN
905
+ # ============================================================
906
+
907
+ class GatedCausalCNN(Module):
908
+ """
909
+ Gated causal dilated CNN.
910
+
911
+ value = W_v(x)
912
+
913
+ score = W_s(x)
914
+
915
+ gated = value * sigmoid(score)
916
+
917
+ output = CausalConv1D(gated)
918
+
919
+ No RoPE is applied here.
920
+
921
+ The convolution itself encodes relative local position
922
+ through its kernel offsets and dilation.
923
+ """
924
+
925
+ def __init__(
926
+ self,
927
+ config,
928
+ layer_id,
929
+ ):
930
+ super().__init__()
931
+
932
+ self.config = config
933
+ self.layer_id = layer_id
934
+
935
+ self.hidden_dim = (
936
+ config.hidden_dim
937
+ )
938
+
939
+ self.window_size = (
940
+ config.layer_window_sizes[
941
+ layer_id
942
+ ]
943
+ )
944
+
945
+ self.dilation = (
946
+ config.layer_dilation_size[
947
+ layer_id
948
+ ]
949
+ )
950
+
951
+ if self.window_size <= 0:
952
+ raise ValueError(
953
+ "GatedCausalCNN requires "
954
+ "window_size > 0."
955
+ )
956
+
957
+ if self.dilation <= 0:
958
+ raise ValueError(
959
+ "GatedCausalCNN requires "
960
+ "dilation > 0."
961
+ )
962
+
963
+ # Receptive field:
964
+ #
965
+ # 1 + (kernel_size - 1) * dilation
966
+ #
967
+ self.receptive_field = (
968
+ 1
969
+ + (
970
+ self.window_size - 1
971
+ ) * self.dilation
972
+ )
973
+
974
+ # ----------------------------------------------------
975
+ # Gated projection
976
+ #
977
+ # One projection gives us:
978
+ #
979
+ # [value | score]
980
+ # ----------------------------------------------------
981
+
982
+ self.gate_proj = Linear(
983
+ self.hidden_dim,
984
+ self.hidden_dim * 2,
985
+ bias=False,
986
+ )
987
+
988
+ # ----------------------------------------------------
989
+ # Depthwise causal convolution
990
+ # ----------------------------------------------------
991
+
992
+ self.conv = Conv1d(
993
+ in_channels=self.hidden_dim,
994
+ out_channels=self.hidden_dim,
995
+ kernel_size=self.window_size,
996
+ dilation=self.dilation,
997
+ groups=self.hidden_dim,
998
+ bias=config.attention_bias,
999
+ )
1000
+
1001
+ # ----------------------------------------------------
1002
+ # Output projection
1003
+ # ----------------------------------------------------
1004
+
1005
+ self.out_proj = Linear(
1006
+ self.hidden_dim,
1007
+ self.hidden_dim,
1008
+ bias=config.attention_bias,
1009
+ )
1010
+
1011
+ def _gate(
1012
+ self,
1013
+ hidden_states,
1014
+ ):
1015
+ """
1016
+ hidden_states:
1017
+ [B, S, D]
1018
+
1019
+ returns:
1020
+ [B, S, D]
1021
+ """
1022
+
1023
+ value, score = self.gate_proj(
1024
+ hidden_states
1025
+ ).chunk(
1026
+ 2,
1027
+ dim=-1,
1028
+ )
1029
+
1030
+ return (
1031
+ value
1032
+ * torch.sigmoid(score)
1033
+ )
1034
+
1035
+ def _causal_conv(
1036
+ self,
1037
+ x,
1038
+ ):
1039
+ """
1040
+ x:
1041
+ [B, S, D]
1042
+
1043
+ Returns:
1044
+ [B, S, D]
1045
+ """
1046
+
1047
+ left_padding = (
1048
+ self.receptive_field - 1
1049
+ )
1050
+
1051
+ # [B, S, D]
1052
+ # ↓
1053
+ # [B, D, S]
1054
+ x = x.transpose(
1055
+ 1,
1056
+ 2,
1057
+ )
1058
+
1059
+ x = F.pad(
1060
+ x,
1061
+ (
1062
+ left_padding,
1063
+ 0,
1064
+ ),
1065
+ )
1066
+
1067
+ x = self.conv(x)
1068
+
1069
+ # [B, D, S]
1070
+ # ↓
1071
+ # [B, S, D]
1072
+ return x.transpose(
1073
+ 1,
1074
+ 2,
1075
+ )
1076
+
1077
+ def forward(
1078
+ self,
1079
+ hidden_states,
1080
+ kv_cache: Optional[Cache] = None,
1081
+ use_cache=False,
1082
+ ):
1083
+ batch_size, seq_len, _ = (
1084
+ hidden_states.shape
1085
+ )
1086
+
1087
+ # ====================================================
1088
+ # No cache
1089
+ # ====================================================
1090
+
1091
+ if (
1092
+ not use_cache
1093
+ or kv_cache is None
1094
+ ):
1095
+ gated = self._gate(
1096
+ hidden_states
1097
+ )
1098
+
1099
+ out = self._causal_conv(
1100
+ gated
1101
+ )
1102
+
1103
+ out = self.out_proj(out)
1104
+
1105
+ return (
1106
+ out,
1107
+ kv_cache,
1108
+ )
1109
+
1110
+ # ====================================================
1111
+ # Cache
1112
+ # ====================================================
1113
+
1114
+ if self.layer_id is None:
1115
+ raise ValueError(
1116
+ "layer_id must be set when "
1117
+ "using a cache."
1118
+ )
1119
+
1120
+ past_len = (
1121
+ kv_cache.get_seq_length(
1122
+ self.layer_id
1123
+ )
1124
+ )
1125
+
1126
+ # ----------------------------------------------------
1127
+ # Retrieve cached raw hidden states
1128
+ #
1129
+ # CNN caches store:
1130
+ #
1131
+ # [B, 1, S, D]
1132
+ #
1133
+ # in the key slot.
1134
+ # ----------------------------------------------------
1135
+
1136
+ if past_len > 0:
1137
+ layer_cache = (
1138
+ kv_cache.layers[
1139
+ self.layer_id
1140
+ ]
1141
+ )
1142
+
1143
+ past_states = (
1144
+ layer_cache.keys[:, 0]
1145
+ )
1146
+
1147
+ # We only need the actual receptive
1148
+ # field before the new token(s).
1149
+ history_len = (
1150
+ self.receptive_field - 1
1151
+ )
1152
+
1153
+ past_states = (
1154
+ past_states[
1155
+ :, -history_len:, :
1156
+ ]
1157
+ )
1158
+
1159
+ else:
1160
+ past_states = (
1161
+ hidden_states[:, :0, :]
1162
+ )
1163
+
1164
+ # ----------------------------------------------------
1165
+ # Concatenate history + new states
1166
+ # ----------------------------------------------------
1167
+
1168
+ states = torch.cat(
1169
+ (
1170
+ past_states,
1171
+ hidden_states,
1172
+ ),
1173
+ dim=1,
1174
+ )
1175
+
1176
+ # ----------------------------------------------------
1177
+ # GATE FIRST
1178
+ # ----------------------------------------------------
1179
+
1180
+ gated = self._gate(
1181
+ states
1182
+ )
1183
+
1184
+ # ----------------------------------------------------
1185
+ # THEN CONV1D
1186
+ # ----------------------------------------------------
1187
+
1188
+ out = self._causal_conv(
1189
+ gated
1190
+ )
1191
+
1192
+ # Only return the outputs belonging
1193
+ # to the newly supplied tokens.
1194
+ out = out[
1195
+ :,
1196
+ -seq_len:,
1197
+ :,
1198
+ ]
1199
+
1200
+ out = self.out_proj(out)
1201
+
1202
+ # ----------------------------------------------------
1203
+ # Cache RAW hidden states
1204
+ #
1205
+ # Do not cache the gated representation.
1206
+ #
1207
+ # The next token needs:
1208
+ #
1209
+ # value(history) *
1210
+ # sigmoid(score(history))
1211
+ #
1212
+ # before convolution.
1213
+ # ----------------------------------------------------
1214
+
1215
+ cache_keys = (
1216
+ hidden_states.unsqueeze(1)
1217
+ )
1218
+
1219
+ cache_values = (
1220
+ hidden_states[
1221
+ ..., :1
1222
+ ].unsqueeze(1)
1223
+ )
1224
+
1225
+ kv_cache.update(
1226
+ cache_keys,
1227
+ cache_values,
1228
+ self.layer_id,
1229
+ )
1230
+
1231
+ return (
1232
+ out,
1233
+ kv_cache,
1234
+ )
1235
+
1236
+
1237
+ # ============================================================
1238
+ # III Decoder Layer
1239
+ # ============================================================
1240
+
1241
+ class IIILayer(Module):
1242
+ def __init__(
1243
+ self,
1244
+ config,
1245
+ layer_id,
1246
+ ):
1247
+ super().__init__()
1248
+
1249
+ self.config = config
1250
+ self.layer_id = layer_id
1251
+
1252
+ self.window_size = (
1253
+ config.layer_window_sizes[
1254
+ layer_id
1255
+ ]
1256
+ )
1257
+
1258
+ self.dilation = (
1259
+ config.layer_dilation_size[
1260
+ layer_id
1261
+ ]
1262
+ )
1263
+
1264
+ # ----------------------------------------------------
1265
+ # Pre-mixer RMSNorm
1266
+ # ----------------------------------------------------
1267
+
1268
+ self.input_layernorm = (
1269
+ IIIRMSNorm(
1270
+ config.hidden_dim,
1271
+ eps=config.rms_norm_eps,
1272
+ )
1273
+ )
1274
+
1275
+ # ----------------------------------------------------
1276
+ # Mixer
1277
+ # ----------------------------------------------------
1278
+
1279
+ if self.window_size == 0:
1280
+ self.is_attention = True
1281
+
1282
+ self.mixer = IIIAttention(
1283
+ config,
1284
+ layer_id=layer_id,
1285
+ )
1286
+
1287
+ else:
1288
+ self.is_attention = False
1289
+
1290
+ self.mixer = GatedCausalCNN(
1291
+ config,
1292
+ layer_id=layer_id,
1293
+ )
1294
+
1295
+ # ----------------------------------------------------
1296
+ # Post-mixer RMSNorm
1297
+ # ----------------------------------------------------
1298
+
1299
+ self.post_mixer_layernorm = (
1300
+ IIIRMSNorm(
1301
+ config.hidden_dim,
1302
+ eps=config.rms_norm_eps,
1303
+ )
1304
+ )
1305
+
1306
+ # ----------------------------------------------------
1307
+ # MLP
1308
+ # ----------------------------------------------------
1309
+
1310
+ self.mlp = IIIMLP(config)
1311
+
1312
+ def forward(
1313
+ self,
1314
+ hidden_states,
1315
+ attention_mask=None,
1316
+ position_ids=None,
1317
+ kv_cache=None,
1318
+ use_cache=False,
1319
+ output_attentions=False,
1320
+ ):
1321
+ # ----------------------------------------------------
1322
+ # Mixer
1323
+ # ----------------------------------------------------
1324
+
1325
+ residual = hidden_states
1326
+
1327
+ hidden_states = (
1328
+ self.input_layernorm(
1329
+ hidden_states
1330
+ )
1331
+ )
1332
+
1333
+ if self.is_attention:
1334
+ (
1335
+ mixer_output,
1336
+ kv_cache,
1337
+ attention_weights,
1338
+ ) = self.mixer(
1339
+ hidden_states,
1340
+ attention_mask=attention_mask,
1341
+ position_ids=position_ids,
1342
+ kv_cache=kv_cache,
1343
+ use_cache=use_cache,
1344
+ output_attentions=(
1345
+ output_attentions
1346
+ ),
1347
+ )
1348
+ else:
1349
+ (
1350
+ mixer_output,
1351
+ kv_cache,
1352
+ ) = self.mixer(
1353
+ hidden_states,
1354
+ kv_cache=kv_cache,
1355
+ use_cache=use_cache,
1356
+ )
1357
+
1358
+ attention_weights = None
1359
+
1360
+ hidden_states = (
1361
+ residual
1362
+ + mixer_output
1363
+ )
1364
+
1365
+ # ----------------------------------------------------
1366
+ # MLP
1367
+ # ----------------------------------------------------
1368
+
1369
+ residual = hidden_states
1370
+
1371
+ hidden_states = (
1372
+ self.post_mixer_layernorm(
1373
+ hidden_states
1374
+ )
1375
+ )
1376
+
1377
+ hidden_states = self.mlp(
1378
+ hidden_states
1379
+ )
1380
+
1381
+ hidden_states = (
1382
+ residual
1383
+ + hidden_states
1384
+ )
1385
+
1386
+ return (
1387
+ hidden_states,
1388
+ kv_cache,
1389
+ attention_weights,
1390
+ )
1391
+
1392
+
1393
+ # ============================================================
1394
+ # Pretrained base
1395
+ # ============================================================
1396
+
1397
+ class IIIPreTrainedModel(
1398
+ PreTrainedModel
1399
+ ):
1400
+ config_class = IIIConfig
1401
+ base_model_prefix = "model"
1402
+
1403
+ _supports_cache_class = True
1404
+
1405
+ def _init_weights(
1406
+ self,
1407
+ module,
1408
+ ):
1409
+ std = getattr(
1410
+ self.config,
1411
+ "initializer_range",
1412
+ 0.02,
1413
+ )
1414
+
1415
+ if isinstance(
1416
+ module,
1417
+ Linear,
1418
+ ):
1419
+ torch.nn.init.normal_(
1420
+ module.weight,
1421
+ mean=0.0,
1422
+ std=std,
1423
+ )
1424
+
1425
+ if module.bias is not None:
1426
+ torch.nn.init.zeros_(
1427
+ module.bias
1428
+ )
1429
+
1430
+ elif isinstance(
1431
+ module,
1432
+ Embedding,
1433
+ ):
1434
+ torch.nn.init.normal_(
1435
+ module.weight,
1436
+ mean=0.0,
1437
+ std=std,
1438
+ )
1439
+
1440
+ if (
1441
+ module.padding_idx
1442
+ is not None
1443
+ ):
1444
+ torch.nn.init.zeros_(
1445
+ module.weight[
1446
+ module.padding_idx
1447
+ ]
1448
+ )
1449
+
1450
+ elif isinstance(
1451
+ module,
1452
+ Conv1d,
1453
+ ):
1454
+ torch.nn.init.normal_(
1455
+ module.weight,
1456
+ mean=0.0,
1457
+ std=std,
1458
+ )
1459
+
1460
+ if module.bias is not None:
1461
+ torch.nn.init.zeros_(
1462
+ module.bias
1463
+ )
1464
+
1465
+ elif isinstance(
1466
+ module,
1467
+ IIIRMSNorm,
1468
+ ):
1469
+ torch.nn.init.ones_(
1470
+ module.weight
1471
+ )
1472
+
1473
+
1474
+ # ============================================================
1475
+ # III Model
1476
+ # ============================================================
1477
+
1478
+ class IIIModel(
1479
+ IIIPreTrainedModel
1480
+ ):
1481
+ def __init__(
1482
+ self,
1483
+ config,
1484
+ ):
1485
+ super().__init__(
1486
+ config
1487
+ )
1488
+
1489
+ # ----------------------------------------------------
1490
+ # Find an attention layer.
1491
+ #
1492
+ # This is important because CNN cache length can be
1493
+ # local, while attention cache length represents the
1494
+ # complete generated sequence.
1495
+ # ----------------------------------------------------
1496
+
1497
+ attention_layers = [
1498
+ i
1499
+ for i, window in enumerate(
1500
+ config.layer_window_sizes
1501
+ )
1502
+ if window == 0
1503
+ ]
1504
+
1505
+ if not attention_layers:
1506
+ raise ValueError(
1507
+ "IIIModel requires at least "
1508
+ "one attention layer."
1509
+ )
1510
+
1511
+ self.first_attention_layer = (
1512
+ attention_layers[0]
1513
+ )
1514
+
1515
+ # ----------------------------------------------------
1516
+ # Token embeddings
1517
+ # ----------------------------------------------------
1518
+
1519
+ self.embed_tokens = Embedding(
1520
+ config.vocab_size,
1521
+ config.hidden_dim,
1522
+ padding_idx=config.pad_token_id,
1523
+ )
1524
+
1525
+ # ----------------------------------------------------
1526
+ # Decoder layers
1527
+ # ----------------------------------------------------
1528
+
1529
+ self.layers = (
1530
+ torch.nn.ModuleList(
1531
+ [
1532
+ IIILayer(
1533
+ config,
1534
+ layer_id=i,
1535
+ )
1536
+ for i in range(
1537
+ config.n_layers
1538
+ )
1539
+ ]
1540
+ )
1541
+ )
1542
+
1543
+ # ----------------------------------------------------
1544
+ # Final norm
1545
+ # ----------------------------------------------------
1546
+
1547
+ self.norm = IIIRMSNorm(
1548
+ config.hidden_dim,
1549
+ eps=config.rms_norm_eps,
1550
+ )
1551
+
1552
+ self.gradient_checkpointing = (
1553
+ False
1554
+ )
1555
+
1556
+ self.post_init()
1557
+
1558
+ def get_input_embeddings(
1559
+ self,
1560
+ ):
1561
+ return self.embed_tokens
1562
+
1563
+ def set_input_embeddings(
1564
+ self,
1565
+ value,
1566
+ ):
1567
+ self.embed_tokens = value
1568
+
1569
+ def _get_past_length(
1570
+ self,
1571
+ past_key_values,
1572
+ ):
1573
+ if past_key_values is None:
1574
+ return 0
1575
+
1576
+ # IMPORTANT:
1577
+ #
1578
+ # Layer 0 is a CNN and may conceptually only need
1579
+ # a local history. Attention layers contain the
1580
+ # complete sequence, so use the first attention
1581
+ # layer to determine the real sequence position.
1582
+ return past_key_values.get_seq_length(
1583
+ self.first_attention_layer
1584
+ )
1585
+
1586
+ def forward(
1587
+ self,
1588
+ input_ids=None,
1589
+ attention_mask=None,
1590
+ position_ids=None,
1591
+ past_key_values=None,
1592
+ inputs_embeds=None,
1593
+ cache_position=None,
1594
+ use_cache=None,
1595
+ output_attentions=False,
1596
+ output_hidden_states=False,
1597
+ return_dict=None,
1598
+ ):
1599
+ if (
1600
+ input_ids is not None
1601
+ and inputs_embeds is not None
1602
+ ):
1603
+ raise ValueError(
1604
+ "Specify either input_ids "
1605
+ "or inputs_embeds, not both."
1606
+ )
1607
+
1608
+ if (
1609
+ input_ids is None
1610
+ and inputs_embeds is None
1611
+ ):
1612
+ raise ValueError(
1613
+ "Either input_ids or "
1614
+ "inputs_embeds must be provided."
1615
+ )
1616
+
1617
+ if use_cache is None:
1618
+ use_cache = (
1619
+ self.config.use_cache
1620
+ )
1621
+
1622
+ if return_dict is None:
1623
+ return_dict = True
1624
+
1625
+ # ----------------------------------------------------
1626
+ # Cache
1627
+ # ----------------------------------------------------
1628
+
1629
+ if use_cache:
1630
+ if past_key_values is None:
1631
+ past_key_values = (
1632
+ DynamicCache()
1633
+ )
1634
+
1635
+ elif not isinstance(
1636
+ past_key_values,
1637
+ Cache,
1638
+ ):
1639
+ raise TypeError(
1640
+ "past_key_values must be "
1641
+ "a Transformers Cache."
1642
+ )
1643
+ else:
1644
+ past_key_values = None
1645
+
1646
+ # ----------------------------------------------------
1647
+ # Inputs
1648
+ # ----------------------------------------------------
1649
+
1650
+ if inputs_embeds is None:
1651
+ hidden_states = (
1652
+ self.embed_tokens(
1653
+ input_ids
1654
+ )
1655
+ )
1656
+ else:
1657
+ hidden_states = (
1658
+ inputs_embeds
1659
+ )
1660
+
1661
+ batch_size, seq_len, _ = (
1662
+ hidden_states.shape
1663
+ )
1664
+
1665
+ # ----------------------------------------------------
1666
+ # Positions
1667
+ # ----------------------------------------------------
1668
+
1669
+ past_length = (
1670
+ self._get_past_length(
1671
+ past_key_values
1672
+ )
1673
+ )
1674
+
1675
+ if position_ids is None:
1676
+ if cache_position is not None:
1677
+ position_ids = (
1678
+ cache_position
1679
+ )
1680
+
1681
+ if position_ids.dim() == 1:
1682
+ position_ids = (
1683
+ position_ids
1684
+ .unsqueeze(0)
1685
+ .expand(
1686
+ batch_size,
1687
+ -1,
1688
+ )
1689
+ )
1690
+
1691
+ else:
1692
+ position_ids = (
1693
+ torch.arange(
1694
+ past_length,
1695
+ past_length
1696
+ + seq_len,
1697
+ device=(
1698
+ hidden_states.device
1699
+ ),
1700
+ )
1701
+ .unsqueeze(0)
1702
+ .expand(
1703
+ batch_size,
1704
+ -1,
1705
+ )
1706
+ )
1707
+
1708
+ # ----------------------------------------------------
1709
+ # Outputs
1710
+ # ----------------------------------------------------
1711
+
1712
+ all_hidden_states = (
1713
+ ()
1714
+ if output_hidden_states
1715
+ else None
1716
+ )
1717
+
1718
+ all_attentions = (
1719
+ ()
1720
+ if output_attentions
1721
+ else None
1722
+ )
1723
+
1724
+ # ----------------------------------------------------
1725
+ # Decoder
1726
+ # ----------------------------------------------------
1727
+
1728
+ for layer in self.layers:
1729
+ if output_hidden_states:
1730
+ all_hidden_states += (
1731
+ hidden_states,
1732
+ )
1733
+
1734
+ (
1735
+ hidden_states,
1736
+ past_key_values,
1737
+ attention_weights,
1738
+ ) = layer(
1739
+ hidden_states,
1740
+ attention_mask=attention_mask,
1741
+ position_ids=position_ids,
1742
+ kv_cache=past_key_values,
1743
+ use_cache=use_cache,
1744
+ output_attentions=(
1745
+ output_attentions
1746
+ ),
1747
+ )
1748
+
1749
+ if output_attentions:
1750
+ all_attentions += (
1751
+ attention_weights,
1752
+ )
1753
+
1754
+ # ----------------------------------------------------
1755
+ # Final norm
1756
+ # ----------------------------------------------------
1757
+
1758
+ hidden_states = self.norm(
1759
+ hidden_states
1760
+ )
1761
+
1762
+ if output_hidden_states:
1763
+ all_hidden_states += (
1764
+ hidden_states,
1765
+ )
1766
+
1767
+ # ----------------------------------------------------
1768
+ # Tuple output
1769
+ # ----------------------------------------------------
1770
+
1771
+ if not return_dict:
1772
+ return tuple(
1773
+ value
1774
+ for value in (
1775
+ hidden_states,
1776
+ past_key_values,
1777
+ all_hidden_states,
1778
+ all_attentions,
1779
+ )
1780
+ if value is not None
1781
+ )
1782
+
1783
+ return BaseModelOutputWithPast(
1784
+ last_hidden_state=hidden_states,
1785
+ past_key_values=(
1786
+ past_key_values
1787
+ if use_cache
1788
+ else None
1789
+ ),
1790
+ hidden_states=(
1791
+ all_hidden_states
1792
+ ),
1793
+ attentions=(
1794
+ all_attentions
1795
+ ),
1796
+ )
1797
+
1798
+
1799
+ # ============================================================
1800
+ # III Causal LM
1801
+ # ============================================================
1802
+
1803
+ class IIIForCausalLM(
1804
+ IIIPreTrainedModel,
1805
+ GenerationMixin,
1806
+ ):
1807
+ _tied_weights_keys = {"lm_head.weight": "model.embed_tokens.weight"}
1808
+
1809
+ def __init__(
1810
+ self,
1811
+ config,
1812
+ ):
1813
+ super().__init__(
1814
+ config
1815
+ )
1816
+
1817
+ self.model = IIIModel(
1818
+ config
1819
+ )
1820
+
1821
+ self.lm_head = Linear(
1822
+ config.hidden_dim,
1823
+ config.vocab_size,
1824
+ bias=False,
1825
+ )
1826
+
1827
+ self.post_init()
1828
+
1829
+ if config.tie_word_embedding:
1830
+ self.lm_head.weight = (
1831
+ self.model.embed_tokens.weight
1832
+ )
1833
+
1834
+ # --------------------------------------------------------
1835
+ # Embeddings
1836
+ # --------------------------------------------------------
1837
+
1838
+ def get_input_embeddings(
1839
+ self,
1840
+ ):
1841
+ return self.model.embed_tokens
1842
+
1843
+ def set_input_embeddings(
1844
+ self,
1845
+ value,
1846
+ ):
1847
+ self.model.embed_tokens = value
1848
+
1849
+ def get_output_embeddings(
1850
+ self,
1851
+ ):
1852
+ return self.lm_head
1853
+
1854
+ def set_output_embeddings(
1855
+ self,
1856
+ new_embeddings,
1857
+ ):
1858
+ self.lm_head = new_embeddings
1859
+
1860
+ # --------------------------------------------------------
1861
+ # Forward
1862
+ # --------------------------------------------------------
1863
+
1864
+ def forward(
1865
+ self,
1866
+ input_ids=None,
1867
+ attention_mask=None,
1868
+ position_ids=None,
1869
+ past_key_values=None,
1870
+ inputs_embeds=None,
1871
+ labels=None,
1872
+ cache_position=None,
1873
+ use_cache=None,
1874
+ output_attentions=False,
1875
+ output_hidden_states=False,
1876
+ return_dict=None,
1877
+ ):
1878
+ if return_dict is None:
1879
+ return_dict = True
1880
+
1881
+ outputs = self.model(
1882
+ input_ids=input_ids,
1883
+ attention_mask=attention_mask,
1884
+ position_ids=position_ids,
1885
+ past_key_values=past_key_values,
1886
+ inputs_embeds=inputs_embeds,
1887
+ cache_position=cache_position,
1888
+ use_cache=use_cache,
1889
+ output_attentions=(
1890
+ output_attentions
1891
+ ),
1892
+ output_hidden_states=(
1893
+ output_hidden_states
1894
+ ),
1895
+ return_dict=True,
1896
+ )
1897
+
1898
+ # ----------------------------------------------------
1899
+ # LM logits
1900
+ # ----------------------------------------------------
1901
+
1902
+ logits = self.lm_head(
1903
+ outputs.last_hidden_state
1904
+ )
1905
+
1906
+ # ----------------------------------------------------
1907
+ # Causal LM loss
1908
+ # ----------------------------------------------------
1909
+
1910
+ loss = None
1911
+
1912
+ if labels is not None:
1913
+ shift_logits = (
1914
+ logits[
1915
+ ...,
1916
+ :-1,
1917
+ :,
1918
+ ]
1919
+ .contiguous()
1920
+ )
1921
+
1922
+ shift_labels = (
1923
+ labels[
1924
+ ...,
1925
+ 1:,
1926
+ ]
1927
+ .contiguous()
1928
+ )
1929
+
1930
+ loss = F.cross_entropy(
1931
+ shift_logits.view(
1932
+ -1,
1933
+ shift_logits.size(-1),
1934
+ ),
1935
+ shift_labels.view(
1936
+ -1
1937
+ ),
1938
+ )
1939
+
1940
+ # ----------------------------------------------------
1941
+ # Tuple output
1942
+ # ----------------------------------------------------
1943
+
1944
+ if not return_dict:
1945
+ result = (
1946
+ logits,
1947
+ outputs.past_key_values,
1948
+ outputs.hidden_states,
1949
+ outputs.attentions,
1950
+ )
1951
+
1952
+ if loss is not None:
1953
+ result = (
1954
+ loss,
1955
+ *result,
1956
+ )
1957
+
1958
+ return result
1959
+
1960
+ return CausalLMOutputWithPast(
1961
+ loss=loss,
1962
+ logits=logits,
1963
+ past_key_values=(
1964
+ outputs.past_key_values
1965
+ ),
1966
+ hidden_states=(
1967
+ outputs.hidden_states
1968
+ ),
1969
+ attentions=(
1970
+ outputs.attentions
1971
+ ),
1972
+ )
1973
+
1974
+ # --------------------------------------------------------
1975
+ # Generation
1976
+ # --------------------------------------------------------
1977
+
1978
+ def prepare_inputs_for_generation(
1979
+ self,
1980
+ input_ids,
1981
+ past_key_values=None,
1982
+ attention_mask=None,
1983
+ inputs_embeds=None,
1984
+ cache_position=None,
1985
+ **kwargs,
1986
+ ):
1987
+ """
1988
+ Prepare only the unprocessed tokens for generation.
1989
+
1990
+ When a cache exists, the model should not recompute
1991
+ hidden states for tokens already represented in the
1992
+ cache.
1993
+ """
1994
+
1995
+ if (
1996
+ past_key_values is not None
1997
+ ):
1998
+ past_length = (
1999
+ past_key_values.get_seq_length(
2000
+ self.model.first_attention_layer
2001
+ )
2002
+ )
2003
+
2004
+ if (
2005
+ input_ids is not None
2006
+ and input_ids.shape[1]
2007
+ > past_length
2008
+ ):
2009
+ input_ids = input_ids[
2010
+ :,
2011
+ past_length:,
2012
+ ]
2013
+
2014
+ elif input_ids is not None:
2015
+ # Usually generation reaches this path with
2016
+ # one new token already supplied.
2017
+ input_ids = input_ids[
2018
+ :,
2019
+ -1:,
2020
+ ]
2021
+
2022
+ if (
2023
+ inputs_embeds is not None
2024
+ ):
2025
+ inputs_embeds = (
2026
+ inputs_embeds[
2027
+ :,
2028
+ -input_ids.shape[1]:,
2029
+ :,
2030
+ ]
2031
+ )
2032
+
2033
+ model_inputs = {}
2034
+
2035
+ if (
2036
+ inputs_embeds is not None
2037
+ and past_key_values is None
2038
+ ):
2039
+ model_inputs[
2040
+ "inputs_embeds"
2041
+ ] = inputs_embeds
2042
+
2043
+ if input_ids is not None:
2044
+ model_inputs[
2045
+ "input_ids"
2046
+ ] = input_ids
2047
+
2048
+ else:
2049
+ model_inputs[
2050
+ "input_ids"
2051
+ ] = input_ids
2052
+
2053
+ model_inputs[
2054
+ "past_key_values"
2055
+ ] = past_key_values
2056
+
2057
+ model_inputs[
2058
+ "attention_mask"
2059
+ ] = attention_mask
2060
+
2061
+ model_inputs[
2062
+ "cache_position"
2063
+ ] = cache_position
2064
+
2065
+ model_inputs[
2066
+ "use_cache"
2067
+ ] = kwargs.get(
2068
+ "use_cache",
2069
+ self.config.use_cache,
2070
+ )
2071
+
2072
+ return model_inputs