loopformer / scripts /recurrent_qwen /lora_utils.py
mukunds's picture
Publish frozen LoopFormer pointer checkpoint and inference code
e29f88c verified
Raw History Blame Contribute Delete
1.27 kB
"""Attach PEFT LoRA only to the shared recurrent decoder group."""
from peft import LoraConfig, inject_adapter_in_model
from .model import RecurrentQwen
def attach_recurrent_lora(
model: RecurrentQwen,
*,
rank: int = 8,
alpha: int = 16,
targets: tuple[str, ...] = ("q_proj", "v_proj"),
) -> None:
"""Mutate R in place; zero-initialized B preserves the original forward.
No bias training, dropout, bridge, or adapters outside R. Original weights
remain frozen. An initial zero gradient for A is expected when B is zero.
"""
if rank < 1 or alpha < 1:
raise ValueError("LoRA rank and alpha must be positive")
valid = {"q_proj", "k_proj", "v_proj", "o_proj", "gate_proj", "up_proj", "down_proj"}
if not targets or len(set(targets)) != len(targets) or not set(targets) <= valid:
raise ValueError(f"Choose unique LoRA targets from {sorted(valid)}")
if getattr(model.recurrent, "peft_config", None):
raise ValueError("Recurrent LoRA is already attached")
config = LoraConfig(
r=rank,
lora_alpha=alpha,
target_modules=list(targets),
lora_dropout=0.0,
bias="none",
init_lora_weights=True,
)
inject_adapter_in_model(config, model.recurrent)