Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

DNS resolver profile for ENS #1185

Merged
merged 7 commits into from
Oct 19, 2018
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
80 changes: 80 additions & 0 deletions EIPS/eip-1185.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,80 @@
---
eip: 1185
mcdee marked this conversation as resolved.
Show resolved Hide resolved
title: Storage of DNS Records in ENS
author: Jim McDonald <[email protected]>
status: Draft
type: Standards Track
category: ERC
created: 2018-06-26
requires: 137
discussions-to: https://ethereum-magicians.org/t/eip1185-dns-resolver-profile-for-ens/1589
---

## Abstract
This EIP defines a resolver profile for ENS that provides features for storage and lookup of DNS records. This allows ENS to be used as a store of authoritative DNS information.

## Motivation
ENS is a highly desirable store for DNS information. It provides the distributed authority of DNS without conflating ownership and authoritative serving of information. With ENS, the owner of a domain has full control over their own DNS records. Also, ENS has the ability (through smart contracts) for a domain's subdomains to be irrevocably assigned to another entity.

## Specification
mcdee marked this conversation as resolved.
Show resolved Hide resolved

The resolver profile to support DNS on ENS follows the resolver specification as defined in #137.

Traditionally, DNS is a zone-based system in that all of the records for a zone are kept together in the same file. This has the benefit of simplicity and atomicity of zone updates, but when transposed to ENS can result in significant gas costs for simple changes. As a result, the resolver works on the basis of record sets. A record set is uniquely defined by the tuple (domain, name, resource record type), for example the tuple (example.com, www.example.com, A) defines the record set of A records for the name www.example.com in the domain example.com. A record set can contain 0 or more values, for example if www.example.com has A records 1.2.3.4 and 5.6.7.8 then the aforementioned tuple will have two values.

The choice to work at the level of record sets rather than zones means that this specification cannot completely support some features of DNS, such as zone transfers and DNSSEC. It would be possible to build a different resolver profile that works at the zone level, however it would be very expensive to carry out updates and so is not considered further for this EIP.

The DNS resolver interface consists of two functions to set DNS information and two functions to query DNS information.

### setDNSRecords(bytes32 node, bytes data)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why not have this take the name and RRType as well? Then the resolver doesn't have the overhead of having to parse records etc.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This allows setDNSRecords() to take multiple RRsets in a single update.


`setDNSRecords()` sets, updates or clears 1 or more DNS records for a given node. It has function signature `0x0af179d7`.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should this say "a DNS RRset", rather than "1 or more DNS records"?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The data can contain multiple RRsets; we could change this to "1 or more DNS RRsets".


The arguments for the function are as follows:
- node: the namehash of the fully-qualified domain in ENS for which to set the records. Namehashes are defined in #137
- data: 1 or more DNS records in DNS wire format. Any record that is supplied without a value will be cleared. Note that all records in the same RRset should be contiguous within the data; if not then the later RRsets will overwrite the earlier one(s)

### clearDNSZone(bytes32 node)

`clearDNSZone()` removes all DNS records for the domain. It has function signature `0xad5780af`.

Although it is possible to clear records individually with `setDNSRecords()` as described above this requires the owner to know all of the records that have been set (as the resolver has no methods to iterate over the records for a given domain), and might require multiple transactions. `clearDNSZone()` removes all zone information in a single operation.
mcdee marked this conversation as resolved.
Show resolved Hide resolved

The arguments for the function is as follows:
- node: the namehash of the fully-qualified domain in ENS for which to clear the records. Namehashes are defined in #137

### dnsRecords(bytes32 node, bytes32 name, uint16 resource) view returns (bytes)

`dnsRecords()` obtains the DNS records for a given node, name and resource. It has function signature `0x2461e851`.

The arguments for the function are as follows:
- node: the namehash of the fully-qualified domain in ENS for which to set the records. Namehashes are defined in #137
- name: the `keccak256()` hash of the name of the record in DNS wire format.
mcdee marked this conversation as resolved.
Show resolved Hide resolved
- resource: the resource record ID. Resource record IDs are defined in https://en.wikipedia.org/wiki/List\_of\_DNS\_record\_types

The function returns all matching records in DNS wire format. If there are no records present the function will return nothing.

### hasDNSRecords(bytes32 node, bytes32 name) view returns (bool)

`hasDNSRecords()` reports if there are any records for the provided name in the domain. It has function signature `0x4cbf6ba4`.

This function is needed by DNS resolvers when working with wildcard resources as defined in https://tools.ietf.org/html/rfc4592

The arguments for the function are as follows:
- node: the namehash of the fully-qualified domain in ENS for which to set the records. Namehashes are defined in #137
- name: the `keccak256()` hash of the name of the record in DNS wire format.

The function returns `true` if there are any records for the provided node and name, otherwise `false`.

## Backwards compatibility
Not applicable.

## Implementation
The reference implementation of the DNS resolver is at https://github.com/wealdtech/wealdtech-solidity/blob/master/contracts/ens/DNSResolver.sol

https://github.com/wealdtech/ethereal.git can be used to test the functionality of the resolver with the "dns set", "dns get" and "dns clear" commands.
## Test Cases
Test cases for the DNS resolver are at https://github.com/wealdtech/wealdtech-solidity/blob/master/test/ens/DNSResolver.js

## Copyright
Copyright and related rights waived via [CC0](https://creativecommons.org/publicdomain/zero/1.0/).