TL;DR
DMARC protects a domain from email spoofing and phishing by instructing receiving servers to reject unauthenticated messages. Prerequisites are correctly configured SPF and DKIM records. Implementation proceeds in stages from p=none (monitoring) through p=quarantine to p=reject. Forensic and aggregate reports enable analysis of all email flows before tightening the policy. Mistakes like premature p=reject or missing email services in SPF block legitimate emails.
Table of Contents (8 sections)
Email spoofing—sending emails with a forged sender address—is one of the most common techniques used in phishing attacks and CEO fraud. DMARC (Domain-based Message Authentication, Reporting, and Conformance) closes this gap by telling email recipients how to handle messages that fail authentication. Implementation requires care—a misconfigured DMARC record with p=reject can block legitimate emails.
Why DMARC Is Essential
Problem without DMARC:
Attacker sends:
From: ceo@unternehmen.de
→ No SPF, no DKIM → receiving servers accept it anyway!
→ Employee sees legitimate sender → clicks on link → attack!
2024 statistics:
→ 3.4 billion phishing emails daily
→ 94% of all malware attacks start with an email
→ CEO fraud losses: >$26 billion worldwide (since 2013)
DMARC protection:
With DMARC p=reject:
→ Email without SPF/DKIM alignment → rejected immediately!
→ Attackers can no longer misuse your domain (technically!)
→ No DMARC-compliant spoofing possible
DMARC requirements:
□ SPF record for all sending domains
□ DKIM signing for all outgoing emails
□ DMARC works ONLY if SPF or DKIM is configured!
Step 1: Configure SPF correctly
SPF (Sender Policy Framework) - Requirement #1:
SPF record created in DNS (TXT record for the domain):
v=spf1 [mechanisms] [qualifier]
Qualifier:
+ (Pass, Default): IP is authorized to send
- (Fail): IP is NOT authorized → reject
~ (SoftFail): Not authorized, but only flag (for migration)
? (Neutral): No statement
Mechanisms:
include:mxserver.example.com → Include the other domain’s SPF
ip4:203.0.113.0/24 → Allow IPv4 range
ip6:2001:db8::/32 → Allow IPv6 range
mx → Allow the domain’s MX server
a → Allow the domain’s A record
all → Everything (as the last element!)
Typical SPF records:
# Only Google Workspace + own IP:
v=spf1 include:_spf.google.com ip4:203.0.113.1 -all
# Microsoft 365 + Mailchimp + own IP:
v=spf1 include:spf.protection.outlook.com include:servers.mcsv.net ip4:203.0.113.1 -all
# Multiple email services:
v=spf1 include:_spf.google.com include:sendgrid.net include:mailgun.org ip4:203.0.113.1 -all
SPF pitfalls:
→ Maximum 10 DNS lookups! (include: counts; every subdomain resolution counts)
→ More than 10 → SPF "PermError" → DMARC fails!
→ Solution: SPF flattening services (convert includes to IPs)
# Test SPF:
dig TXT example.com | grep spf
# Tool: MXToolbox SPF Check, DMARC Analyzer
Step 2: Configure DKIM
DKIM (DomainKeys Identified Mail) - Prerequisite #2:
How DKIM works:
Outgoing email: Header is signed with a private key
Recipient verifies: Signature with public key (from DNS)
DNS record (TXT record for Selector._domainkey.example.com):
mail._domainkey.example.com. IN TXT "v=DKIM1; k=rsa; p=MIIBIjANBgkq..."
# "mail" = Selector (may vary, e.g., "google", "mg" for Mailgun)
DKIM for various email providers:
Google Workspace:
→ Admin Console → Apps → Gmail → Authentication
→ Enable DKIM → Copy DNS record from the console
→ Selector: "google"
Microsoft 365:
→ Security.microsoft.com → Email Authentication → DKIM
→ Enable DKIM for domain → Create CNAME records
→ Selector: "selector1", "selector2"
Postfix (own mail server):
# Install OpenDKIM:
apt install opendkim opendkim-tools
# Generate key pair:
mkdir -p /etc/opendkim/keys/example.com
opendkim-genkey -s mail -d example.com
# Enter public key in DNS
cat /etc/opendkim/keys/example.com/mail.txt
# /etc/opendkim.conf:
Domain example.com
KeyFile /etc/opendkim/keys/example.com/mail.private
Selector mail
DKIM Key Rotation:
→ 1024-bit RSA: obsolete, switch to 2048 bits!
→ Annual rotation recommended
→ Keep multiple selectors active simultaneously (during rotation)
→ Activate "selector2" → deactivate the old one → deactivate "selector1"
Verify DKIM:
dig TXT mail._domainkey.example.com
# Tool: MXToolbox DKIM Lookup
Step 3: Create DMARC record
DMARC record - DNS TXT record for _dmarc.example.com:
Minimal DMARC record (monitoring mode):
v=DMARC1; p=none; rua=mailto:dmarc-reports@example.com
Full DMARC record:
v=DMARC1;
p=quarantine; # Policy: none / quarantine / reject
pct=25; # Percentage of emails to which the policy applies
sp=none; # Subdomain policy (default: p-value)
adkim=r; # DKIM alignment: r=relaxed, s=strict
aspf=r; # SPF alignment: r=relaxed, s=strict
rua=mailto:dmarc@example.com; # Aggregate reports
ruf=mailto:forensic@example.com; # Forensic reports (optional)
fo=1; # Forensic: 0=both, 1=one fails, d/s=DKIM/SPF
Alignment explained:
relaxed (r): Org domain must match (mail.example.com → example.com ✓)
strict (s): Exact domain must match (mail.example.com → example.com ✗)
DMARC policy values:
p=none: No action (reporting only!) → Initial state
p=quarantine: DMARC failure → Spam folder or soft reject
p=reject: DMARC failure → Reject immediately → Strongest protection level!
Set DNS record:
# DNS entry (with your DNS provider):
Name: _dmarc.example.com
Type: TXT
Value: v=DMARC1; p=none; rua=mailto:dmarc-reports@example.com
# Verify:
dig TXT _dmarc.example.com
Step 4: Analyze DMARC reports
Understanding aggregate reports (rua):
Reports are sent daily by receiving mail servers:
→ XML format (from Google, Microsoft, Yahoo, etc.)
→ Contains: IP address, number of emails, SPF/DKIM result, DMARC policy
XML structure (simplified):
<feedback>
<report_metadata>
<org_name>Google Inc.</org_name>
<date_range><begin>17092512001709</begin><end>33</end><begin>7</begin><end>6</end><begin>00</begin></date_range>
</report_metadata>
<policy_published>
<domain>example.com</domain>
<p>none</p>
</policy_published>
<record>
<row>
<source_ip>209.85.220.41</source_ip>
<!-- Google IP -->
<count>450</count>
<policy_evaluated>
<disposition>none</disposition>
<dkim>pass</dkim>
<!-- DKIM-Ergebnis -->
<spf>pass</spf>
<!-- SPF-Ergebnis -->
</policy_evaluated>
</row>
<row>
<source_ip>198.51.100.42</source_ip>
<!-- Unbekannte IP! -->
<count>3</count>
<policy_evaluated>
<disposition>none</disposition>
<dkim>fail</dkim>
<spf>fail</spf>
<!-- Kein SPF für diese IP! -->
</policy_evaluated>
</row>
</record>
</feedback>
→ 450 emails from Google: SPF+DKIM pass → legitimate sender ✓
→ 3 emails from 198.51.100.42: FAIL → spoofing or forgotten sender!
DMARC reporting services (XML analysis):
→ Free: Postmark DMARC (dmarcdigests.com), Google Postmaster Tools
→ Affordable: DMARC Analyzer, Valimail Monitor
→ Professional: Agari, Red Sift OnDMARC
→ Self-hosted: parsedmarc + Elasticsearch/Kibana
Step 5: Rollout Strategy
DMARC Rollout: From none to reject (recommended timeline):
Weeks 1–4: Monitoring phase (p=none)
_dmarc.example.com TXT "v=DMARC1; p=none; rua=mailto:dmarc@example.com"
Actions:
□ Collect and analyze all aggregate reports
□ Identify all sending systems (marketing, CRM, monitoring, etc.)
□ Correctly configure SPF for all senders
□ Enable DKIM for all senders
□ Goal: 100% DMARC pass rate for legitimate emails
Weeks 5–8: Quarantine 25% (initial enforcement)
_dmarc.example.com TXT "v=DMARC1; p=quarantine; pct=25; rua=..."
→ 25% of DMARC-failed emails → Spam folder (attacker traffic)
→ 75% of DMARC-failed emails: no action yet
→ Continue analyzing reports: are there any legitimate failures?
Weeks 9–12: Quarantine 75%
_dmarc.example.com TXT "v=DMARC1; p=quarantine; pct=75; rua=..."
→ 75% of attacker emails → Spam
Weeks 13–16: Quarantine 100%
_dmarc.example.com TXT "v=DMARC1; p=quarantine; pct=100; rua=..."
→ All DMARC fails → Spam
Week 17+: Reject (Full protection)
_dmarc.example.com TXT "v=DMARC1; p=reject; rua=..."
→ DMARC failure → immediately rejected → spoofing impossible!
Common rollout errors:
→ Rejecting too quickly: forgotten sender → legitimate emails rejected!
→ SPF lookup limit exceeded (>10 DNS lookups)
→ DKIM for mailing lists (list rewriting breaks DKIM signature)
→ Subdomains forgotten: marketing.example.com sends without DMARC alignment
Subdomains and Multi-Domain Scenarios
Subdomain handling:
Default: DMARC policy applies ONLY to the specified domain
_dmarc.example.com → applies to example.com emails
→ Subdomains (mail.example.com) inherit the policy
Explicit subdomain policy (sp=):
v=DMARC1; p=reject; sp=none;
→ Main domain: reject
→ Subdomains: none (no enforcement)
→ Useful if subdomains are still being configured!
Separate DMARC records for subdomains:
_dmarc.mail.example.com TXT "v=DMARC1; p=reject; ..."
→ Overrides inherited policy
Multi-domain scenarios:
example.com (main domain): DMARC p=reject
example.de (German domain): own DMARC record!
example-test.com (test domain): DMARC p=reject + SPF "-all" without IPs
→ No one can send from this domain!
Parked/Inactive Domains:
# Domains that do not send: Configure DMARC + SPF to prevent abuse!
_dmarc.oldomain.com TXT "v=DMARC1; p=reject; rua=mailto:dmarc@example.com"
oldomain.com TXT "v=spf1 -all" # No one is allowed to send
# DKIM: no key → automatically fails (ok, since SPF also fails)
DMARC Monitoring Tools
Free and affordable DMARC monitoring solutions:
Free tools:
parsedmarc (Open Source Python):
→ Reads reports from IMAP mailbox
→ Saves to Elasticsearch or CSV
→ Dashboard in Kibana or Grafana
pip install parsedmarc
parsedmarc -c parsedmarc.ini [email.xml]
Google Postmaster Tools:
→ postmaster.google.com
→ Shows delivery rates, DMARC compliance, and reputation for Google recipients
→ Free, but only for Google traffic
MXToolbox DMARC Report Analyzer:
→ mxtoolbox.com/dmarc
→ Checks DMARC record + SPF + DKIM
Cost-effective SaaS solutions:
DMARC Analyzer (Mailhardener): starting at €25/month
EasyDMARC: starting at $0 (Freemium)
Valimail Monitor: starting at $0 (Freemium)
dmarcian: starting at $249/year
Key KPIs for DMARC monitoring:
□ DMARC pass rate: Target >98% (for all legitimate senders)
□ Fail rate: decreases after rollout (spoofing traffic)
□ Sources: Do all legitimate senders have a 100% pass rate?
□ Abuse reports (call): Which IPs are spoofing the domain? Next Step
Our certified security experts will advise you on the topics covered in this article — free and without obligation.
Free · 30 minutes · No obligation
