Add an option to always ignore the system resolver
This makes startup faster when DoH resolvers without a static IP are used (Google).
This commit is contained in:
parent
931916097e
commit
1d35e249c9
|
@ -42,6 +42,7 @@ type Config struct {
|
|||
SourceIPv6 bool `toml:"ipv6_servers"`
|
||||
MaxClients uint32 `toml:"max_clients"`
|
||||
FallbackResolver string `toml:"fallback_resolver"`
|
||||
IgnoreSystemDNS bool `toml:"ignore_system_dns"`
|
||||
}
|
||||
|
||||
func newConfig() Config {
|
||||
|
@ -61,6 +62,7 @@ func newConfig() Config {
|
|||
SourceIPv6: false,
|
||||
MaxClients: 100,
|
||||
FallbackResolver: DefaultFallbackResolver,
|
||||
IgnoreSystemDNS: false,
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -132,6 +134,9 @@ func ConfigLoad(proxy *Proxy, svcFlag *string, config_file string) error {
|
|||
dlog.UseLogFile(*config.LogFile)
|
||||
}
|
||||
proxy.xTransport.fallbackResolver = config.FallbackResolver
|
||||
if len(config.FallbackResolver) > 0 {
|
||||
proxy.xTransport.ignoreSystemDNS = config.IgnoreSystemDNS
|
||||
}
|
||||
proxy.timeout = time.Duration(config.Timeout) * time.Millisecond
|
||||
proxy.maxClients = config.MaxClients
|
||||
proxy.mainProto = "udp"
|
||||
|
|
|
@ -14,7 +14,7 @@
|
|||
## List of servers to use
|
||||
## If this line is commented, all registered servers will be used
|
||||
|
||||
# server_names = ['scaleway-fr', 'google', 'yandex']
|
||||
#server_names = ['scaleway-fr', 'google', 'yandex']
|
||||
|
||||
|
||||
## List of local addresses and ports to listen to. Can be IPv4 and/or IPv6.
|
||||
|
@ -93,6 +93,11 @@ cert_refresh_delay = 30
|
|||
fallback_resolver = "9.9.9.9:53"
|
||||
|
||||
|
||||
## Never try to use the system DNS settings; unconditionally use the
|
||||
## fallback resolver.
|
||||
|
||||
ignore_system_dns = false
|
||||
|
||||
|
||||
#########################
|
||||
# Filters #
|
||||
|
|
|
@ -30,6 +30,7 @@ type XTransport struct {
|
|||
timeout time.Duration
|
||||
cachedIPs CachedIPs
|
||||
fallbackResolver string
|
||||
ignoreSystemDNS bool
|
||||
}
|
||||
|
||||
func NewXTransport(timeout time.Duration) *XTransport {
|
||||
|
@ -37,6 +38,7 @@ func NewXTransport(timeout time.Duration) *XTransport {
|
|||
cachedIPs: CachedIPs{cache: make(map[string]string)},
|
||||
timeout: timeout,
|
||||
fallbackResolver: DefaultFallbackResolver,
|
||||
ignoreSystemDNS: false,
|
||||
}
|
||||
dialer := &net.Dialer{Timeout: timeout, KeepAlive: timeout, DualStack: true}
|
||||
transport := &http.Transport{
|
||||
|
@ -87,6 +89,49 @@ func (xTransport *XTransport) Fetch(method string, url *url.URL, accept string,
|
|||
if body != nil {
|
||||
req.Body = *body
|
||||
}
|
||||
var err error
|
||||
host := url.Host
|
||||
xTransport.cachedIPs.RLock()
|
||||
cachedIP := xTransport.cachedIPs.cache[host]
|
||||
xTransport.cachedIPs.RUnlock()
|
||||
if !xTransport.ignoreSystemDNS || len(cachedIP) > 0 {
|
||||
start := time.Now()
|
||||
resp, err := client.Do(req)
|
||||
rtt := time.Since(start)
|
||||
if err == nil {
|
||||
if resp == nil {
|
||||
err = errors.New("Webserver returned an error")
|
||||
} else if resp.StatusCode < 200 || resp.StatusCode > 299 {
|
||||
err = fmt.Errorf("Webserver returned code %d", resp.StatusCode)
|
||||
}
|
||||
return resp, rtt, err
|
||||
}
|
||||
dlog.Debugf("[%s]: [%s]", req.URL, err)
|
||||
} else {
|
||||
dlog.Debug("Ignoring system DNS")
|
||||
}
|
||||
if len(cachedIP) > 0 && err != nil {
|
||||
dlog.Debugf("IP for [%s] was cached to [%s], but connection failed: [%s]", host, cachedIP, err)
|
||||
return nil, 0, err
|
||||
}
|
||||
dnsClient := new(dns.Client)
|
||||
msg := new(dns.Msg)
|
||||
msg.SetQuestion(dns.Fqdn(host), dns.TypeA)
|
||||
msg.SetEdns0(4096, true)
|
||||
dlog.Noticef("System DNS configuration not usable yet, exceptionally resolving [%s] using fallback resolver [%s]", host, xTransport.fallbackResolver)
|
||||
in, _, err := dnsClient.Exchange(msg, xTransport.fallbackResolver)
|
||||
if err != nil {
|
||||
return nil, 0, err
|
||||
}
|
||||
if len(in.Answer) <= 0 {
|
||||
return nil, 0, fmt.Errorf("No IP found for [%s]", host)
|
||||
}
|
||||
foundIP := in.Answer[0].(*dns.A).A.String()
|
||||
xTransport.cachedIPs.Lock()
|
||||
xTransport.cachedIPs.cache[host] = foundIP
|
||||
xTransport.cachedIPs.Unlock()
|
||||
dlog.Debugf("[%s] IP address [%s] added to the cache", host, foundIP)
|
||||
|
||||
start := time.Now()
|
||||
resp, err := client.Do(req)
|
||||
rtt := time.Since(start)
|
||||
|
@ -96,43 +141,9 @@ func (xTransport *XTransport) Fetch(method string, url *url.URL, accept string,
|
|||
} else if resp.StatusCode < 200 || resp.StatusCode > 299 {
|
||||
err = fmt.Errorf("Webserver returned code %d", resp.StatusCode)
|
||||
}
|
||||
return resp, rtt, err
|
||||
}
|
||||
host := url.Host
|
||||
xTransport.cachedIPs.RLock()
|
||||
cachedIP := xTransport.cachedIPs.cache[host]
|
||||
xTransport.cachedIPs.RUnlock()
|
||||
if len(cachedIP) > 0 {
|
||||
dlog.Debugf("IP for [%s] was cached to [%s], but connection failed: [%s]", host, cachedIP, err)
|
||||
return resp, rtt, err
|
||||
}
|
||||
dnsClient := new(dns.Client)
|
||||
msg := new(dns.Msg)
|
||||
msg.SetQuestion(dns.Fqdn(host), dns.TypeA)
|
||||
msg.SetEdns0(4096, true)
|
||||
dlog.Noticef("System DNS configuration not usable yet, exceptionally resolving [%s] using fallback resolver [%s]", host, xTransport.fallbackResolver)
|
||||
in, _, err := dnsClient.Exchange(msg, xTransport.fallbackResolver)
|
||||
if err != nil {
|
||||
return resp, rtt, err
|
||||
}
|
||||
if len(in.Answer) <= 0 {
|
||||
return resp, rtt, fmt.Errorf("No IP found for [%s]", host)
|
||||
}
|
||||
foundIP := in.Answer[0].(*dns.A).A.String()
|
||||
xTransport.cachedIPs.Lock()
|
||||
xTransport.cachedIPs.cache[host] = foundIP
|
||||
xTransport.cachedIPs.Unlock()
|
||||
dlog.Debugf("[%s] IP address [%s] added to the cache", host, foundIP)
|
||||
|
||||
start = time.Now()
|
||||
resp, err = client.Do(req)
|
||||
rtt = time.Since(start)
|
||||
if err == nil {
|
||||
if resp == nil {
|
||||
err = errors.New("Webserver returned an error")
|
||||
} else if resp.StatusCode < 200 || resp.StatusCode > 299 {
|
||||
err = fmt.Errorf("Webserver returned code %d", resp.StatusCode)
|
||||
}
|
||||
dlog.Debugf("[%s]: [%s]", req.URL, err)
|
||||
}
|
||||
return resp, rtt, err
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue