Why would an unused domain even need any resources records?
It’s common for domains to go unused. Sometimes they’re purchased for a potential idea or project. Other times, it’s to protect a name or trademark, or maybe they’re meant for use internally on a protected and private network. But the internet does weird stuff and sometimes there are steps that should be taken even if these domains aren’t being used.
In August of 2023, @byt3bl33d3r gave a talk at Defcon 31 called “SpamChannel: Spoofing Emails From 2 Million+ Domains and Virtually Becoming Satan,” on how he was able to use Cloudflare Workers to send email as millions of domains and pass
many all of the protections meant to stop abuse. The talk is worth watching to see how these systems can be abused. Talk: https://www.youtube.com/watch?v=NwnT15q_PS8.
One takeaway from the talk was to add a null SPF record with “v=spf1 -all” in order to stop this kind of oversight and abuse. This got me thinking: What other DNS records should be in place to protect the abuse of a publicly unused domain?
MX (Mail Exchanger) Records
If the domain isn’t used, we’ll never be receiving email. While this record can simply be left out, we can help tell the internet that’s the case. In fact, RFC 7505 “A ‘Null MX’ No Service Resource Record for Domains That Accept No Mail” provides just this mechanism. A dot ( . ).
Sender Policy Framework, SPF
Of all the resource records, SPF provides the most direct example of how to let others on the web know to not accept email for the domain. In RFC 7208 “Sender Policy Framework (SPF) for Authorizing Use of Domains in Email”, it states, “Publishing SPF records for domains that send no mail is a well-established best practice.” My experience shows that’s not the case. At least as of 2023. But it is right there in the RFC which is helpful.
Domain-based Message Authentication, Reporting, and Conformance, DMARC
This may be overkill, but in the case pointed in the talk, I believe it’s simply extra insurance to go ahead and configure. And, like SPF, configuration helps everybody else detect the abuse and is simply a good netizen practice. For DMARC, there is not a “best practice” for this use case outlined within RFC 7489: Domain-based Message Authentication, Reporting, and Conformance (DMARC). However, it’s pretty straight forward to tell the world to reject anything for this domain with the declaration below.
v=DMARC1 → Required. This directive is always the same and required. Simply tells the version, of which there is only one.
p=reject → Required. This is the Requested Mail Receiver Policy and is required for any DMARC record. “Reject” simply tells mail receivers to reject email that fails the DMARC mechanism check.
adkim=s; aspf=s → These defines strict (opp. relaxed) conformance/alignment with SPF or DKIM as required. Because there are no DKIM records for this domain and the SPF doesn’t permit a valid sender, these should fail.
sp → Note: This directive provides a policy if we were using subdomains. In its absence, all subdomains are covered by the primary policy so this isn’t required.
pct → Note: This provides a mechanism for mail receivers to apply the policy to a portion of mail received from the sending domain. This is helpful when testing out the impact of a new policy adjustment, especially for high volume senders. Default is to apply to 100 percent so this directive is unnecessary.
DomainKeys Identified Mail, DKIM
DKIM uses selectors to provide a mechanism of providing multiple public keys per signing domain. You can find the details of this within RFC 4871: DomainKeys Identified Mail (DKIM) Signatures. Because of this, when DKIM is used, it’s common to find many different selectors in use. And while some selectors are common (e.g. selector1, selector2, dkim, k1, google), there is no “default” selector we can provide a junk or null value to in order to ensure this check fails. However, requiring DKIM alignment within the DMARC policy should tell a receiving party to require valid DKIM which should always fail, thereby keeping the domain from being abused via email.
Certification Authority Authorization, CAA
CAA records allow a DNS domain name holder to specify one or more Certification Authorities authorized to issue certificates for that domain. The absence of a CAA record enables the domain holder to use any CA they want. Because this is an unused domain, there should never be a certificate issued (at least publicly) for any resources in this domain. RFC 8659: DNS Certification Authority Authorization (CAA) Resource Record provides a mechanism for disallowing CAs following the CAA standard from issuing certificates by creating a CAA record with a value of a semicolon only ( ; ).
Note: For private use of a domain name, an additional benefit of using this mechanism to block certificate issuance is with Certificate Transparency (CT) information leakage. RFC 9162 defines CT as a system of public logs that seek to eventually record all certificates issued by publicly trusted certificate authorities. Blocking them from issuing certificates aids in protecting the private use of certificates and unintended information disclosure.
Root Domain Records: A, AAAA
These records are probably unnecessary and simply personal preference. There are really two acceptable choices here: 1) no records at all, or 2) use of addresses that won’t work on a public or private network. I’ve seen folks recommend private address spaces such as 192.168.0.0/16 or 10.0.0.0/8 or 172.16.0.0/24. However, these records could be abused as they would still potentially resolve to an address that is in use on a private network. If we’re going to use an address for these records, we want it to point to an address that cannot be used. Fortunately, engineers provided options for this in the ipv4 and ipv6 address space.
ipv4 root domain A record or “@”: 192.0.2.1 RFC 5737: IPv4 Address Blocks Reserved for Documentation sets aside 192.0.2.0/24 for use in documentation and advises operators to block or otherwise make inoperable, these addresses on private, public, and local networks.
ipv6 root domain AAAA record: 2001:DB8:: RFC 3849: IPv6 Address Prefix Reserved for Documentation sets aside 2001:DB8::/32 for use in documentation and advises operators to block or otherwise make inoperable, these addresses on private, public, and local networks.
www CNAME record: There is a lot of debate about whether to use or not use www. The reality is that many things, including some users, prepend a domain name with www for a myriad of reasons. I usually throw this in there to save them a step and give them the domain root answer right away. And with CNAME flattening, I don’t see any downside to including this.
Wildcard DNS: There may be benefits to using a wildcard dns record, if your provider supports this functionality. This will always provide an answer for anything at your domain instead of an NXDOMAIN response.
The DNS Security Extensions: DNSSEC
And of course, none of this ensures the party querying your domain gets a trusted response unless you are signing your zones. Make sure to enable DNSSEC on those zones. If you ever end up using the domain, it’s one less thing you’ll forget about and later have to enable anyway. More info on DNSSEC.
Putting It All Together
Here’s an example zone file with all the recommendations.