6.5 — Causal (autoregressive) masking
Goal: Add the causal mask to the attention computation: a triangular pattern of −∞ scores that forbids any query from attending to keys at future positions. Understand how this preserves the autoregressive factorisation while letting the forward pass remain fully parallel.
1. Why this session exists
The language-modelling objective of 5.3 requires the prediction at position to depend only on tokens . Self-attention as written in 6.4 violates this: every query position attends to every key position , including future tokens.
The fix is the causal mask: a one-line modification of the score matrix that sets attention to future positions to exactly zero, while leaving the attention to past positions free. The mask is what lets a decoder-only Transformer be trained in parallel on all positions of a sequence from a single forward pass — the trick that makes Transformer pretraining feasible at LLM scale.
This session does two things:
- Define the causal mask and write it inside the scaled dot-product formula.
- Explain why we add to the pre-softmax scores rather than zeroing out post-softmax weights.[1, 2]
2. The causal constraint
For an autoregressive language model, the conditional distribution must be a function of only. If a self-attention layer at position attended to for some , then would depend on future tokens — the factorisation would be invalid, and at inference time we would not be able to use the model autoregressively.
Concretely: for query position , the attention weight on key position must satisfy
This is the causal mask condition. The output at position is then a convex combination of values at positions — never anything from the future.
3. The mask matrix and where to put it
Define the mask :
Pictorially, is lower triangular with zeros on and below the diagonal and above:
(here ). Add to the pre-softmax scores :
The exponential of is exactly , so any entry of the softmax with a score is zero in the output. The remaining entries are renormalised so that each row sums to — automatically, by the softmax denominator being computed only over the unmasked positions.
In code, is replaced by a very large negative number (e.g. , or the dtype's most-negative finite value). The result is numerically indistinguishable from after softmax.
4. Pre-softmax vs post-softmax masking
A naive alternative would be to zero out the post-softmax weights:
This is wrong. Two reasons:
(a) The rows no longer sum to 1. The softmax denominator was computed over all positions; removing some entries afterwards breaks normalisation. The output is now a fraction of a convex combination, scaled by the total weight that survived the mask. Different rows scale differently. The attention sub-layer's output magnitude varies wildly with the mask, which makes training unstable.
(b) Gradients still flow to masked positions. If depended on and at masked positions through the softmax denominator, then for is non-zero — gradient leaks to the future. Pre-softmax masking with stops gradient flow because .
Both problems vanish when we add inside the softmax: the denominator is computed only over unmasked positions, the rows sum to 1 by construction, and the gradients to masked positions are exactly zero.
This is the structural reason every Transformer implementation uses pre-softmax additive masking. Anywhere you see "boolean mask," what's actually being done is "replace masked-out scores by a large negative number before softmax."
5. Training-time parallelism
The payoff of pre-softmax masking is the one that motivates the whole design.
Suppose you have a document and you want to train the model to predict from at every position . With an RNN (5.5), this required sequential steps of the forward pass. With a Transformer using causal masking, it requires one forward pass:
- Embed the input sequence: .
- Apply self-attention with the causal mask. Each row of the output is a function of only — guaranteed by the mask even though all rows were computed in parallel.
- Apply the rest of the block (FFN, residuals, norms), all of which are per-position operations (6.8) that automatically preserve causality.
- Compute the per-position logits and the per-position cross-entropy loss (5.3 §4).
In one pass: supervised next-token predictions, corresponding losses, a single backward pass that updates the parameters using all gradient signals.
This is the trick. RNNs cannot do this — the sequential dependency in the recurrence forbids it. Self-attention can, because the causal mask makes parallel computation safe.
5.1 Inference is still sequential
The training parallelism does not extend to inference. To generate token given , we need to feed the model the current prefix, compute the logits at position , sample, append, and repeat. The mask is the same at inference — it just doesn't help: we are computing one new attention row per generation step, and we have to do them in order.
The mismatch is the source of the KV cache trick we will see in 6.14: at inference, the keys and values at positions never change once computed, so we cache them and only compute the new at each step. Training fills the entire buffer in one pass; inference incrementally appends rows.
6. Other masks: padding, sliding window, prefix-LM
The causal mask is the canonical one, but the additive- machinery handles any pattern of "this query may not attend to this key":
- Padding masks. When sequences in a batch have different lengths, the shorter ones are padded. The pad tokens must not contribute to attention. Add to the columns of the score matrix corresponding to padded keys.
- Sliding-window mask (Mistral, Longformer). Each query can attend only to a fixed window of past tokens. The mask is a "thick diagonal" — block all pairs with or . Cuts attention cost from to . Detailed in 6.13 (Part 2).
- Prefix-LM mask. The first tokens of the sequence (the "prefix") attend bidirectionally; positions after attend causally. The mask is a block matrix: full ones in the prefix block, lower triangular in the autoregressive block. Used by T5 and some instruction-tuned variants.
- Cross-attention masks. When attending between two sequences, masks can express "this target token may attend to these source tokens." Used in encoder-decoder Transformers.
All of these are additive masks applied pre-softmax, like the causal one. The only thing that varies is the pattern of zeros vs .
7. What we keep going forward
The causal mask is the single line of code that turns a self-attention layer into an autoregressive one:
From this point on, "self-attention in a decoder-only LLM" means this masked form. Everything else — multi-head (6.4), positional encoding (6.6, 6.7), FFN (6.8), residuals and norms (Part 2) — operates under the causal-mask assumption.
(a) Show that applying softmax row-wise to (with the causal mask) gives a lower-triangular attention matrix whose every row sums to 1. Verify on a example by hand.
(b) Show that for is exactly zero. (Use and the softmax formula.) Why does this mean "no gradient flows to future-position keys"?
(c) Suppose you implement causal masking by zeroing out the post-softmax weights for . Construct a small example showing that the rows no longer sum to 1, and explain why this breaks the convex-combination interpretation of attention.
(d) A document of length is trained with the causal-attention objective. How many supervised next-token predictions are made from a single forward + backward pass? Compare with an RNN trained on the same document.
(e) Construct the additive mask for a sliding-window attention with window and sequence length . Confirm that the mask is sparse (most entries are ) and that attention cost drops from entries to entries.
References
- [1]
Raschka, S. (2024). Build a Large Language Model (From Scratch), Chapters 3–4. Manning. — Self-attention implementation (6.3, 6.4), causal masking (6.5), pre-norm block (6.10–6.11).
↩ - [2]
Radford, A., Narasimhan, K., Salimans, T., & Sutskever, I. (2018). "Improving language understanding by generative pre-training" (GPT-1). OpenAI technical report. — Decoder-only Transformer with causal self-attention (6.3, 6.5); first use of learned PE (Appendix 6.B).
↩