This chapter requires IR-01 (forward swap rates from the discount curve) and IR-02 (multi-curve discounting). You should understand what a swap is and how its fixed rate is determined. No option pricing background needed; the necessary measure theory is introduced here.
By the end, you can price any ATM swaption under Black or Bachelier and read the implied volatility surface off market data.
The forward swap rate
Recall from Chapter 01 that a par swap equates fixed and floating legs. Generalising the par condition to a swap starting at $T_\alpha$ with payments at $T_{\alpha+1}, \ldots, T_\beta$, and replacing $P(0, T_i)$ with $P(t, T_i)$, the value of a payer swap (pay fixed $K$, receive floating) at time $t \leq T_\alpha$ is $V_{\text{payer}}(t) = P(t, T_\alpha) - P(t, T_\beta) - K \, A_{\alpha,\beta}(t)$, where the annuity is $A_{\alpha,\beta}(t) = \sum_{j=\alpha+1}^{\beta} \tau_j \, P(t, T_j)$. The forward swap rate $S_{\alpha,\beta}(t)$ is the fixed rate that makes $V_{\text{payer}}(t) = 0$:
At $t = 0$, everything reduces to the Chapter 01 discount factors. For the 5Y×5Y swaption used throughout this chapter (expiry $T_\alpha = 5$, swap ending $T_\beta = 10$): $P(0,5) = 0.8251$, $P(0,10) = 0.6663$, $A_{5,10}(0) = 3.64$, giving $S_{5,10}(0) = 4.36\%$.
A payer swaption gives the holder the right, at expiry $T_\alpha$, to enter a payer swap that exchanges fixed payments (red, down) for floating payments (blue, up) over $[T_\alpha, T_\beta]$. The option is exercised only if the prevailing swap rate exceeds the strike $K$.
The swaption payoff
A payer swaption with expiry $T_\alpha$ and strike $K$ gives the holder the right to enter the payer swap at expiry. They exercise only if the swap has positive value, i.e. if the prevailing swap rate exceeds $K$. The payoff at expiry is:
This is the familiar call payoff $(S - K)^+$, but on a swap rate rather than a stock price, scaled by the annuity $A_{\alpha,\beta}(T_\alpha)$. The annuity plays the role of contract size: the swaption is worth approximately $A \times 1\,\text{bp}$ in sensitivity per basis point of rate move above the strike.
Pricing in the annuity measure
We want the value today of the payoff $A_{\alpha,\beta}(T_\alpha) \cdot (S_{\alpha,\beta}(T_\alpha) - K)^+$. Under the risk-neutral measure $\mathbb{Q}$ associated with the bank-account numéraire $B(t) = \exp(\int_0^t r_s\,ds)$, the time-zero value of any $T_\alpha$-payoff $X$ is $V_0 = \mathbb{E}^{\mathbb{Q}}[B(T_\alpha)^{-1} X]$. Specialising to the swaption payoff and writing the stochastic discount factor explicitly, we have a fundamental identity that we use throughout the rest of this series, namely the risk-neutral representation of any zero-coupon bond:
Applying $V_0 = \mathbb{E}^{\mathbb{Q}}[B(T_\alpha)^{-1}\,X]$ to $X = A_{\alpha,\beta}(T_\alpha)\,(S_{\alpha,\beta}(T_\alpha) - K)^+$:
This expectation is difficult to evaluate directly because the stochastic discount factor $\exp(-\int_0^{T_\alpha} r_s\,ds)$, the annuity $A_{\alpha,\beta}(T_\alpha)$, and the forward swap rate $S_{\alpha,\beta}(T_\alpha)$ are all correlated random variables. The solution is a change of numéraire.
The idea is to choose a new numéraire that absorbs the annoying $A_{\alpha,\beta}$ factor. The annuity measure $\mathbb{Q}^A$ (also called the swap measure) is the probability measure associated with using $A_{\alpha,\beta}(t)$ as the numéraire. The annuity is a strictly positive linear combination of zero-coupon bond prices, $A_{\alpha,\beta}(t) = \sum_{j=\alpha+1}^{\beta} \tau_j P(t,T_j)$, and so qualifies as the price process of a self-financing portfolio of traded assets. By the fundamental change-of-numéraire theorem (Brigo and Mercurio, [1], Section 2.4 and Proposition 2.3.1), the price of any European payoff can be written as:
For the swaption payoff, the $A_{\alpha,\beta}(T_\alpha)$ in the numerator cancels with the denominator, giving:
Why is this useful? Under $\mathbb{Q}^A$, the forward swap rate $S_{\alpha,\beta}(t)$ is a martingale. To see this, recall the definition $S_{\alpha,\beta}(t) = (P(t,T_\alpha) - P(t,T_\beta))/A_{\alpha,\beta}(t)$. The numerator $P(t,T_\alpha) - P(t,T_\beta)$ is the time-$t$ value of a self-financing portfolio that is long one zero-coupon bond maturing at $T_\alpha$ and short one maturing at $T_\beta$, hence the price process of a tradable asset. Its ratio to the numéraire $A_{\alpha,\beta}(t)$ is therefore a $\mathbb{Q}^A$-martingale by the change-of-numéraire theorem (Brigo and Mercurio, [1], Proposition 2.3.1). A martingale has no drift, which means $S_{\alpha,\beta}(t)$ satisfies an SDE of the form:
with no $dt$ term. The pricing problem reduces to: choose a distribution for $S_{\alpha,\beta}(T_\alpha)$ and compute the expectation $\mathbb{E}^{\mathbb{Q}^A}[(S - K)^+]$. Two choices of "something" give the two industry-standard formulas.
Black's formula (lognormal model)
Assume $S_{\alpha,\beta}(t)$ is lognormally distributed under $\mathbb{Q}^A$: $dS = \sigma_B S \, dW^A$, where $\sigma_B$ is a constant (the Black volatility). Then $S_{\alpha,\beta}(T_\alpha) = S_{\alpha,\beta}(0) \exp(-\tfrac{1}{2}\sigma_B^2 T_\alpha + \sigma_B W^A_{T_\alpha})$, and the expectation has the closed-form solution:
where $\Phi(\cdot)$ is the standard normal CDF. This is structurally identical to the Black-Scholes formula, with the forward swap rate replacing the stock price and the annuity replacing the discount factor. Black vol was the dominant quoting convention for decades, but it breaks when rates are near zero or negative: the $\ln(S/K)$ term is undefined for $S \leq 0$. See Brigo and Mercurio [1], Section 1.8.1.
Bachelier's formula (normal model)
The Bachelier (normal) model assumes $S_{\alpha,\beta}(t)$ is normally distributed: $dS = \sigma_N \, dW^A$, where $\sigma_N$ is a constant (the normal volatility, in absolute terms). The swap rate can go negative under this model, which is empirically appropriate (EUR and JPY rates were negative for years). The martingale property is preserved, and the expectation gives:
where $\varphi(\cdot)$ is the standard normal PDF. At the money ($S = K$, so $d = 0$), this simplifies to $V_0 = A_{\alpha,\beta}(0) \cdot \sigma_N \sqrt{T_\alpha} / \sqrt{2\pi}$, giving a clean "vol times square root of time" scaling. See Brigo and Mercurio [1], Section 1.8.2.
Since around 2020, normal vol has become the dominant quoting convention for USD and EUR swaptions. Both formulas coexist in practice: you need to be fluent in both, and to convert between them when comparing across desks or systems.
Python implementation
The code below prices a payer swaption using the Bachelier formula. The annuity and forward swap rate are computed directly from the discount curve of Chapter 01.
# Self-contained example
import torch
from dataclasses import dataclass
@dataclass
class SwaptionSpec:
"""European swaption specification."""
expiry: float # option expiry T_exp (years)
tenor: float # swap tenor (years)
strike: float # fixed rate K
notional: float = 1.0
def bachelier_payer_swaption(
forward_rate: torch.Tensor,
strike: torch.Tensor,
expiry: torch.Tensor,
normal_vol: torch.Tensor,
annuity: torch.Tensor,
) -> torch.Tensor:
"""
Bachelier (normal) formula for a payer swaption.
V = A * [(S - K) * Phi(d) + sigma_N * sqrt(T) * phi(d)]
d = (S - K) / (sigma_N * sqrt(T))
where Phi = standard normal CDF, phi = standard normal PDF.
"""
sqrt_T = torch.sqrt(expiry)
std = normal_vol * sqrt_T
d = (forward_rate - strike) / std
# Standard normal CDF and PDF via torch
normal = torch.distributions.Normal(0, 1)
Phi_d = normal.cdf(d)
phi_d = torch.exp(normal.log_prob(d))
return annuity * (d * Phi_d + phi_d) * std
def black_payer_swaption(
forward_rate: torch.Tensor,
strike: torch.Tensor,
expiry: torch.Tensor,
lognormal_vol: torch.Tensor,
annuity: torch.Tensor,
) -> torch.Tensor:
"""
Black (lognormal) formula for a payer swaption.
V = A * [S * Phi(d+) - K * Phi(d-)]
d+/- = [ln(S/K) +/- 0.5 * sigma^2 * T] / (sigma * sqrt(T))
"""
sqrt_T = torch.sqrt(expiry)
d_plus = (torch.log(forward_rate / strike) + 0.5 * lognormal_vol**2 * expiry) / (lognormal_vol * sqrt_T)
d_minus = d_plus - lognormal_vol * sqrt_T
normal = torch.distributions.Normal(0, 1)
return annuity * (forward_rate * normal.cdf(d_plus) - strike * normal.cdf(d_minus))
# ── ATM normal vol surface (illustrative, bp p.a.) ──
# NOTE: This is a compact 7x6 subset of the 3D surface chart below,
# using the same illustrative levels for matching expiry/tenor cells.
expiries = torch.tensor([0.5, 1.0, 2.0, 3.0, 5.0, 7.0, 10.0])
tenors = torch.tensor([1.0, 2.0, 3.0, 5.0, 7.0, 10.0])
# Each row = expiry, each col = tenor (in bp)
atm_vols_bp = torch.tensor([
[63.0, 70.0, 76.0, 87.0, 93.0, 100.0], # 6M
[72.0, 80.0, 86.0, 96.0, 103.0, 109.0], # 1Y
[78.0, 87.0, 93.0, 103.0, 110.0, 116.0], # 2Y
[81.0, 90.0, 96.0, 106.0, 112.0, 118.0], # 3Y
[76.0, 85.0, 91.0, 102.0, 109.0, 115.0], # 5Y
[70.0, 79.0, 86.0, 97.0, 104.0, 111.0], # 7Y
[63.0, 72.0, 79.0, 91.0, 98.0, 106.0], # 10Y
])
# ── Price a 5Y x 5Y ATM payer swaption ──
S_fwd = torch.tensor(0.0436, requires_grad=True) # forward swap rate (5Yx5Y)
K = torch.tensor(0.0436) # ATM strike
T_exp = torch.tensor(5.0)
sigma_N = torch.tensor(102.0e-4) # 102 bp in decimal
A = torch.tensor(3.64) # annuity factor
price = bachelier_payer_swaption(S_fwd, K, T_exp, sigma_N, A)
price.backward()
print(f"5Yx5Y ATM payer swaption:")
print(f" Price = {price.item():.6f}")
print(f" Delta = {S_fwd.grad.item():.4f}")
The ATM volatility surface
There is not one swaption; there are hundreds. The market quotes ATM swaptions across a grid of expiry $T_\alpha$ and swap tenor $T_\beta - T_\alpha$. The cell at (expiry, tenor) contains the ATM normal implied volatility $\sigma_N$ for that combination. This grid is the ATM swaption volatility surface.
The surface has characteristic shapes. Short-expiry vols tend to be higher per unit time (more near-term uncertainty). Long-tenor swaps have higher absolute vol because the payoff is sensitive to more of the curve. The surface is not smooth: it reflects supply-demand dynamics, hedging flows, and structural features of each expiry-tenor bucket. The 3D visualisation below shows a realistic USD SOFR ATM normal vol surface. Note the irregularities: this is what real surfaces look like.
In the XVA context, what matters is whether your model can fit the ATM surface across the expiry-tenor grid. Hull-White 1F (Chapter 05, Draft) fits the ATM surface reasonably well, which is sufficient for most CVA calculations. For more precise swaption-driven exposures or for capturing the smile (how vol changes with strike), you would need SABR or a stochastic-vol extension, but that is beyond the scope of this series.
Summary
This chapter derived two pricing formulas for European swaptions: Black's formula (lognormal forward swap rate) and Bachelier's formula (normal forward swap rate). Both rest on the change of numeraire from the risk-neutral measure to the annuity measure, under which the forward swap rate $S_{\alpha,\beta}(t)$ is a martingale. The ATM volatility surface, a grid of implied volatilities indexed by expiry and tenor, encodes the market's view of future rate uncertainty and serves as the calibration target for the Hull-White model.
The swaption market is the calibration target for any interest rate model. When Chapter 05 (Draft) calibrates Hull-White, it will find parameters $a$ and $\sigma$ by matching the model's swaption prices to market prices from this surface. The Bachelier formula is the inversion function: given a market price, compute $\sigma_N$; given model parameters, compute a model price; minimise the difference. The ATM vol surface defines what "correct calibration" means.
Swaptions have positive observed market prices. This is only possible if rates are random: a deterministic path implies zero option value. In IR-04, we make this precise: we show formally why rates must be modelled as stochastic processes, and introduce the Wiener process as the simplest mathematical object with the right properties. The swaption volatility surface we built here becomes the calibration target in IR-06 (draft).
References
- D. Brigo and F. Mercurio, Interest Rate Models: Theory and Practice, 2nd edition, Springer, 2006. Sections 1.4 (swap pricing), 1.8 (swaptions), 2.2-2.4 (change of numeraire), and 6.3 (swaption pricing under specific models).
- R. Rebonato, Volatility and Correlation, 2nd edition, Wiley, 2004. Chapters 6-8 cover the swaption volatility surface, smile dynamics, and calibration targets.
- F. Black, "The Pricing of Commodity Contracts," Journal of Financial Economics, 3(1-2), 1976. The original Black formula.
- L. Bachelier, "Théorie de la Spéculation," Annales Scientifiques de l'École Normale Supérieure, 1900. The earliest option pricing model.