Cracks in the Cryptography: Auditing DKIM Key Strength for Attack Surface
A fortress is only as strong as its weakest door; for email, that door is often a forgotten 1024-bit DKIM key on a marketing subdomain.

Most red teamers see a domain with `p=reject` in its DMARC record and move on. The front door is locked. But that's a rookie mistake. A perfect DMARC policy is a promise, not a physical law. Its entire integrity hinges on the strength of its underlying authentication mechanisms: SPF and DKIM.
While SPF is a simple IP address check, DKIM relies on public-key cryptography. And that cryptography ages. A DKIM key generated in 2017 is not the same as one generated today. The industry has moved from 1024-bit RSA keys to a 2048-bit minimum for a reason. Attackers know this. They aren't trying to break your DMARC policy; they're hunting for the one forgotten, weak DKIM key that lets them bypass it entirely.
This is a guide to thinking like they do. We're going to profile a target's DKIM infrastructure, not just to see if it exists, but to assess its actual, practical strength. We're looking for the cracks.
The Goal: Finding the Neglected Key
Let's be clear. The objective isn't to spend millions on cloud compute to factor a single 1024-bit RSA key. While technically feasible for a nation-state, it's not the point for most attackers. The presence of a 1024-bit key is a *symptom* of a much more exploitable disease: neglect.
A domain still using a weak key, especially on a non-primary selector, signals a piece of infrastructure that's been forgotten. It could be an old marketing automation platform, a legacy transactional email service, or a dev environment that was never properly decommissioned. These are the dark corners of an organization's attack surface.
Finding that key means you've found a trusted, but unmonitored, signing authority. A successful forgery using this key won't just look legitimate to a human; it will produce a `dkim=pass` verdict that satisfies the target's own DMARC policy. For a Business Email Compromise (BEC) scenario, it's the ultimate prize: a perfectly authenticated email from a trusted domain that you, the attacker, control completely.
Phase 1: Advanced Selector Enumeration
Before you can check a key's strength, you have to find the key. A domain can have dozens of DKIM selectors, each corresponding to a different sending service. The `s=` tag in a DKIM-Signature header specifies which selector was used. Our first job is to build a list of all possible selectors for a target domain.
The Defender's Advantage: DMARC RUA Reports
If you're a defender, you have the ultimate source of truth: your DMARC aggregate (`rua`) reports. These XML reports, sent by receiving mail servers, explicitly list every selector they observed for your domain, whether it passed or failed. This is the fastest way to get a complete inventory. An attacker, of course, doesn't have this luxury.
The Attacker's Toolkit: Public Records and Brute-Force
For external reconnaissance, attackers have to get creative. Certificate Transparency (CT) logs are a great starting point. Companies often register TLS certificates for subdomains that include email addresses for verification, and these records are public. An email like `admin@mailer.example.com` found in a certificate for `some-internal-tool.example.com` gives you two things: a potential subdomain (`mailer`) and a hint about their email infrastructure.
Beyond that, it's a game of educated guessing and brute-force. Most services use predictable selector patterns: `s1`, `s2`, `google`, `mandrill`, `sfmc`, `selector1`, or date-based selectors like `20240401`. You can script a simple DNS query loop to check for the existence of `[selector]._domainkey.example.com` against a wordlist of common selectors. Each `TXT` record you find is a potential key to audit.
$ dig default._domainkey.example.com TXT
; <<>> DiG 9.16.1-Ubuntu <<>> default._domainkey.example.com TXT
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 59791
;; QUESTION SECTION:
;default._domainkey.example.com. IN TXT
;; ANSWER SECTION:
default._domainkey.example.com. 300 IN TXT "v=DKIM1; k=rsa; p=MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA..."
Phase 2: Bulk Auditing Key Strength
With a list of potential selectors, the next step is to retrieve and analyze each public key. The key itself is embedded in the `p=` tag of the DKIM `TXT` record, encoded in Base64.
Decoding the Public Key
To check the key's strength, you need to extract the value of the `p=` tag, Base64-decode it, and then parse the resulting data. This data is an ASN.1 structure representing the RSA public key. The bit length of the key's modulus determines its strength. RFC 8301, published in 2018, formally recommended that signers and verifiers discontinue support for keys shorter than 2048 bits. A 1024-bit key is a clear sign of a legacy configuration.
Scripting the Audit
Manually checking dozens of keys is tedious. This is a task for automation. A simple Python script using the `dnspython` library can query for the `TXT` records, and the `cryptography` library can parse the public key. The script should iterate through your enumerated selectors, fetch the DNS record, extract the `p=` data, decode it, load it as a public key object, and then simply print the `key_size` attribute. Anything less than 2048 is a finding.
The goal is to build a table: `Domain`, `Selector`, `Key Strength`, `Notes`. You're not just looking for `1024`. You're looking for any deviation from a strong, unified policy. If the main domain uses 2048-bit keys but a marketing subdomain uses 1024, you've found an inconsistency. That's where you dig in.
Phase 3: Hunting for the `t=y` Goldmine
Alongside weak keys, there's another flag that screams 'exploit me': the test mode tag (`t=y`).
According to RFC 6376, the `t=y` tag in a DKIM record indicates that the domain is in testing mode. This is a signal to receiving mail servers that they should not treat messages from this domain as fully secured. A signature that fails validation might be ignored or given less weight, because the domain owner has explicitly stated they are still working out the kinks.
The operational impact is severe. An attacker can send a forged email from a domain with `t=y` and a deliberately invalid DKIM signature. The receiver sees the `dkim=fail` result, but upon checking the public key, also sees the `t=y` flag. The policy engine might decide not to penalize the email, effectively giving the forgery a free pass. It neutralizes the protective value of DKIM for that selector.
A Signer MAY wish to tag its keys as being in testing mode. Verifiers seeing a test mode tag in the key record SHOULD NOT treat a message from that Signer as secure, even if the signature verifies. — RFC 6376, Section 3.6.1
These are almost always found on forgotten subdomains used for development, staging, or transient marketing campaigns. Finding a `t=y` tag on a domain that actively sends email is a critical vulnerability. Your bulk audit script should be modified to parse and flag any record containing this tag.
Mapping Findings to Attack Vectors
Finding a weak key or a test-mode flag is just reconnaissance. The final step is understanding how to weaponize it.
Forgery via a Cracked 1024-bit Key
This is the endgame. If an attacker can successfully factor the 1024-bit public key to derive the private key, they gain the ability to create valid DKIM signatures for any email content they desire. They can craft a perfect spearphishing email, sign it with the stolen key, and send it. The receiving server will see a valid signature from a trusted domain, resulting in a `dkim=pass` and, if the `From` header aligns, a `dmarc=pass`. The email lands in the inbox with all the authority of the legitimate sender.
Authentication-Results: mx.example.com; dkim=pass (good signature) header.s=forgotten-selector header.d=target-domain.com; spf=pass (sender IP is 1.2.3.4) smtp.mailfrom=attacker.net; dmarc=pass (p=REJECT dis=NONE) header.from=target-domain.com
DKIM Replay vs. Forgery
It's important to distinguish this from a DKIM replay attack. In a replay, an attacker takes an existing, legitimately signed email and tries to reuse the signature on a modified message. This is often defeated because critical headers like `Subject` and `To` are usually included in the signature hash (`h=` tag), and any changes to the body will break the body hash (`bh=` tag). Forgery with a cracked private key has none of these limitations. You are the signer. You control which headers are signed and what the body contains. You can create a novel, malicious payload and generate a perfect signature for it on the fly.
Case Study: The Forgotten Marketing Key
Imagine a large enterprise, `globalcorp.com`, with a strict `p=reject` DMARC policy. Their primary mail flow through Google Workspace and Salesforce is locked down with 2048-bit DKIM keys. Everything looks secure.
However, an attacker performing the audit we've described discovers `promo2019._domainkey.events.globalcorp.com`. The subdomain `events.globalcorp.com` was used for a conference four years ago with a niche marketing email platform. The DNS record for its DKIM key is still active, and it's a 1024-bit key.
The platform was decommissioned, but nobody scrubbed the DNS. For a sophisticated threat actor, this is the opening. By factoring the key, they can now send emails from `@events.globalcorp.com`. Since `globalcorp.com` has a wildcard DMARC policy (`p=reject` on the organizational domain applies to all subdomains), a signed email from this subdomain will pass DMARC checks at receiving gateways. They can now send a highly convincing phishing email to `globalcorp.com` employees, appearing to come from an internal, trusted source. The attack doesn't target the strong front door; it slips through a rusted, forgotten side gate.
The takeaway
DMARC is not a magic shield. It's a policy language that depends on the cryptographic and infrastructural choices you make beneath it. A `p=reject` policy built on a foundation of aging, 1024-bit keys is a house of cards waiting for a light breeze.
Proactive, continuous auditing of your own public-facing DNS records is not optional. You must enumerate your selectors, validate your key strengths, and hunt for dangerous flags like `t=y` with the same vigor as an attacker. While you can script these checks manually, platforms like MailSleuth.AI can help automate this discovery and continuously monitor for configuration drift, turning a periodic fire drill into a managed process. Find your weak keys before someone else does.
We dissect phishing campaigns and email infrastructure so you don't have to.


