CUDA Tape Operations: Attention #
Keep the original matrices available when scaling a native contraction loses range.
One device flag gates the host transfer. A flagged call downloads its original operands and reuses the reference contraction's finite-coefficient replay, in the buffer's actual precision. The guard is conservative: zero contractions, including exact orthogonality, can also take this CPU path. Nonfinite inputs retain the native result. This is range recovery, not a proof of ATen.
Instances For
Apply the centered softmax VJP without discarding the original matrix cotangent.
Contraction range loss or a nonfinite centered result triggers recovery; otherwise the ordinary
GPU operations are retained. A flagged finite contraction is reconstructed through the pullback
using the saved probabilities, rather than first rounding gradient @ valueᵀ to infinity.
Nonfinite original operands or saved probabilities retain the ordinary native buffer.
Instances For
The normalized product's local pullback, including its differentiable multiplier. Recovery uses the actual saved probabilities and retains the original contraction through the multiplier. The existing scalar-product guard also checks the pointwise factors, requiring a device-flag synchronization in addition to the output-finiteness checks. Fully blocked rows suppress their upstream values. Elsewhere nonfinite originals keep native results rather than round-trip NaN payloads.
Instances For
Compose scaled dot-product attention from numerical buffer operations.
Inputs have shape (batch, n, d); an optional (batch, n, n) mask marks allowed entries.
Returns the output and saved probabilities. The caller owns both buffers and keeps Q/K/V and
probabilities alive until backward. Blocked probabilities and fully blocked rows are zero.
Instances For
Attention's local VJP, composed in Lean from the saved probabilities and numerical primitives.
dP = dOut Vᵀ. For each row, choose a maximal-probability coordinate and subtract its
dP value: centered = dP - anchor, dS = P * (centered - sum(P * centered)).
For normalized exact-real probabilities this is the usual softmax VJP; rounded probabilities
need not sum exactly to one, so the centered and uncentered computations can differ.
dQ = scale * dS K, dK = scale * dSᵀ Q, and dV = Pᵀ dOut.
All arguments are borrowed. Fully blocked rows contribute zero even for nonfinite cotangents.
The contraction check can replay finite dOut and V through the complete centered pullback
using the actual saved probabilities. This can recover a finite score cotangent even when dP
cannot be represented on its own. Native operations, transfers, and codecs remain trust boundaries.
Instances For
Record a row-normalized matrix product on the existing native tape. Only saved probabilities are workspace; input buffers remain borrowed tape parents.
Instances For
Multi-head self-attention #
Forward structure matches Spec.MultiHeadAttention.forward:
Q = x @ Wq,K = x @ Wk,V = x @ Wv- reshape to heads
(numHeads, n, headDim) - attention per head (batched):
softmax(Q Kᵀ / sqrt(headDim)) @ V - combine heads, then output projection
@ Wo
Masking:
- Blocked entries contribute zero softmax numerator, and fully blocked rows return zero.
- Lean composes forward and backward and retains probabilities on its tape.
- LibTorch executes the numerical primitives without recording an autograd graph.
- The host
Tensor Boolmask is copied to the device.
Attention on a fixed input shape, selected by the optional-batch public adapter.
Instances For
Self-attention with shared projection weights and an optional leading batch dimension.
Without batch, the input is [n, dModel]; batch := some b selects [b, n, dModel].
The head count is numHeads, including one for single-head attention.