Text Generation
Transformers
Safetensors
English
cma
custom_code
causal-lm
small-language-model
base-model
byte-level
Instructions to use User01110/CMA-1M-Mini with libraries, inference providers, notebooks, and local apps. Follow these links to get started.
- Libraries
- Transformers
How to use User01110/CMA-1M-Mini with Transformers:
# Use a pipeline as a high-level helper from transformers import pipeline pipe = pipeline("text-generation", model="User01110/CMA-1M-Mini", trust_remote_code=True)# Load model directly from transformers import AutoModelForCausalLM model = AutoModelForCausalLM.from_pretrained("User01110/CMA-1M-Mini", trust_remote_code=True, device_map="auto") - Notebooks
- Google Colab
- Kaggle
- Local Apps Settings
- vLLM
How to use User01110/CMA-1M-Mini with vLLM:
Install from pip and serve model
# Install vLLM from pip: pip install vllm # Start the vLLM server: vllm serve "User01110/CMA-1M-Mini" # Call the server using curl (OpenAI-compatible API): curl -X POST "http://localhost:8000/v1/completions" \ -H "Content-Type: application/json" \ --data '{ "model": "User01110/CMA-1M-Mini", "prompt": "Once upon a time,", "max_tokens": 512, "temperature": 0.5 }'Use Docker
docker model run hf.co/User01110/CMA-1M-Mini
- SGLang
How to use User01110/CMA-1M-Mini with SGLang:
Install from pip and serve model
# Install SGLang from pip: pip install sglang # Start the SGLang server: python3 -m sglang.launch_server \ --model-path "User01110/CMA-1M-Mini" \ --host 0.0.0.0 \ --port 30000 # Call the server using curl (OpenAI-compatible API): curl -X POST "http://localhost:30000/v1/completions" \ -H "Content-Type: application/json" \ --data '{ "model": "User01110/CMA-1M-Mini", "prompt": "Once upon a time,", "max_tokens": 512, "temperature": 0.5 }'Use Docker images
docker run --gpus all \ --shm-size 32g \ -p 30000:30000 \ -v ~/.cache/huggingface:/root/.cache/huggingface \ --env "HF_TOKEN=<secret>" \ --ipc=host \ lmsysorg/sglang:latest \ python3 -m sglang.launch_server \ --model-path "User01110/CMA-1M-Mini" \ --host 0.0.0.0 \ --port 30000 # Call the server using curl (OpenAI-compatible API): curl -X POST "http://localhost:30000/v1/completions" \ -H "Content-Type: application/json" \ --data '{ "model": "User01110/CMA-1M-Mini", "prompt": "Once upon a time,", "max_tokens": 512, "temperature": 0.5 }' - Docker Model Runner
How to use User01110/CMA-1M-Mini with Docker Model Runner:
docker model run hf.co/User01110/CMA-1M-Mini
Commit ·
564ee09
0
Parent(s):
CMA-1M Mini release
Browse files- .gitattributes +35 -0
- README.md +266 -0
- benchmark_results.json +52 -0
- config.json +31 -0
- generation_config.json +7 -0
- model.safetensors +3 -0
- modeling_cma.py +375 -0
- tokenizer.json +377 -0
- tokenizer_config.json +10 -0
- training_config.json +54 -0
.gitattributes
ADDED
|
@@ -0,0 +1,35 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
*.7z filter=lfs diff=lfs merge=lfs -text
|
| 2 |
+
*.arrow filter=lfs diff=lfs merge=lfs -text
|
| 3 |
+
*.bin filter=lfs diff=lfs merge=lfs -text
|
| 4 |
+
*.bz2 filter=lfs diff=lfs merge=lfs -text
|
| 5 |
+
*.ckpt filter=lfs diff=lfs merge=lfs -text
|
| 6 |
+
*.ftz filter=lfs diff=lfs merge=lfs -text
|
| 7 |
+
*.gz filter=lfs diff=lfs merge=lfs -text
|
| 8 |
+
*.h5 filter=lfs diff=lfs merge=lfs -text
|
| 9 |
+
*.joblib filter=lfs diff=lfs merge=lfs -text
|
| 10 |
+
*.lfs.* filter=lfs diff=lfs merge=lfs -text
|
| 11 |
+
*.mlmodel filter=lfs diff=lfs merge=lfs -text
|
| 12 |
+
*.model filter=lfs diff=lfs merge=lfs -text
|
| 13 |
+
*.msgpack filter=lfs diff=lfs merge=lfs -text
|
| 14 |
+
*.npy filter=lfs diff=lfs merge=lfs -text
|
| 15 |
+
*.npz filter=lfs diff=lfs merge=lfs -text
|
| 16 |
+
*.onnx filter=lfs diff=lfs merge=lfs -text
|
| 17 |
+
*.ot filter=lfs diff=lfs merge=lfs -text
|
| 18 |
+
*.parquet filter=lfs diff=lfs merge=lfs -text
|
| 19 |
+
*.pb filter=lfs diff=lfs merge=lfs -text
|
| 20 |
+
*.pickle filter=lfs diff=lfs merge=lfs -text
|
| 21 |
+
*.pkl filter=lfs diff=lfs merge=lfs -text
|
| 22 |
+
*.pt filter=lfs diff=lfs merge=lfs -text
|
| 23 |
+
*.pth filter=lfs diff=lfs merge=lfs -text
|
| 24 |
+
*.rar filter=lfs diff=lfs merge=lfs -text
|
| 25 |
+
*.safetensors filter=lfs diff=lfs merge=lfs -text
|
| 26 |
+
saved_model/**/* filter=lfs diff=lfs merge=lfs -text
|
| 27 |
+
*.tar.* filter=lfs diff=lfs merge=lfs -text
|
| 28 |
+
*.tar filter=lfs diff=lfs merge=lfs -text
|
| 29 |
+
*.tflite filter=lfs diff=lfs merge=lfs -text
|
| 30 |
+
*.tgz filter=lfs diff=lfs merge=lfs -text
|
| 31 |
+
*.wasm filter=lfs diff=lfs merge=lfs -text
|
| 32 |
+
*.xz filter=lfs diff=lfs merge=lfs -text
|
| 33 |
+
*.zip filter=lfs diff=lfs merge=lfs -text
|
| 34 |
+
*.zst filter=lfs diff=lfs merge=lfs -text
|
| 35 |
+
*tfevents* filter=lfs diff=lfs merge=lfs -text
|
README.md
ADDED
|
@@ -0,0 +1,266 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
---
|
| 2 |
+
library_name: transformers
|
| 3 |
+
pipeline_tag: text-generation
|
| 4 |
+
language:
|
| 5 |
+
- en
|
| 6 |
+
tags:
|
| 7 |
+
- custom_code
|
| 8 |
+
- causal-lm
|
| 9 |
+
- cma
|
| 10 |
+
- small-language-model
|
| 11 |
+
- base-model
|
| 12 |
+
- byte-level
|
| 13 |
+
- safetensors
|
| 14 |
+
datasets:
|
| 15 |
+
- HuggingFaceFW/fineweb_edu_100BT-shuffled
|
| 16 |
+
- mlfoundations/dclm-baseline-1.0-parquet
|
| 17 |
+
- HuggingFaceTB/dclm-edu
|
| 18 |
+
- HuggingFaceTB/smollm-corpus
|
| 19 |
+
- HuggingFaceTB/finemath
|
| 20 |
+
widget:
|
| 21 |
+
- text: "The process of photosynthesis"
|
| 22 |
+
example_title: Science
|
| 23 |
+
- text: "Once upon a time, in a quiet village"
|
| 24 |
+
example_title: Story
|
| 25 |
+
- text: "A computer program is"
|
| 26 |
+
example_title: Technology
|
| 27 |
+
---
|
| 28 |
+
|
| 29 |
+
# CMA-1M Mini
|
| 30 |
+
|
| 31 |
+
> [!WARNING]
|
| 32 |
+
> **Experimental research model ? generations are fully unreliable.** CMA-1M Mini
|
| 33 |
+
> exists only as a test bed for understanding how Channel-Mixing Attention works,
|
| 34 |
+
> where it helps, and where its limits and failure modes appear. Do not treat its
|
| 35 |
+
> output as factual, safe, coherent, or suitable for production or real-world
|
| 36 |
+
> decisions.
|
| 37 |
+
|
| 38 |
+
CMA-1M Mini is a **958,692-parameter base causal language model** built to test
|
| 39 |
+
Channel-Mixing Attention (CMA) at very small scale. It combines causal grouped-query
|
| 40 |
+
token attention with content-dependent mixing across each token's hidden channels.
|
| 41 |
+
The model uses a lossless byte-level tokenizer, tied embeddings, native BF16 weights,
|
| 42 |
+
and a 2,048-token context window.
|
| 43 |
+
|
| 44 |
+
| | |
|
| 45 |
+
|---|---|
|
| 46 |
+
| Parameters | 958,692 |
|
| 47 |
+
| Architecture | Decoder-only CMA causal LM |
|
| 48 |
+
| Context | 2,048 byte tokens |
|
| 49 |
+
| Vocabulary | 260 tokens: 256 bytes + PAD/BOS/EOS/UNK |
|
| 50 |
+
| Weight format | BF16 Safetensors |
|
| 51 |
+
| Intended interface | Plain-text completion |
|
| 52 |
+
|
| 53 |
+
> This is a pretrained base model, not a chat or instruction model. Give it ordinary
|
| 54 |
+
> text to continue; no chat template or role markers are required.
|
| 55 |
+
|
| 56 |
+
## Quick start
|
| 57 |
+
|
| 58 |
+
The architecture is provided as custom Transformers code, so
|
| 59 |
+
`trust_remote_code=True` is required. PyTorch 2.5 or newer is recommended.
|
| 60 |
+
|
| 61 |
+
```python
|
| 62 |
+
import torch
|
| 63 |
+
from transformers import AutoModelForCausalLM, AutoTokenizer
|
| 64 |
+
|
| 65 |
+
repo_id = "User01110/CMA-1M-Mini"
|
| 66 |
+
device = "cuda" if torch.cuda.is_available() else "cpu"
|
| 67 |
+
dtype = (
|
| 68 |
+
torch.bfloat16
|
| 69 |
+
if device == "cuda" and torch.cuda.is_bf16_supported()
|
| 70 |
+
else torch.float32
|
| 71 |
+
)
|
| 72 |
+
|
| 73 |
+
tokenizer = AutoTokenizer.from_pretrained(
|
| 74 |
+
repo_id,
|
| 75 |
+
trust_remote_code=True,
|
| 76 |
+
)
|
| 77 |
+
model = AutoModelForCausalLM.from_pretrained(
|
| 78 |
+
repo_id,
|
| 79 |
+
trust_remote_code=True,
|
| 80 |
+
dtype=dtype,
|
| 81 |
+
).to(device).eval()
|
| 82 |
+
|
| 83 |
+
prompt = "The process of photosynthesis"
|
| 84 |
+
inputs = tokenizer(prompt, return_tensors="pt")
|
| 85 |
+
inputs = {name: tensor.to(device) for name, tensor in inputs.items()}
|
| 86 |
+
|
| 87 |
+
with torch.inference_mode():
|
| 88 |
+
output = model.generate(
|
| 89 |
+
**inputs,
|
| 90 |
+
max_new_tokens=96,
|
| 91 |
+
do_sample=False,
|
| 92 |
+
)
|
| 93 |
+
|
| 94 |
+
print(tokenizer.decode(output[0], skip_special_tokens=True))
|
| 95 |
+
```
|
| 96 |
+
|
| 97 |
+
The tokenizer automatically prepends `<bos>` during normal encoding. It does not
|
| 98 |
+
append `<eos>` to a prompt; generation ends when the model emits EOS or reaches the
|
| 99 |
+
requested length. If you deliberately use `add_special_tokens=False`, prepend BOS
|
| 100 |
+
yourself.
|
| 101 |
+
|
| 102 |
+
## Generation options
|
| 103 |
+
|
| 104 |
+
The included generation defaults are deterministic decoding with a repetition
|
| 105 |
+
penalty of 1.2. Override them per request as needed.
|
| 106 |
+
|
| 107 |
+
| Goal | Recommended settings |
|
| 108 |
+
|---|---|
|
| 109 |
+
| Reproducible completion | `do_sample=False` |
|
| 110 |
+
| Balanced sampling | `do_sample=True, temperature=0.8, top_p=0.9, top_k=50` |
|
| 111 |
+
| More varied text | `do_sample=True, temperature=1.0, top_p=0.95` |
|
| 112 |
+
| Reduce loops | `repetition_penalty=1.1` to `1.2` |
|
| 113 |
+
| Beam search | `do_sample=False, num_beams=4` |
|
| 114 |
+
| Output length | Set `max_new_tokens`; keep prompt + output within 2,048 tokens |
|
| 115 |
+
|
| 116 |
+
Example with sampling:
|
| 117 |
+
|
| 118 |
+
```python
|
| 119 |
+
with torch.inference_mode():
|
| 120 |
+
output = model.generate(
|
| 121 |
+
**inputs,
|
| 122 |
+
max_new_tokens=128,
|
| 123 |
+
do_sample=True,
|
| 124 |
+
temperature=0.8,
|
| 125 |
+
top_p=0.9,
|
| 126 |
+
top_k=50,
|
| 127 |
+
repetition_penalty=1.15,
|
| 128 |
+
)
|
| 129 |
+
```
|
| 130 |
+
|
| 131 |
+
For the high-level pipeline API:
|
| 132 |
+
|
| 133 |
+
```python
|
| 134 |
+
import torch
|
| 135 |
+
from transformers import pipeline
|
| 136 |
+
|
| 137 |
+
generator = pipeline(
|
| 138 |
+
"text-generation",
|
| 139 |
+
model="User01110/CMA-1M-Mini",
|
| 140 |
+
tokenizer="User01110/CMA-1M-Mini",
|
| 141 |
+
trust_remote_code=True,
|
| 142 |
+
dtype="auto",
|
| 143 |
+
device=0 if torch.cuda.is_available() else -1,
|
| 144 |
+
)
|
| 145 |
+
|
| 146 |
+
result = generator(
|
| 147 |
+
"In a distant future,",
|
| 148 |
+
max_new_tokens=80,
|
| 149 |
+
do_sample=True,
|
| 150 |
+
temperature=0.8,
|
| 151 |
+
top_p=0.9,
|
| 152 |
+
)
|
| 153 |
+
print(result[0]["generated_text"])
|
| 154 |
+
```
|
| 155 |
+
|
| 156 |
+
To score text rather than generate it:
|
| 157 |
+
|
| 158 |
+
```python
|
| 159 |
+
encoded = tokenizer("CMA models text one byte at a time.", return_tensors="pt")
|
| 160 |
+
encoded = {name: tensor.to(device) for name, tensor in encoded.items()}
|
| 161 |
+
|
| 162 |
+
with torch.inference_mode():
|
| 163 |
+
result = model(**encoded, labels=encoded["input_ids"])
|
| 164 |
+
|
| 165 |
+
print(float(result.loss))
|
| 166 |
+
```
|
| 167 |
+
|
| 168 |
+
## Tokenizer and context
|
| 169 |
+
|
| 170 |
+
- Every UTF-8 byte has a token, so ordinary text cannot become out-of-vocabulary.
|
| 171 |
+
- The four control tokens are `<pad>` (0), `<bos>` (1), `<eos>` (2), and `<unk>` (3).
|
| 172 |
+
- The context limit is 2,048 **byte tokens**, not 2,048 words or subword tokens.
|
| 173 |
+
- Non-ASCII text usually consumes multiple byte tokens per character.
|
| 174 |
+
- For long inputs, explicitly keep the most recent 2,048 tokens rather than relying
|
| 175 |
+
on implicit truncation.
|
| 176 |
+
- The tokenizer has no arithmetic-specific splitting, chat template, or hidden prompt
|
| 177 |
+
transformation.
|
| 178 |
+
|
| 179 |
+
## Architecture
|
| 180 |
+
|
| 181 |
+
| Component | Configuration |
|
| 182 |
+
|---|---|
|
| 183 |
+
| Hidden width / layers | 128 / 6 |
|
| 184 |
+
| Token attention | 4 query heads, 2 key-value heads |
|
| 185 |
+
| Position encoding | Contiguous-half rotary embeddings, no scaling |
|
| 186 |
+
| CMA layout | 8 channel slots x 16 channels |
|
| 187 |
+
| CMA routing | 2 heads, expansion 2, content-dependent softmax mixing |
|
| 188 |
+
| CMA initialization | 90% diagonal routing prior with a dense base path |
|
| 189 |
+
| Feed-forward gate | SiLU-gated routed values |
|
| 190 |
+
| Normalization | RMSNorm |
|
| 191 |
+
| Embeddings | Input and output weights tied |
|
| 192 |
+
| Attention runtime | Native PyTorch scaled-dot-product attention |
|
| 193 |
+
|
| 194 |
+
For each token, CMA projects dense values, reshapes them into channel slots, and
|
| 195 |
+
learns a softmax mixing matrix between those slots. A bounded learned coefficient
|
| 196 |
+
controls the routed difference from the dense base value, so routing enriches rather
|
| 197 |
+
than replaces the fallback path.
|
| 198 |
+
|
| 199 |
+
The exported generation implementation does not maintain a KV cache. This keeps the
|
| 200 |
+
custom model compact and straightforward, but long autoregressive generations will
|
| 201 |
+
recompute the active context and are slower than cached generation.
|
| 202 |
+
|
| 203 |
+
## Training data
|
| 204 |
+
|
| 205 |
+
The model was pretrained as a general causal language model on the following mixture.
|
| 206 |
+
Percentages describe the trained-token mixture.
|
| 207 |
+
|
| 208 |
+
| Source | Share |
|
| 209 |
+
|---|---:|
|
| 210 |
+
| [FineWeb-Edu 100BT](https://huggingface.co/datasets/HuggingFaceFW/fineweb_edu_100BT-shuffled) | 45% |
|
| 211 |
+
| [DCLM-Baseline 1.0](https://huggingface.co/datasets/mlfoundations/dclm-baseline-1.0-parquet) | 25% |
|
| 212 |
+
| [DCLM-Edu](https://huggingface.co/datasets/HuggingFaceTB/dclm-edu) | 10% |
|
| 213 |
+
| [Cosmopedia v2](https://huggingface.co/datasets/HuggingFaceTB/smollm-corpus) | 10% |
|
| 214 |
+
| [FineMath 4+](https://huggingface.co/datasets/HuggingFaceTB/finemath) | 10% |
|
| 215 |
+
|
| 216 |
+
No benchmark-specific prompts, task detectors, arithmetic vocabulary, or
|
| 217 |
+
inference-time answer rules are built into the model.
|
| 218 |
+
|
| 219 |
+
## Evaluation
|
| 220 |
+
|
| 221 |
+
Evaluation is zero-shot. The four lm-eval tasks use normalized accuracy when
|
| 222 |
+
provided by lm-eval 0.4.12. ArithMark-2 uses raw continuation log-likelihood sums.
|
| 223 |
+
Weights are evaluated in BF16 with FP32 likelihood softmax and an automatic BOS
|
| 224 |
+
prefix.
|
| 225 |
+
|
| 226 |
+
| Benchmark | Accuracy |
|
| 227 |
+
|---|---:|
|
| 228 |
+
| HellaSwag | 29.35% |
|
| 229 |
+
| ARC-Easy | 29.29% |
|
| 230 |
+
| ARC-Challenge | 21.76% |
|
| 231 |
+
| PIQA | 54.62% |
|
| 232 |
+
| ArithMark-2 | 27.44% |
|
| 233 |
+
| **Open SLM Leaderboard-style average** | **34.23%** |
|
| 234 |
+
|
| 235 |
+
The combined score is
|
| 236 |
+
`(HellaSwag + mean(ARC-Easy, ARC-Challenge) + PIQA + ArithMark-2) / 4`.
|
| 237 |
+
This is a report-only reproduction of the leaderboard formula, not an official
|
| 238 |
+
leaderboard submission. WikiText-103 normalized validation BPB is **1.6974**.
|
| 239 |
+
Exact machine-readable results are available in
|
| 240 |
+
[`benchmark_results.json`](./benchmark_results.json).
|
| 241 |
+
|
| 242 |
+
## Intended use and limitations
|
| 243 |
+
|
| 244 |
+
CMA-1M Mini is intended for architecture research, educational experiments,
|
| 245 |
+
lightweight language-model tooling, and controlled comparisons at tiny scale.
|
| 246 |
+
|
| 247 |
+
- At fewer than one million parameters, generations are short-range and frequently
|
| 248 |
+
incoherent; the model should not be treated as a knowledge source.
|
| 249 |
+
- It is not instruction-tuned, conversationally aligned, tool-using, or safety-tuned.
|
| 250 |
+
- Training data is predominantly English even though byte tokenization can represent
|
| 251 |
+
any UTF-8 text.
|
| 252 |
+
- Outputs may reproduce biases, inaccuracies, or undesirable patterns from public
|
| 253 |
+
training corpora.
|
| 254 |
+
- Do not use it for consequential medical, legal, financial, or safety decisions.
|
| 255 |
+
- Loading custom code executes files from the repository. Review the code or pin a
|
| 256 |
+
trusted revision in security-sensitive environments.
|
| 257 |
+
|
| 258 |
+
## Repository contents
|
| 259 |
+
|
| 260 |
+
- `model.safetensors` — BF16 model weights
|
| 261 |
+
- `modeling_cma.py` — Transformers-compatible CMA implementation
|
| 262 |
+
- `config.json` and `generation_config.json` — architecture and decoding defaults
|
| 263 |
+
- `tokenizer.json` and `tokenizer_config.json` — deterministic byte tokenizer
|
| 264 |
+
- `benchmark_results.json` — exact evaluation metrics and protocol metadata
|
| 265 |
+
- `training_config.json` — reproducibility configuration
|
| 266 |
+
|
benchmark_results.json
ADDED
|
@@ -0,0 +1,52 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
{
|
| 2 |
+
"step": 12000,
|
| 3 |
+
"parameters": 958692,
|
| 4 |
+
"lm_eval_version": "0.4.12",
|
| 5 |
+
"evaluation_dtype": "bfloat16",
|
| 6 |
+
"softmax_dtype": "float32",
|
| 7 |
+
"evaluation_autocast": false,
|
| 8 |
+
"num_fewshot": 0,
|
| 9 |
+
"bos_prefix": true,
|
| 10 |
+
"leaderboard_accuracy": {
|
| 11 |
+
"arc_easy": 0.29292929292929293,
|
| 12 |
+
"arc_challenge": 0.2175767918088737,
|
| 13 |
+
"hellaswag": 0.29346743676558457,
|
| 14 |
+
"piqa": 0.5462459194776932
|
| 15 |
+
},
|
| 16 |
+
"lm_eval_metric_policy": "acc_norm when available, otherwise acc",
|
| 17 |
+
"selection_metric": "validation.normalized_bpb (lower is better)",
|
| 18 |
+
"arithmark_2.0": {
|
| 19 |
+
"acc": 0.2744,
|
| 20 |
+
"correct": 686,
|
| 21 |
+
"total": 2500,
|
| 22 |
+
"by_operator_count": {
|
| 23 |
+
"1": {
|
| 24 |
+
"acc": 0.2552,
|
| 25 |
+
"correct": 319,
|
| 26 |
+
"total": 1250
|
| 27 |
+
},
|
| 28 |
+
"2": {
|
| 29 |
+
"acc": 0.30666666666666664,
|
| 30 |
+
"correct": 230,
|
| 31 |
+
"total": 750
|
| 32 |
+
},
|
| 33 |
+
"3": {
|
| 34 |
+
"acc": 0.274,
|
| 35 |
+
"correct": 137,
|
| 36 |
+
"total": 500
|
| 37 |
+
}
|
| 38 |
+
}
|
| 39 |
+
},
|
| 40 |
+
"arc_average": 0.2552530423690833,
|
| 41 |
+
"open_slm_leaderboard_average": 0.34234159965309024,
|
| 42 |
+
"average_formula": "(hellaswag + mean(arc_easy, arc_challenge) + piqa + arithmark_2.0) / 4",
|
| 43 |
+
"validation": {
|
| 44 |
+
"loss": 1.1765458586014317,
|
| 45 |
+
"perplexity": 3.2431525260156,
|
| 46 |
+
"normalized_bpb": 1.6973968755827331,
|
| 47 |
+
"tokens": 1144831,
|
| 48 |
+
"normalized_utf8_bytes": 1144831,
|
| 49 |
+
"window": 2048,
|
| 50 |
+
"stride": 1024
|
| 51 |
+
}
|
| 52 |
+
}
|
config.json
ADDED
|
@@ -0,0 +1,31 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
{
|
| 2 |
+
"architectures": [
|
| 3 |
+
"CMAForCausalLM"
|
| 4 |
+
],
|
| 5 |
+
"auto_map": {
|
| 6 |
+
"AutoConfig": "modeling_cma.CMAConfig",
|
| 7 |
+
"AutoModelForCausalLM": "modeling_cma.CMAForCausalLM"
|
| 8 |
+
},
|
| 9 |
+
"model_type": "cma",
|
| 10 |
+
"vocab_size": 260,
|
| 11 |
+
"seq_len": 2048,
|
| 12 |
+
"max_position_embeddings": 2048,
|
| 13 |
+
"n_positions": 2048,
|
| 14 |
+
"n_ctx": 2048,
|
| 15 |
+
"d_model": 128,
|
| 16 |
+
"n_layers": 6,
|
| 17 |
+
"n_heads": 4,
|
| 18 |
+
"n_kv_heads": 2,
|
| 19 |
+
"chunk": 16,
|
| 20 |
+
"cma_heads": 2,
|
| 21 |
+
"expand": 2,
|
| 22 |
+
"cma_identity_prob": 0.9,
|
| 23 |
+
"bos_token_id": 1,
|
| 24 |
+
"eos_token_id": 2,
|
| 25 |
+
"pad_token_id": 0,
|
| 26 |
+
"tie_word_embeddings": true,
|
| 27 |
+
"safe_serialization": true,
|
| 28 |
+
"minimum_torch_version": "2.5",
|
| 29 |
+
"torch_dtype": "bfloat16",
|
| 30 |
+
"transformers_version": "5.13.0"
|
| 31 |
+
}
|
generation_config.json
ADDED
|
@@ -0,0 +1,7 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
{
|
| 2 |
+
"bos_token_id": 1,
|
| 3 |
+
"eos_token_id": 2,
|
| 4 |
+
"pad_token_id": 0,
|
| 5 |
+
"do_sample": false,
|
| 6 |
+
"repetition_penalty": 1.2
|
| 7 |
+
}
|
model.safetensors
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:79ccdc8674a3bb2dd32c3d6eba6fffec2ed1e4e55254ad2ebf8dda1c42bf2c4b
|
| 3 |
+
size 2127320
|
modeling_cma.py
ADDED
|
@@ -0,0 +1,375 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
|
| 2 |
+
import math
|
| 3 |
+
|
| 4 |
+
import torch
|
| 5 |
+
import torch.nn as nn
|
| 6 |
+
import torch.nn.functional as F
|
| 7 |
+
# CMA is text-only. Disable Transformers' optional vision backend before it
|
| 8 |
+
# imports PreTrainedModel: some cloud images expose a system torchvision built
|
| 9 |
+
# against a different PyTorch, which otherwise crashes on torchvision::nms.
|
| 10 |
+
import transformers as _transformers
|
| 11 |
+
import transformers.utils as _transformers_utils
|
| 12 |
+
from transformers.utils import import_utils as _transformers_import_utils
|
| 13 |
+
|
| 14 |
+
|
| 15 |
+
def _cma_torchvision_unavailable():
|
| 16 |
+
return False
|
| 17 |
+
|
| 18 |
+
|
| 19 |
+
_transformers_import_utils._torchvision_available = False
|
| 20 |
+
_transformers_import_utils.is_torchvision_available = _cma_torchvision_unavailable
|
| 21 |
+
_transformers_import_utils.is_torchvision_v2_available = _cma_torchvision_unavailable
|
| 22 |
+
_transformers_utils.is_torchvision_available = _cma_torchvision_unavailable
|
| 23 |
+
_transformers_utils.is_torchvision_v2_available = _cma_torchvision_unavailable
|
| 24 |
+
_transformers.is_torchvision_available = _cma_torchvision_unavailable
|
| 25 |
+
_transformers.is_torchvision_v2_available = _cma_torchvision_unavailable
|
| 26 |
+
try:
|
| 27 |
+
from transformers import GenerationMixin
|
| 28 |
+
except ImportError:
|
| 29 |
+
from transformers.generation import GenerationMixin
|
| 30 |
+
from transformers import PretrainedConfig, PreTrainedModel
|
| 31 |
+
from transformers.modeling_outputs import CausalLMOutputWithPast
|
| 32 |
+
|
| 33 |
+
|
| 34 |
+
class CMAConfig(PretrainedConfig):
|
| 35 |
+
model_type = "cma"
|
| 36 |
+
|
| 37 |
+
def __init__(
|
| 38 |
+
self,
|
| 39 |
+
vocab_size=260,
|
| 40 |
+
seq_len=2048,
|
| 41 |
+
d_model=128,
|
| 42 |
+
n_layers=6,
|
| 43 |
+
n_heads=4,
|
| 44 |
+
n_kv_heads=2,
|
| 45 |
+
chunk=16,
|
| 46 |
+
cma_heads=2,
|
| 47 |
+
expand=2,
|
| 48 |
+
cma_identity_prob=0.90,
|
| 49 |
+
max_position_embeddings=None,
|
| 50 |
+
n_positions=None,
|
| 51 |
+
n_ctx=None,
|
| 52 |
+
**kwargs,
|
| 53 |
+
):
|
| 54 |
+
super().__init__(**kwargs)
|
| 55 |
+
self.vocab_size = vocab_size
|
| 56 |
+
self.seq_len = seq_len
|
| 57 |
+
self.max_position_embeddings = max_position_embeddings or seq_len
|
| 58 |
+
self.n_positions = n_positions or self.max_position_embeddings
|
| 59 |
+
self.n_ctx = n_ctx or self.max_position_embeddings
|
| 60 |
+
self.d_model = d_model
|
| 61 |
+
self.n_layers = n_layers
|
| 62 |
+
self.n_heads = n_heads
|
| 63 |
+
self.n_kv_heads = n_kv_heads
|
| 64 |
+
self.chunk = chunk
|
| 65 |
+
self.cma_heads = cma_heads
|
| 66 |
+
self.expand = expand
|
| 67 |
+
self.cma_identity_prob = cma_identity_prob
|
| 68 |
+
|
| 69 |
+
|
| 70 |
+
class RMSNorm(nn.Module):
|
| 71 |
+
def __init__(self, d):
|
| 72 |
+
super().__init__()
|
| 73 |
+
self.w = nn.Parameter(torch.ones(d))
|
| 74 |
+
|
| 75 |
+
def forward(self, x):
|
| 76 |
+
return F.rms_norm(
|
| 77 |
+
x, (x.shape[-1],), self.w.to(dtype=x.dtype), eps=1e-6
|
| 78 |
+
)
|
| 79 |
+
|
| 80 |
+
|
| 81 |
+
def rope_cache(seq_len, head_dim, device, base=10000.0):
|
| 82 |
+
inv = 1.0 / (
|
| 83 |
+
base ** (torch.arange(0, head_dim, 2, device=device).float() / head_dim)
|
| 84 |
+
)
|
| 85 |
+
t = torch.arange(seq_len, device=device).float()
|
| 86 |
+
freqs = torch.outer(t, inv)
|
| 87 |
+
return torch.cos(freqs), torch.sin(freqs)
|
| 88 |
+
|
| 89 |
+
|
| 90 |
+
def apply_rope(x, cos, sin):
|
| 91 |
+
x1, x2 = x.chunk(2, dim=-1)
|
| 92 |
+
return torch.cat([x1 * cos - x2 * sin, x2 * cos + x1 * sin], dim=-1)
|
| 93 |
+
|
| 94 |
+
|
| 95 |
+
class TokenAttention(nn.Module):
|
| 96 |
+
def __init__(self, d, n_heads, n_kv_heads):
|
| 97 |
+
super().__init__()
|
| 98 |
+
if d % n_heads or n_heads % n_kv_heads:
|
| 99 |
+
raise ValueError("d_model % n_heads and n_heads % n_kv_heads must be zero.")
|
| 100 |
+
self.h, self.kv_h, self.hd = n_heads, n_kv_heads, d // n_heads
|
| 101 |
+
self.q = nn.Linear(d, d, bias=False)
|
| 102 |
+
self.k = nn.Linear(d, n_kv_heads * self.hd, bias=False)
|
| 103 |
+
self.v = nn.Linear(d, n_kv_heads * self.hd, bias=False)
|
| 104 |
+
self.o = nn.Linear(d, d, bias=False)
|
| 105 |
+
self.qn, self.kn = RMSNorm(self.hd), RMSNorm(self.hd)
|
| 106 |
+
|
| 107 |
+
def forward(self, x, cos, sin):
|
| 108 |
+
B, T, d = x.shape
|
| 109 |
+
q = self.q(x).view(B, T, self.h, self.hd).transpose(1, 2)
|
| 110 |
+
k = self.k(x).view(B, T, self.kv_h, self.hd).transpose(1, 2)
|
| 111 |
+
v = self.v(x).view(B, T, self.kv_h, self.hd).transpose(1, 2)
|
| 112 |
+
q, k = self.qn(q), self.kn(k)
|
| 113 |
+
q, k = apply_rope(q, cos, sin), apply_rope(k, cos, sin)
|
| 114 |
+
# Native GQA keeps compact K/V heads and lets SDPA select a fused CUDA
|
| 115 |
+
# implementation without materializing repeated K/V activations.
|
| 116 |
+
y = F.scaled_dot_product_attention(
|
| 117 |
+
q,
|
| 118 |
+
k,
|
| 119 |
+
v,
|
| 120 |
+
is_causal=True,
|
| 121 |
+
enable_gqa=self.h != self.kv_h,
|
| 122 |
+
)
|
| 123 |
+
return self.o(y.transpose(1, 2).reshape(B, T, d))
|
| 124 |
+
|
| 125 |
+
|
| 126 |
+
class CMA(nn.Module):
|
| 127 |
+
def __init__(self, d, chunk=16, heads=2, expand=2, identity_prob=0.90):
|
| 128 |
+
super().__init__()
|
| 129 |
+
if min(d, chunk, heads, expand) <= 0:
|
| 130 |
+
raise ValueError("CMA dimensions and expansion must be positive.")
|
| 131 |
+
if d % chunk or chunk % heads:
|
| 132 |
+
raise ValueError("CMA requires d % chunk == 0 and chunk % heads == 0.")
|
| 133 |
+
if d // chunk < 2:
|
| 134 |
+
raise ValueError("CMA requires at least two channel slots.")
|
| 135 |
+
if not 0.0 < identity_prob < 1.0:
|
| 136 |
+
raise ValueError("cma_identity_prob must be between zero and one.")
|
| 137 |
+
|
| 138 |
+
self.d, self.n, self.c, self.h = d, d // chunk, chunk, heads
|
| 139 |
+
self.hd, self.expand = chunk // heads, expand
|
| 140 |
+
self.chunk_emb = nn.Parameter(torch.randn(self.n, chunk) * 0.02)
|
| 141 |
+
self.wqk = nn.Parameter(torch.randn(self.n, chunk, 2 * chunk) * 0.02)
|
| 142 |
+
self.global_proj = nn.Linear(d, chunk, bias=False)
|
| 143 |
+
self.wv = nn.Linear(d, d * expand, bias=False)
|
| 144 |
+
self.bias = nn.Parameter(torch.zeros(heads, self.n, self.n))
|
| 145 |
+
self.qn, self.kn = RMSNorm(self.hd), RMSNorm(self.hd)
|
| 146 |
+
self.logit_scale = nn.Parameter(torch.zeros(heads))
|
| 147 |
+
self.layer_gain = nn.Parameter(torch.zeros(heads))
|
| 148 |
+
self.route_gate_weight = nn.Parameter(torch.randn(heads, self.hd) * 0.02)
|
| 149 |
+
self.route_gate_bias = nn.Parameter(torch.zeros(heads))
|
| 150 |
+
self.gate = nn.Linear(d, d * expand, bias=False)
|
| 151 |
+
self.o = nn.Linear(d * expand, d, bias=False)
|
| 152 |
+
nn.init.zeros_(self.o.weight)
|
| 153 |
+
|
| 154 |
+
diagonal_bias = math.log(
|
| 155 |
+
(self.n - 1) * identity_prob / (1.0 - identity_prob)
|
| 156 |
+
)
|
| 157 |
+
with torch.no_grad():
|
| 158 |
+
self.bias.add_(torch.eye(self.n) * diagonal_bias)
|
| 159 |
+
|
| 160 |
+
def _routing(self, x):
|
| 161 |
+
batch_tokens = x.numel() // self.d
|
| 162 |
+
xc = x.reshape(batch_tokens, self.n, self.c)
|
| 163 |
+
global_state = self.global_proj(x).reshape(batch_tokens, 1, self.c)
|
| 164 |
+
q_input = xc + self.chunk_emb + global_state
|
| 165 |
+
value_slots = self.wv(x).reshape(
|
| 166 |
+
batch_tokens, self.n, self.h, self.hd, self.expand
|
| 167 |
+
)
|
| 168 |
+
key_input = value_slots.mean(dim=-1).reshape(batch_tokens, self.n, self.c)
|
| 169 |
+
key_input = key_input + self.chunk_emb
|
| 170 |
+
|
| 171 |
+
q = torch.einsum("bnc,nco->bno", q_input, self.wqk[..., : self.c])
|
| 172 |
+
k = torch.einsum("bnc,nco->bno", key_input, self.wqk[..., self.c :])
|
| 173 |
+
v = value_slots.reshape(
|
| 174 |
+
batch_tokens, self.n, self.h, self.hd * self.expand
|
| 175 |
+
).transpose(1, 2)
|
| 176 |
+
q = self.qn(q.reshape(batch_tokens, self.n, self.h, self.hd)).transpose(1, 2)
|
| 177 |
+
k = self.kn(k.reshape(batch_tokens, self.n, self.h, self.hd)).transpose(1, 2)
|
| 178 |
+
q = F.normalize(q.float(), dim=-1).to(v.dtype)
|
| 179 |
+
k = F.normalize(k.float(), dim=-1).to(v.dtype)
|
| 180 |
+
|
| 181 |
+
scale = self.logit_scale.clamp(max=math.log(100.0)).exp()
|
| 182 |
+
logits = (q * scale.view(1, self.h, 1, 1).to(q.dtype)) @ k.transpose(-2, -1)
|
| 183 |
+
logits = logits + self.bias.unsqueeze(0).to(logits.dtype)
|
| 184 |
+
attn = F.softmax(logits, dim=-1, dtype=torch.float32).to(v.dtype)
|
| 185 |
+
routed = attn @ v
|
| 186 |
+
route_signal = (
|
| 187 |
+
(q.float() * self.route_gate_weight.float().view(1, self.h, 1, self.hd)).sum(-1)
|
| 188 |
+
+ self.route_gate_bias.float().view(1, self.h, 1)
|
| 189 |
+
+ self.layer_gain.float().view(1, self.h, 1)
|
| 190 |
+
)
|
| 191 |
+
route_coeff = torch.tanh(route_signal).to(v.dtype)
|
| 192 |
+
contribution = route_coeff.unsqueeze(-1) * (routed - v)
|
| 193 |
+
return v, attn, route_coeff, contribution, logits
|
| 194 |
+
|
| 195 |
+
def forward(self, x):
|
| 196 |
+
B, T, _ = x.shape
|
| 197 |
+
v, _, _, contribution, _ = self._routing(x)
|
| 198 |
+
y = (v + contribution).transpose(1, 2).reshape(B, T, self.d * self.expand)
|
| 199 |
+
return self.o(y * F.silu(self.gate(x)))
|
| 200 |
+
|
| 201 |
+
@torch.no_grad()
|
| 202 |
+
def diagnostic_stats(self, x):
|
| 203 |
+
probe_count = x.shape[0] if x.ndim > 2 else 1
|
| 204 |
+
v, attn, route_coeff, contribution, logits = self._routing(x)
|
| 205 |
+
B, T, _ = x.shape
|
| 206 |
+
base = v.transpose(1, 2).reshape(B, T, self.d * self.expand)
|
| 207 |
+
routed = (v + contribution).transpose(1, 2).reshape(
|
| 208 |
+
B, T, self.d * self.expand
|
| 209 |
+
)
|
| 210 |
+
gate = F.silu(self.gate(x))
|
| 211 |
+
base_output = self.o(base * gate)
|
| 212 |
+
routed_output = self.o(routed * gate)
|
| 213 |
+
output_delta = (routed_output - base_output).reshape(-1, self.d)
|
| 214 |
+
token_effect = (
|
| 215 |
+
output_delta.float().norm(dim=-1)
|
| 216 |
+
/ routed_output.reshape(-1, self.d).float().norm(dim=-1).clamp_min(1e-12)
|
| 217 |
+
)
|
| 218 |
+
probe_effect = token_effect.reshape(probe_count, -1).mean(dim=-1)
|
| 219 |
+
probs = attn.float().clamp_min(1e-9)
|
| 220 |
+
entropy = -(probs * probs.log()).sum(dim=-1) / math.log(self.n)
|
| 221 |
+
diagonal_mass = probs.diagonal(dim1=-2, dim2=-1).mean()
|
| 222 |
+
if self.h > 1:
|
| 223 |
+
flattened = probs.transpose(0, 1).reshape(self.h, -1)
|
| 224 |
+
normalized = F.normalize(flattened, dim=-1)
|
| 225 |
+
similarity = normalized @ normalized.mT
|
| 226 |
+
head_similarity = (
|
| 227 |
+
similarity.sum() - similarity.diagonal().sum()
|
| 228 |
+
) / (self.h * (self.h - 1))
|
| 229 |
+
else:
|
| 230 |
+
head_similarity = probs.new_zeros(())
|
| 231 |
+
return {
|
| 232 |
+
"token_effect": token_effect,
|
| 233 |
+
"probe_effect": probe_effect,
|
| 234 |
+
"entropy": entropy.mean().item(),
|
| 235 |
+
"diagonal_mass": diagonal_mass.item(),
|
| 236 |
+
"head_similarity": head_similarity.item(),
|
| 237 |
+
"gate_abs": route_coeff.float().abs().mean().item(),
|
| 238 |
+
"gate_saturation": (route_coeff.float().abs() > 0.95).float().mean().item(),
|
| 239 |
+
"logit_max": logits.float().abs().max().item(),
|
| 240 |
+
}
|
| 241 |
+
|
| 242 |
+
|
| 243 |
+
class Block(nn.Module):
|
| 244 |
+
def __init__(self, config):
|
| 245 |
+
super().__init__()
|
| 246 |
+
d = config.d_model
|
| 247 |
+
self.n1, self.n2 = RMSNorm(d), RMSNorm(d)
|
| 248 |
+
self.attn = TokenAttention(d, config.n_heads, config.n_kv_heads)
|
| 249 |
+
self.mix = CMA(
|
| 250 |
+
d,
|
| 251 |
+
config.chunk,
|
| 252 |
+
config.cma_heads,
|
| 253 |
+
config.expand,
|
| 254 |
+
config.cma_identity_prob,
|
| 255 |
+
)
|
| 256 |
+
|
| 257 |
+
def forward(self, x, cos, sin):
|
| 258 |
+
x = x + self.attn(self.n1(x), cos, sin)
|
| 259 |
+
x = x + self.mix(self.n2(x))
|
| 260 |
+
return x
|
| 261 |
+
|
| 262 |
+
|
| 263 |
+
class CMAModel(nn.Module):
|
| 264 |
+
def __init__(self, config):
|
| 265 |
+
super().__init__()
|
| 266 |
+
d = config.d_model
|
| 267 |
+
self.config = config
|
| 268 |
+
self.emb = nn.Embedding(config.vocab_size, d)
|
| 269 |
+
self.blocks = nn.ModuleList(Block(config) for _ in range(config.n_layers))
|
| 270 |
+
self.norm = RMSNorm(d)
|
| 271 |
+
hd = d // config.n_heads
|
| 272 |
+
cos, sin = rope_cache(config.seq_len, hd, "cpu")
|
| 273 |
+
self.register_buffer("cos", cos)
|
| 274 |
+
self.register_buffer("sin", sin)
|
| 275 |
+
|
| 276 |
+
def forward_hidden(self, idx):
|
| 277 |
+
if idx.size(1) > self.config.seq_len:
|
| 278 |
+
idx = idx[:, -self.config.seq_len :]
|
| 279 |
+
x = self.emb(idx)
|
| 280 |
+
device_type = x.device.type
|
| 281 |
+
rope_dtype = (
|
| 282 |
+
torch.get_autocast_dtype(device_type)
|
| 283 |
+
if torch.is_autocast_enabled(device_type)
|
| 284 |
+
else x.dtype
|
| 285 |
+
)
|
| 286 |
+
cos = self.cos[: idx.size(1)].to(device=idx.device, dtype=rope_dtype)
|
| 287 |
+
sin = self.sin[: idx.size(1)].to(device=idx.device, dtype=rope_dtype)
|
| 288 |
+
for b in self.blocks:
|
| 289 |
+
x = b(x, cos, sin)
|
| 290 |
+
return self.norm(x)
|
| 291 |
+
|
| 292 |
+
|
| 293 |
+
class CMAForCausalLM(PreTrainedModel, GenerationMixin):
|
| 294 |
+
config_class = CMAConfig
|
| 295 |
+
base_model_prefix = "model"
|
| 296 |
+
_tied_weights_keys = {"head.weight": "model.emb.weight"}
|
| 297 |
+
all_tied_weights_keys = {"head.weight": "model.emb.weight"}
|
| 298 |
+
|
| 299 |
+
def __init__(self, config):
|
| 300 |
+
super().__init__(config)
|
| 301 |
+
self.model = CMAModel(config)
|
| 302 |
+
self.head = nn.Linear(config.d_model, config.vocab_size, bias=False)
|
| 303 |
+
# Modern Transformers creates loader metadata and performs configured
|
| 304 |
+
# tying in post_init(); omitting it leaves all_tied_weights_keys absent.
|
| 305 |
+
self.post_init()
|
| 306 |
+
self.head.weight = self.model.emb.weight
|
| 307 |
+
|
| 308 |
+
def get_input_embeddings(self):
|
| 309 |
+
return self.model.emb
|
| 310 |
+
|
| 311 |
+
def set_input_embeddings(self, value):
|
| 312 |
+
self.model.emb = value
|
| 313 |
+
|
| 314 |
+
def get_output_embeddings(self):
|
| 315 |
+
return self.head
|
| 316 |
+
|
| 317 |
+
def set_output_embeddings(self, new_embeddings):
|
| 318 |
+
self.head = new_embeddings
|
| 319 |
+
|
| 320 |
+
def raw_logits(self, idx):
|
| 321 |
+
return self.head(self.model.forward_hidden(idx))
|
| 322 |
+
|
| 323 |
+
def logits(self, idx):
|
| 324 |
+
return self.raw_logits(idx)
|
| 325 |
+
|
| 326 |
+
def _masked_logits(self, input_ids, attention_mask):
|
| 327 |
+
if attention_mask is None or bool(attention_mask.all()):
|
| 328 |
+
return self.logits(input_ids)
|
| 329 |
+
|
| 330 |
+
B, T = input_ids.shape
|
| 331 |
+
out = None
|
| 332 |
+
for i in range(B):
|
| 333 |
+
keep = attention_mask[i].bool().nonzero(as_tuple=False).flatten()
|
| 334 |
+
if keep.numel() == 0:
|
| 335 |
+
keep = torch.tensor([T - 1], device=input_ids.device)
|
| 336 |
+
trimmed = input_ids[i, keep].unsqueeze(0)
|
| 337 |
+
logits_i = self.logits(trimmed)
|
| 338 |
+
if out is None:
|
| 339 |
+
out = logits_i.new_zeros(B, T, logits_i.size(-1))
|
| 340 |
+
out[i, keep, :] = logits_i[0, -keep.numel() :, :]
|
| 341 |
+
return out
|
| 342 |
+
|
| 343 |
+
def forward(
|
| 344 |
+
self,
|
| 345 |
+
input_ids=None,
|
| 346 |
+
attention_mask=None,
|
| 347 |
+
labels=None,
|
| 348 |
+
use_cache=False,
|
| 349 |
+
past_key_values=None,
|
| 350 |
+
**kwargs,
|
| 351 |
+
):
|
| 352 |
+
if input_ids.size(1) > self.config.seq_len:
|
| 353 |
+
input_ids = input_ids[:, -self.config.seq_len :]
|
| 354 |
+
if attention_mask is not None:
|
| 355 |
+
attention_mask = attention_mask[:, -self.config.seq_len :]
|
| 356 |
+
if labels is not None:
|
| 357 |
+
labels = labels[:, -self.config.seq_len :]
|
| 358 |
+
logits = self._masked_logits(input_ids, attention_mask)
|
| 359 |
+
loss = None
|
| 360 |
+
if labels is not None:
|
| 361 |
+
shift_logits = logits[:, :-1, :].contiguous()
|
| 362 |
+
shift_labels = labels[:, 1:].contiguous()
|
| 363 |
+
loss = F.cross_entropy(
|
| 364 |
+
shift_logits.view(-1, shift_logits.size(-1)).float(),
|
| 365 |
+
shift_labels.view(-1),
|
| 366 |
+
ignore_index=-100,
|
| 367 |
+
)
|
| 368 |
+
return CausalLMOutputWithPast(loss=loss, logits=logits, past_key_values=None)
|
| 369 |
+
|
| 370 |
+
def prepare_inputs_for_generation(self, input_ids, **kwargs):
|
| 371 |
+
attention_mask = kwargs.get("attention_mask")
|
| 372 |
+
result = {"input_ids": input_ids[:, -self.config.seq_len :]}
|
| 373 |
+
if attention_mask is not None:
|
| 374 |
+
result["attention_mask"] = attention_mask[:, -self.config.seq_len :]
|
| 375 |
+
return result
|
tokenizer.json
ADDED
|
@@ -0,0 +1,377 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
{
|
| 2 |
+
"version": "1.0",
|
| 3 |
+
"truncation": null,
|
| 4 |
+
"padding": null,
|
| 5 |
+
"added_tokens": [
|
| 6 |
+
{
|
| 7 |
+
"id": 0,
|
| 8 |
+
"content": "<pad>",
|
| 9 |
+
"single_word": false,
|
| 10 |
+
"lstrip": false,
|
| 11 |
+
"rstrip": false,
|
| 12 |
+
"normalized": false,
|
| 13 |
+
"special": true
|
| 14 |
+
},
|
| 15 |
+
{
|
| 16 |
+
"id": 1,
|
| 17 |
+
"content": "<bos>",
|
| 18 |
+
"single_word": false,
|
| 19 |
+
"lstrip": false,
|
| 20 |
+
"rstrip": false,
|
| 21 |
+
"normalized": false,
|
| 22 |
+
"special": true
|
| 23 |
+
},
|
| 24 |
+
{
|
| 25 |
+
"id": 2,
|
| 26 |
+
"content": "<eos>",
|
| 27 |
+
"single_word": false,
|
| 28 |
+
"lstrip": false,
|
| 29 |
+
"rstrip": false,
|
| 30 |
+
"normalized": false,
|
| 31 |
+
"special": true
|
| 32 |
+
},
|
| 33 |
+
{
|
| 34 |
+
"id": 3,
|
| 35 |
+
"content": "<unk>",
|
| 36 |
+
"single_word": false,
|
| 37 |
+
"lstrip": false,
|
| 38 |
+
"rstrip": false,
|
| 39 |
+
"normalized": false,
|
| 40 |
+
"special": true
|
| 41 |
+
}
|
| 42 |
+
],
|
| 43 |
+
"normalizer": null,
|
| 44 |
+
"pre_tokenizer": {
|
| 45 |
+
"type": "ByteLevel",
|
| 46 |
+
"add_prefix_space": false,
|
| 47 |
+
"trim_offsets": true,
|
| 48 |
+
"use_regex": true
|
| 49 |
+
},
|
| 50 |
+
"post_processor": {
|
| 51 |
+
"type": "TemplateProcessing",
|
| 52 |
+
"single": [
|
| 53 |
+
{
|
| 54 |
+
"SpecialToken": {
|
| 55 |
+
"id": "<bos>",
|
| 56 |
+
"type_id": 0
|
| 57 |
+
}
|
| 58 |
+
},
|
| 59 |
+
{
|
| 60 |
+
"Sequence": {
|
| 61 |
+
"id": "A",
|
| 62 |
+
"type_id": 0
|
| 63 |
+
}
|
| 64 |
+
}
|
| 65 |
+
],
|
| 66 |
+
"pair": [
|
| 67 |
+
{
|
| 68 |
+
"SpecialToken": {
|
| 69 |
+
"id": "<bos>",
|
| 70 |
+
"type_id": 0
|
| 71 |
+
}
|
| 72 |
+
},
|
| 73 |
+
{
|
| 74 |
+
"Sequence": {
|
| 75 |
+
"id": "A",
|
| 76 |
+
"type_id": 0
|
| 77 |
+
}
|
| 78 |
+
},
|
| 79 |
+
{
|
| 80 |
+
"Sequence": {
|
| 81 |
+
"id": "B",
|
| 82 |
+
"type_id": 0
|
| 83 |
+
}
|
| 84 |
+
}
|
| 85 |
+
],
|
| 86 |
+
"special_tokens": {
|
| 87 |
+
"<bos>": {
|
| 88 |
+
"id": "<bos>",
|
| 89 |
+
"ids": [
|
| 90 |
+
1
|
| 91 |
+
],
|
| 92 |
+
"tokens": [
|
| 93 |
+
"<bos>"
|
| 94 |
+
]
|
| 95 |
+
}
|
| 96 |
+
}
|
| 97 |
+
},
|
| 98 |
+
"decoder": {
|
| 99 |
+
"type": "ByteLevel",
|
| 100 |
+
"add_prefix_space": true,
|
| 101 |
+
"trim_offsets": true,
|
| 102 |
+
"use_regex": true
|
| 103 |
+
},
|
| 104 |
+
"model": {
|
| 105 |
+
"type": "BPE",
|
| 106 |
+
"dropout": null,
|
| 107 |
+
"unk_token": "<unk>",
|
| 108 |
+
"continuing_subword_prefix": null,
|
| 109 |
+
"end_of_word_suffix": null,
|
| 110 |
+
"fuse_unk": false,
|
| 111 |
+
"byte_fallback": false,
|
| 112 |
+
"ignore_merges": false,
|
| 113 |
+
"vocab": {
|
| 114 |
+
"<pad>": 0,
|
| 115 |
+
"<bos>": 1,
|
| 116 |
+
"<eos>": 2,
|
| 117 |
+
"<unk>": 3,
|
| 118 |
+
"!": 4,
|
| 119 |
+
"\"": 5,
|
| 120 |
+
"#": 6,
|
| 121 |
+
"$": 7,
|
| 122 |
+
"%": 8,
|
| 123 |
+
"&": 9,
|
| 124 |
+
"'": 10,
|
| 125 |
+
"(": 11,
|
| 126 |
+
")": 12,
|
| 127 |
+
"*": 13,
|
| 128 |
+
"+": 14,
|
| 129 |
+
",": 15,
|
| 130 |
+
"-": 16,
|
| 131 |
+
".": 17,
|
| 132 |
+
"/": 18,
|
| 133 |
+
"0": 19,
|
| 134 |
+
"1": 20,
|
| 135 |
+
"2": 21,
|
| 136 |
+
"3": 22,
|
| 137 |
+
"4": 23,
|
| 138 |
+
"5": 24,
|
| 139 |
+
"6": 25,
|
| 140 |
+
"7": 26,
|
| 141 |
+
"8": 27,
|
| 142 |
+
"9": 28,
|
| 143 |
+
":": 29,
|
| 144 |
+
";": 30,
|
| 145 |
+
"<": 31,
|
| 146 |
+
"=": 32,
|
| 147 |
+
">": 33,
|
| 148 |
+
"?": 34,
|
| 149 |
+
"@": 35,
|
| 150 |
+
"A": 36,
|
| 151 |
+
"B": 37,
|
| 152 |
+
"C": 38,
|
| 153 |
+
"D": 39,
|
| 154 |
+
"E": 40,
|
| 155 |
+
"F": 41,
|
| 156 |
+
"G": 42,
|
| 157 |
+
"H": 43,
|
| 158 |
+
"I": 44,
|
| 159 |
+
"J": 45,
|
| 160 |
+
"K": 46,
|
| 161 |
+
"L": 47,
|
| 162 |
+
"M": 48,
|
| 163 |
+
"N": 49,
|
| 164 |
+
"O": 50,
|
| 165 |
+
"P": 51,
|
| 166 |
+
"Q": 52,
|
| 167 |
+
"R": 53,
|
| 168 |
+
"S": 54,
|
| 169 |
+
"T": 55,
|
| 170 |
+
"U": 56,
|
| 171 |
+
"V": 57,
|
| 172 |
+
"W": 58,
|
| 173 |
+
"X": 59,
|
| 174 |
+
"Y": 60,
|
| 175 |
+
"Z": 61,
|
| 176 |
+
"[": 62,
|
| 177 |
+
"\\": 63,
|
| 178 |
+
"]": 64,
|
| 179 |
+
"^": 65,
|
| 180 |
+
"_": 66,
|
| 181 |
+
"`": 67,
|
| 182 |
+
"a": 68,
|
| 183 |
+
"b": 69,
|
| 184 |
+
"c": 70,
|
| 185 |
+
"d": 71,
|
| 186 |
+
"e": 72,
|
| 187 |
+
"f": 73,
|
| 188 |
+
"g": 74,
|
| 189 |
+
"h": 75,
|
| 190 |
+
"i": 76,
|
| 191 |
+
"j": 77,
|
| 192 |
+
"k": 78,
|
| 193 |
+
"l": 79,
|
| 194 |
+
"m": 80,
|
| 195 |
+
"n": 81,
|
| 196 |
+
"o": 82,
|
| 197 |
+
"p": 83,
|
| 198 |
+
"q": 84,
|
| 199 |
+
"r": 85,
|
| 200 |
+
"s": 86,
|
| 201 |
+
"t": 87,
|
| 202 |
+
"u": 88,
|
| 203 |
+
"v": 89,
|
| 204 |
+
"w": 90,
|
| 205 |
+
"x": 91,
|
| 206 |
+
"y": 92,
|
| 207 |
+
"z": 93,
|
| 208 |
+
"{": 94,
|
| 209 |
+
"|": 95,
|
| 210 |
+
"}": 96,
|
| 211 |
+
"~": 97,
|
| 212 |
+
"¡": 98,
|
| 213 |
+
"¢": 99,
|
| 214 |
+
"£": 100,
|
| 215 |
+
"¤": 101,
|
| 216 |
+
"¥": 102,
|
| 217 |
+
"¦": 103,
|
| 218 |
+
"§": 104,
|
| 219 |
+
"¨": 105,
|
| 220 |
+
"©": 106,
|
| 221 |
+
"ª": 107,
|
| 222 |
+
"«": 108,
|
| 223 |
+
"¬": 109,
|
| 224 |
+
"®": 110,
|
| 225 |
+
"¯": 111,
|
| 226 |
+
"°": 112,
|
| 227 |
+
"±": 113,
|
| 228 |
+
"²": 114,
|
| 229 |
+
"³": 115,
|
| 230 |
+
"´": 116,
|
| 231 |
+
"µ": 117,
|
| 232 |
+
"¶": 118,
|
| 233 |
+
"·": 119,
|
| 234 |
+
"¸": 120,
|
| 235 |
+
"¹": 121,
|
| 236 |
+
"º": 122,
|
| 237 |
+
"»": 123,
|
| 238 |
+
"¼": 124,
|
| 239 |
+
"½": 125,
|
| 240 |
+
"¾": 126,
|
| 241 |
+
"¿": 127,
|
| 242 |
+
"À": 128,
|
| 243 |
+
"Á": 129,
|
| 244 |
+
"Â": 130,
|
| 245 |
+
"Ã": 131,
|
| 246 |
+
"Ä": 132,
|
| 247 |
+
"Å": 133,
|
| 248 |
+
"Æ": 134,
|
| 249 |
+
"Ç": 135,
|
| 250 |
+
"È": 136,
|
| 251 |
+
"É": 137,
|
| 252 |
+
"Ê": 138,
|
| 253 |
+
"Ë": 139,
|
| 254 |
+
"Ì": 140,
|
| 255 |
+
"Í": 141,
|
| 256 |
+
"Î": 142,
|
| 257 |
+
"Ï": 143,
|
| 258 |
+
"Ð": 144,
|
| 259 |
+
"Ñ": 145,
|
| 260 |
+
"Ò": 146,
|
| 261 |
+
"Ó": 147,
|
| 262 |
+
"Ô": 148,
|
| 263 |
+
"Õ": 149,
|
| 264 |
+
"Ö": 150,
|
| 265 |
+
"×": 151,
|
| 266 |
+
"Ø": 152,
|
| 267 |
+
"Ù": 153,
|
| 268 |
+
"Ú": 154,
|
| 269 |
+
"Û": 155,
|
| 270 |
+
"Ü": 156,
|
| 271 |
+
"Ý": 157,
|
| 272 |
+
"Þ": 158,
|
| 273 |
+
"ß": 159,
|
| 274 |
+
"à": 160,
|
| 275 |
+
"á": 161,
|
| 276 |
+
"â": 162,
|
| 277 |
+
"ã": 163,
|
| 278 |
+
"ä": 164,
|
| 279 |
+
"å": 165,
|
| 280 |
+
"æ": 166,
|
| 281 |
+
"ç": 167,
|
| 282 |
+
"è": 168,
|
| 283 |
+
"é": 169,
|
| 284 |
+
"ê": 170,
|
| 285 |
+
"ë": 171,
|
| 286 |
+
"ì": 172,
|
| 287 |
+
"í": 173,
|
| 288 |
+
"î": 174,
|
| 289 |
+
"ï": 175,
|
| 290 |
+
"ð": 176,
|
| 291 |
+
"ñ": 177,
|
| 292 |
+
"ò": 178,
|
| 293 |
+
"ó": 179,
|
| 294 |
+
"ô": 180,
|
| 295 |
+
"õ": 181,
|
| 296 |
+
"ö": 182,
|
| 297 |
+
"÷": 183,
|
| 298 |
+
"ø": 184,
|
| 299 |
+
"ù": 185,
|
| 300 |
+
"ú": 186,
|
| 301 |
+
"û": 187,
|
| 302 |
+
"ü": 188,
|
| 303 |
+
"ý": 189,
|
| 304 |
+
"þ": 190,
|
| 305 |
+
"ÿ": 191,
|
| 306 |
+
"Ā": 192,
|
| 307 |
+
"ā": 193,
|
| 308 |
+
"Ă": 194,
|
| 309 |
+
"ă": 195,
|
| 310 |
+
"Ą": 196,
|
| 311 |
+
"ą": 197,
|
| 312 |
+
"Ć": 198,
|
| 313 |
+
"ć": 199,
|
| 314 |
+
"Ĉ": 200,
|
| 315 |
+
"ĉ": 201,
|
| 316 |
+
"Ċ": 202,
|
| 317 |
+
"ċ": 203,
|
| 318 |
+
"Č": 204,
|
| 319 |
+
"č": 205,
|
| 320 |
+
"Ď": 206,
|
| 321 |
+
"ď": 207,
|
| 322 |
+
"Đ": 208,
|
| 323 |
+
"đ": 209,
|
| 324 |
+
"Ē": 210,
|
| 325 |
+
"ē": 211,
|
| 326 |
+
"Ĕ": 212,
|
| 327 |
+
"ĕ": 213,
|
| 328 |
+
"Ė": 214,
|
| 329 |
+
"ė": 215,
|
| 330 |
+
"Ę": 216,
|
| 331 |
+
"ę": 217,
|
| 332 |
+
"Ě": 218,
|
| 333 |
+
"ě": 219,
|
| 334 |
+
"Ĝ": 220,
|
| 335 |
+
"ĝ": 221,
|
| 336 |
+
"Ğ": 222,
|
| 337 |
+
"ğ": 223,
|
| 338 |
+
"Ġ": 224,
|
| 339 |
+
"ġ": 225,
|
| 340 |
+
"Ģ": 226,
|
| 341 |
+
"ģ": 227,
|
| 342 |
+
"Ĥ": 228,
|
| 343 |
+
"ĥ": 229,
|
| 344 |
+
"Ħ": 230,
|
| 345 |
+
"ħ": 231,
|
| 346 |
+
"Ĩ": 232,
|
| 347 |
+
"ĩ": 233,
|
| 348 |
+
"Ī": 234,
|
| 349 |
+
"ī": 235,
|
| 350 |
+
"Ĭ": 236,
|
| 351 |
+
"ĭ": 237,
|
| 352 |
+
"Į": 238,
|
| 353 |
+
"į": 239,
|
| 354 |
+
"İ": 240,
|
| 355 |
+
"ı": 241,
|
| 356 |
+
"IJ": 242,
|
| 357 |
+
"ij": 243,
|
| 358 |
+
"Ĵ": 244,
|
| 359 |
+
"ĵ": 245,
|
| 360 |
+
"Ķ": 246,
|
| 361 |
+
"ķ": 247,
|
| 362 |
+
"ĸ": 248,
|
| 363 |
+
"Ĺ": 249,
|
| 364 |
+
"ĺ": 250,
|
| 365 |
+
"Ļ": 251,
|
| 366 |
+
"ļ": 252,
|
| 367 |
+
"Ľ": 253,
|
| 368 |
+
"ľ": 254,
|
| 369 |
+
"Ŀ": 255,
|
| 370 |
+
"ŀ": 256,
|
| 371 |
+
"Ł": 257,
|
| 372 |
+
"ł": 258,
|
| 373 |
+
"Ń": 259
|
| 374 |
+
},
|
| 375 |
+
"merges": []
|
| 376 |
+
}
|
| 377 |
+
}
|
tokenizer_config.json
ADDED
|
@@ -0,0 +1,10 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
{
|
| 2 |
+
"backend": "tokenizers",
|
| 3 |
+
"bos_token": "<bos>",
|
| 4 |
+
"clean_up_tokenization_spaces": false,
|
| 5 |
+
"eos_token": "<eos>",
|
| 6 |
+
"model_max_length": 2048,
|
| 7 |
+
"pad_token": "<pad>",
|
| 8 |
+
"tokenizer_class": "TokenizersBackend",
|
| 9 |
+
"unk_token": "<unk>"
|
| 10 |
+
}
|
training_config.json
ADDED
|
@@ -0,0 +1,54 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
{
|
| 2 |
+
"steps": 20000,
|
| 3 |
+
"batch_size": 512,
|
| 4 |
+
"grad_accum": 4,
|
| 5 |
+
"seq_len": 2048,
|
| 6 |
+
"eval_seq_len": 2048,
|
| 7 |
+
"d_model": 128,
|
| 8 |
+
"n_layers": 6,
|
| 9 |
+
"n_heads": 4,
|
| 10 |
+
"n_kv_heads": 2,
|
| 11 |
+
"chunk": 16,
|
| 12 |
+
"cma_heads": 2,
|
| 13 |
+
"expand": 2,
|
| 14 |
+
"cma_identity_prob": 0.9,
|
| 15 |
+
"lr": 0.001,
|
| 16 |
+
"muon_momentum": 0.95,
|
| 17 |
+
"muon_ns_steps": 5,
|
| 18 |
+
"muon_adjust_lr_fn": "match_rms_adamw",
|
| 19 |
+
"warmup": 500,
|
| 20 |
+
"wd": 0.01,
|
| 21 |
+
"grad_clip": 5.0,
|
| 22 |
+
"log_every": 5,
|
| 23 |
+
"early_eval_step": 1000,
|
| 24 |
+
"diag_every": 1000,
|
| 25 |
+
"eval_every": 2000,
|
| 26 |
+
"val_batch_size": 32,
|
| 27 |
+
"val_batches": 0,
|
| 28 |
+
"val_stride": 1024,
|
| 29 |
+
"infer_tokens": 512,
|
| 30 |
+
"infer_repeat_penalty": 1.2,
|
| 31 |
+
"infer_prompt": "The process of photosynthesis",
|
| 32 |
+
"lm_eval_tasks": "arc_easy,arc_challenge,hellaswag,piqa",
|
| 33 |
+
"lm_eval_batch_size": "auto",
|
| 34 |
+
"lm_eval_device": "cuda",
|
| 35 |
+
"lm_eval_dtype": "bfloat16",
|
| 36 |
+
"lm_eval_softmax_dtype": "float32",
|
| 37 |
+
"lm_eval_expected_version": "0.4.12",
|
| 38 |
+
"lm_eval_retries": 3,
|
| 39 |
+
"lm_eval_export_dir": "CMA_1M_Mini_lm_eval_hf",
|
| 40 |
+
"lm_eval_output_dir": "lm_eval_results_CMA_1M_Mini",
|
| 41 |
+
"arithmark_batch_size": 16,
|
| 42 |
+
"arithmark_data_path": "benchmark_cache/arithmark_2.0.jsonl",
|
| 43 |
+
"arithmark_force_download": false,
|
| 44 |
+
"recipe_version": "CMA_1M_mini_byte_c16_h2_e2_muon_w500_cosine20k_b512_ga4_ctx2k_async_v7",
|
| 45 |
+
"hf_repo_id": "User01110/CMA-1M-Mini",
|
| 46 |
+
"hf_repo_private": false,
|
| 47 |
+
"hub_upload_retries": 3,
|
| 48 |
+
"tokenizer_name": "local-byte-level",
|
| 49 |
+
"tokenizer_revision": "byte-v1",
|
| 50 |
+
"data_seed": 1337,
|
| 51 |
+
"shuffle_buffer": 50000,
|
| 52 |
+
"tokenize_batch_size": 64,
|
| 53 |
+
"compile": true
|
| 54 |
+
}
|