mirror of
https://github.com/tailscale/tailscale.git
synced 2025-12-03 02:21:58 +00:00
net/dns: replace resolver IPs with type for DoH
We currently plumb full URLs for DNS resolvers from the control server down to the client. But when we pass the values into the net/dns package, we throw away any URL that isn't a bare IP. This commit continues the plumbing, and gets the URL all the way to the built in forwarder. (It stops before plumbing URLs into the OS configurations that can handle them.) For #2596 Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
This commit is contained in:
committed by
David Crawshaw
parent
7bfd4f521d
commit
9502b515f1
@@ -11,6 +11,7 @@ import (
|
||||
|
||||
"inet.af/netaddr"
|
||||
"tailscale.com/net/dns/resolver"
|
||||
"tailscale.com/types/dnstype"
|
||||
"tailscale.com/util/dnsname"
|
||||
)
|
||||
|
||||
@@ -20,14 +21,14 @@ type Config struct {
|
||||
// which aren't covered by more specific per-domain routes below.
|
||||
// If empty, the OS's default resolvers (the ones that predate
|
||||
// Tailscale altering the configuration) are used.
|
||||
DefaultResolvers []netaddr.IPPort
|
||||
DefaultResolvers []dnstype.Resolver
|
||||
// Routes maps a DNS suffix to the resolvers that should be used
|
||||
// for queries that fall within that suffix.
|
||||
// If a query doesn't match any entry in Routes, the
|
||||
// DefaultResolvers are used.
|
||||
// A Routes entry with no resolvers means the route should be
|
||||
// authoritatively answered using the contents of Hosts.
|
||||
Routes map[dnsname.FQDN][]netaddr.IPPort
|
||||
Routes map[dnsname.FQDN][]dnstype.Resolver
|
||||
// SearchDomains are DNS suffixes to try when expanding
|
||||
// single-label queries.
|
||||
SearchDomains []dnsname.FQDN
|
||||
@@ -45,7 +46,7 @@ type Config struct {
|
||||
// spammy stuff like *.arpa entries and replacing it with a total count.
|
||||
func (c *Config) WriteToBufioWriter(w *bufio.Writer) {
|
||||
w.WriteString("{DefaultResolvers:")
|
||||
resolver.WriteIPPorts(w, c.DefaultResolvers)
|
||||
resolver.WriteDNSResolvers(w, c.DefaultResolvers)
|
||||
|
||||
w.WriteString(" Routes:")
|
||||
resolver.WriteRoutes(w, c.Routes)
|
||||
@@ -65,10 +66,21 @@ func (c Config) hasRoutes() bool {
|
||||
return len(c.Routes) > 0
|
||||
}
|
||||
|
||||
// hasDefaultResolversOnly reports whether the only resolvers in c are
|
||||
// DefaultResolvers.
|
||||
func (c Config) hasDefaultResolversOnly() bool {
|
||||
return c.hasDefaultResolvers() && !c.hasRoutes()
|
||||
// hasDefaultIPResolversOnly reports whether the only resolvers in c are
|
||||
// DefaultResolvers, and that those resolvers are simple IP addresses.
|
||||
func (c Config) hasDefaultIPResolversOnly() bool {
|
||||
if !c.hasDefaultResolvers() || c.hasRoutes() {
|
||||
return false
|
||||
}
|
||||
for _, r := range c.DefaultResolvers {
|
||||
if ipp, err := netaddr.ParseIPPort(r.Addr); err == nil && ipp.Port() == 53 {
|
||||
continue
|
||||
}
|
||||
if _, err := netaddr.ParseIP(r.Addr); err != nil {
|
||||
return false
|
||||
}
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
func (c Config) hasDefaultResolvers() bool {
|
||||
@@ -78,9 +90,9 @@ func (c Config) hasDefaultResolvers() bool {
|
||||
// singleResolverSet returns the resolvers used by c.Routes if all
|
||||
// routes use the same resolvers, or nil if multiple sets of resolvers
|
||||
// are specified.
|
||||
func (c Config) singleResolverSet() []netaddr.IPPort {
|
||||
func (c Config) singleResolverSet() []dnstype.Resolver {
|
||||
var (
|
||||
prev []netaddr.IPPort
|
||||
prev []dnstype.Resolver
|
||||
prevInitialized bool
|
||||
)
|
||||
for _, resolvers := range c.Routes {
|
||||
@@ -89,7 +101,7 @@ func (c Config) singleResolverSet() []netaddr.IPPort {
|
||||
prevInitialized = true
|
||||
continue
|
||||
}
|
||||
if !sameIPPorts(prev, resolvers) {
|
||||
if !sameResolverNames(prev, resolvers) {
|
||||
return nil
|
||||
}
|
||||
}
|
||||
@@ -108,16 +120,29 @@ func (c Config) matchDomains() []dnsname.FQDN {
|
||||
return ret
|
||||
}
|
||||
|
||||
func sameIPPorts(a, b []netaddr.IPPort) bool {
|
||||
func sameResolverNames(a, b []dnstype.Resolver) bool {
|
||||
if len(a) != len(b) {
|
||||
return false
|
||||
}
|
||||
for i := range a {
|
||||
if a[i].Addr != b[i].Addr {
|
||||
return false
|
||||
}
|
||||
if !sameIPs(a[i].BootstrapResolution, b[i].BootstrapResolution) {
|
||||
return false
|
||||
}
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
func sameIPs(a, b []netaddr.IP) bool {
|
||||
if len(a) != len(b) {
|
||||
return false
|
||||
}
|
||||
for i := range a {
|
||||
if a[i] != b[i] {
|
||||
return false
|
||||
}
|
||||
}
|
||||
|
||||
return true
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user