DKIM Replay Attacks
The DKIM replay problem (draft-ietf-dkim-replay-problem) — how one legitimately signed message gets resent to millions, why l=/x= don't fix it, current mitigations and their tradeoffs, and what it means for ESP infrastructure.
Foundational6 min read
Who it is for ESP operators, Senders
Applies to senders on any platform
ContentsOn this page — 5 sections
If your domain signs mail with DKIM, an attacker who gets hold of one message you signed can resend it, unchanged, to millions of new recipients, and every copy still carries your valid signature. DKIM replay is an attack on senders' infrastructure, not an attack that forges messages against recipients.
DKIM (RFC 6376) authenticates the content of a message, not its transport path or envelope. The d= domain therefore "vouches" for spam it never sent to those recipients, and the attacker spends its reputation.
The problem is described in draft-ietf-dkim-replay-problem (Chuang/Google, Crocker, Robinson/Google, Gondwana/Fastmail). Status as of 2026-07: the draft's last revision (-00) is dated 2023-07-28 and has expired. The IETF DKIM working group has since moved from describing the problem to working on a solution, DKIM2. The draft remains the reference description of the attack.
Attack mechanics
- The attacker creates or compromises an account at a sender with a high reputation, such as a free mailbox provider or an ESP free trial, and gets one message signed by the target's
d=domain. The content is the attacker's payload (spam or phishing), or a harmless message into which the payload can be inserted later (seel=below). - The attacker captures the fully signed message. This is trivial, because the attacker is the recipient: they send it to themselves.
- The attacker injects the message again, through their own infrastructure, to a new recipient list of any size. The RFC 5321 envelope (
MAIL FROM,RCPT TO) is not signed, so it can be rewritten freely. The RFC 5322 headers and body are untouched, sobh=andb=still verify. - Receivers see a valid DKIM signature, an aligned
d=from a trusted domain, and a DMARC pass. Reputation systems attribute the mail volume, and the complaints and spam classifications that follow, to the signing domain.
None of this violates RFC 6376. In fact, the RFC notes that mailing a signed message again cannot be told apart from legitimate forwarding. That is exactly the property that lets DKIM survive forwarding when SPF breaks. The core difficulty, according to the draft, is that receivers cannot tell legitimate forwarding (alias forwarding, mailing lists, "send to a friend") from a replay attack. Any simple fix that stops replay also stops forwarding.
Why existing DKIM tags don't fix it
| Tag | Why it fails |
|---|---|
l= (body length) |
It is irrelevant at best and harmful at worst. It limits which body octets are signed, but does nothing to bind the recipients. Worse, l= lets the attacker append unsigned malicious content that displays after the signed part while the signature still validates (exploited in the wild, 2024). Never sign with l=. |
x= (expiration) |
It limits how long the signature is valid, but cannot tell a legitimate 2-hour forwarding delay from a 2-hour replay campaign. Replay campaigns send their volume within minutes of obtaining the signed message, well inside any x= window long enough for real delivery delays (queue retries, greylisting, mailing-list digests). RFC 6376 itself says x= is not a defense against replay. |
t= (timestamp) |
Informational only, with the same window problem as x=. |
Signing To: |
The To: header is usually signed, but replay does not change it. The spam is delivered to RCPT TO recipients who do not appear in the signed To:. A mismatch between the signed To: and the actual recipient is also normal (Bcc, aliases, forwarding, mailing lists), so receivers cannot fail messages on that basis. |
Current mitigations and tradeoffs
DKIM as specified has no complete fix. The measures below reduce exposure and limit the damage. The fix at protocol level is the DKIM2 effort, which binds signatures to the SMTP envelope at each hop.
Sender and ESP side
| Mitigation | Mechanism | Tradeoffs |
|---|---|---|
| Oversigning | List To:, Subject:, From:, Reply-To: and Cc: in h= one more time than they occur. An attacker then cannot add another instance (for example, a second Subject that some mail clients display) without breaking the signature. |
Cheap, so always do it. It defeats only the variants that add headers. Pure replay of the unchanged message is not affected. |
Short x= expiration |
Sign with x= set a small number of hours after t=. This narrows the replay window, and old replayed copies fail. |
Legitimately delayed delivery (retries after a 4xx from the receiver, greylisting) also fails verification. Many verifiers ignore x= entirely, and attackers replay quickly. |
Separate selectors and d= domains for each stream or tenant |
Sign each customer or mail stream with its own selector or subdomain, so that a replay incident damages the identifier of one tenant, not the platform's shared domain. | It does not prevent replay. It limits the damage to reputation, and makes the abusive tenant identifiable and its selector revocable (publish an empty p= to disable the selector). Managing the keys adds work at ESP scale. |
| Per-recipient signing | Compute a separate signature for each RCPT TO, with the recipient bound into the signed content (for example, through a signed header specific to each recipient). | The strongest option within the protocol, but it needs one signing operation and a distinct set of body and headers for each recipient, which removes the efficiency of delivering to several recipients at once. It breaks legitimate forwarding to a different address, and there is no standard for how verifiers should check the binding. |
| Checking content and recipients before the first signature | The attack requires one signed payload, so abuse controls on trial accounts, scanning of outbound content, and URL reputation checks at signing time all act as controls against DKIM replay. | An arms race. Payloads that look harmless (the l= trick, remote content) evade scanning. |
| Monitoring for volume anomalies | Watch data from Google Postmaster Tools and from feedback loops (FBLs) for spikes in spam rate and volume on a d= domain or selector that do not match your own sending logs. That mismatch is the sign of a replay in progress. |
It detects, but does not prevent. The response is to revoke the selector and escalate to the providers. |
Receiver side (what the draft discusses)
- Counting and rate observation: the same signature (or
bh=) suddenly seen across an unusually large set of unrelated recipients is the fingerprint of a replay. This needs visibility at large scale, which favors big mailbox providers, and coordination between systems. - Differences between envelope and headers: replayed mail usually shows
MAIL FROMandRCPT TOdomains unrelated to the signing domain and to the signedTo:. This can be used as a scoring signal, but not as a strict rule, because forwarding produces the same pattern. - Receivers are advised to treat a valid DKIM signature as an identifier for reputation, not as a pass that guarantees trust. Replay exploits exactly the shortcut of treating a valid signature as proof of trust.
Impact on ESPs
- ESPs are a favorite target for obtaining signed messages. A free trial gives attackers a way to get messages signed by a domain with a warmed-up reputation. One signed message from a trial account can be replayed at a volume greater than the ESP's entire legitimate daily sending.
- The damage falls on whichever
d=domain signs the message. If all customers sign with the ESP's shared domain, one incident degrades delivery for every customer. This is the strongest architectural argument for ad=domain and selectors specific to each customer (see M3AAWG Sending Domains BCP). - Incident response: identify the replayed message (from FBL samples, or a spike in spam rate in Postmaster Tools), revoke the selector (empty
p=), suspend the account it came from, and switch the legitimate stream to a new selector. Keep keys for old selectors separate for each stream, so that you can revoke precisely. - Do not respond to a replay incident by adding
l=or by removingTo:fromh=. Both make things worse.
Related articles
- DKIM, including oversigning and
l= - DKIM2, the protocol redesign in progress, whose envelope binding is the actual fix
- Reputation Monitoring, on detecting the spike
Check your own record
The free check reads what your domain publishes in DNS.
In this topic
- SPF (Sender Policy Framework)
- DKIM (DomainKeys Identified Mail)
- DKIM Key Rotation
- DKIM2 (in-progress IETF work)