This is the second part of DNS Security series. In this post we will talk in detail about DNSSEC. Traditionally DNS doesn't support any security mechanism. RFC 4033 defines DNSSEC architecture.
So how does a client initiate DNSSEC name resolution? The answer lies in an additional record type OPT(RRCODE =41) which is defined in RFC 6891
The very first packet a client/resolver send, look like this. Here the client is informing Authoritative Server that it accepts DNSSEC by setting DO (DNSSEC OK) bit in Flags (0x8000), Note that the last field Data length is 0 (2 bytes), but if there are further RDATA for example ECS (EDNS0 Client Subnet) then this Data length field contain length. All further Query & Response must contain this additional OPT Record.
DNS OPT Record:
- Name : 1 byte : must be 0
- Type : 2 byte : 00 29
- UDP Payload Size: 2 byte : 0x1000 , traditionally UDP packets are much smaller like 512 bytes but with DNSSEC response have lot of records. In plain-text DNS if response is larges than 512 bytes, TC(truncation bit) is set so the client can try DNS over TCP, but with this option larger packet size over UDP is possible.
- Higher bits : 1 byte : 0x00
- Version : 1 Byte : 0x00
- Flags : 2 bytes : 0x8000
- RDATALEN : 2 byte : 0x00 00
So how the DNS Resource Record(RR) are protected ?
Confidentiality and Integrity — two pillars of data security. Confidentiality ensures that encrypted information remains unreadable to unauthorized eyes, preserving its secrecy. Integrity, on the other hand, maintains the authenticity of data; it can be viewed in its original form, yet any alteration without affecting the signature is impossible, guaranteeing its trustworthiness. DNSSEC uses Integrity. RR are signed with private keys and can be verified using public keys.
DNSSEC has two type of keys
ZSK (Zone Signing Key) : This is used to sign any RR like A, TXT, SRV etc.
KSK(Key Signing Key) : These are used to sign the ZSK.
This page lists what types of algorithms with there ids, are supported.
There are 3 new type of Resource Record(RR) defined by DNSSEC.NSEC/NSEC3 I will cover in a separate post.
RRSIG: Each RR in DNSSEC will have a matching RRSIG record, this essentially contains signature. RR data is first hashed and then signed using the private key of ZSK. As can be seen below RRSIG record of ietf.org. , it uses RSA/SHA-1 algorithm , all the fields are self explainatory, key-tag field is used to match DNSKEY record.
DNSKEY: So now we have received the signature but how do we verify it ? We need public key of ZSK to verify, DNSKEY RR contains public-key information. Client can query this record type and pull the public key to verify signature in RRSIG.
Note the Key id (40452) of DNSKEY is matching RRSIG, this means that DNSKEY record contains public part of key-pair which is used to sign the RRSIG record. How this key-id is calculate is mentioned in RFC. But the question is why should we trust this public key of ZSK ? A MiTM ( Man-in-the-Middle) can send these information. As mentioned earlier, every record in DNSSEC must have a RRSIG.
RRSIG for DNSKEY of ZSK is signed using KSK.
RRSIG for DNSKEY of KSK is self-signed.
DS: Delegation Signer: Now the question is why a client would trust even KSK ? To answer this a child zone publish hash of public-key of KSK to its parents zone, which signs by its own ZSK and that's how a chain of trust is established.
Now having defined all the basics of DNSSEC, let walk though how can a DNS record are verified when a client queries for a hostname. I am referring to this cloudshark packet capture https://www.cloudshark.org/captures/79e23786259b
- Client request A (IPv4) record for www.ietf.org and in its query it insert OPT record to convey the server that it support DNSSEC.
- Server responds with A record and also attached RRSIG record for this A record.
- Now for client to verify this signature, it needs a public key. So the client queries for DNSKEY record.
- In response serve send both ZSK public key, KSK public key and there respective RRSIG.
- Client can raise the signature in RRSIG A record (obtained in Step 2) to ZSK public key and verify that both hash of A record and signature matches. A record is now verified.
- Client also verifies signature of ZSK DNSKEY RRSIG by raising to KSK public key and verify that both matches. ZSK is now verified.
- Now in order to verify the KSK, client request DS record, DS record contain hash of KSK public, which is signed by parent zone(.org.) ZSK.
- In the current setup child zone is ietf and parent zone is org and we have verified, now whole process repeats for child zone as org and parent zone as dot . (root zone)
- Root Zone is something we always trust and there is a signing ceremony every quarter where new keys of all 13 root zones are generated and distributed.
- This is how we build a chain of trust and from child zone we verifies all the records all the way up to root zone.
The above process can be visualize like this
This concludes part 1 of DNSSEC. In next part I will cover NSEC/NSEC3.
Thanks for reading and please let me know in comments if any doubts are there.