Преглед на файлове

libnetwork: extract DNS client exchange to method

forwardExtDNS() will now continue with the next external DNS sever if
co.ReadMsg() returns (nil, nil). Previously it would abort resolving the
query and not reply to the container client. The implementation of
ReadMsg() in the currently- vendored version of miekg/dns cannot return
(nil, nil) so the difference is immaterial in practice.

Signed-off-by: Cory Snider <csnider@mirantis.com>
Cory Snider преди 2 години
родител
ревизия
9cf8c4f689
променени са 1 файла, в които са добавени 45 реда и са изтрити 38 реда
  1. 45 38
      libnetwork/resolver.go

+ 45 - 38
libnetwork/resolver.go

@@ -452,58 +452,26 @@ func (r *resolver) dialExtDNS(proto string, server extDNSEntry) (net.Conn, error
 
 func (r *resolver) forwardExtDNS(proto string, maxSize int, query *dns.Msg) *dns.Msg {
 	queryName, queryType := query.Question[0].Name, query.Question[0].Qtype
-	var resp *dns.Msg
-	for i, extDNS := range r.extDNSList {
+	for _, extDNS := range r.extDNSList {
 		if extDNS.IPStr == "" {
 			break
 		}
-		extConn, err := r.dialExtDNS(proto, extDNS)
-		if err != nil {
-			logrus.WithField("retries", i).WithError(err).Warn("[resolver] connect failed")
-			continue
-		}
-		logrus.Debugf("[resolver] query %s (%s) from %s, forwarding to %s:%s", queryName, dns.TypeToString[queryType],
-			extConn.LocalAddr().String(), proto, extDNS.IPStr)
-
-		// Timeout has to be set for every IO operation.
-		if err := extConn.SetDeadline(time.Now().Add(extIOTimeout)); err != nil {
-			logrus.WithError(err).Error("[resolver] error setting conn deadline")
-		}
-		co := &dns.Conn{
-			Conn:    extConn,
-			UDPSize: uint16(maxSize),
-		}
-		defer co.Close()
 
 		// limits the number of outstanding concurrent queries.
 		if !r.forwardQueryStart() {
 			old := r.tStamp
 			r.tStamp = time.Now()
 			if r.tStamp.Sub(old) > logInterval {
-				logrus.Errorf("[resolver] more than %v concurrent queries from %s", maxConcurrent, extConn.LocalAddr().String())
+				logrus.Errorf("[resolver] more than %v concurrent queries", maxConcurrent)
 			}
 			continue
 		}
-
-		err = co.WriteMsg(query)
-		if err != nil {
-			r.forwardQueryEnd()
-			logrus.Debugf("[resolver] send to DNS server failed, %s", err)
-			continue
-		}
-
-		resp, err = co.ReadMsg()
-		if err != nil {
-			r.forwardQueryEnd()
-			logrus.WithError(err).Warnf("[resolver] failed to read from DNS server: %s, query: %s", extConn.RemoteAddr().String(), query.Question[0].String())
-			continue
-		}
+		resp := r.exchange(proto, extDNS, maxSize, query)
 		r.forwardQueryEnd()
-
 		if resp == nil {
-			logrus.Debugf("[resolver] external DNS %s:%s returned empty response for %q", proto, extDNS.IPStr, queryName)
-			break
+			continue
 		}
+
 		switch resp.Rcode {
 		case dns.RcodeServerFailure, dns.RcodeRefused:
 			// Server returned FAILURE: continue with the next external DNS server
@@ -544,7 +512,46 @@ func (r *resolver) forwardExtDNS(proto string, maxSize int, query *dns.Msg) *dns
 			logrus.Debugf("[resolver] external DNS %s:%s did not return any %s records for %q", proto, extDNS.IPStr, dns.TypeToString[queryType], queryName)
 		}
 		resp.Compress = true
-		break
+		return resp
+	}
+
+	return nil
+}
+
+func (r *resolver) exchange(proto string, extDNS extDNSEntry, maxSize int, query *dns.Msg) *dns.Msg {
+	queryName, queryType := query.Question[0].Name, query.Question[0].Qtype
+	extConn, err := r.dialExtDNS(proto, extDNS)
+	if err != nil {
+		logrus.WithError(err).Warn("[resolver] connect failed")
+		return nil
+	}
+	logrus.Debugf("[resolver] query %s (%s) from %s, forwarding to %s:%s", queryName, dns.TypeToString[queryType],
+		extConn.LocalAddr().String(), proto, extDNS.IPStr)
+
+	// Timeout has to be set for every IO operation.
+	if err := extConn.SetDeadline(time.Now().Add(extIOTimeout)); err != nil {
+		logrus.WithError(err).Error("[resolver] error setting conn deadline")
+	}
+	co := &dns.Conn{
+		Conn:    extConn,
+		UDPSize: uint16(maxSize),
+	}
+	defer co.Close()
+
+	err = co.WriteMsg(query)
+	if err != nil {
+		logrus.Debugf("[resolver] send to DNS server failed, %s", err)
+		return nil
+	}
+
+	resp, err := co.ReadMsg()
+	if err != nil {
+		logrus.WithError(err).Warnf("[resolver] failed to read from DNS server: %s, query: %s", extConn.RemoteAddr().String(), query.Question[0].String())
+		return nil
+	}
+
+	if resp == nil {
+		logrus.Debugf("[resolver] external DNS %s:%s returned empty response for %q", proto, extDNS.IPStr, queryName)
 	}
 	return resp
 }