nameserver_tcp.go 6.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235
  1. package dns
  2. import (
  3. "bytes"
  4. "context"
  5. "encoding/binary"
  6. "net/url"
  7. "sync/atomic"
  8. "time"
  9. "github.com/xtls/xray-core/common/buf"
  10. "github.com/xtls/xray-core/common/errors"
  11. "github.com/xtls/xray-core/common/net"
  12. "github.com/xtls/xray-core/common/net/cnc"
  13. "github.com/xtls/xray-core/common/protocol/dns"
  14. "github.com/xtls/xray-core/common/session"
  15. dns_feature "github.com/xtls/xray-core/features/dns"
  16. "github.com/xtls/xray-core/features/routing"
  17. "github.com/xtls/xray-core/transport/internet"
  18. )
  19. // TCPNameServer implemented DNS over TCP (RFC7766).
  20. type TCPNameServer struct {
  21. cacheController *CacheController
  22. destination *net.Destination
  23. reqID uint32
  24. dial func(context.Context) (net.Conn, error)
  25. clientIP net.IP
  26. }
  27. // NewTCPNameServer creates DNS over TCP server object for remote resolving.
  28. func NewTCPNameServer(
  29. url *url.URL,
  30. dispatcher routing.Dispatcher,
  31. disableCache bool, serveStale bool, serveExpiredTTL uint32,
  32. clientIP net.IP,
  33. ) (*TCPNameServer, error) {
  34. s, err := baseTCPNameServer(url, "TCP", disableCache, serveStale, serveExpiredTTL, clientIP)
  35. if err != nil {
  36. return nil, err
  37. }
  38. s.dial = func(ctx context.Context) (net.Conn, error) {
  39. link, err := dispatcher.Dispatch(toDnsContext(ctx, s.destination.String()), *s.destination)
  40. if err != nil {
  41. return nil, err
  42. }
  43. return cnc.NewConnection(
  44. cnc.ConnectionInputMulti(link.Writer),
  45. cnc.ConnectionOutputMulti(link.Reader),
  46. ), nil
  47. }
  48. errors.LogInfo(context.Background(), "DNS: created TCP client initialized for ", url.String())
  49. return s, nil
  50. }
  51. // NewTCPLocalNameServer creates DNS over TCP client object for local resolving
  52. func NewTCPLocalNameServer(url *url.URL, disableCache bool, serveStale bool, serveExpiredTTL uint32, clientIP net.IP) (*TCPNameServer, error) {
  53. s, err := baseTCPNameServer(url, "TCPL", disableCache, serveStale, serveExpiredTTL, clientIP)
  54. if err != nil {
  55. return nil, err
  56. }
  57. s.dial = func(ctx context.Context) (net.Conn, error) {
  58. return internet.DialSystem(ctx, *s.destination, nil)
  59. }
  60. errors.LogInfo(context.Background(), "DNS: created Local TCP client initialized for ", url.String())
  61. return s, nil
  62. }
  63. func baseTCPNameServer(url *url.URL, prefix string, disableCache bool, serveStale bool, serveExpiredTTL uint32, clientIP net.IP) (*TCPNameServer, error) {
  64. port := net.Port(53)
  65. if url.Port() != "" {
  66. var err error
  67. if port, err = net.PortFromString(url.Port()); err != nil {
  68. return nil, err
  69. }
  70. }
  71. dest := net.TCPDestination(net.ParseAddress(url.Hostname()), port)
  72. s := &TCPNameServer{
  73. cacheController: NewCacheController(prefix+"//"+dest.NetAddr(), disableCache, serveStale, serveExpiredTTL),
  74. destination: &dest,
  75. clientIP: clientIP,
  76. }
  77. return s, nil
  78. }
  79. // Name implements Server.
  80. func (s *TCPNameServer) Name() string {
  81. return s.cacheController.name
  82. }
  83. // IsDisableCache implements Server.
  84. func (s *TCPNameServer) IsDisableCache() bool {
  85. return s.cacheController.disableCache
  86. }
  87. func (s *TCPNameServer) newReqID() uint16 {
  88. return uint16(atomic.AddUint32(&s.reqID, 1))
  89. }
  90. // getCacheController implements CachedNameserver.
  91. func (s *TCPNameServer) getCacheController() *CacheController {
  92. return s.cacheController
  93. }
  94. // sendQuery implements CachedNameserver.
  95. func (s *TCPNameServer) sendQuery(ctx context.Context, noResponseErrCh chan<- error, fqdn string, option dns_feature.IPOption) {
  96. errors.LogInfo(ctx, s.Name(), " querying DNS for: ", fqdn)
  97. reqs := buildReqMsgs(fqdn, option, s.newReqID, genEDNS0Options(s.clientIP, 0))
  98. var deadline time.Time
  99. if d, ok := ctx.Deadline(); ok {
  100. deadline = d
  101. } else {
  102. deadline = time.Now().Add(time.Second * 5)
  103. }
  104. for _, req := range reqs {
  105. go func(r *dnsRequest) {
  106. dnsCtx := ctx
  107. if inbound := session.InboundFromContext(ctx); inbound != nil {
  108. dnsCtx = session.ContextWithInbound(dnsCtx, inbound)
  109. }
  110. dnsCtx = session.ContextWithContent(dnsCtx, &session.Content{
  111. Protocol: "dns",
  112. SkipDNSResolve: true,
  113. })
  114. var cancel context.CancelFunc
  115. dnsCtx, cancel = context.WithDeadline(dnsCtx, deadline)
  116. defer cancel()
  117. b, err := dns.PackMessage(r.msg)
  118. if err != nil {
  119. errors.LogErrorInner(ctx, err, "failed to pack dns query")
  120. if noResponseErrCh != nil {
  121. noResponseErrCh <- err
  122. }
  123. return
  124. }
  125. conn, err := s.dial(dnsCtx)
  126. if err != nil {
  127. errors.LogErrorInner(ctx, err, "failed to dial namesever")
  128. if noResponseErrCh != nil {
  129. noResponseErrCh <- err
  130. }
  131. return
  132. }
  133. defer conn.Close()
  134. dnsReqBuf := buf.New()
  135. err = binary.Write(dnsReqBuf, binary.BigEndian, uint16(b.Len()))
  136. if err != nil {
  137. errors.LogErrorInner(ctx, err, "binary write failed")
  138. if noResponseErrCh != nil {
  139. noResponseErrCh <- err
  140. }
  141. return
  142. }
  143. _, err = dnsReqBuf.Write(b.Bytes())
  144. if err != nil {
  145. errors.LogErrorInner(ctx, err, "buffer write failed")
  146. if noResponseErrCh != nil {
  147. noResponseErrCh <- err
  148. }
  149. return
  150. }
  151. b.Release()
  152. _, err = conn.Write(dnsReqBuf.Bytes())
  153. if err != nil {
  154. errors.LogErrorInner(ctx, err, "failed to send query")
  155. if noResponseErrCh != nil {
  156. noResponseErrCh <- err
  157. }
  158. return
  159. }
  160. dnsReqBuf.Release()
  161. respBuf := buf.New()
  162. defer respBuf.Release()
  163. n, err := respBuf.ReadFullFrom(conn, 2)
  164. if err != nil && n == 0 {
  165. errors.LogErrorInner(ctx, err, "failed to read response length")
  166. if noResponseErrCh != nil {
  167. noResponseErrCh <- err
  168. }
  169. return
  170. }
  171. var length uint16
  172. err = binary.Read(bytes.NewReader(respBuf.Bytes()), binary.BigEndian, &length)
  173. if err != nil {
  174. errors.LogErrorInner(ctx, err, "failed to parse response length")
  175. if noResponseErrCh != nil {
  176. noResponseErrCh <- err
  177. }
  178. return
  179. }
  180. respBuf.Clear()
  181. n, err = respBuf.ReadFullFrom(conn, int32(length))
  182. if err != nil && n == 0 {
  183. errors.LogErrorInner(ctx, err, "failed to read response length")
  184. if noResponseErrCh != nil {
  185. noResponseErrCh <- err
  186. }
  187. return
  188. }
  189. rec, err := parseResponse(respBuf.Bytes())
  190. if err != nil {
  191. errors.LogErrorInner(ctx, err, "failed to parse DNS over TCP response")
  192. if noResponseErrCh != nil {
  193. noResponseErrCh <- err
  194. }
  195. return
  196. }
  197. s.cacheController.updateRecord(r, rec)
  198. }(req)
  199. }
  200. }
  201. // QueryIP implements Server.
  202. func (s *TCPNameServer) QueryIP(ctx context.Context, domain string, option dns_feature.IPOption) ([]net.IP, uint32, error) {
  203. return queryIP(ctx, s, domain, option)
  204. }