DMARC Record Checker
Enter a domain and we will break the record down tag by tag, explain what each one means, and check that external report addresses are authorised. That last part is what most often breaks reporting.
What DMARC is and what it adds to SPF and DKIM
DMARC (RFC 9989) is a TXT record at _dmarc.example.com in which the domain owner tells receivers three things: which mail to treat as genuine, what to do with the rest, and where to send reports.
SPF and DKIM answer technical questions: is this server allowed, and was the message altered. Neither tells the receiver what to do when a check fails, and neither looks at the From address the recipient sees. DMARC closes both gaps: it sets the policy and requires the authenticated domain to match the From domain.
The second reason to deploy it is reporting. Daily or more often, mailbox providers send a summary: how much mail claimed to be from you, from which addresses, and how much passed authentication. Without that data you know nothing about spoofing, or about your own campaigns quietly failing authentication.
How DMARC reaches a verdict
The receiver takes the domain from the From header and looks for a record at its _dmarc name. If there is none, it walks up the DNS tree to the organizational domain. RFC 9989 added this tree walk; before it, receivers relied on the public suffix list alone. The message then passes if at least one of these holds:
- SPF passed and the envelope domain aligns with From;
- DKIM passed and the d= domain of the signature aligns with From.
The two are evaluated independently, and one is enough. SPF passing for somebody else's domain contributes nothing, and the same goes for DKIM. If neither holds, the receiver applies the policy from p (or sp and np for subdomains).
About domain alignment
Two tags set the mode: aspf for SPF and adkim for DKIM. Both default to r, relaxed: the domains must share an organizational domain, so a signature from news.example.com counts for From on example.com. Strict mode s demands a literal match, and the subdomain no longer passes.
Strict alignment is rarely needed. It stops spoofing from subdomains, but only works when every sending path signs with exactly the domain shown in From. Turning it on while you send through a service is a reliable way to break your own mail.
Why DMARC fails when SPF and DKIM both pass
The most common complaint: both checks are green on their own and DMARC is red. By default a sending service uses its own envelope, so SPF passes for its domain, and signs with its own key, so DKIM passes for that same domain. Both results are real, and neither aligns with your From.
The fix is connecting your own domain inside the service. For DKIM you publish a selector on your domain, usually a CNAME to the service's key, and the signature starts carrying your domain. For SPF you set up your own Return-Path on a subdomain, if the service supports it. One of the two is enough, but DKIM is the better one to rely on: forwarding breaks SPF, while the signature stays valid as long as nobody edits the message. The alignment of a specific message shows up in the email header analyzer.
Three stages of rollout
- p=none: monitoring. Delivery is unchanged, reports accumulate.
- p=quarantine: failing mail is treated as suspicious and usually lands in spam.
- p=reject: failing mail is refused, usually during the SMTP session, and reaches neither the inbox nor spam. This is the end goal for a domain that wants protection from spoofing.
The t=y flag replaced the old pct. With it, receivers apply the policy one step softer: quarantine acts as none, reject as quarantine. The flag does not affect reports and changes nothing under p=none.
Since February 2024 Gmail has required DMARC from anyone sending more than 5,000 messages a day to its accounts, and Yahoo from bulk senders. Both accept p=none as long as the check passes and the From domain is aligned. DMARC on its own does not guarantee the inbox, though. Details are in our breakdowns of the Gmail requirements and the Yahoo requirements.
Example record and its tags
v=DMARC1; p=quarantine; sp=quarantine; np=reject; rua=mailto:dmarc@example.com; adkim=r; aspf=rUnder RFC 9989 only the v tag has to come first, and the rest can be in any order. The older RFC 7489 required p right after it, which is why most records are still written that way. A record on the organizational domain also covers subdomains that have none of their own.
p,sp,np: the policy for the domain itself, for its subdomains, and for subdomains that do not exist in DNS. Mail from non-existent subdomains is almost always forged. Withoutnp,spapplies; withoutsp,pdoes.t: test mode, described above.ruaandruf: addresses for aggregate and failure reports.adkimandaspf: the alignment mode.fo: when to send failure reports;psd: a marker for public suffixes and complex domain hierarchies that an ordinary domain does not need.
RFC 9989 removed pct, rf and ri, and receivers on the new standard ignore them. The one exception is BIMI: its draft still refuses a pct below 100 under p=quarantine, and the logo is not shown.
The order to tighten the policy
Jumping straight to p=reject is the single most common way to lose mail: a misconfigured DMARC hurts delivery. The sequence that works takes a couple of months:
p=nonewith a reporting address. Nothing is blocked; you are simply watching who sends as you. Keep it for two to four weeks.- Bring every one of your own senders to
dkim=passwith an aligned domain. p=quarantine, witht=yfor the first weeks until reports confirm your own mail passes. Then drop the flag, and suspect mail lands in spam rather than disappearing.p=reject. By this point the reports should show no legitimate source still failing.
We would not compress this. The time goes not into technical work but into collecting enough reporting history to cover every sender. Infrequent sources such as annual notices and seasonal campaigns otherwise never show up in the sample and break at the worst possible moment.
How to read DMARC reports
Aggregate reports arrive as a compressed XML file. Reading them by eye is unpleasant, but the structure is simple: for every IP address that sent mail claiming to be your domain, you get a message count, the SPF and DKIM outcomes and the policy applied.
The point of the first few weeks is inventory, not catching attackers. Almost always two or three legitimate senders turn up that everyone had forgotten: an invoicing service, the contact form on the website, the finance team's CRM. Those need to pass authentication before you tighten anything.
If reports go to another domain, such as a report-processing service, that domain must confirm it accepts them with a record at example.com._report._dmarc.service.com holding v=DMARC1. Without it receivers skip the address, and no reports arrive, with no error anywhere. The checker above tests that record for every external address.
Failure reports (ruf=) contain fragments of the messages themselves, which is personal data, so many providers do not send them. Do not build a process around them.
What usually goes wrong
- The record sits at p=none for years. Nobody reads the reports, nothing is protected, but the compliance box is ticked.
- No rua. There is a policy but no feedback, so you cannot tell whether an attacker or your own sending service is failing.
- rua on an external domain without authorisation. Reports never arrive, and nothing indicates why, just silence.
- p=reject with active subdomains. Mail from subdomains starts being rejected if they have no authentication of their own.
- sp=none under a strict p. Subdomains stay wide open to spoofing.
- SPF without DKIM. Forwarded mail loses SPF and is left with no aligned check at all.
Email rejected per DMARC policy: what happened
This line means the message failed DMARC and the sending domain told receivers to reject such mail. The receiver did what your own record asked. Usually the cause is alignment, as described above: the message went through a service that sends and signs with its own domain. Less often it is forwarding without a DKIM signature, or a new service nobody connected.
Gmail's 4.7.40 and 5.7.40 errors are the opposite case: the sending domain has no DMARC record, or the record specifies no policy, and Gmail requires one from bulk senders. With 4.7.40 the mail is rate limited, with 5.7.40 it is blocked. A record with p=none is enough, and it can be put together in the DMARC generator.
Sources
- RFC 9989, section 3.2.10: relaxed and strict alignment
- RFC 9989, section 4.7: record format and tags
- RFC 9989, section 4.10: DNS tree walk
- RFC 9989, section 5.1: rollout steps for domain owners
- RFC 9989, appendix A.6: why pct was removed
- RFC 9990, section 4: verifying external report destinations
- RFC 9991: failure reports
- BIMI draft: pct=100 required under p=quarantine
- Google: email sender guidelines, from February 1, 2024
- Google: SMTP error reference, 4.7.40 and 5.7.40
- Yahoo Sender Hub: requirements for bulk senders
DMARC questions
Read next
Clean your list before moving to p=reject
A strict policy hurts domain reputation if campaigns keep going to dead addresses and spam traps. uChecker verifies your list before you send, and the first 100 addresses are free.
Check your list