Spaces:
Sleeping
Sleeping
Pratyush Bhardwaj
load latest weights + enable trained MTP draft head (use_writer_mtp)
68576c8 verified | """Probing the model's internal "thoughts" (inspired by Anthropic's circuit work). | |
| We can't do full attribution graphs cheaply, but two lightweight probes go a long | |
| way on this architecture: | |
| logit_lens apply the (tied) LM head to each Block-AttnRes block state to | |
| see what the model "predicts" at each depth — the thought | |
| sharpening from block to block. | |
| representation_report per-block geometry of the concept space: rms norm, | |
| anisotropy (mean pairwise cosine — high == degenerate), and | |
| effective rank (how many dimensions are actually used). | |
| Both consume the per-block states exposed by CortexLM._trunk(..., collect=True). | |
| """ | |
| from __future__ import annotations | |
| import jax | |
| import jax.numpy as jnp | |
| import numpy as np | |
| def block_states(model, tokens): | |
| _, states = model._trunk(jnp.asarray(tokens), collect=True) | |
| return states | |
| def logit_lens(model, tokens, k: int = 5, pos: int = -1): | |
| """Top-k predictions + entropy at `pos` for every block state.""" | |
| _, states = model._trunk(jnp.asarray(tokens), collect=True) | |
| out = [] | |
| for i, h in enumerate(states): | |
| logits = model._head(h)[:, pos].astype(jnp.float32) # [B, V] | |
| probs = jax.nn.softmax(logits, axis=-1) | |
| top_p, top_i = jax.lax.top_k(probs, k) | |
| ent = -jnp.sum(probs * jnp.log(probs + 1e-9), axis=-1) | |
| out.append({ | |
| "stage": i, | |
| "top_ids": np.asarray(top_i), | |
| "top_probs": np.asarray(top_p), | |
| "entropy": np.asarray(ent), | |
| }) | |
| return out | |
| def representation_report(model, tokens, sample: int = 512, seed: int = 0): | |
| """Per-block geometry of the hidden states.""" | |
| _, states = model._trunk(jnp.asarray(tokens), collect=True) | |
| rng = np.random.default_rng(seed) | |
| rows = [] | |
| for i, h in enumerate(states): | |
| hf = np.asarray(h, dtype=np.float32).reshape(-1, h.shape[-1]) | |
| if hf.shape[0] > sample: | |
| hf = hf[rng.choice(hf.shape[0], sample, replace=False)] | |
| rms = float(np.sqrt((hf ** 2).mean())) | |
| hn = hf / (np.linalg.norm(hf, axis=-1, keepdims=True) + 1e-8) | |
| sims = hn @ hn.T | |
| n = sims.shape[0] | |
| aniso = float((sims.sum() - np.trace(sims)) / (n * (n - 1))) # mean off-diag cosine | |
| # effective rank = exp(entropy of normalized singular-value spectrum) | |
| s = np.linalg.svd(hf - hf.mean(0, keepdims=True), compute_uv=False) | |
| p = (s ** 2) / max((s ** 2).sum(), 1e-9) | |
| erank = float(np.exp(-(p * np.log(p + 1e-12)).sum())) | |
| rows.append({"stage": i, "rms": rms, "anisotropy": aniso, "eff_rank": erank}) | |
| return rows | |
| def format_report(rows) -> str: | |
| lines = [f"{'stage':>6} {'rms':>10} {'anisotropy':>12} {'eff_rank':>10}"] | |
| for r in rows: | |
| lines.append(f"{r['stage']:>6} {r['rms']:>10.3f} {r['anisotropy']:>12.3f} {r['eff_rank']:>10.1f}") | |
| return "\n".join(lines) | |