ypwhere commited on
Commit
17fdc04
·
verified ·
1 Parent(s): 1e25c03

Publish LQK strict final model

Browse files
README.md ADDED
@@ -0,0 +1,19 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ ---
2
+ license: other
3
+ language:
4
+ - en
5
+ library_name: transformers
6
+ pipeline_tag: text-generation
7
+ tags:
8
+ - babylm
9
+ - babylm-2026
10
+ - custom-code
11
+ datasets:
12
+ - BabyLM-community/BabyLM-2026-Strict
13
+ ---
14
+
15
+ # LQK — BabyLM 2026 Strict
16
+
17
+ LQK is a 116M-parameter causal model built on a Llama-1-style decoder with Qwen3-Next-style gated attention and Kimi Attention Residuals (AttnRes). This seed-1337 model was trained for 10 epochs on the official BabyLM 2026 Strict data with its exact 16k byte-level BPE tokenizer.
18
+
19
+ Load with `AutoModelForCausalLM.from_pretrained("ypwhere/LQK-BabyLM-Strict", trust_remote_code=True)`. The repository provides `main` plus the 28 required `chck_*M` checkpoint revisions. Training-data terms remain governed by the BabyLM release; the included nanoGPT-derived model code is provided for research reproducibility.
REVISION_MANIFEST.json ADDED
@@ -0,0 +1,268 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ {
2
+ "schema_version": 1,
3
+ "generated_at": "2026-07-20T02:30:16.643539+00:00",
4
+ "repo_id": "ypwhere/LQK-BabyLM-Strict",
5
+ "track": "strict",
6
+ "dtype": "float16",
7
+ "tokenizer_sha256": "f13720328807e761dc92192111d89ece0119987875f890f3665eba477b5d727c",
8
+ "source_manifest": "/Volumes/T9/babylm-2026/checkpoints/offdev/vast/bl100m-d512L32-do0.1-gate-attnres8-offdev-aoaw28-aoat31-u57-b16ga32/checkpoint_manifest.json",
9
+ "main": {
10
+ "role": "final",
11
+ "source_path": "ckpt_final-w0910M-i004797.pt",
12
+ "source_sha256": "dfaff6e50e0759fed5469af2022205228068aa12354537de22ebcde769b32995"
13
+ },
14
+ "revisions": [
15
+ {
16
+ "revision": "chck_1M",
17
+ "source_path": "ckpt_000005.pt",
18
+ "source_sha256": "6fa3f4ffc942b646d7e10bcd2ae6d4d340a8c53221e54d4c10c2de990e064467",
19
+ "original_revision": "chck_1M",
20
+ "iter_num": 5,
21
+ "words_seen": 949462,
22
+ "tokens_seen": 1310720
23
+ },
24
+ {
25
+ "revision": "chck_2M",
26
+ "source_path": "ckpt_000011.pt",
27
+ "source_sha256": "c5b1346784c8ade00bf9c935e57b539928a8fbd8cbd08160031fe2692e966bd4",
28
+ "original_revision": "chck_2M",
29
+ "iter_num": 11,
30
+ "words_seen": 2086910,
31
+ "tokens_seen": 2883584
32
+ },
33
+ {
34
+ "revision": "chck_3M",
35
+ "source_path": "ckpt_000016.pt",
36
+ "source_sha256": "36c8043db9cf0f784ca5856ab9ea4ecb9c1e358f8cc9f661ac32a04398d60f6f",
37
+ "original_revision": "chck_3M",
38
+ "iter_num": 16,
39
+ "words_seen": 3032669,
40
+ "tokens_seen": 4194304
41
+ },
42
+ {
43
+ "revision": "chck_4M",
44
+ "source_path": "ckpt_000021.pt",
45
+ "source_sha256": "e3d2185fdbc80984bb9613d8b669966ea3102f8881bb63add6843c16a7c67282",
46
+ "original_revision": "chck_4M",
47
+ "iter_num": 21,
48
+ "words_seen": 3981969,
49
+ "tokens_seen": 5505024
50
+ },
51
+ {
52
+ "revision": "chck_5M",
53
+ "source_path": "ckpt_000026.pt",
54
+ "source_sha256": "f2f80e00ce96b67e843900eefc3b00dd28c66f808c08280fb158cb440bd0ad61",
55
+ "original_revision": "chck_5M",
56
+ "iter_num": 26,
57
+ "words_seen": 4931564,
58
+ "tokens_seen": 6815744
59
+ },
60
+ {
61
+ "revision": "chck_6M",
62
+ "source_path": "ckpt_000032.pt",
63
+ "source_sha256": "655dd3c62b75a2ef34148484811e3220bdc25e87e80ca6b3f32631304064c8a1",
64
+ "original_revision": "chck_6M",
65
+ "iter_num": 32,
66
+ "words_seen": 6065034,
67
+ "tokens_seen": 8388608
68
+ },
69
+ {
70
+ "revision": "chck_7M",
71
+ "source_path": "ckpt_000037.pt",
72
+ "source_sha256": "39681bdcfa49ceb5f86bf4922ee2f80d315bf2f95bbae8a816fc5b4486ff7877",
73
+ "original_revision": "chck_7M",
74
+ "iter_num": 37,
75
+ "words_seen": 7013912,
76
+ "tokens_seen": 9699328
77
+ },
78
+ {
79
+ "revision": "chck_8M",
80
+ "source_path": "ckpt_000042.pt",
81
+ "source_sha256": "35097df18e56bf78a23fc74ff7dc17713e0366dfaa4e73b25c95d05b40670891",
82
+ "original_revision": "chck_8M",
83
+ "iter_num": 42,
84
+ "words_seen": 7963439,
85
+ "tokens_seen": 11010048
86
+ },
87
+ {
88
+ "revision": "chck_9M",
89
+ "source_path": "ckpt_000047.pt",
90
+ "source_sha256": "b53dfa64832f0bfd6f0273dd525448d6d69ae24d86b525de992220b183f40d2b",
91
+ "original_revision": "chck_9M",
92
+ "iter_num": 47,
93
+ "words_seen": 8911753,
94
+ "tokens_seen": 12320768
95
+ },
96
+ {
97
+ "revision": "chck_10M",
98
+ "source_path": "ckpt_000053.pt",
99
+ "source_sha256": "7faf1ef0a1f476798a7ad58ab0013f540a18ca257d80e9a3632c8c7225517d12",
100
+ "original_revision": "chck_10M",
101
+ "iter_num": 53,
102
+ "words_seen": 10050807,
103
+ "tokens_seen": 13893632
104
+ },
105
+ {
106
+ "revision": "chck_20M",
107
+ "source_path": "ckpt_000105.pt",
108
+ "source_sha256": "bb6085b947df97e3fa9644b2f6f5bbc819a24fa0667e8f541afef1bd7a0a6883",
109
+ "original_revision": "chck_20M",
110
+ "iter_num": 105,
111
+ "words_seen": 19917876,
112
+ "tokens_seen": 27525120
113
+ },
114
+ {
115
+ "revision": "chck_30M",
116
+ "source_path": "ckpt_000158.pt",
117
+ "source_sha256": "81c432bd63dea4047f2304f20a2bf369dacdd56466d12d622fa798e4bc55fa9e",
118
+ "original_revision": "chck_30M",
119
+ "iter_num": 158,
120
+ "words_seen": 29980340,
121
+ "tokens_seen": 41418752
122
+ },
123
+ {
124
+ "revision": "chck_40M",
125
+ "source_path": "ckpt_000211.pt",
126
+ "source_sha256": "2f5ce57ddf0fbb6af09ee61f7779b8dd8b972b5026f3ac8715949cfe4cf3a837",
127
+ "original_revision": "chck_40M",
128
+ "iter_num": 211,
129
+ "words_seen": 40043320,
130
+ "tokens_seen": 55312384
131
+ },
132
+ {
133
+ "revision": "chck_50M",
134
+ "source_path": "ckpt_000264.pt",
135
+ "source_sha256": "2c0c562991293f43b03f2e5b3fdbbbe52676558a18022c700d9e9a9051450bd5",
136
+ "original_revision": "chck_50M",
137
+ "iter_num": 264,
138
+ "words_seen": 50093276,
139
+ "tokens_seen": 69206016
140
+ },
141
+ {
142
+ "revision": "chck_60M",
143
+ "source_path": "ckpt_000316.pt",
144
+ "source_sha256": "9f9ffa85cee106fca9eb46d7b84c6f12e21883ffcedcbf667831fcd72d128331",
145
+ "original_revision": "chck_60M",
146
+ "iter_num": 316,
147
+ "words_seen": 59951092,
148
+ "tokens_seen": 82837504
149
+ },
150
+ {
151
+ "revision": "chck_70M",
152
+ "source_path": "ckpt_000369.pt",
153
+ "source_sha256": "791c49f2f1c7eff2f23e9102e10858a7263a10175a7f0eccaffd8799db4cf572",
154
+ "original_revision": "chck_70M",
155
+ "iter_num": 369,
156
+ "words_seen": 70005835,
157
+ "tokens_seen": 96731136
158
+ },
159
+ {
160
+ "revision": "chck_80M",
161
+ "source_path": "ckpt_000422.pt",
162
+ "source_sha256": "bb61fb617bdd87de4e6d2023fbd17038fe56279922476d13dddb096762c67b61",
163
+ "original_revision": "chck_80M",
164
+ "iter_num": 422,
165
+ "words_seen": 80073013,
166
+ "tokens_seen": 110624768
167
+ },
168
+ {
169
+ "revision": "chck_90M",
170
+ "source_path": "ckpt_000474.pt",
171
+ "source_sha256": "d63fc71506f1a0b67dd9ac245e5936b89805f4625c72ecfeefafed0487b33ba1",
172
+ "original_revision": "chck_90M",
173
+ "iter_num": 474,
174
+ "words_seen": 89937046,
175
+ "tokens_seen": 124256256
176
+ },
177
+ {
178
+ "revision": "chck_100M",
179
+ "source_path": "ckpt_000527.pt",
180
+ "source_sha256": "b2693b41e93cf8eb0e57f0df238c3391f4be8b57c28a8b9b5e63798a28d7f24a",
181
+ "original_revision": "chck_100M",
182
+ "iter_num": 527,
183
+ "words_seen": 99996136,
184
+ "tokens_seen": 138149888
185
+ },
186
+ {
187
+ "revision": "chck_200M",
188
+ "source_path": "ckpt_001054.pt",
189
+ "source_sha256": "0659d403b9c23e54e40a7564f5494351751b572ea4e66209aba26f940df20a98",
190
+ "original_revision": "chck_200M",
191
+ "iter_num": 1054,
192
+ "words_seen": 199982884,
193
+ "tokens_seen": 276299776
194
+ },
195
+ {
196
+ "revision": "chck_300M",
197
+ "source_path": "ckpt_001581.pt",
198
+ "source_sha256": "a5265a307ab28b45f1cfbcf02bb25c0283774b296c9c16eeb945ee38078a1e18",
199
+ "original_revision": "chck_300M",
200
+ "iter_num": 1581,
201
+ "words_seen": 299987936,
202
+ "tokens_seen": 414449664
203
+ },
204
+ {
205
+ "revision": "chck_400M",
206
+ "source_path": "ckpt_002108.pt",
207
+ "source_sha256": "d425113cb065a90c8a39c7dc2099464be9613c90d409b265b6dae0ada51f356e",
208
+ "original_revision": "chck_400M",
209
+ "iter_num": 2108,
210
+ "words_seen": 399991397,
211
+ "tokens_seen": 552599552
212
+ },
213
+ {
214
+ "revision": "chck_500M",
215
+ "source_path": "ckpt_002635.pt",
216
+ "source_sha256": "64b6d22c0ce288f4d7b711c0cb0d47c74c536e0fc92bbb4643f7451f1d966b08",
217
+ "original_revision": "chck_500M",
218
+ "iter_num": 2635,
219
+ "words_seen": 499981660,
220
+ "tokens_seen": 690749440
221
+ },
222
+ {
223
+ "revision": "chck_600M",
224
+ "source_path": "ckpt_003162.pt",
225
+ "source_sha256": "2574ff5d8e536f7983fe5e524f0fa5ee8ee0f684f797a6303c23ea8ac24ac57a",
226
+ "original_revision": "chck_600M",
227
+ "iter_num": 3162,
228
+ "words_seen": 599971774,
229
+ "tokens_seen": 828899328
230
+ },
231
+ {
232
+ "revision": "chck_700M",
233
+ "source_path": "ckpt_003689.pt",
234
+ "source_sha256": "2b66c9aaea75a1e2b083462f9cd683d6a96735ff78c2efd2c0ac1e7a70acfb25",
235
+ "original_revision": "chck_700M",
236
+ "iter_num": 3689,
237
+ "words_seen": 699959933,
238
+ "tokens_seen": 967049216
239
+ },
240
+ {
241
+ "revision": "chck_800M",
242
+ "source_path": "ckpt_004216.pt",
243
+ "source_sha256": "b09a8a5efe69aa1eac7c0ca761e6e73d9ba14c7b37b35b45464c247c76734202",
244
+ "original_revision": "chck_800M",
245
+ "iter_num": 4216,
246
+ "words_seen": 799956340,
247
+ "tokens_seen": 1105199104
248
+ },
249
+ {
250
+ "revision": "chck_900M",
251
+ "source_path": "ckpt_004743.pt",
252
+ "source_sha256": "27772c31bf49988742accabdf273a0a4e0f4611acb79612c78e0541651af6a48",
253
+ "original_revision": "chck_900M",
254
+ "iter_num": 4743,
255
+ "words_seen": 899951513,
256
+ "tokens_seen": 1243348992
257
+ },
258
+ {
259
+ "revision": "chck_1000M",
260
+ "source_path": "ckpt_004797.pt",
261
+ "source_sha256": "0f1e4cd13d67dabfdea0155a9dfe1ab5e59e8f423c64e1242b2fd690818facce",
262
+ "original_revision": "chck_910M",
263
+ "iter_num": 4797,
264
+ "words_seen": 910196864,
265
+ "tokens_seen": 1257504768
266
+ }
267
+ ]
268
+ }
checkpoint_source.json ADDED
@@ -0,0 +1,26 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ {
2
+ "filename": "ckpt_final-w0910M-i004797.pt",
3
+ "sha256": "dfaff6e50e0759fed5469af2022205228068aa12354537de22ebcde769b32995",
4
+ "role": "final",
5
+ "iter_num": 4797,
6
+ "num_updates": 4797,
7
+ "tokens_seen": 1257504768,
8
+ "words_seen": 910196864,
9
+ "labels": [
10
+ {
11
+ "series": "words",
12
+ "name": "words_final",
13
+ "revision": "chck_910M",
14
+ "target": 910196864,
15
+ "actual": 910196864
16
+ },
17
+ {
18
+ "series": "tokens",
19
+ "name": "tokens_final",
20
+ "revision": "chck_1258M",
21
+ "target": 1257504768,
22
+ "actual": 1257504768
23
+ }
24
+ ],
25
+ "git_sha": "71b982e505ea3f804c54a4b4c0834bd1eee54da8"
26
+ }
config.json ADDED
@@ -0,0 +1,60 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ {
2
+ "architectures": [
3
+ "NanoGPTForCausalLM"
4
+ ],
5
+ "attn_res_block_size": 8,
6
+ "auto_map": {
7
+ "AutoConfig": "modeling_nanogpt.NanoGPTConfig",
8
+ "AutoModel": "modeling_nanogpt.NanoGPTModel",
9
+ "AutoModelForCausalLM": "modeling_nanogpt.NanoGPTForCausalLM",
10
+ "AutoModelForMaskedLM": "modeling_nanogpt.NanoGPTForMaskedLM"
11
+ },
12
+ "bias": false,
13
+ "bidirectional": false,
14
+ "block_size": 512,
15
+ "bos_token_id": 0,
16
+ "dropout": 0.0,
17
+ "eos_token_id": 0,
18
+ "layer_norm_epsilon": 1e-05,
19
+ "model_type": "nanogpt",
20
+ "n_embd": 512,
21
+ "n_head": 8,
22
+ "n_layer": 32,
23
+ "nanogpt_checkpoint": {
24
+ "filename": "ckpt_final-w0910M-i004797.pt",
25
+ "git_sha": "71b982e505ea3f804c54a4b4c0834bd1eee54da8",
26
+ "iter_num": 4797,
27
+ "labels": [
28
+ {
29
+ "actual": 910196864,
30
+ "name": "words_final",
31
+ "revision": "chck_910M",
32
+ "series": "words",
33
+ "target": 910196864
34
+ },
35
+ {
36
+ "actual": 1257504768,
37
+ "name": "tokens_final",
38
+ "revision": "chck_1258M",
39
+ "series": "tokens",
40
+ "target": 1257504768
41
+ }
42
+ ],
43
+ "num_updates": 4797,
44
+ "role": "final",
45
+ "sha256": "dfaff6e50e0759fed5469af2022205228068aa12354537de22ebcde769b32995",
46
+ "tokens_seen": 1257504768,
47
+ "words_seen": 910196864
48
+ },
49
+ "pad_token_id": 0,
50
+ "rope_theta": 10000.0,
51
+ "swiglu_mult": 2.6666666666666665,
52
+ "torch_dtype": "float16",
53
+ "transformers_version": "4.51.3",
54
+ "use_attn_gate": true,
55
+ "use_attn_res": true,
56
+ "use_rmsnorm": true,
57
+ "use_rope": true,
58
+ "use_swiglu": true,
59
+ "vocab_size": 16000
60
+ }
generation_config.json ADDED
@@ -0,0 +1,7 @@
 
 
 
 
 
 
 
 
1
+ {
2
+ "_from_model_config": true,
3
+ "bos_token_id": 0,
4
+ "eos_token_id": 0,
5
+ "pad_token_id": 0,
6
+ "transformers_version": "4.51.3"
7
+ }
model.safetensors ADDED
@@ -0,0 +1,3 @@
 
 
 
 
1
+ version https://git-lfs.github.com/spec/v1
2
+ oid sha256:f770c157d21962a019cb933368ad8ce29b9082f22ca59b599bdac2ff65f215d7
3
+ size 232630672
modeling_nanogpt.py ADDED
@@ -0,0 +1,427 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ """
2
+ Self-contained HuggingFace wrapper for the nanoGPT architecture used in the BabyLM
3
+ ablations: LayerNorm/RMSNorm x MLP/SwiGLU x learned-absolute/RoPE positions.
4
+
5
+ This single file defines BOTH the config and the models so it can be copied verbatim
6
+ into a model repo and loaded with `trust_remote_code=True` by the BabyLM 2026
7
+ evaluation pipeline:
8
+ * AutoModelForCausalLM -> NanoGPTForCausalLM (causal zero-shot)
9
+ * AutoModelForMaskedLM -> NanoGPTForMaskedLM (bidirectional MNTP zero-shot)
10
+ * AutoModel -> NanoGPTModel (GLUE fine-tuning backbone)
11
+
12
+ Module/parameter names mirror nanoGPT's model.py `GPT` exactly, so a nanoGPT
13
+ checkpoint state_dict loads with NO key remapping. Two behaviours differ from
14
+ model.py on purpose (both required by the eval harness):
15
+ * forward always returns full-sequence logits (B, T, V), not just the last step.
16
+ * attention honours an optional padding `attention_mask` (needed for GLUE's
17
+ left-padded batches; nanoGPT's own forward assumes dense, causal-only inputs).
18
+ """
19
+
20
+ import math
21
+
22
+ import torch
23
+ import torch.nn as nn
24
+ import transformers
25
+ from torch.nn import functional as F
26
+
27
+ from transformers import GenerationMixin, PretrainedConfig, PreTrainedModel
28
+ from transformers.modeling_outputs import BaseModelOutput, CausalLMOutput, MaskedLMOutput
29
+
30
+
31
+ class NanoGPTConfig(PretrainedConfig):
32
+ model_type = "nanogpt"
33
+ # let generic HF utilities (and the GLUE classifier's `config.hidden_size`) work
34
+ attribute_map = {
35
+ "hidden_size": "n_embd",
36
+ "num_attention_heads": "n_head",
37
+ "num_hidden_layers": "n_layer",
38
+ "max_position_embeddings": "block_size",
39
+ }
40
+
41
+ def __init__(
42
+ self,
43
+ vocab_size=16384,
44
+ block_size=512,
45
+ n_layer=8,
46
+ n_head=8,
47
+ n_embd=512,
48
+ dropout=0.0,
49
+ bias=False,
50
+ use_rmsnorm=False,
51
+ use_swiglu=False,
52
+ swiglu_mult=8 / 3,
53
+ use_rope=False,
54
+ use_attn_gate=False,
55
+ use_attn_res=False,
56
+ attn_res_block_size=2,
57
+ bidirectional=False,
58
+ rope_theta=10000.0,
59
+ layer_norm_epsilon=1e-5,
60
+ tie_word_embeddings=True,
61
+ **kwargs,
62
+ ):
63
+ self.vocab_size = vocab_size
64
+ self.block_size = block_size
65
+ self.n_layer = n_layer
66
+ self.n_head = n_head
67
+ self.n_embd = n_embd
68
+ self.dropout = dropout
69
+ self.bias = bias
70
+ self.use_rmsnorm = use_rmsnorm
71
+ self.use_swiglu = use_swiglu
72
+ self.swiglu_mult = swiglu_mult
73
+ self.use_rope = use_rope
74
+ self.use_attn_gate = use_attn_gate
75
+ self.use_attn_res = use_attn_res
76
+ self.attn_res_block_size = attn_res_block_size
77
+ self.bidirectional = bidirectional
78
+ self.rope_theta = rope_theta
79
+ self.layer_norm_epsilon = layer_norm_epsilon
80
+ super().__init__(tie_word_embeddings=tie_word_embeddings, **kwargs)
81
+
82
+
83
+ # --------------------------------------------------------------------------- norms
84
+ class LayerNorm(nn.Module):
85
+ """LayerNorm with an optional bias (mirrors nanoGPT)."""
86
+
87
+ def __init__(self, ndim, bias, eps=1e-5):
88
+ super().__init__()
89
+ self.weight = nn.Parameter(torch.ones(ndim))
90
+ self.bias = nn.Parameter(torch.zeros(ndim)) if bias else None
91
+ self.eps = eps
92
+
93
+ def forward(self, input):
94
+ return F.layer_norm(input, self.weight.shape, self.weight, self.bias, self.eps)
95
+
96
+
97
+ class RMSNorm(nn.Module):
98
+ def __init__(self, ndim, eps=1e-5):
99
+ super().__init__()
100
+ self.weight = nn.Parameter(torch.ones(ndim))
101
+ self.eps = eps
102
+
103
+ def forward(self, input):
104
+ rms = torch.sqrt(input.pow(2).mean(dim=-1, keepdim=True) + self.eps)
105
+ return (input / rms) * self.weight
106
+
107
+
108
+ def make_norm(config):
109
+ if config.use_rmsnorm:
110
+ return RMSNorm(config.n_embd, eps=config.layer_norm_epsilon)
111
+ return LayerNorm(config.n_embd, bias=config.bias, eps=config.layer_norm_epsilon)
112
+
113
+
114
+ def attn_res_mix(sources, q, norm):
115
+ """Softmax attention over depth; normed keys and raw values, matching nanoGPT."""
116
+ values = torch.stack(sources)
117
+ logits = torch.einsum("c,sbtc->sbt", q, norm(values))
118
+ return torch.einsum("sbt,sbtc->btc", logits.softmax(dim=0), values)
119
+
120
+
121
+ # ---------------------------------------------------------------------------- rope
122
+ def build_rope_cache(seq_len, head_dim, base=10000.0):
123
+ inv_freq = 1.0 / (base ** (torch.arange(0, head_dim, 2).float() / head_dim))
124
+ angles = torch.outer(torch.arange(seq_len).float(), inv_freq)
125
+ cos = torch.cat([angles, angles], dim=-1).cos()
126
+ sin = torch.cat([angles, angles], dim=-1).sin()
127
+ return cos, sin
128
+
129
+
130
+ def rotate_half(x):
131
+ x1, x2 = x.chunk(2, dim=-1)
132
+ return torch.cat([-x2, x1], dim=-1)
133
+
134
+
135
+ def apply_rope(x, cos, sin):
136
+ # x: (B, n_head, T, head_dim); done in fp32 to match nanoGPT
137
+ seq_len = x.size(2)
138
+ dtype = x.dtype
139
+ x = x.float()
140
+ out = x * cos[:seq_len, :] + rotate_half(x) * sin[:seq_len, :]
141
+ return out.to(dtype)
142
+
143
+
144
+ # ----------------------------------------------------------------------- attention
145
+ class CausalSelfAttention(nn.Module):
146
+ def __init__(self, config):
147
+ super().__init__()
148
+ assert config.n_embd % config.n_head == 0
149
+ self.c_attn = nn.Linear(config.n_embd, 3 * config.n_embd, bias=config.bias)
150
+ self.c_proj = nn.Linear(config.n_embd, config.n_embd, bias=config.bias)
151
+ self.attn_dropout = nn.Dropout(config.dropout)
152
+ self.resid_dropout = nn.Dropout(config.dropout)
153
+ self.n_head = config.n_head
154
+ self.n_embd = config.n_embd
155
+ self.dropout = config.dropout
156
+ self.use_attn_gate = config.use_attn_gate
157
+ self.bidirectional = config.bidirectional
158
+ if self.use_attn_gate:
159
+ self.attn_gate = nn.Linear(config.n_embd, config.n_embd, bias=config.bias)
160
+ self.use_rope = config.use_rope
161
+ if self.use_rope:
162
+ self.head_dim = config.n_embd // config.n_head
163
+ assert self.head_dim % 2 == 0, "RoPE needs an even head_dim"
164
+ self.rope_cache_len = config.block_size
165
+ self.rope_theta = config.rope_theta
166
+ # Build lazily on the real execution device. Transformers 5.x may
167
+ # instantiate remote-code models under a meta-device context; an
168
+ # eagerly-created non-persistent tensor then survives as
169
+ # uninitialized storage because it is absent from the state dict.
170
+ self.register_buffer("rope_cos", None, persistent=False)
171
+ self.register_buffer("rope_sin", None, persistent=False)
172
+
173
+ def _get_rope_cache(self, device):
174
+ if self.rope_cos is None or self.rope_cos.device != device:
175
+ cos, sin = build_rope_cache(
176
+ self.rope_cache_len,
177
+ self.head_dim,
178
+ base=self.rope_theta,
179
+ )
180
+ self.rope_cos = cos.to(device=device)
181
+ self.rope_sin = sin.to(device=device)
182
+ return self.rope_cos, self.rope_sin
183
+
184
+ def forward(self, x, attention_mask=None):
185
+ B, T, C = x.size()
186
+ q, k, v = self.c_attn(x).split(self.n_embd, dim=2)
187
+ k = k.view(B, T, self.n_head, C // self.n_head).transpose(1, 2) # (B, nh, T, hs)
188
+ q = q.view(B, T, self.n_head, C // self.n_head).transpose(1, 2)
189
+ v = v.view(B, T, self.n_head, C // self.n_head).transpose(1, 2)
190
+
191
+ if self.use_rope:
192
+ rope_cos, rope_sin = self._get_rope_cache(q.device)
193
+ q = apply_rope(q, rope_cos, rope_sin)
194
+ k = apply_rope(k, rope_cos, rope_sin)
195
+
196
+ dropout_p = self.dropout if self.training else 0.0
197
+ if attention_mask is None:
198
+ # Dense causal is numerically identical to nanoGPT training. The
199
+ # bidirectional export uses the same weights with no triangular mask.
200
+ y = F.scaled_dot_product_attention(
201
+ q, k, v, attn_mask=None, dropout_p=dropout_p,
202
+ is_causal=not self.bidirectional,
203
+ )
204
+ else:
205
+ keep = attention_mask.to(torch.bool)[:, None, None, :] # (B, 1, 1, T)
206
+ if self.bidirectional:
207
+ attn_mask = keep
208
+ else:
209
+ causal = torch.ones(T, T, dtype=torch.bool, device=x.device).tril()
210
+ attn_mask = causal[None, None, :, :] & keep
211
+ y = F.scaled_dot_product_attention(
212
+ q, k, v, attn_mask=attn_mask, dropout_p=dropout_p, is_causal=False
213
+ )
214
+
215
+ y = y.transpose(1, 2).contiguous().view(B, T, C)
216
+ if self.use_attn_gate:
217
+ y = y * torch.sigmoid(self.attn_gate(x)) # elementwise input-dependent gate on attn output (Qwen)
218
+ y = self.resid_dropout(self.c_proj(y))
219
+ return y
220
+
221
+
222
+ # ----------------------------------------------------------------------------- mlp
223
+ class MLP(nn.Module):
224
+ def __init__(self, config):
225
+ super().__init__()
226
+ self.c_fc = nn.Linear(config.n_embd, 4 * config.n_embd, bias=config.bias)
227
+ self.gelu = nn.GELU()
228
+ self.c_proj = nn.Linear(4 * config.n_embd, config.n_embd, bias=config.bias)
229
+ self.dropout = nn.Dropout(config.dropout)
230
+
231
+ def forward(self, x):
232
+ return self.dropout(self.c_proj(self.gelu(self.c_fc(x))))
233
+
234
+
235
+ class SwiGLU(nn.Module):
236
+ """Gated MLP, SiLU gate (Shazeer 2020). Hidden snapped to a multiple of 64."""
237
+
238
+ def __init__(self, config):
239
+ super().__init__()
240
+ hidden_size = int(config.swiglu_mult * config.n_embd)
241
+ hidden_size = round(hidden_size / 64) * 64
242
+ self.c_gate = nn.Linear(config.n_embd, hidden_size, bias=config.bias)
243
+ self.c_val = nn.Linear(config.n_embd, hidden_size, bias=config.bias)
244
+ self.c_proj = nn.Linear(hidden_size, config.n_embd, bias=config.bias)
245
+ self.dropout = nn.Dropout(config.dropout)
246
+
247
+ def forward(self, input):
248
+ return self.dropout(self.c_proj(F.silu(self.c_gate(input)) * self.c_val(input)))
249
+
250
+
251
+ def make_mlp(config):
252
+ return SwiGLU(config) if config.use_swiglu else MLP(config)
253
+
254
+
255
+ class Block(nn.Module):
256
+ def __init__(self, config, layer_idx):
257
+ super().__init__()
258
+ self.ln_1 = make_norm(config)
259
+ self.attn = CausalSelfAttention(config)
260
+ self.ln_2 = make_norm(config)
261
+ self.mlp = make_mlp(config)
262
+ self.use_attn_res = config.use_attn_res
263
+ if config.use_attn_res:
264
+ self.block_start = (2 * layer_idx) % config.attn_res_block_size == 0
265
+ self.attn_res_q1 = nn.Parameter(torch.zeros(config.n_embd))
266
+ self.attn_res_norm1 = RMSNorm(config.n_embd)
267
+ self.attn_res_q2 = nn.Parameter(torch.zeros(config.n_embd))
268
+ self.attn_res_norm2 = RMSNorm(config.n_embd)
269
+
270
+ def forward(self, x, attention_mask=None):
271
+ x = x + self.attn(self.ln_1(x), attention_mask)
272
+ x = x + self.mlp(self.ln_2(x))
273
+ return x
274
+
275
+ def forward_attn_res(self, blocks, partial, attention_mask=None):
276
+ h = attn_res_mix(blocks + [partial], self.attn_res_q1, self.attn_res_norm1)
277
+ if self.block_start:
278
+ blocks = blocks + [partial]
279
+ partial = None
280
+ attn_out = self.attn(self.ln_1(h), attention_mask)
281
+ partial = attn_out if partial is None else partial + attn_out
282
+ h = attn_res_mix(blocks + [partial], self.attn_res_q2, self.attn_res_norm2)
283
+ partial = partial + self.mlp(self.ln_2(h))
284
+ return blocks, partial
285
+
286
+
287
+ # ---------------------------------------------------------------- shared backbone
288
+ def _build_transformer(config):
289
+ transformer = nn.ModuleDict(
290
+ dict(
291
+ wte=nn.Embedding(config.vocab_size, config.n_embd),
292
+ drop=nn.Dropout(config.dropout),
293
+ h=nn.ModuleList([Block(config, i) for i in range(config.n_layer)]),
294
+ ln_f=make_norm(config),
295
+ )
296
+ )
297
+ if not config.use_rope:
298
+ transformer.wpe = nn.Embedding(config.block_size, config.n_embd)
299
+ return transformer
300
+
301
+
302
+ def _init_attn_res(model, config):
303
+ if not config.use_attn_res:
304
+ return
305
+ size = config.attn_res_block_size
306
+ assert size >= 2 and size % 2 == 0
307
+ assert (2 * config.n_layer) % size == 0
308
+ model.attn_res_qf = nn.Parameter(torch.zeros(config.n_embd))
309
+ model.attn_res_normf = RMSNorm(config.n_embd)
310
+
311
+
312
+ def _transformer_forward(model, transformer, config, input_ids, attention_mask):
313
+ _, t = input_ids.size()
314
+ tok_emb = transformer.wte(input_ids)
315
+ if config.use_rope:
316
+ x = transformer.drop(tok_emb)
317
+ else:
318
+ pos = torch.arange(0, t, dtype=torch.long, device=input_ids.device)
319
+ x = transformer.drop(tok_emb + transformer.wpe(pos))
320
+ if config.use_attn_res:
321
+ blocks, partial = [], x
322
+ for block in transformer.h:
323
+ blocks, partial = block.forward_attn_res(blocks, partial, attention_mask)
324
+ x = attn_res_mix(blocks + [partial], model.attn_res_qf, model.attn_res_normf)
325
+ else:
326
+ for block in transformer.h:
327
+ x = block(x, attention_mask)
328
+ x = transformer.ln_f(x)
329
+ return x
330
+
331
+
332
+ class NanoGPTPreTrainedModel(PreTrainedModel):
333
+ config_class = NanoGPTConfig
334
+ base_model_prefix = "transformer"
335
+ main_input_name = "input_ids"
336
+ _no_split_modules = ["Block"]
337
+
338
+ def _init_weights(self, module):
339
+ if isinstance(module, nn.Linear):
340
+ nn.init.normal_(module.weight, mean=0.0, std=0.02)
341
+ if module.bias is not None:
342
+ nn.init.zeros_(module.bias)
343
+ elif isinstance(module, nn.Embedding):
344
+ nn.init.normal_(module.weight, mean=0.0, std=0.02)
345
+
346
+
347
+ class NanoGPTModel(NanoGPTPreTrainedModel):
348
+ """Backbone returning last_hidden_state (AutoModel target; used by GLUE)."""
349
+
350
+ _keys_to_ignore_on_load_unexpected = [r"lm_head.weight"]
351
+
352
+ def __init__(self, config):
353
+ super().__init__(config)
354
+ self.transformer = _build_transformer(config)
355
+ _init_attn_res(self, config)
356
+ self.post_init()
357
+
358
+ def get_input_embeddings(self):
359
+ return self.transformer.wte
360
+
361
+ def set_input_embeddings(self, value):
362
+ self.transformer.wte = value
363
+
364
+ def forward(self, input_ids=None, attention_mask=None, **kwargs):
365
+ x = _transformer_forward(self, self.transformer, self.config, input_ids, attention_mask)
366
+ return BaseModelOutput(last_hidden_state=x)
367
+
368
+
369
+ class NanoGPTForCausalLM(NanoGPTPreTrainedModel, GenerationMixin):
370
+ """LM-head model (AutoModelForCausalLM target; used by zero-shot ranking)."""
371
+
372
+ # Transformers 4.x expects a list of tied output keys, while 5.x changed
373
+ # this class attribute to an output->input mapping. Keep the published
374
+ # remote-code model loadable in both the official BabyLM 4.51 environment
375
+ # and current Transformers releases.
376
+ _tied_weights_keys = (
377
+ {"lm_head.weight": "transformer.wte.weight"}
378
+ if int(transformers.__version__.split(".", 1)[0]) >= 5
379
+ else ["lm_head.weight"]
380
+ )
381
+
382
+ def __init__(self, config):
383
+ super().__init__(config)
384
+ self.transformer = _build_transformer(config)
385
+ self.lm_head = nn.Linear(config.n_embd, config.vocab_size, bias=False)
386
+ _init_attn_res(self, config)
387
+ self.post_init()
388
+
389
+ def get_input_embeddings(self):
390
+ return self.transformer.wte
391
+
392
+ def set_input_embeddings(self, value):
393
+ self.transformer.wte = value
394
+
395
+ def get_output_embeddings(self):
396
+ return self.lm_head
397
+
398
+ def set_output_embeddings(self, value):
399
+ self.lm_head = value
400
+
401
+ def forward(self, input_ids=None, attention_mask=None, labels=None, **kwargs):
402
+ x = _transformer_forward(self, self.transformer, self.config, input_ids, attention_mask)
403
+ logits = self.lm_head(x)
404
+ loss = None
405
+ if labels is not None:
406
+ loss = F.cross_entropy(
407
+ logits[..., :-1, :].reshape(-1, logits.size(-1)),
408
+ labels[..., 1:].reshape(-1),
409
+ ignore_index=-1,
410
+ )
411
+ return CausalLMOutput(loss=loss, logits=logits)
412
+
413
+
414
+ class NanoGPTForMaskedLM(NanoGPTForCausalLM):
415
+ """Same LM head, with unshifted MLM loss for the bidirectional export."""
416
+
417
+ def forward(self, input_ids=None, attention_mask=None, labels=None, **kwargs):
418
+ x = _transformer_forward(self, self.transformer, self.config, input_ids, attention_mask)
419
+ logits = self.lm_head(x)
420
+ loss = None
421
+ if labels is not None:
422
+ loss = F.cross_entropy(
423
+ logits.reshape(-1, logits.size(-1)),
424
+ labels.reshape(-1),
425
+ ignore_index=-100,
426
+ )
427
+ return MaskedLMOutput(loss=loss, logits=logits)
special_tokens_map.json ADDED
@@ -0,0 +1,4 @@
 
 
 
 
 
1
+ {
2
+ "eos_token": "<|endoftext|>",
3
+ "pad_token": "<|endoftext|>"
4
+ }
tokenizer.json ADDED
The diff for this file is too large to render. See raw diff
 
tokenizer_config.json ADDED
@@ -0,0 +1,19 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ {
2
+ "add_prefix_space": true,
3
+ "added_tokens_decoder": {
4
+ "0": {
5
+ "content": "<|endoftext|>",
6
+ "lstrip": false,
7
+ "normalized": false,
8
+ "rstrip": false,
9
+ "single_word": false,
10
+ "special": true
11
+ }
12
+ },
13
+ "clean_up_tokenization_spaces": false,
14
+ "eos_token": "<|endoftext|>",
15
+ "extra_special_tokens": {},
16
+ "model_max_length": 1000000000000000019884624838656,
17
+ "pad_token": "<|endoftext|>",
18
+ "tokenizer_class": "PreTrainedTokenizer"
19
+ }