1// DNS server implementation.
2
3package dns
4
5import (
6	"context"
7	"crypto/tls"
8	"encoding/binary"
9	"errors"
10	"io"
11	"net"
12	"strings"
13	"sync"
14	"time"
15)
16
17// Default maximum number of TCP queries before we close the socket.
18const maxTCPQueries = 128
19
20// aLongTimeAgo is a non-zero time, far in the past, used for
21// immediate cancelation of network operations.
22var aLongTimeAgo = time.Unix(1, 0)
23
24// Handler is implemented by any value that implements ServeDNS.
25type Handler interface {
26	ServeDNS(w ResponseWriter, r *Msg)
27}
28
29// The HandlerFunc type is an adapter to allow the use of
30// ordinary functions as DNS handlers.  If f is a function
31// with the appropriate signature, HandlerFunc(f) is a
32// Handler object that calls f.
33type HandlerFunc func(ResponseWriter, *Msg)
34
35// ServeDNS calls f(w, r).
36func (f HandlerFunc) ServeDNS(w ResponseWriter, r *Msg) {
37	f(w, r)
38}
39
40// A ResponseWriter interface is used by an DNS handler to
41// construct an DNS response.
42type ResponseWriter interface {
43	// LocalAddr returns the net.Addr of the server
44	LocalAddr() net.Addr
45	// RemoteAddr returns the net.Addr of the client that sent the current request.
46	RemoteAddr() net.Addr
47	// WriteMsg writes a reply back to the client.
48	WriteMsg(*Msg) error
49	// Write writes a raw buffer back to the client.
50	Write([]byte) (int, error)
51	// Close closes the connection.
52	Close() error
53	// TsigStatus returns the status of the Tsig.
54	TsigStatus() error
55	// TsigTimersOnly sets the tsig timers only boolean.
56	TsigTimersOnly(bool)
57	// Hijack lets the caller take over the connection.
58	// After a call to Hijack(), the DNS package will not do anything with the connection.
59	Hijack()
60}
61
62// A ConnectionStater interface is used by a DNS Handler to access TLS connection state
63// when available.
64type ConnectionStater interface {
65	ConnectionState() *tls.ConnectionState
66}
67
68type response struct {
69	closed         bool // connection has been closed
70	hijacked       bool // connection has been hijacked by handler
71	tsigTimersOnly bool
72	tsigStatus     error
73	tsigRequestMAC string
74	tsigSecret     map[string]string // the tsig secrets
75	udp            net.PacketConn    // i/o connection if UDP was used
76	tcp            net.Conn          // i/o connection if TCP was used
77	udpSession     *SessionUDP       // oob data to get egress interface right
78	pcSession      net.Addr          // address to use when writing to a generic net.PacketConn
79	writer         Writer            // writer to output the raw DNS bits
80}
81
82// handleRefused returns a HandlerFunc that returns REFUSED for every request it gets.
83func handleRefused(w ResponseWriter, r *Msg) {
84	m := new(Msg)
85	m.SetRcode(r, RcodeRefused)
86	w.WriteMsg(m)
87}
88
89// HandleFailed returns a HandlerFunc that returns SERVFAIL for every request it gets.
90// Deprecated: This function is going away.
91func HandleFailed(w ResponseWriter, r *Msg) {
92	m := new(Msg)
93	m.SetRcode(r, RcodeServerFailure)
94	// does not matter if this write fails
95	w.WriteMsg(m)
96}
97
98// ListenAndServe Starts a server on address and network specified Invoke handler
99// for incoming queries.
100func ListenAndServe(addr string, network string, handler Handler) error {
101	server := &Server{Addr: addr, Net: network, Handler: handler}
102	return server.ListenAndServe()
103}
104
105// ListenAndServeTLS acts like http.ListenAndServeTLS, more information in
106// http://golang.org/pkg/net/http/#ListenAndServeTLS
107func ListenAndServeTLS(addr, certFile, keyFile string, handler Handler) error {
108	cert, err := tls.LoadX509KeyPair(certFile, keyFile)
109	if err != nil {
110		return err
111	}
112
113	config := tls.Config{
114		Certificates: []tls.Certificate{cert},
115	}
116
117	server := &Server{
118		Addr:      addr,
119		Net:       "tcp-tls",
120		TLSConfig: &config,
121		Handler:   handler,
122	}
123
124	return server.ListenAndServe()
125}
126
127// ActivateAndServe activates a server with a listener from systemd,
128// l and p should not both be non-nil.
129// If both l and p are not nil only p will be used.
130// Invoke handler for incoming queries.
131func ActivateAndServe(l net.Listener, p net.PacketConn, handler Handler) error {
132	server := &Server{Listener: l, PacketConn: p, Handler: handler}
133	return server.ActivateAndServe()
134}
135
136// Writer writes raw DNS messages; each call to Write should send an entire message.
137type Writer interface {
138	io.Writer
139}
140
141// Reader reads raw DNS messages; each call to ReadTCP or ReadUDP should return an entire message.
142type Reader interface {
143	// ReadTCP reads a raw message from a TCP connection. Implementations may alter
144	// connection properties, for example the read-deadline.
145	ReadTCP(conn net.Conn, timeout time.Duration) ([]byte, error)
146	// ReadUDP reads a raw message from a UDP connection. Implementations may alter
147	// connection properties, for example the read-deadline.
148	ReadUDP(conn *net.UDPConn, timeout time.Duration) ([]byte, *SessionUDP, error)
149}
150
151// PacketConnReader is an optional interface that Readers can implement to support using generic net.PacketConns.
152type PacketConnReader interface {
153	Reader
154
155	// ReadPacketConn reads a raw message from a generic net.PacketConn UDP connection. Implementations may
156	// alter connection properties, for example the read-deadline.
157	ReadPacketConn(conn net.PacketConn, timeout time.Duration) ([]byte, net.Addr, error)
158}
159
160// defaultReader is an adapter for the Server struct that implements the Reader and
161// PacketConnReader interfaces using the readTCP, readUDP and readPacketConn funcs
162// of the embedded Server.
163type defaultReader struct {
164	*Server
165}
166
167var _ PacketConnReader = defaultReader{}
168
169func (dr defaultReader) ReadTCP(conn net.Conn, timeout time.Duration) ([]byte, error) {
170	return dr.readTCP(conn, timeout)
171}
172
173func (dr defaultReader) ReadUDP(conn *net.UDPConn, timeout time.Duration) ([]byte, *SessionUDP, error) {
174	return dr.readUDP(conn, timeout)
175}
176
177func (dr defaultReader) ReadPacketConn(conn net.PacketConn, timeout time.Duration) ([]byte, net.Addr, error) {
178	return dr.readPacketConn(conn, timeout)
179}
180
181// DecorateReader is a decorator hook for extending or supplanting the functionality of a Reader.
182// Implementations should never return a nil Reader.
183// Readers should also implement the optional PacketConnReader interface.
184// PacketConnReader is required to use a generic net.PacketConn.
185type DecorateReader func(Reader) Reader
186
187// DecorateWriter is a decorator hook for extending or supplanting the functionality of a Writer.
188// Implementations should never return a nil Writer.
189type DecorateWriter func(Writer) Writer
190
191// A Server defines parameters for running an DNS server.
192type Server struct {
193	// Address to listen on, ":dns" if empty.
194	Addr string
195	// if "tcp" or "tcp-tls" (DNS over TLS) it will invoke a TCP listener, otherwise an UDP one
196	Net string
197	// TCP Listener to use, this is to aid in systemd's socket activation.
198	Listener net.Listener
199	// TLS connection configuration
200	TLSConfig *tls.Config
201	// UDP "Listener" to use, this is to aid in systemd's socket activation.
202	PacketConn net.PacketConn
203	// Handler to invoke, dns.DefaultServeMux if nil.
204	Handler Handler
205	// Default buffer size to use to read incoming UDP messages. If not set
206	// it defaults to MinMsgSize (512 B).
207	UDPSize int
208	// The net.Conn.SetReadTimeout value for new connections, defaults to 2 * time.Second.
209	ReadTimeout time.Duration
210	// The net.Conn.SetWriteTimeout value for new connections, defaults to 2 * time.Second.
211	WriteTimeout time.Duration
212	// TCP idle timeout for multiple queries, if nil, defaults to 8 * time.Second (RFC 5966).
213	IdleTimeout func() time.Duration
214	// Secret(s) for Tsig map[<zonename>]<base64 secret>. The zonename must be in canonical form (lowercase, fqdn, see RFC 4034 Section 6.2).
215	TsigSecret map[string]string
216	// If NotifyStartedFunc is set it is called once the server has started listening.
217	NotifyStartedFunc func()
218	// DecorateReader is optional, allows customization of the process that reads raw DNS messages.
219	DecorateReader DecorateReader
220	// DecorateWriter is optional, allows customization of the process that writes raw DNS messages.
221	DecorateWriter DecorateWriter
222	// Maximum number of TCP queries before we close the socket. Default is maxTCPQueries (unlimited if -1).
223	MaxTCPQueries int
224	// Whether to set the SO_REUSEPORT socket option, allowing multiple listeners to be bound to a single address.
225	// It is only supported on go1.11+ and when using ListenAndServe.
226	ReusePort bool
227	// AcceptMsgFunc will check the incoming message and will reject it early in the process.
228	// By default DefaultMsgAcceptFunc will be used.
229	MsgAcceptFunc MsgAcceptFunc
230
231	// Shutdown handling
232	lock     sync.RWMutex
233	started  bool
234	shutdown chan struct{}
235	conns    map[net.Conn]struct{}
236
237	// A pool for UDP message buffers.
238	udpPool sync.Pool
239}
240
241func (srv *Server) isStarted() bool {
242	srv.lock.RLock()
243	started := srv.started
244	srv.lock.RUnlock()
245	return started
246}
247
248func makeUDPBuffer(size int) func() interface{} {
249	return func() interface{} {
250		return make([]byte, size)
251	}
252}
253
254func (srv *Server) init() {
255	srv.shutdown = make(chan struct{})
256	srv.conns = make(map[net.Conn]struct{})
257
258	if srv.UDPSize == 0 {
259		srv.UDPSize = MinMsgSize
260	}
261	if srv.MsgAcceptFunc == nil {
262		srv.MsgAcceptFunc = DefaultMsgAcceptFunc
263	}
264	if srv.Handler == nil {
265		srv.Handler = DefaultServeMux
266	}
267
268	srv.udpPool.New = makeUDPBuffer(srv.UDPSize)
269}
270
271func unlockOnce(l sync.Locker) func() {
272	var once sync.Once
273	return func() { once.Do(l.Unlock) }
274}
275
276// ListenAndServe starts a nameserver on the configured address in *Server.
277func (srv *Server) ListenAndServe() error {
278	unlock := unlockOnce(&srv.lock)
279	srv.lock.Lock()
280	defer unlock()
281
282	if srv.started {
283		return &Error{err: "server already started"}
284	}
285
286	addr := srv.Addr
287	if addr == "" {
288		addr = ":domain"
289	}
290
291	srv.init()
292
293	switch srv.Net {
294	case "tcp", "tcp4", "tcp6":
295		l, err := listenTCP(srv.Net, addr, srv.ReusePort)
296		if err != nil {
297			return err
298		}
299		srv.Listener = l
300		srv.started = true
301		unlock()
302		return srv.serveTCP(l)
303	case "tcp-tls", "tcp4-tls", "tcp6-tls":
304		if srv.TLSConfig == nil || (len(srv.TLSConfig.Certificates) == 0 && srv.TLSConfig.GetCertificate == nil) {
305			return errors.New("dns: neither Certificates nor GetCertificate set in Config")
306		}
307		network := strings.TrimSuffix(srv.Net, "-tls")
308		l, err := listenTCP(network, addr, srv.ReusePort)
309		if err != nil {
310			return err
311		}
312		l = tls.NewListener(l, srv.TLSConfig)
313		srv.Listener = l
314		srv.started = true
315		unlock()
316		return srv.serveTCP(l)
317	case "udp", "udp4", "udp6":
318		l, err := listenUDP(srv.Net, addr, srv.ReusePort)
319		if err != nil {
320			return err
321		}
322		u := l.(*net.UDPConn)
323		if e := setUDPSocketOptions(u); e != nil {
324			u.Close()
325			return e
326		}
327		srv.PacketConn = l
328		srv.started = true
329		unlock()
330		return srv.serveUDP(u)
331	}
332	return &Error{err: "bad network"}
333}
334
335// ActivateAndServe starts a nameserver with the PacketConn or Listener
336// configured in *Server. Its main use is to start a server from systemd.
337func (srv *Server) ActivateAndServe() error {
338	unlock := unlockOnce(&srv.lock)
339	srv.lock.Lock()
340	defer unlock()
341
342	if srv.started {
343		return &Error{err: "server already started"}
344	}
345
346	srv.init()
347
348	if srv.PacketConn != nil {
349		// Check PacketConn interface's type is valid and value
350		// is not nil
351		if t, ok := srv.PacketConn.(*net.UDPConn); ok && t != nil {
352			if e := setUDPSocketOptions(t); e != nil {
353				return e
354			}
355		}
356		srv.started = true
357		unlock()
358		return srv.serveUDP(srv.PacketConn)
359	}
360	if srv.Listener != nil {
361		srv.started = true
362		unlock()
363		return srv.serveTCP(srv.Listener)
364	}
365	return &Error{err: "bad listeners"}
366}
367
368// Shutdown shuts down a server. After a call to Shutdown, ListenAndServe and
369// ActivateAndServe will return.
370func (srv *Server) Shutdown() error {
371	return srv.ShutdownContext(context.Background())
372}
373
374// ShutdownContext shuts down a server. After a call to ShutdownContext,
375// ListenAndServe and ActivateAndServe will return.
376//
377// A context.Context may be passed to limit how long to wait for connections
378// to terminate.
379func (srv *Server) ShutdownContext(ctx context.Context) error {
380	srv.lock.Lock()
381	if !srv.started {
382		srv.lock.Unlock()
383		return &Error{err: "server not started"}
384	}
385
386	srv.started = false
387
388	if srv.PacketConn != nil {
389		srv.PacketConn.SetReadDeadline(aLongTimeAgo) // Unblock reads
390	}
391
392	if srv.Listener != nil {
393		srv.Listener.Close()
394	}
395
396	for rw := range srv.conns {
397		rw.SetReadDeadline(aLongTimeAgo) // Unblock reads
398	}
399
400	srv.lock.Unlock()
401
402	if testShutdownNotify != nil {
403		testShutdownNotify.Broadcast()
404	}
405
406	var ctxErr error
407	select {
408	case <-srv.shutdown:
409	case <-ctx.Done():
410		ctxErr = ctx.Err()
411	}
412
413	if srv.PacketConn != nil {
414		srv.PacketConn.Close()
415	}
416
417	return ctxErr
418}
419
420var testShutdownNotify *sync.Cond
421
422// getReadTimeout is a helper func to use system timeout if server did not intend to change it.
423func (srv *Server) getReadTimeout() time.Duration {
424	if srv.ReadTimeout != 0 {
425		return srv.ReadTimeout
426	}
427	return dnsTimeout
428}
429
430// serveTCP starts a TCP listener for the server.
431func (srv *Server) serveTCP(l net.Listener) error {
432	defer l.Close()
433
434	if srv.NotifyStartedFunc != nil {
435		srv.NotifyStartedFunc()
436	}
437
438	var wg sync.WaitGroup
439	defer func() {
440		wg.Wait()
441		close(srv.shutdown)
442	}()
443
444	for srv.isStarted() {
445		rw, err := l.Accept()
446		if err != nil {
447			if !srv.isStarted() {
448				return nil
449			}
450			if neterr, ok := err.(net.Error); ok && neterr.Temporary() {
451				continue
452			}
453			return err
454		}
455		srv.lock.Lock()
456		// Track the connection to allow unblocking reads on shutdown.
457		srv.conns[rw] = struct{}{}
458		srv.lock.Unlock()
459		wg.Add(1)
460		go srv.serveTCPConn(&wg, rw)
461	}
462
463	return nil
464}
465
466// serveUDP starts a UDP listener for the server.
467func (srv *Server) serveUDP(l net.PacketConn) error {
468	defer l.Close()
469
470	reader := Reader(defaultReader{srv})
471	if srv.DecorateReader != nil {
472		reader = srv.DecorateReader(reader)
473	}
474
475	lUDP, isUDP := l.(*net.UDPConn)
476	readerPC, canPacketConn := reader.(PacketConnReader)
477	if !isUDP && !canPacketConn {
478		return &Error{err: "PacketConnReader was not implemented on Reader returned from DecorateReader but is required for net.PacketConn"}
479	}
480
481	if srv.NotifyStartedFunc != nil {
482		srv.NotifyStartedFunc()
483	}
484
485	var wg sync.WaitGroup
486	defer func() {
487		wg.Wait()
488		close(srv.shutdown)
489	}()
490
491	rtimeout := srv.getReadTimeout()
492	// deadline is not used here
493	for srv.isStarted() {
494		var (
495			m    []byte
496			sPC  net.Addr
497			sUDP *SessionUDP
498			err  error
499		)
500		if isUDP {
501			m, sUDP, err = reader.ReadUDP(lUDP, rtimeout)
502		} else {
503			m, sPC, err = readerPC.ReadPacketConn(l, rtimeout)
504		}
505		if err != nil {
506			if !srv.isStarted() {
507				return nil
508			}
509			if netErr, ok := err.(net.Error); ok && netErr.Temporary() {
510				continue
511			}
512			return err
513		}
514		if len(m) < headerSize {
515			if cap(m) == srv.UDPSize {
516				srv.udpPool.Put(m[:srv.UDPSize])
517			}
518			continue
519		}
520		wg.Add(1)
521		go srv.serveUDPPacket(&wg, m, l, sUDP, sPC)
522	}
523
524	return nil
525}
526
527// Serve a new TCP connection.
528func (srv *Server) serveTCPConn(wg *sync.WaitGroup, rw net.Conn) {
529	w := &response{tsigSecret: srv.TsigSecret, tcp: rw}
530	if srv.DecorateWriter != nil {
531		w.writer = srv.DecorateWriter(w)
532	} else {
533		w.writer = w
534	}
535
536	reader := Reader(defaultReader{srv})
537	if srv.DecorateReader != nil {
538		reader = srv.DecorateReader(reader)
539	}
540
541	idleTimeout := tcpIdleTimeout
542	if srv.IdleTimeout != nil {
543		idleTimeout = srv.IdleTimeout()
544	}
545
546	timeout := srv.getReadTimeout()
547
548	limit := srv.MaxTCPQueries
549	if limit == 0 {
550		limit = maxTCPQueries
551	}
552
553	for q := 0; (q < limit || limit == -1) && srv.isStarted(); q++ {
554		m, err := reader.ReadTCP(w.tcp, timeout)
555		if err != nil {
556			// TODO(tmthrgd): handle error
557			break
558		}
559		srv.serveDNS(m, w)
560		if w.closed {
561			break // Close() was called
562		}
563		if w.hijacked {
564			break // client will call Close() themselves
565		}
566		// The first read uses the read timeout, the rest use the
567		// idle timeout.
568		timeout = idleTimeout
569	}
570
571	if !w.hijacked {
572		w.Close()
573	}
574
575	srv.lock.Lock()
576	delete(srv.conns, w.tcp)
577	srv.lock.Unlock()
578
579	wg.Done()
580}
581
582// Serve a new UDP request.
583func (srv *Server) serveUDPPacket(wg *sync.WaitGroup, m []byte, u net.PacketConn, udpSession *SessionUDP, pcSession net.Addr) {
584	w := &response{tsigSecret: srv.TsigSecret, udp: u, udpSession: udpSession, pcSession: pcSession}
585	if srv.DecorateWriter != nil {
586		w.writer = srv.DecorateWriter(w)
587	} else {
588		w.writer = w
589	}
590
591	srv.serveDNS(m, w)
592	wg.Done()
593}
594
595func (srv *Server) serveDNS(m []byte, w *response) {
596	dh, off, err := unpackMsgHdr(m, 0)
597	if err != nil {
598		// Let client hang, they are sending crap; any reply can be used to amplify.
599		return
600	}
601
602	req := new(Msg)
603	req.setHdr(dh)
604
605	switch action := srv.MsgAcceptFunc(dh); action {
606	case MsgAccept:
607		if req.unpack(dh, m, off) == nil {
608			break
609		}
610
611		fallthrough
612	case MsgReject, MsgRejectNotImplemented:
613		opcode := req.Opcode
614		req.SetRcodeFormatError(req)
615		req.Zero = false
616		if action == MsgRejectNotImplemented {
617			req.Opcode = opcode
618			req.Rcode = RcodeNotImplemented
619		}
620
621		// Are we allowed to delete any OPT records here?
622		req.Ns, req.Answer, req.Extra = nil, nil, nil
623
624		w.WriteMsg(req)
625		fallthrough
626	case MsgIgnore:
627		if w.udp != nil && cap(m) == srv.UDPSize {
628			srv.udpPool.Put(m[:srv.UDPSize])
629		}
630
631		return
632	}
633
634	w.tsigStatus = nil
635	if w.tsigSecret != nil {
636		if t := req.IsTsig(); t != nil {
637			if secret, ok := w.tsigSecret[t.Hdr.Name]; ok {
638				w.tsigStatus = TsigVerify(m, secret, "", false)
639			} else {
640				w.tsigStatus = ErrSecret
641			}
642			w.tsigTimersOnly = false
643			w.tsigRequestMAC = req.Extra[len(req.Extra)-1].(*TSIG).MAC
644		}
645	}
646
647	if w.udp != nil && cap(m) == srv.UDPSize {
648		srv.udpPool.Put(m[:srv.UDPSize])
649	}
650
651	srv.Handler.ServeDNS(w, req) // Writes back to the client
652}
653
654func (srv *Server) readTCP(conn net.Conn, timeout time.Duration) ([]byte, error) {
655	// If we race with ShutdownContext, the read deadline may
656	// have been set in the distant past to unblock the read
657	// below. We must not override it, otherwise we may block
658	// ShutdownContext.
659	srv.lock.RLock()
660	if srv.started {
661		conn.SetReadDeadline(time.Now().Add(timeout))
662	}
663	srv.lock.RUnlock()
664
665	var length uint16
666	if err := binary.Read(conn, binary.BigEndian, &length); err != nil {
667		return nil, err
668	}
669
670	m := make([]byte, length)
671	if _, err := io.ReadFull(conn, m); err != nil {
672		return nil, err
673	}
674
675	return m, nil
676}
677
678func (srv *Server) readUDP(conn *net.UDPConn, timeout time.Duration) ([]byte, *SessionUDP, error) {
679	srv.lock.RLock()
680	if srv.started {
681		// See the comment in readTCP above.
682		conn.SetReadDeadline(time.Now().Add(timeout))
683	}
684	srv.lock.RUnlock()
685
686	m := srv.udpPool.Get().([]byte)
687	n, s, err := ReadFromSessionUDP(conn, m)
688	if err != nil {
689		srv.udpPool.Put(m)
690		return nil, nil, err
691	}
692	m = m[:n]
693	return m, s, nil
694}
695
696func (srv *Server) readPacketConn(conn net.PacketConn, timeout time.Duration) ([]byte, net.Addr, error) {
697	srv.lock.RLock()
698	if srv.started {
699		// See the comment in readTCP above.
700		conn.SetReadDeadline(time.Now().Add(timeout))
701	}
702	srv.lock.RUnlock()
703
704	m := srv.udpPool.Get().([]byte)
705	n, addr, err := conn.ReadFrom(m)
706	if err != nil {
707		srv.udpPool.Put(m)
708		return nil, nil, err
709	}
710	m = m[:n]
711	return m, addr, nil
712}
713
714// WriteMsg implements the ResponseWriter.WriteMsg method.
715func (w *response) WriteMsg(m *Msg) (err error) {
716	if w.closed {
717		return &Error{err: "WriteMsg called after Close"}
718	}
719
720	var data []byte
721	if w.tsigSecret != nil { // if no secrets, dont check for the tsig (which is a longer check)
722		if t := m.IsTsig(); t != nil {
723			data, w.tsigRequestMAC, err = TsigGenerate(m, w.tsigSecret[t.Hdr.Name], w.tsigRequestMAC, w.tsigTimersOnly)
724			if err != nil {
725				return err
726			}
727			_, err = w.writer.Write(data)
728			return err
729		}
730	}
731	data, err = m.Pack()
732	if err != nil {
733		return err
734	}
735	_, err = w.writer.Write(data)
736	return err
737}
738
739// Write implements the ResponseWriter.Write method.
740func (w *response) Write(m []byte) (int, error) {
741	if w.closed {
742		return 0, &Error{err: "Write called after Close"}
743	}
744
745	switch {
746	case w.udp != nil:
747		if u, ok := w.udp.(*net.UDPConn); ok {
748			return WriteToSessionUDP(u, m, w.udpSession)
749		}
750		return w.udp.WriteTo(m, w.pcSession)
751	case w.tcp != nil:
752		if len(m) > MaxMsgSize {
753			return 0, &Error{err: "message too large"}
754		}
755
756		msg := make([]byte, 2+len(m))
757		binary.BigEndian.PutUint16(msg, uint16(len(m)))
758		copy(msg[2:], m)
759		return w.tcp.Write(msg)
760	default:
761		panic("dns: internal error: udp and tcp both nil")
762	}
763}
764
765// LocalAddr implements the ResponseWriter.LocalAddr method.
766func (w *response) LocalAddr() net.Addr {
767	switch {
768	case w.udp != nil:
769		return w.udp.LocalAddr()
770	case w.tcp != nil:
771		return w.tcp.LocalAddr()
772	default:
773		panic("dns: internal error: udp and tcp both nil")
774	}
775}
776
777// RemoteAddr implements the ResponseWriter.RemoteAddr method.
778func (w *response) RemoteAddr() net.Addr {
779	switch {
780	case w.udpSession != nil:
781		return w.udpSession.RemoteAddr()
782	case w.pcSession != nil:
783		return w.pcSession
784	case w.tcp != nil:
785		return w.tcp.RemoteAddr()
786	default:
787		panic("dns: internal error: udpSession, pcSession and tcp are all nil")
788	}
789}
790
791// TsigStatus implements the ResponseWriter.TsigStatus method.
792func (w *response) TsigStatus() error { return w.tsigStatus }
793
794// TsigTimersOnly implements the ResponseWriter.TsigTimersOnly method.
795func (w *response) TsigTimersOnly(b bool) { w.tsigTimersOnly = b }
796
797// Hijack implements the ResponseWriter.Hijack method.
798func (w *response) Hijack() { w.hijacked = true }
799
800// Close implements the ResponseWriter.Close method
801func (w *response) Close() error {
802	if w.closed {
803		return &Error{err: "connection already closed"}
804	}
805	w.closed = true
806
807	switch {
808	case w.udp != nil:
809		// Can't close the udp conn, as that is actually the listener.
810		return nil
811	case w.tcp != nil:
812		return w.tcp.Close()
813	default:
814		panic("dns: internal error: udp and tcp both nil")
815	}
816}
817
818// ConnectionState() implements the ConnectionStater.ConnectionState() interface.
819func (w *response) ConnectionState() *tls.ConnectionState {
820	type tlsConnectionStater interface {
821		ConnectionState() tls.ConnectionState
822	}
823	if v, ok := w.tcp.(tlsConnectionStater); ok {
824		t := v.ConnectionState()
825		return &t
826	}
827	return nil
828}
829