resolver.go 60 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843
  1. /*
  2. * Copyright (c) 2022, Psiphon Inc.
  3. * All rights reserved.
  4. *
  5. * This program is free software: you can redistribute it and/or modify
  6. * it under the terms of the GNU General Public License as published by
  7. * the Free Software Foundation, either version 3 of the License, or
  8. * (at your option) any later version.
  9. *
  10. * This program is distributed in the hope that it will be useful,
  11. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  13. * GNU General Public License for more details.
  14. *
  15. * You should have received a copy of the GNU General Public License
  16. * along with this program. If not, see <http://www.gnu.org/licenses/>.
  17. *
  18. */
  19. // Package resolver implements a DNS stub resolver, or DNS client, which
  20. // resolves domain names.
  21. //
  22. // The resolver is Psiphon-specific and oriented towards blocking resistance.
  23. // See ResolveIP for more details.
  24. package resolver
  25. import (
  26. "context"
  27. "encoding/hex"
  28. "fmt"
  29. "net"
  30. "sync"
  31. "sync/atomic"
  32. "syscall"
  33. "time"
  34. "github.com/Psiphon-Labs/psiphon-tunnel-core/psiphon/common"
  35. "github.com/Psiphon-Labs/psiphon-tunnel-core/psiphon/common/errors"
  36. "github.com/Psiphon-Labs/psiphon-tunnel-core/psiphon/common/parameters"
  37. "github.com/Psiphon-Labs/psiphon-tunnel-core/psiphon/common/prng"
  38. "github.com/Psiphon-Labs/psiphon-tunnel-core/psiphon/common/transforms"
  39. lrucache "github.com/cognusion/go-cache-lru"
  40. "github.com/miekg/dns"
  41. "golang.org/x/net/idna"
  42. )
  43. const (
  44. resolverCacheDefaultTTL = 1 * time.Minute
  45. resolverCacheReapFrequency = 1 * time.Minute
  46. resolverCacheMaxEntries = 10000
  47. resolverServersUpdateTTL = 5 * time.Second
  48. resolverDefaultAttemptsPerServer = 2
  49. resolverDefaultRequestTimeout = 5 * time.Second
  50. resolverDefaultAwaitTimeout = 10 * time.Millisecond
  51. resolverDefaultAnswerTTL = 1 * time.Minute
  52. resolverDNSPort = "53"
  53. udpPacketBufferSize = 1232
  54. )
  55. // NetworkConfig specifies network-level configuration for a Resolver.
  56. type NetworkConfig struct {
  57. // GetDNSServers returns a list of system DNS server addresses (IP:port, or
  58. // IP only with port 53 assumed), as determined via OS APIs, in priority
  59. // order. GetDNSServers may be nil.
  60. GetDNSServers func() []string
  61. // BindToDevice should ensure the input file descriptor, a UDP socket, is
  62. // excluded from VPN routing. BindToDevice may be nil.
  63. BindToDevice func(fd int) (string, error)
  64. // AllowDefaultResolverWithBindToDevice indicates that it's safe to use
  65. // the default resolver when BindToDevice is configured, as the host OS
  66. // will automatically exclude DNS requests from the VPN.
  67. AllowDefaultResolverWithBindToDevice bool
  68. // IPv6Synthesize should apply NAT64 synthesis to the input IPv4 address,
  69. // returning a synthesized IPv6 address that will route to the same
  70. // endpoint. IPv6Synthesize may be nil.
  71. IPv6Synthesize func(IPv4 string) string
  72. // HasIPv6Route should return true when the host has an IPv6 route.
  73. // Resolver has an internal implementation, hasRoutableIPv6Interface, to
  74. // determine this, but it can fail on some platforms ("route ip+net:
  75. // netlinkrib: permission denied" on Android, for example; see Go issue
  76. // 40569). When HasIPv6Route is nil, the internal implementation is used.
  77. HasIPv6Route func() bool
  78. // LogWarning is an optional callback which is used to log warnings and
  79. // transient errors which would otherwise not be recorded or returned.
  80. LogWarning func(error)
  81. // LogHostnames indicates whether to log hostname in errors or not.
  82. LogHostnames bool
  83. // CacheExtensionInitialTTL specifies a minimum TTL to use when caching
  84. // domain resolution results. This minimum will override any TTL in the
  85. // DNS response. CacheExtensionInitialTTL is off when 0.
  86. CacheExtensionInitialTTL time.Duration
  87. // CacheExtensionVerifiedTTL specifies the minimum TTL to set for a cached
  88. // domain resolution result after the result has been verified.
  89. // CacheExtensionVerifiedTTL is off when 0.
  90. //
  91. // DNS cache extension is a workaround to partially mitigate issues with
  92. // obtaining underlying system DNS server IPs on platforms such as iOS
  93. // once a VPN is running and after network changes, such as changing from
  94. // Wi-Fi to mobile. While ResolveParameters.AlternateDNSServer can be
  95. // used to specify a known public DNS server, it may be the case that
  96. // public DNS servers are blocked or always falling back to a public DNS
  97. // server creates unusual traffic. And while it may be possible to use
  98. // the default system resolver, it lacks certain circumvention
  99. // capabilities.
  100. //
  101. // Extending the TTL for cached responses allows Psiphon to redial domains
  102. // using recently successful IPs.
  103. //
  104. // CacheExtensionInitialTTL allows for a greater initial minimum TTL, so
  105. // that the response entry remains in the cache long enough for a dial to
  106. // fully complete and verify the endpoint. Psiphon will call
  107. // Resolver.VerifyExtendCacheTTL once a dial has authenticated, for
  108. // example, the destination Psiphon server. VerifyCacheExtension will
  109. // further extend the corresponding TTL to CacheExtensionVerifiedTTL, a
  110. // longer TTL. CacheExtensionInitialTTL is intended to be on the order of
  111. // minutes and CacheExtensionVerifiedTTL may be on the order of hours.
  112. //
  113. // When CacheExtensionVerifiedTTL is on, the DNS cache is not flushed on
  114. // network changes, to allow for the previously cached entries to remain
  115. // available in the problematic scenario. Like adjusting TTLs, this is an
  116. // explicit trade-off which doesn't adhere to standard best practise, but
  117. // is expected to be more blocking resistent; this approach also assumes
  118. // that endpoints such as CDN IPs are typically available on any network.
  119. CacheExtensionVerifiedTTL time.Duration
  120. }
  121. func (c *NetworkConfig) allowDefaultResolver() bool {
  122. // When BindToDevice is configured, the standard library resolver is not
  123. // used, as the system resolver may not route outside of the VPN.
  124. return c.BindToDevice == nil || c.AllowDefaultResolverWithBindToDevice
  125. }
  126. func (c *NetworkConfig) logWarning(err error) {
  127. if c.LogWarning != nil {
  128. c.LogWarning(err)
  129. }
  130. }
  131. // ResolveParameters specifies the configuration and behavior of a single
  132. // ResolveIP call, a single domain name resolution.
  133. //
  134. // New ResolveParameters may be generated by calling MakeResolveParameters,
  135. // which takes tactics parameters as an input.
  136. //
  137. // ResolveParameters may be persisted for replay.
  138. type ResolveParameters struct {
  139. // AttemptsPerServer specifies how many requests to send to each DNS
  140. // server before trying the next server. IPv4 and IPv6 requests are sent
  141. // concurrently and count as one attempt.
  142. AttemptsPerServer int
  143. // AttemptsPerPreferredServer is AttemptsPerServer for a preferred
  144. // alternate DNS server.
  145. AttemptsPerPreferredServer int
  146. // RequestTimeout specifies how long to wait for a valid response before
  147. // moving on to the next attempt.
  148. RequestTimeout time.Duration
  149. // AwaitTimeout specifies how long to await an additional response after
  150. // the first response is received. This additional wait time applies only
  151. // when there is either no IPv4 or IPv6 response.
  152. AwaitTimeout time.Duration
  153. // PreresolvedIPAddress specifies an IP address result to be used in place
  154. // of making a request.
  155. PreresolvedIPAddress string
  156. // PreresolvedDomain is the domain for which PreresolvedIPAddress is to be
  157. // used.
  158. PreresolvedDomain string
  159. // AlternateDNSServer specifies an alterate DNS server (IP:port, or IP
  160. // only with port 53 assumed) to be used when either no system DNS
  161. // servers are available or when PreferAlternateDNSServer is set.
  162. AlternateDNSServer string
  163. // PreferAlternateDNSServer indicates whether to prioritize using the
  164. // AlternateDNSServer. When set, the AlternateDNSServer is attempted
  165. // before any system DNS servers.
  166. PreferAlternateDNSServer bool
  167. // ProtocolTransformName specifies the name associated with
  168. // ProtocolTransformSpec and is used for metrics.
  169. ProtocolTransformName string
  170. // ProtocolTransformSpec specifies a transform to apply to the DNS request packet.
  171. // See: "github.com/Psiphon-Labs/psiphon-tunnel-core/psiphon/common/transforms".
  172. //
  173. // As transforms operate on strings and DNS requests are binary,
  174. // transforms should be expressed using hex characters.
  175. //
  176. // DNS transforms include strategies discovered by the Geneva team,
  177. // https://geneva.cs.umd.edu.
  178. ProtocolTransformSpec transforms.Spec
  179. // ProtocolTransformSeed specifies the seed to use for generating random
  180. // data in the ProtocolTransformSpec transform. To replay a transform,
  181. // specify the same seed.
  182. ProtocolTransformSeed *prng.Seed
  183. // RandomQNameCasingSeed specifies the seed for randomizing the casing of
  184. // the QName (hostname) in the DNS request. If not set, the QName casing
  185. // will remain unchanged. To reproduce the same random casing, use the same
  186. // seed.
  187. RandomQNameCasingSeed *prng.Seed
  188. // ResponseQNameMustMatch specifies whether the response's question section
  189. // must contain exactly one entry, and that entry's QName (hostname) must
  190. // exactly match the QName sent in the DNS request.
  191. //
  192. // RFC 1035 does not specify that the question section in the response must
  193. // exactly match the question section in the request, but this behavior is
  194. // expected [1].
  195. //
  196. // [1]: https://datatracker.ietf.org/doc/html/draft-vixie-dnsext-dns0x20-00#section-2.2.
  197. ResponseQNameMustMatch bool
  198. // IncludeEDNS0 indicates whether to include the EDNS(0) UDP maximum
  199. // response size extension in DNS requests. The resolver can handle
  200. // responses larger than 512 bytes (RFC 1035 maximum) regardless of
  201. // whether the extension is included; the extension may be included as
  202. // part of appearing similar to other DNS traffic.
  203. IncludeEDNS0 bool
  204. firstAttemptWithAnswer int32
  205. qnameMismatches int32
  206. }
  207. // GetFirstAttemptWithAnswer returns the index of the first request attempt
  208. // that received a valid response, for the most recent ResolveIP call using
  209. // this ResolveParameters. This information is used for logging metrics. The
  210. // first attempt has index 1. GetFirstAttemptWithAnswer return 0 when no
  211. // request attempt has reported a valid response.
  212. //
  213. // The caller is responsible for synchronizing use of a ResolveParameters
  214. // instance (e.g, use a distinct ResolveParameters per ResolveIP to ensure
  215. // GetFirstAttemptWithAnswer refers to a specific ResolveIP).
  216. func (r *ResolveParameters) GetFirstAttemptWithAnswer() int {
  217. return int(atomic.LoadInt32(&r.firstAttemptWithAnswer))
  218. }
  219. func (r *ResolveParameters) setFirstAttemptWithAnswer(attempt int) {
  220. atomic.StoreInt32(&r.firstAttemptWithAnswer, int32(attempt))
  221. }
  222. // GetQNameMismatches returns, for the most recent ResolveIP call using this
  223. // ResolveParameters, the number of DNS requests where the response's question
  224. // section either:
  225. // - Did not contain exactly one entry; or
  226. // - Contained one entry that had a QName (hostname) that did not match the
  227. // QName sent in the DNS request.
  228. //
  229. // This information is used for logging metrics.
  230. //
  231. // The caller is responsible for synchronizing use of a ResolveParameters
  232. // instance (e.g, use a distinct ResolveParameters per ResolveIP to ensure
  233. // GetQNameMismatches refers to a specific ResolveIP).
  234. func (r *ResolveParameters) GetQNameMismatches() int {
  235. return int(atomic.LoadInt32(&r.qnameMismatches))
  236. }
  237. func (r *ResolveParameters) setQNameMismatches(mismatches int) {
  238. atomic.StoreInt32(&r.qnameMismatches, int32(mismatches))
  239. }
  240. // Implementation note: Go's standard net.Resolver supports specifying a
  241. // custom Dial function. This could be used to implement at least a large
  242. // subset of the Resolver functionality on top of Go's standard library
  243. // resolver. However, net.Resolver is limited to using the CGO resolver on
  244. // Android, https://github.com/golang/go/issues/8877, in which case the
  245. // custom Dial function is not used. Furthermore, the the pure Go resolver in
  246. // net/dnsclient_unix.go appears to not be used on Windows at this time.
  247. //
  248. // Go also provides golang.org/x/net/dns/dnsmessage, a DNS message marshaller,
  249. // which could potentially be used in place of github.com/miekg/dns.
  250. // Resolver is a DNS stub resolver, or DNS client, which resolves domain
  251. // names. A Resolver instance maintains a cache, a network state snapshot,
  252. // and metrics. All ResolveIP calls will share the same cache and state.
  253. // Multiple concurrent ResolveIP calls are supported.
  254. type Resolver struct {
  255. networkConfig *NetworkConfig
  256. mutex sync.Mutex
  257. networkID string
  258. hasIPv6Route bool
  259. systemServers []string
  260. lastServersUpdate time.Time
  261. cache *lrucache.Cache
  262. metrics resolverMetrics
  263. }
  264. type resolverMetrics struct {
  265. resolves int
  266. cacheHits int
  267. verifiedCacheExtensions int
  268. requestsIPv4 int
  269. requestsIPv6 int
  270. responsesIPv4 int
  271. responsesIPv6 int
  272. defaultResolves int
  273. defaultSuccesses int
  274. peakInFlight int
  275. minRTT time.Duration
  276. maxRTT time.Duration
  277. }
  278. func newResolverMetrics() resolverMetrics {
  279. return resolverMetrics{minRTT: -1}
  280. }
  281. // NewResolver creates a new Resolver instance.
  282. func NewResolver(networkConfig *NetworkConfig, networkID string) *Resolver {
  283. r := &Resolver{
  284. networkConfig: networkConfig,
  285. metrics: newResolverMetrics(),
  286. }
  287. // updateNetworkState will initialize the cache and network state,
  288. // including system DNS servers.
  289. r.updateNetworkState(networkID)
  290. return r
  291. }
  292. // Stop clears the Resolver cache and resets metrics. Stop must be called only
  293. // after ceasing all in-flight ResolveIP goroutines, or else the cache or
  294. // metrics may repopulate. A Resolver may be resumed after calling Stop, but
  295. // Update must be called first.
  296. func (r *Resolver) Stop() {
  297. r.mutex.Lock()
  298. defer r.mutex.Unlock()
  299. // r.networkConfig is not set to nil to avoid possible nil pointer
  300. // dereferences by concurrent ResolveIP calls.
  301. r.networkID = ""
  302. r.hasIPv6Route = false
  303. r.systemServers = nil
  304. r.cache.Flush()
  305. r.metrics = newResolverMetrics()
  306. }
  307. // MakeResolveParameters generates ResolveParameters using the input tactics
  308. // parameters and optional frontingProviderID context.
  309. func (r *Resolver) MakeResolveParameters(
  310. p parameters.ParametersAccessor,
  311. frontingProviderID string,
  312. frontingDialDomain string) (*ResolveParameters, error) {
  313. params := &ResolveParameters{
  314. AttemptsPerServer: p.Int(parameters.DNSResolverAttemptsPerServer),
  315. AttemptsPerPreferredServer: p.Int(parameters.DNSResolverAttemptsPerPreferredServer),
  316. RequestTimeout: p.Duration(parameters.DNSResolverRequestTimeout),
  317. AwaitTimeout: p.Duration(parameters.DNSResolverAwaitTimeout),
  318. }
  319. // When a frontingProviderID is specified, generate a pre-resolved IP
  320. // address, based on tactics configuration.
  321. if frontingProviderID != "" {
  322. if frontingDialDomain == "" {
  323. return nil, errors.TraceNew("missing fronting dial domain")
  324. }
  325. if p.WeightedCoinFlip(parameters.DNSResolverPreresolvedIPAddressProbability) {
  326. CIDRs := p.LabeledCIDRs(parameters.DNSResolverPreresolvedIPAddressCIDRs, frontingProviderID)
  327. if len(CIDRs) > 0 {
  328. CIDR := CIDRs[prng.Intn(len(CIDRs))]
  329. IP, err := generateIPAddressFromCIDR(CIDR)
  330. if err != nil {
  331. return nil, errors.Trace(err)
  332. }
  333. params.PreresolvedIPAddress = IP.String()
  334. params.PreresolvedDomain = frontingDialDomain
  335. }
  336. }
  337. }
  338. // When preferring an alternate DNS server, select the alternate from
  339. // DNSResolverPreferredAlternateServers. This list is for circumvention
  340. // operations, such as using a public DNS server with a protocol
  341. // transform. Otherwise, select from DNSResolverAlternateServers, which
  342. // is a fallback list of DNS servers to be used when the system DNS
  343. // servers cannot be obtained.
  344. preferredServers := p.Strings(parameters.DNSResolverPreferredAlternateServers)
  345. preferAlternateDNSServer := len(preferredServers) > 0 && p.WeightedCoinFlip(
  346. parameters.DNSResolverPreferAlternateServerProbability)
  347. alternateServers := preferredServers
  348. if !preferAlternateDNSServer {
  349. alternateServers = p.Strings(parameters.DNSResolverAlternateServers)
  350. }
  351. // Select an alternate DNS server, typically a public DNS server. Ensure
  352. // tactics is configured with an empty DNSResolverAlternateServers list
  353. // in cases where attempts to public DNS server are unwanted.
  354. if len(alternateServers) > 0 {
  355. alternateServer := alternateServers[prng.Intn(len(alternateServers))]
  356. // Check that the alternateServer has a well-formed IP address; and add
  357. // a default port if none it present.
  358. host, _, err := net.SplitHostPort(alternateServer)
  359. if err != nil {
  360. // Assume the SplitHostPort error is due to missing port.
  361. host = alternateServer
  362. alternateServer = net.JoinHostPort(alternateServer, resolverDNSPort)
  363. }
  364. if net.ParseIP(host) == nil {
  365. // Log warning and proceed without this DNS server.
  366. r.networkConfig.logWarning(
  367. errors.TraceNew("invalid alternate DNS server IP address"))
  368. } else {
  369. params.AlternateDNSServer = alternateServer
  370. params.PreferAlternateDNSServer = preferAlternateDNSServer
  371. }
  372. }
  373. // Select a DNS transform. DNS request transforms are "scoped" by
  374. // alternate DNS server (IP address without port); that is, when an
  375. // alternate DNS server is certain to be attempted first, a transform
  376. // associated with and known to work with that DNS server will be
  377. // selected. Otherwise, a transform from the default scope
  378. // (transforms.SCOPE_ANY == "") is selected.
  379. //
  380. // In any case, ResolveIP will only apply a transform on the first request
  381. // attempt.
  382. if p.WeightedCoinFlip(parameters.DNSResolverProtocolTransformProbability) {
  383. specs := p.ProtocolTransformSpecs(
  384. parameters.DNSResolverProtocolTransformSpecs)
  385. scopedSpecNames := p.ProtocolTransformScopedSpecNames(
  386. parameters.DNSResolverProtocolTransformScopedSpecNames)
  387. // The alternate DNS server will be the first attempt if
  388. // PreferAlternateDNSServer or the list of system DNS servers is empty.
  389. //
  390. // Limitation: the system DNS server list may change, due to a later
  391. // Resolver.update call when ResolveIP is called with these
  392. // ResolveParameters.
  393. _, systemServers := r.getNetworkState()
  394. scope := transforms.SCOPE_ANY
  395. if params.AlternateDNSServer != "" &&
  396. (params.PreferAlternateDNSServer || len(systemServers) == 0) {
  397. // Remove the port number, as the scope key is an IP address only.
  398. //
  399. // TODO: when we only just added the default port above, which is
  400. // the common case, we could avoid this extra split.
  401. host, _, err := net.SplitHostPort(params.AlternateDNSServer)
  402. if err != nil {
  403. return nil, errors.Trace(err)
  404. }
  405. scope = host
  406. }
  407. name, spec := specs.Select(scope, scopedSpecNames)
  408. if spec != nil {
  409. params.ProtocolTransformName = name
  410. params.ProtocolTransformSpec = spec
  411. var err error
  412. params.ProtocolTransformSeed, err = prng.NewSeed()
  413. if err != nil {
  414. return nil, errors.Trace(err)
  415. }
  416. }
  417. }
  418. if p.WeightedCoinFlip(parameters.DNSResolverQNameRandomizeCasingProbability) {
  419. var err error
  420. params.RandomQNameCasingSeed, err = prng.NewSeed()
  421. if err != nil {
  422. return nil, errors.Trace(err)
  423. }
  424. }
  425. params.ResponseQNameMustMatch = p.WeightedCoinFlip(parameters.DNSResolverQNameMustMatchProbability)
  426. if p.WeightedCoinFlip(parameters.DNSResolverIncludeEDNS0Probability) {
  427. params.IncludeEDNS0 = true
  428. }
  429. return params, nil
  430. }
  431. // ResolveAddress splits the input host:port address, calls ResolveIP to
  432. // resolve the IP address of the host, selects an IP if there are multiple,
  433. // and returns a rejoined IP:port.
  434. //
  435. // IP address selection is random. When network input is set
  436. // to "ip4"/"tcp4"/"udp4" or "ip6"/"tcp6"/"udp6", selection is limited to
  437. // IPv4 or IPv6, respectively.
  438. func (r *Resolver) ResolveAddress(
  439. ctx context.Context,
  440. networkID string,
  441. params *ResolveParameters,
  442. network, address string) (string, error) {
  443. hostname, port, err := net.SplitHostPort(address)
  444. if err != nil {
  445. return "", errors.Trace(err)
  446. }
  447. IPs, err := r.ResolveIP(ctx, networkID, params, hostname)
  448. if err != nil {
  449. return "", errors.Trace(err)
  450. }
  451. // Don't shuffle or otherwise mutate the slice returned by ResolveIP.
  452. permutedIndexes := prng.Perm(len(IPs))
  453. index := 0
  454. switch network {
  455. case "ip4", "tcp4", "udp4":
  456. index = -1
  457. for _, i := range permutedIndexes {
  458. if IPs[i].To4() != nil {
  459. index = i
  460. break
  461. }
  462. }
  463. case "ip6", "tcp6", "udp6":
  464. index = -1
  465. for _, i := range permutedIndexes {
  466. if IPs[i].To4() == nil {
  467. index = i
  468. break
  469. }
  470. }
  471. }
  472. if index == -1 {
  473. return "", errors.Tracef("no IP for network '%s'", network)
  474. }
  475. return net.JoinHostPort(IPs[index].String(), port), nil
  476. }
  477. // ResolveIP resolves a domain name.
  478. //
  479. // The input params may be nil, in which case default timeouts are used.
  480. //
  481. // ResolveIP performs concurrent A and AAAA lookups, returns any valid
  482. // response IPs, and caches results. An error is returned when there are
  483. // no valid response IPs.
  484. //
  485. // ResolveIP is not a general purpose resolver and is Psiphon-specific. For
  486. // example, resolved domains are expected to exist; ResolveIP does not
  487. // fallback to TCP; does not consult any "hosts" file; does not perform RFC
  488. // 3484 sorting logic (see Go issue 18518); only implements a subset of
  489. // Go/glibc/resolv.conf(5) resolver parameters (attempts and timeouts, but
  490. // not rotate, single-request etc.) ResolveIP does not implement singleflight
  491. // logic, as the Go resolver does, and allows multiple concurrent request for
  492. // the same domain -- Psiphon won't often resolve the exact same domain
  493. // multiple times concurrently, and, when it does, there's a circumvention
  494. // benefit to attempting different DNS servers and protocol transforms.
  495. //
  496. // ResolveIP does not currently support DoT, DoH, or TCP; those protocols are
  497. // often blocked or less common. Instead, ResolveIP makes a best effort to
  498. // evade plaintext UDP DNS interference by ignoring invalid responses and by
  499. // optionally applying protocol transforms that may evade blocking.
  500. //
  501. // Due to internal caching, the caller must not mutate returned net.IP slice
  502. // or entries.
  503. func (r *Resolver) ResolveIP(
  504. ctx context.Context,
  505. networkID string,
  506. params *ResolveParameters,
  507. hostname string) ([]net.IP, error) {
  508. // ResolveIP does _not_ lock r.mutex for the lifetime of the function, to
  509. // ensure many ResolveIP calls can run concurrently.
  510. // If the hostname is already an IP address, just return that. For
  511. // metrics, this does not count as a resolve, as the caller may invoke
  512. // ResolveIP for all dials.
  513. IP := net.ParseIP(hostname)
  514. if IP != nil {
  515. return []net.IP{IP}, nil
  516. }
  517. // Count all resolves of an actual domain, including cached and
  518. // pre-resolved cases.
  519. r.updateMetricResolves()
  520. // Call updateNetworkState immediately before resolving, as a best effort
  521. // to ensure that system DNS servers and IPv6 routing network state
  522. // reflects the current network. updateNetworkState locks the Resolver
  523. // mutex for its duration, and so concurrent ResolveIP calls may block at
  524. // this point. However, all updateNetworkState operations are local to
  525. // the host or device; and, if the networkID is unchanged since the last
  526. // call, updateNetworkState may not perform any operations; and after the
  527. // updateNetworkState call, ResolveIP proceeds without holding the mutex
  528. // lock. As a result, this step should not prevent ResolveIP concurrency.
  529. r.updateNetworkState(networkID)
  530. if params == nil {
  531. // Supply default ResolveParameters
  532. params = &ResolveParameters{
  533. AttemptsPerServer: resolverDefaultAttemptsPerServer,
  534. AttemptsPerPreferredServer: resolverDefaultAttemptsPerServer,
  535. RequestTimeout: resolverDefaultRequestTimeout,
  536. AwaitTimeout: resolverDefaultAwaitTimeout,
  537. }
  538. }
  539. // When PreresolvedIPAddress is set, tactics parameters determined the IP address
  540. // in this case.
  541. if params.PreresolvedIPAddress != "" && params.PreresolvedDomain == hostname {
  542. IP := net.ParseIP(params.PreresolvedIPAddress)
  543. if IP == nil {
  544. // Unexpected case, as MakeResolveParameters selects the IP address.
  545. return nil, errors.TraceNew("invalid IP address")
  546. }
  547. return []net.IP{IP}, nil
  548. }
  549. // Use a snapshot of the current network state, including IPv6 routing and
  550. // system DNS servers.
  551. //
  552. // Limitation: these values are used even if the network changes in the
  553. // middle of a ResolveIP call; ResolveIP is not interrupted if the
  554. // network changes.
  555. hasIPv6Route, systemServers := r.getNetworkState()
  556. // Use the standard library resolver when there's no GetDNSServers, or the
  557. // system server list is otherwise empty, and no alternate DNS server is
  558. // configured.
  559. //
  560. // Note that in the case where there are no system DNS servers and there
  561. // is an AlternateDNSServer, if the AlternateDNSServer attempt fails,
  562. // control does not flow back to defaultResolverLookupIP. On platforms
  563. // without GetDNSServers, the caller must arrange for distinct attempts
  564. // that try a AlternateDNSServer, or just use the standard library
  565. // resolver.
  566. //
  567. // ResolveIP should always be called, even when defaultResolverLookupIP is
  568. // expected to be used, to ensure correct metrics counts and ensure a
  569. // consistent error message log stack for all DNS-related failures.
  570. //
  571. if len(systemServers) == 0 &&
  572. params.AlternateDNSServer == "" &&
  573. r.networkConfig.allowDefaultResolver() {
  574. IPs, err := defaultResolverLookupIP(ctx, hostname, r.networkConfig.LogHostnames)
  575. r.updateMetricDefaultResolver(err == nil)
  576. if err != nil {
  577. return nil, errors.Trace(err)
  578. }
  579. return IPs, err
  580. }
  581. // Consult the cache before making queries. This comes after the standard
  582. // library case, to allow the standard library to provide its own caching
  583. // logic.
  584. IPs := r.getCache(hostname)
  585. if IPs != nil {
  586. // TODO: it would be safer to make and return a copy of the cached
  587. // slice, instead of depending on all callers to not mutate the slice.
  588. return IPs, nil
  589. }
  590. // Set the list of DNS servers to attempt. AlternateDNSServer is used
  591. // first when PreferAlternateDNSServer is set; otherwise
  592. // AlternateDNSServer is used only when there is no system DNS server.
  593. var servers []string
  594. if params.AlternateDNSServer != "" &&
  595. (len(systemServers) == 0 || params.PreferAlternateDNSServer) {
  596. servers = []string{params.AlternateDNSServer}
  597. }
  598. servers = append(servers, systemServers...)
  599. if len(servers) == 0 {
  600. return nil, errors.TraceNew("no DNS servers")
  601. }
  602. // Set the request timeout and set up a reusable timer for handling
  603. // request and await timeouts.
  604. //
  605. // We expect to always have a request timeout. Handle the unexpected no
  606. // timeout, 0, case by setting the longest timeout possible, ~290 years;
  607. // always having a non-zero timeout makes the following code marginally
  608. // simpler.
  609. requestTimeout := params.RequestTimeout
  610. if requestTimeout == 0 {
  611. requestTimeout = 1<<63 - 1
  612. }
  613. var timer *time.Timer
  614. timerDrained := true
  615. resetTimer := func(timeout time.Duration) {
  616. if timer == nil {
  617. timer = time.NewTimer(timeout)
  618. } else {
  619. if !timerDrained && !timer.Stop() {
  620. <-timer.C
  621. }
  622. timer.Reset(timeout)
  623. }
  624. timerDrained = false
  625. }
  626. // Orchestrate the DNS requests
  627. resolveCtx, cancelFunc := context.WithCancelCause(ctx)
  628. defer cancelFunc(nil)
  629. waitGroup := new(sync.WaitGroup)
  630. conns := common.NewConns[net.Conn]()
  631. type answer struct {
  632. attempt int
  633. questionType resolverQuestionType
  634. IPs []net.IP
  635. TTLs []time.Duration
  636. }
  637. var maxAttempts int
  638. if params.PreferAlternateDNSServer {
  639. maxAttempts = params.AttemptsPerPreferredServer
  640. maxAttempts += (len(servers) - 1) * params.AttemptsPerServer
  641. } else {
  642. maxAttempts = len(servers) * params.AttemptsPerServer
  643. }
  644. answerChan := make(chan *answer, maxAttempts*2)
  645. inFlight := 0
  646. awaitA := true
  647. awaitAAAA := hasIPv6Route
  648. var result *answer
  649. var lastErr atomic.Value
  650. trackResult := func(a *answer) {
  651. // A result is sent from every attempt goroutine that is launched,
  652. // even in the case of an error, in which case the result is nil.
  653. // Update the number of in-flight attempts as results are received.
  654. // Mark no longer awaiting A or AAAA as long as there is a valid
  655. // response, even if there are no IPs in the IPv6 case.
  656. if inFlight > 0 {
  657. inFlight -= 1
  658. }
  659. if a != nil {
  660. switch a.questionType {
  661. case resolverQuestionTypeA:
  662. awaitA = false
  663. case resolverQuestionTypeAAAA:
  664. awaitAAAA = false
  665. }
  666. }
  667. }
  668. stop := false
  669. for i := 0; !stop && i < maxAttempts; i++ {
  670. var index int
  671. if params.PreferAlternateDNSServer {
  672. if i < params.AttemptsPerPreferredServer {
  673. index = 0
  674. } else {
  675. index = 1 + ((i - params.AttemptsPerPreferredServer) / params.AttemptsPerServer)
  676. }
  677. } else {
  678. index = i / params.AttemptsPerServer
  679. }
  680. server := servers[index]
  681. // Only the first attempt pair tries techniques that may not be
  682. // compatible with all DNS servers.
  683. useProtocolTransform := (i == 0 && params.ProtocolTransformSpec != nil)
  684. useRandomQNameCasing := (i == 0 && params.RandomQNameCasingSeed != nil)
  685. responseQNameMustMatch := (i == 0 && params.ResponseQNameMustMatch)
  686. // Send A and AAAA requests concurrently.
  687. questionTypes := []resolverQuestionType{resolverQuestionTypeA, resolverQuestionTypeAAAA}
  688. if !hasIPv6Route {
  689. questionTypes = questionTypes[0:1]
  690. }
  691. for _, questionType := range questionTypes {
  692. waitGroup.Add(1)
  693. // For metrics, track peak concurrent in-flight requests for
  694. // a _single_ ResolveIP. inFlight for this ResolveIP is also used
  695. // to determine whether to await additional responses once the
  696. // first, valid response is received. For that logic to be
  697. // correct, we must increment inFlight in this outer goroutine to
  698. // ensure the await logic sees either inFlight > 0 or an answer
  699. // in the channel.
  700. inFlight += 1
  701. r.updateMetricPeakInFlight(inFlight)
  702. go func(attempt int, questionType resolverQuestionType, useProtocolTransform, useRandomQNameCasing, responseQNameMustMatch bool) {
  703. defer waitGroup.Done()
  704. // Always send a result back to the main loop, even if this
  705. // attempt fails, so the main loop proceeds to the next
  706. // iteration immediately. Nil is sent in failure cases. When
  707. // the answer is not nil, it's already been sent.
  708. var a *answer
  709. defer func() {
  710. if a == nil {
  711. // The channel should have sufficient buffering for
  712. // the send to never block; the default case is used
  713. // to avoid a hang in the case of a bug.
  714. select {
  715. case answerChan <- a:
  716. default:
  717. }
  718. }
  719. }()
  720. // The request count metric counts the _intention_ to send
  721. // requests, as there's a possibility that newResolverConn or
  722. // performDNSQuery fail locally before sending a request packet.
  723. switch questionType {
  724. case resolverQuestionTypeA:
  725. r.updateMetricRequestsIPv4()
  726. case resolverQuestionTypeAAAA:
  727. r.updateMetricRequestsIPv6()
  728. }
  729. // While it's possible, and potentially more optimal, to use
  730. // the same UDP socket for both the A and AAAA request, we
  731. // use a distinct socket per request, as common DNS clients do.
  732. conn, err := r.newResolverConn(r.networkConfig.logWarning, server)
  733. if err != nil {
  734. lastErr.Store(errors.Trace(err))
  735. return
  736. }
  737. defer conn.Close()
  738. // There's no context.Context support in the underlying API
  739. // used by performDNSQuery, so instead collect all the
  740. // request conns so that they can be closed, and any blocking
  741. // network I/O interrupted, below, if resolveCtx is done.
  742. if !conns.Add(conn) {
  743. // Add fails when conns is already closed. Do not
  744. // overwrite lastErr in this case.
  745. return
  746. }
  747. // performDNSQuery will send the request and read a response.
  748. // performDNSQuery will continue reading responses until it
  749. // receives a valid response, which can mitigate a subset of
  750. // DNS injection attacks (to the limited extent possible for
  751. // plaintext DNS).
  752. //
  753. // For IPv4, NXDOMAIN or a response with no IPs is not
  754. // expected for domains resolved by Psiphon, so
  755. // performDNSQuery treats such a response as invalid. For
  756. // IPv6, a response with no IPs, may be valid(even though the
  757. // response could be forged); the resolver will continue its
  758. // attempts loop if it has no other IPs.
  759. //
  760. // Each performDNSQuery has no timeout and runs
  761. // until it has read a valid response or the requestCtx is
  762. // done. This allows for slow arriving, valid responses to
  763. // eventually succeed, even if the read time exceeds
  764. // requestTimeout, as long as the read time is less than the
  765. // requestCtx timeout.
  766. //
  767. // With this approach, the overall ResolveIP call may have
  768. // more than 2 performDNSQuery requests in-flight at a time,
  769. // as requestTimeout is used to schedule sending the next
  770. // attempt but not cancel the current attempt. For
  771. // connectionless UDP, the resulting network traffic should
  772. // be similar to common DNS clients which do cancel request
  773. // before beginning the next attempt.
  774. IPs, TTLs, RTT, err := performDNSQuery(
  775. resolveCtx,
  776. r.networkConfig.logWarning,
  777. params,
  778. useProtocolTransform,
  779. useRandomQNameCasing,
  780. conn,
  781. questionType,
  782. hostname,
  783. responseQNameMustMatch)
  784. // Update the min/max RTT metric when reported (>=0) even if
  785. // the result is an error; i.e., the even if there was an
  786. // invalid response.
  787. //
  788. // Limitation: since individual requests aren't cancelled
  789. // after requestTimeout, RTT metrics won't reflect
  790. // no-response cases, although request and response count
  791. // disparities will still show up in the metrics.
  792. if RTT >= 0 {
  793. r.updateMetricRTT(RTT)
  794. }
  795. if err != nil {
  796. lastErr.Store(errors.Trace(err))
  797. return
  798. }
  799. // Update response stats.
  800. switch questionType {
  801. case resolverQuestionTypeA:
  802. r.updateMetricResponsesIPv4()
  803. case resolverQuestionTypeAAAA:
  804. r.updateMetricResponsesIPv6()
  805. }
  806. // Send the answer back to the main loop.
  807. if len(IPs) > 0 || questionType == resolverQuestionTypeAAAA {
  808. a = &answer{
  809. attempt: attempt,
  810. questionType: questionType,
  811. IPs: IPs,
  812. TTLs: TTLs}
  813. // The channel should have sufficient buffering for
  814. // the send to never block; the default case is used
  815. // to avoid a hang in the case of a bug.
  816. select {
  817. case answerChan <- a:
  818. default:
  819. }
  820. }
  821. }(i+1, questionType, useProtocolTransform, useRandomQNameCasing, responseQNameMustMatch)
  822. }
  823. resetTimer(requestTimeout)
  824. select {
  825. case result = <-answerChan:
  826. trackResult(result)
  827. if result != nil {
  828. // When the first answer, a response with valid IPs, arrives, exit
  829. // the attempts loop. The following await branch may collect
  830. // additional answers.
  831. params.setFirstAttemptWithAnswer(result.attempt)
  832. stop = true
  833. }
  834. case <-timer.C:
  835. // When requestTimeout arrives, loop around and launch the next
  836. // attempt; leave the existing requests running in case they
  837. // eventually respond.
  838. timerDrained = true
  839. case <-resolveCtx.Done():
  840. // When resolveCtx is done, exit the attempts loop.
  841. //
  842. // Append the existing lastErr, which may convey useful
  843. // information to be reported in a failed_tunnel error message.
  844. lastErr.Store(errors.Tracef(
  845. "%v (lastErr: %v)", context.Cause(resolveCtx), lastErr.Load()))
  846. stop = true
  847. }
  848. }
  849. // Receive any additional answers, now present in the channel, which
  850. // arrived concurrent with the first answer. This receive avoids a race
  851. // condition where inFlight may now be 0, with additional answers
  852. // enqueued, in which case the following await branch is not taken.
  853. //
  854. // It's possible for the attempts loop to exit with no received answer due
  855. // to timeouts or cancellation while, concurrently, an answer is sent to
  856. // the channel. In this case, when result == nil, we ignore the answers
  857. // and leave this as a failed resolve.
  858. if result != nil {
  859. for loop := true; loop; {
  860. select {
  861. case nextAnswer := <-answerChan:
  862. trackResult(nextAnswer)
  863. if nextAnswer != nil {
  864. result.IPs = append(result.IPs, nextAnswer.IPs...)
  865. result.TTLs = append(result.TTLs, nextAnswer.TTLs...)
  866. }
  867. default:
  868. loop = false
  869. }
  870. }
  871. }
  872. // When we have an answer, await -- for a short time,
  873. // params.AwaitTimeout -- extra answers from any remaining in-flight
  874. // requests. Only await if the request isn't cancelled and we don't
  875. // already have at least one IPv4 and one IPv6 response; only await AAAA
  876. // if it was sent; note that a valid AAAA response may include no IPs
  877. // lastErr is not set in timeout/cancelled cases here, since we already
  878. // have an answer.
  879. if result != nil &&
  880. resolveCtx.Err() == nil &&
  881. inFlight > 0 &&
  882. (awaitA || awaitAAAA) &&
  883. params.AwaitTimeout > 0 {
  884. resetTimer(params.AwaitTimeout)
  885. for {
  886. stop := false
  887. select {
  888. case nextAnswer := <-answerChan:
  889. trackResult(nextAnswer)
  890. if nextAnswer != nil {
  891. result.IPs = append(result.IPs, nextAnswer.IPs...)
  892. result.TTLs = append(result.TTLs, nextAnswer.TTLs...)
  893. }
  894. case <-timer.C:
  895. timerDrained = true
  896. stop = true
  897. case <-resolveCtx.Done():
  898. stop = true
  899. }
  900. if stop || inFlight == 0 || (!awaitA && !awaitAAAA) {
  901. break
  902. }
  903. }
  904. }
  905. if timer != nil {
  906. timer.Stop()
  907. }
  908. // Interrupt all workers.
  909. cancelFunc(errors.TraceNew("resolve canceled"))
  910. conns.CloseAll()
  911. waitGroup.Wait()
  912. // When there's no answer, or when there's only an empty IPv6 answer,
  913. // return the last error.
  914. if result == nil ||
  915. (result.questionType == resolverQuestionTypeAAAA && len(result.IPs) == 0) {
  916. err := lastErr.Load()
  917. if err == nil {
  918. err = context.Cause(resolveCtx)
  919. }
  920. if err == nil {
  921. err = errors.TraceNew("unexpected missing error")
  922. }
  923. if r.networkConfig.LogHostnames {
  924. err = fmt.Errorf("resolve %s : %w", hostname, err.(error))
  925. }
  926. return nil, errors.Trace(err.(error))
  927. }
  928. if len(result.IPs) == 0 {
  929. // Unexpected, since a len(IPs) > 0 check precedes sending to answerChan.
  930. return nil, errors.TraceNew("unexpected no IPs")
  931. }
  932. // Update the cache now, after all results are gathered.
  933. r.setCache(hostname, result.IPs, result.TTLs)
  934. return result.IPs, nil
  935. }
  936. // VerifyCacheExtension extends the TTL for any cached result for the
  937. // specified hostname to at least NetworkConfig.CacheExtensionVerifiedTTL.
  938. func (r *Resolver) VerifyCacheExtension(hostname string) {
  939. r.mutex.Lock()
  940. defer r.mutex.Unlock()
  941. if r.networkConfig.CacheExtensionVerifiedTTL == 0 {
  942. return
  943. }
  944. if net.ParseIP(hostname) != nil {
  945. return
  946. }
  947. entry, expires, ok := r.cache.GetWithExpiration(hostname)
  948. if !ok {
  949. return
  950. }
  951. // Change the TTL only if the entry expires and the existing TTL isn't
  952. // longer than the extension.
  953. neverExpires := time.Time{}
  954. if expires == neverExpires ||
  955. expires.After(time.Now().Add(r.networkConfig.CacheExtensionVerifiedTTL)) {
  956. return
  957. }
  958. r.cache.Set(hostname, entry, r.networkConfig.CacheExtensionVerifiedTTL)
  959. r.metrics.verifiedCacheExtensions += 1
  960. }
  961. // GetMetrics returns a summary of DNS metrics.
  962. func (r *Resolver) GetMetrics() string {
  963. r.mutex.Lock()
  964. defer r.mutex.Unlock()
  965. // When r.metrics.minRTT < 0, min/maxRTT is unset.
  966. minRTT := "n/a"
  967. maxRTT := minRTT
  968. if r.metrics.minRTT >= 0 {
  969. minRTT = fmt.Sprintf("%d", r.metrics.minRTT/time.Millisecond)
  970. maxRTT = fmt.Sprintf("%d", r.metrics.maxRTT/time.Millisecond)
  971. }
  972. extend := ""
  973. if r.networkConfig.CacheExtensionVerifiedTTL > 0 {
  974. extend = fmt.Sprintf("| extend %d ", r.metrics.verifiedCacheExtensions)
  975. }
  976. defaultResolves := ""
  977. if r.networkConfig.allowDefaultResolver() {
  978. defaultResolves = fmt.Sprintf(
  979. " | def %d/%d", r.metrics.defaultResolves, r.metrics.defaultSuccesses)
  980. }
  981. // Note that the number of system resolvers is a point-in-time value,
  982. // while the others are cumulative.
  983. return fmt.Sprintf("resolves %d | hit %d %s| req v4/v6 %d/%d | resp %d/%d | peak %d | rtt %s - %s ms. | sys %d%s",
  984. r.metrics.resolves,
  985. r.metrics.cacheHits,
  986. extend,
  987. r.metrics.requestsIPv4,
  988. r.metrics.requestsIPv6,
  989. r.metrics.responsesIPv4,
  990. r.metrics.responsesIPv6,
  991. r.metrics.peakInFlight,
  992. minRTT,
  993. maxRTT,
  994. len(r.systemServers),
  995. defaultResolves)
  996. }
  997. // updateNetworkState updates the system DNS server list, IPv6 state, and the
  998. // cache.
  999. //
  1000. // Any errors that occur while querying network state are logged; in error
  1001. // conditions the functionality of the resolver may be reduced, but the
  1002. // resolver remains operational.
  1003. func (r *Resolver) updateNetworkState(networkID string) {
  1004. r.mutex.Lock()
  1005. defer r.mutex.Unlock()
  1006. // Only perform blocking/expensive update operations when necessary.
  1007. updateAll := false
  1008. updateIPv6Route := false
  1009. updateServers := false
  1010. flushCache := false
  1011. // If r.cache is nil, this is the first update call in NewResolver. Create
  1012. // the cache and perform all updates.
  1013. if r.cache == nil {
  1014. r.cache = lrucache.NewWithLRU(
  1015. resolverCacheDefaultTTL,
  1016. resolverCacheReapFrequency,
  1017. resolverCacheMaxEntries)
  1018. updateAll = true
  1019. }
  1020. // Perform all updates when the networkID has changed, which indicates a
  1021. // different network.
  1022. if r.networkID != networkID {
  1023. updateAll = true
  1024. }
  1025. if updateAll {
  1026. updateIPv6Route = true
  1027. updateServers = true
  1028. flushCache = true
  1029. }
  1030. // Even when the networkID has not changed, update DNS servers
  1031. // periodically. This is similar to how other DNS clients
  1032. // poll /etc/resolv.conf, including the period of 5s.
  1033. if time.Since(r.lastServersUpdate) > resolverServersUpdateTTL {
  1034. updateServers = true
  1035. }
  1036. // Update hasIPv6Route, which indicates whether the current network has an
  1037. // IPv6 route and so if DNS requests for AAAA records will be sent.
  1038. // There's no use for AAAA records on IPv4-only networks; and other
  1039. // common DNS clients omit AAAA requests on IPv4-only records, so these
  1040. // requests would otherwise be unusual.
  1041. //
  1042. // There's no hasIPv4Route as we always need to resolve A records,
  1043. // particularly for IPv4-only endpoints; for IPv6-only networks,
  1044. // NetworkConfig.IPv6Synthesize should be used to accomodate IPv4 DNS
  1045. // server addresses, and dials performed outside the Resolver will
  1046. // similarly use NAT 64 (on iOS; on Android, 464XLAT will handle this
  1047. // transparently).
  1048. if updateIPv6Route {
  1049. // TODO: the HasIPv6Route callback provides hasRoutableIPv6Interface
  1050. // functionality on platforms where that internal implementation
  1051. // fails. In particular, "route ip+net: netlinkrib: permission
  1052. // denied" on Android; see Go issue 40569). This Android case can be
  1053. // fixed, and the callback retired, by sharing the workaround now
  1054. // implemented in inproxy.pionNetwork.Interfaces.
  1055. if r.networkConfig.HasIPv6Route != nil {
  1056. r.hasIPv6Route = r.networkConfig.HasIPv6Route()
  1057. } else {
  1058. hasIPv6Route, err := hasRoutableIPv6Interface()
  1059. if err != nil {
  1060. // Log warning and proceed without IPv6.
  1061. r.networkConfig.logWarning(
  1062. errors.Tracef("unable to determine IPv6 route: %v", err))
  1063. hasIPv6Route = false
  1064. }
  1065. r.hasIPv6Route = hasIPv6Route
  1066. }
  1067. }
  1068. // Update the list of system DNS servers. It's not an error condition here
  1069. // if the list is empty: a subsequent ResolveIP may use
  1070. // ResolveParameters which specifies an AlternateDNSServer.
  1071. if updateServers && r.networkConfig.GetDNSServers != nil {
  1072. systemServers := []string{}
  1073. for _, systemServer := range r.networkConfig.GetDNSServers() {
  1074. host, _, err := net.SplitHostPort(systemServer)
  1075. if err != nil {
  1076. // Assume the SplitHostPort error is due to systemServer being
  1077. // an IP only, and append the default port, 53. If
  1078. // systemServer _isn't_ an IP, the following ParseIP will fail.
  1079. host = systemServer
  1080. systemServer = net.JoinHostPort(systemServer, resolverDNSPort)
  1081. }
  1082. if net.ParseIP(host) == nil {
  1083. // Log warning and proceed without this DNS server.
  1084. r.networkConfig.logWarning(
  1085. errors.TraceNew("invalid DNS server IP address"))
  1086. continue
  1087. }
  1088. systemServers = append(systemServers, systemServer)
  1089. }
  1090. // Check if the list of servers has changed, including order. If
  1091. // changed, flush the cache even if the networkID has not changed.
  1092. // Cached results are only considered valid as long as the system DNS
  1093. // configuration remains the same.
  1094. equal := len(r.systemServers) == len(systemServers)
  1095. if equal {
  1096. for i := 0; i < len(r.systemServers); i++ {
  1097. if r.systemServers[i] != systemServers[i] {
  1098. equal = false
  1099. break
  1100. }
  1101. }
  1102. }
  1103. flushCache = flushCache || !equal
  1104. // Concurrency note: once the r.systemServers slice is set, the
  1105. // contents of the backing array must not be modified due to
  1106. // concurrent ResolveIP calls.
  1107. r.systemServers = systemServers
  1108. r.lastServersUpdate = time.Now()
  1109. }
  1110. // Skip cache flushes when the extended DNS caching mechanism is enabled.
  1111. // TODO: retain only verified cache entries?
  1112. if flushCache && r.networkConfig.CacheExtensionVerifiedTTL == 0 {
  1113. r.cache.Flush()
  1114. }
  1115. // Set r.networkID only after all operations complete without errors; if
  1116. // r.networkID were set earlier, a subsequent
  1117. // ResolveIP/updateNetworkState call might proceed as if the network
  1118. // state were updated for the specified network ID.
  1119. r.networkID = networkID
  1120. }
  1121. func (r *Resolver) getNetworkState() (bool, []string) {
  1122. r.mutex.Lock()
  1123. defer r.mutex.Unlock()
  1124. return r.hasIPv6Route, r.systemServers
  1125. }
  1126. func (r *Resolver) setCache(hostname string, IPs []net.IP, TTLs []time.Duration) {
  1127. r.mutex.Lock()
  1128. defer r.mutex.Unlock()
  1129. // The shortest TTL is used. In some cases, a DNS server may omit the TTL
  1130. // or set a 0 TTL, in which case the default is used.
  1131. TTL := resolverDefaultAnswerTTL
  1132. for _, answerTTL := range TTLs {
  1133. if answerTTL > 0 && answerTTL < TTL {
  1134. TTL = answerTTL
  1135. }
  1136. }
  1137. // When NetworkConfig.CacheExtensionInitialTTL configured, ensure the TTL
  1138. // is no shorter than CacheExtensionInitialTTL.
  1139. if r.networkConfig.CacheExtensionInitialTTL != 0 &&
  1140. TTL < r.networkConfig.CacheExtensionInitialTTL {
  1141. TTL = r.networkConfig.CacheExtensionInitialTTL
  1142. }
  1143. // Limitation: with concurrent ResolveIPs for the same domain, the last
  1144. // setCache call determines the cache value. The results are not merged.
  1145. r.cache.Set(hostname, IPs, TTL)
  1146. }
  1147. func (r *Resolver) getCache(hostname string) []net.IP {
  1148. r.mutex.Lock()
  1149. defer r.mutex.Unlock()
  1150. entry, ok := r.cache.Get(hostname)
  1151. if !ok {
  1152. return nil
  1153. }
  1154. r.metrics.cacheHits += 1
  1155. return entry.([]net.IP)
  1156. }
  1157. // newResolverConn creates a UDP socket that will send packets to serverAddr.
  1158. // serverAddr is an IP:port, which allows specifying the port for testing or
  1159. // in rare cases where the port isn't 53.
  1160. func (r *Resolver) newResolverConn(
  1161. logWarning func(error),
  1162. serverAddr string) (retConn net.Conn, retErr error) {
  1163. defer func() {
  1164. if retErr != nil {
  1165. logWarning(retErr)
  1166. }
  1167. }()
  1168. // When configured, attempt to synthesize an IPv6 address from
  1169. // an IPv4 address for compatibility on DNS64/NAT64 networks.
  1170. // If synthesize fails, try the original address.
  1171. if r.networkConfig.IPv6Synthesize != nil {
  1172. serverIPStr, port, err := net.SplitHostPort(serverAddr)
  1173. if err != nil {
  1174. return nil, errors.Trace(err)
  1175. }
  1176. serverIP := net.ParseIP(serverIPStr)
  1177. if serverIP != nil && serverIP.To4() != nil {
  1178. synthesized := r.networkConfig.IPv6Synthesize(serverIPStr)
  1179. if synthesized != "" && net.ParseIP(synthesized) != nil {
  1180. serverAddr = net.JoinHostPort(synthesized, port)
  1181. }
  1182. }
  1183. }
  1184. dialer := &net.Dialer{}
  1185. if r.networkConfig.BindToDevice != nil {
  1186. dialer.Control = func(_, _ string, c syscall.RawConn) error {
  1187. var controlErr error
  1188. err := c.Control(func(fd uintptr) {
  1189. _, err := r.networkConfig.BindToDevice(int(fd))
  1190. if err != nil {
  1191. controlErr = errors.Tracef("BindToDevice failed: %v", err)
  1192. return
  1193. }
  1194. })
  1195. if controlErr != nil {
  1196. return errors.Trace(controlErr)
  1197. }
  1198. return errors.Trace(err)
  1199. }
  1200. }
  1201. // context.Background is ok in this case as the UDP dial is just a local
  1202. // syscall to create the socket.
  1203. conn, err := dialer.DialContext(context.Background(), "udp", serverAddr)
  1204. if err != nil {
  1205. return nil, errors.Trace(err)
  1206. }
  1207. return conn, nil
  1208. }
  1209. func (r *Resolver) updateMetricResolves() {
  1210. r.mutex.Lock()
  1211. defer r.mutex.Unlock()
  1212. r.metrics.resolves += 1
  1213. }
  1214. func (r *Resolver) updateMetricRequestsIPv4() {
  1215. r.mutex.Lock()
  1216. defer r.mutex.Unlock()
  1217. r.metrics.requestsIPv4 += 1
  1218. }
  1219. func (r *Resolver) updateMetricRequestsIPv6() {
  1220. r.mutex.Lock()
  1221. defer r.mutex.Unlock()
  1222. r.metrics.requestsIPv6 += 1
  1223. }
  1224. func (r *Resolver) updateMetricResponsesIPv4() {
  1225. r.mutex.Lock()
  1226. defer r.mutex.Unlock()
  1227. r.metrics.responsesIPv4 += 1
  1228. }
  1229. func (r *Resolver) updateMetricResponsesIPv6() {
  1230. r.mutex.Lock()
  1231. defer r.mutex.Unlock()
  1232. r.metrics.responsesIPv6 += 1
  1233. }
  1234. func (r *Resolver) updateMetricDefaultResolver(success bool) {
  1235. r.mutex.Lock()
  1236. defer r.mutex.Unlock()
  1237. r.metrics.defaultResolves += 1
  1238. if success {
  1239. r.metrics.defaultSuccesses += 1
  1240. }
  1241. }
  1242. func (r *Resolver) updateMetricPeakInFlight(inFlight int) {
  1243. r.mutex.Lock()
  1244. defer r.mutex.Unlock()
  1245. if inFlight > r.metrics.peakInFlight {
  1246. r.metrics.peakInFlight = inFlight
  1247. }
  1248. }
  1249. func (r *Resolver) updateMetricRTT(rtt time.Duration) {
  1250. r.mutex.Lock()
  1251. defer r.mutex.Unlock()
  1252. if rtt < 0 {
  1253. // Ignore invalid input.
  1254. return
  1255. }
  1256. // When r.metrics.minRTT < 0, min/maxRTT is unset.
  1257. if r.metrics.minRTT < 0 || rtt < r.metrics.minRTT {
  1258. r.metrics.minRTT = rtt
  1259. }
  1260. if rtt > r.metrics.maxRTT {
  1261. r.metrics.maxRTT = rtt
  1262. }
  1263. }
  1264. func hasRoutableIPv6Interface() (bool, error) {
  1265. interfaces, err := net.Interfaces()
  1266. if err != nil {
  1267. return false, errors.Trace(err)
  1268. }
  1269. for _, in := range interfaces {
  1270. if (in.Flags&net.FlagUp == 0) ||
  1271. // Note: don't exclude interfaces with the net.FlagPointToPoint
  1272. // flag, which is set for certain mobile networks
  1273. (in.Flags&net.FlagLoopback != 0) {
  1274. continue
  1275. }
  1276. addrs, err := in.Addrs()
  1277. if err != nil {
  1278. return false, errors.Trace(err)
  1279. }
  1280. for _, addr := range addrs {
  1281. if IPNet, ok := addr.(*net.IPNet); ok &&
  1282. IPNet.IP.To4() == nil &&
  1283. !IPNet.IP.IsLinkLocalUnicast() {
  1284. return true, nil
  1285. }
  1286. }
  1287. }
  1288. return false, nil
  1289. }
  1290. func generateIPAddressFromCIDR(CIDR string) (net.IP, error) {
  1291. _, IPNet, err := net.ParseCIDR(CIDR)
  1292. if err != nil {
  1293. return nil, errors.Trace(err)
  1294. }
  1295. // A retry is required, since a CIDR may include broadcast IPs (a.b.c.0) or
  1296. // other invalid values. The number of retries is limited to ensure we
  1297. // don't hang in the case of a misconfiguration.
  1298. for i := 0; i < 10; i++ {
  1299. randBytes := prng.Bytes(len(IPNet.IP))
  1300. IP := make(net.IP, len(IPNet.IP))
  1301. // The 1 bits in the mask must apply to the IP in the CIDR and the 0
  1302. // bits in the mask are available to randomize.
  1303. for i := 0; i < len(IP); i++ {
  1304. IP[i] = (IPNet.IP[i] & IPNet.Mask[i]) | (randBytes[i] & ^IPNet.Mask[i])
  1305. }
  1306. if IP.IsGlobalUnicast() && !common.IsBogon(IP) {
  1307. return IP, nil
  1308. }
  1309. }
  1310. return nil, errors.TraceNew("failed to generate random IP")
  1311. }
  1312. type resolverQuestionType int
  1313. const (
  1314. resolverQuestionTypeA = 0
  1315. resolverQuestionTypeAAAA = 1
  1316. )
  1317. func performDNSQuery(
  1318. resolveCtx context.Context,
  1319. logWarning func(error),
  1320. params *ResolveParameters,
  1321. useProtocolTransform bool,
  1322. useRandomQNameCasing bool,
  1323. conn net.Conn,
  1324. questionType resolverQuestionType,
  1325. hostname string,
  1326. responseQNameMustMatch bool) ([]net.IP, []time.Duration, time.Duration, error) {
  1327. if useProtocolTransform {
  1328. if params.ProtocolTransformSpec == nil ||
  1329. params.ProtocolTransformSeed == nil {
  1330. return nil, nil, -1, errors.TraceNew("invalid protocol transform configuration")
  1331. }
  1332. // miekg/dns expects conn to be a net.PacketConn or else it writes the
  1333. // TCP length prefix
  1334. udpConn, ok := conn.(*net.UDPConn)
  1335. if !ok {
  1336. return nil, nil, -1, errors.TraceNew("conn is not a *net.UDPConn")
  1337. }
  1338. conn = &transformDNSPacketConn{
  1339. UDPConn: udpConn,
  1340. transform: params.ProtocolTransformSpec,
  1341. seed: params.ProtocolTransformSeed,
  1342. }
  1343. }
  1344. // Convert to punycode.
  1345. hostname, err := idna.ToASCII(hostname)
  1346. if err != nil {
  1347. return nil, nil, -1, errors.Trace(err)
  1348. }
  1349. if useRandomQNameCasing {
  1350. hostname = common.ToRandomASCIICasing(hostname, params.RandomQNameCasingSeed)
  1351. }
  1352. // UDPSize sets the receive buffer to > 512, even when we don't include
  1353. // EDNS(0), which will mitigate issues with RFC 1035 non-compliant
  1354. // servers. See Go issue 51127.
  1355. dnsConn := &dns.Conn{
  1356. Conn: conn,
  1357. UDPSize: udpPacketBufferSize,
  1358. }
  1359. defer dnsConn.Close()
  1360. // SetQuestion initializes request.MsgHdr.Id to a random value
  1361. request := &dns.Msg{MsgHdr: dns.MsgHdr{RecursionDesired: true}}
  1362. switch questionType {
  1363. case resolverQuestionTypeA:
  1364. request.SetQuestion(dns.Fqdn(hostname), dns.TypeA)
  1365. case resolverQuestionTypeAAAA:
  1366. request.SetQuestion(dns.Fqdn(hostname), dns.TypeAAAA)
  1367. default:
  1368. return nil, nil, -1, errors.TraceNew("unknown DNS request question type")
  1369. }
  1370. if params.IncludeEDNS0 {
  1371. // miekg/dns: "RFC 6891, Section 6.1.1 allows the OPT record to appear
  1372. // anywhere in the additional record section, but it's usually at the
  1373. // end..."
  1374. request.SetEdns0(udpPacketBufferSize, false)
  1375. }
  1376. startTime := time.Now()
  1377. // Send the DNS request
  1378. err = dnsConn.WriteMsg(request)
  1379. if err != nil {
  1380. return nil, nil, -1, errors.Trace(err)
  1381. }
  1382. // Read and process the DNS response
  1383. var IPs []net.IP
  1384. var TTLs []time.Duration
  1385. var qnameMismatches int
  1386. defer func() {
  1387. params.setQNameMismatches(qnameMismatches)
  1388. }()
  1389. var lastErr error
  1390. RTT := time.Duration(-1)
  1391. for {
  1392. // Stop when resolveCtx is done; the caller, ResolveIP, will also
  1393. // close conn, which will interrupt a blocking dnsConn.ReadMsg.
  1394. if resolveCtx.Err() != nil {
  1395. // ResolveIP, which calls performDNSQuery, already records the
  1396. // context error (e.g., context timeout), so instead report
  1397. // lastErr, when present, as it may contain more useful
  1398. // information about why a response was rejected.
  1399. err := lastErr
  1400. if err == nil {
  1401. err = errors.Trace(context.Cause(resolveCtx))
  1402. }
  1403. return nil, nil, RTT, err
  1404. }
  1405. // Read a response. RTT is the elapsed time between sending the
  1406. // request and reading the last received response.
  1407. response, err := dnsConn.ReadMsg()
  1408. RTT = time.Since(startTime)
  1409. if err == nil && response.MsgHdr.Id != request.MsgHdr.Id {
  1410. err = dns.ErrId
  1411. }
  1412. if err != nil {
  1413. // Try reading again, in case the first response packet failed to
  1414. // unmarshal or had an invalid ID. The Go resolver also does this;
  1415. // see Go issue 13281.
  1416. if resolveCtx.Err() == nil {
  1417. // Only log if resolveCtx is not done; otherwise the error could
  1418. // be due to conn being closed by ResolveIP.
  1419. lastErr = errors.Tracef("invalid response: %v", err)
  1420. logWarning(lastErr)
  1421. }
  1422. continue
  1423. }
  1424. if len(response.Question) != 1 || response.Question[0].Name != dns.Fqdn(hostname) {
  1425. qnameMismatches++
  1426. if responseQNameMustMatch {
  1427. lastErr = errors.Tracef("unexpected QName")
  1428. logWarning(lastErr)
  1429. continue
  1430. }
  1431. }
  1432. // Check the RCode.
  1433. //
  1434. // For IPv4, we expect RCodeSuccess as Psiphon will typically only
  1435. // resolve domains that exist and have a valid IP (when this isn't
  1436. // the case, and we retry, the overall ResolveIP and its parent dial
  1437. // will still abort after resolveCtx is done, or RequestTimeout
  1438. // expires for maxAttempts).
  1439. //
  1440. // For IPv6, we should also expect RCodeSuccess even if there is no
  1441. // AAAA record, as long as the domain exists and has an A record.
  1442. // However, per RFC 6147 section 5.1.2, we may receive
  1443. // NXDOMAIN: "...some servers respond with RCODE=3 to a AAAA query
  1444. // even if there is an A record available for that owner name. Those
  1445. // servers are in clear violation of the meaning of RCODE 3...". In
  1446. // this case, we coalesce NXDOMAIN into success to treat the response
  1447. // the same as success with no AAAA record.
  1448. //
  1449. // All other RCodes, which are unexpected, lead to a read retry.
  1450. if response.MsgHdr.Rcode != dns.RcodeSuccess &&
  1451. !(questionType == resolverQuestionTypeAAAA && response.MsgHdr.Rcode == dns.RcodeNameError) {
  1452. errMsg, ok := dns.RcodeToString[response.MsgHdr.Rcode]
  1453. if !ok {
  1454. errMsg = fmt.Sprintf("Rcode: %d", response.MsgHdr.Rcode)
  1455. }
  1456. lastErr = errors.Tracef("unexpected RCode: %v", errMsg)
  1457. logWarning(lastErr)
  1458. continue
  1459. }
  1460. // Extract all IP answers, along with corresponding TTLs for caching.
  1461. // Perform additional validation, which may lead to another read
  1462. // retry. However, if _any_ valid IP is found, stop reading and
  1463. // return that result. Again, the validation is only best effort.
  1464. checkFailed := false
  1465. for _, answer := range response.Answer {
  1466. haveAnswer := false
  1467. var IP net.IP
  1468. var TTLSec uint32
  1469. switch questionType {
  1470. case resolverQuestionTypeA:
  1471. if a, ok := answer.(*dns.A); ok {
  1472. IP = a.A
  1473. TTLSec = a.Hdr.Ttl
  1474. haveAnswer = true
  1475. }
  1476. case resolverQuestionTypeAAAA:
  1477. if aaaa, ok := answer.(*dns.AAAA); ok {
  1478. IP = aaaa.AAAA
  1479. TTLSec = aaaa.Hdr.Ttl
  1480. haveAnswer = true
  1481. }
  1482. }
  1483. if !haveAnswer {
  1484. continue
  1485. }
  1486. err := checkDNSAnswerIP(IP)
  1487. if err != nil {
  1488. checkFailed = true
  1489. lastErr = errors.Tracef("invalid IP: %v", err)
  1490. logWarning(lastErr)
  1491. // Check the next answer
  1492. continue
  1493. }
  1494. IPs = append(IPs, IP)
  1495. TTLs = append(TTLs, time.Duration(TTLSec)*time.Second)
  1496. }
  1497. // For IPv4, an IP is expected, as noted in the comment above.
  1498. //
  1499. // In potential cases where we resolve a domain that has only an IPv6
  1500. // address, the concurrent AAAA request will deliver its result to
  1501. // ResolveIP, and that answer will be selected, so only the "await"
  1502. // logic will delay the parent dial in that case.
  1503. if questionType == resolverQuestionTypeA && len(IPs) == 0 && !checkFailed {
  1504. checkFailed = true
  1505. lastErr = errors.TraceNew("unexpected empty A response")
  1506. logWarning(lastErr)
  1507. }
  1508. // Retry if there are no valid IPs and any error; if no error, this
  1509. // may be a valid AAAA response with no IPs, in which case return the
  1510. // result.
  1511. if len(IPs) == 0 && checkFailed {
  1512. continue
  1513. }
  1514. return IPs, TTLs, RTT, nil
  1515. }
  1516. }
  1517. func checkDNSAnswerIP(IP net.IP) error {
  1518. if IP == nil {
  1519. return errors.TraceNew("IP is nil")
  1520. }
  1521. // Limitation: this could still be a phony/injected response, it's not
  1522. // possible to verify with plaintext DNS, but a "bogon" IP is clearly
  1523. // invalid.
  1524. if common.IsBogon(IP) {
  1525. return errors.TraceNew("IP is bogon")
  1526. }
  1527. // Create a temporary socket bound to the destination IP. This checks
  1528. // thats the local host has a route to this IP. If not, we'll reject the
  1529. // IP. This prevents selecting an IP which is guaranteed to fail to dial.
  1530. // Use UDP as this results in no network traffic; the destination port is
  1531. // arbitrary. The Go resolver performs a similar operation.
  1532. //
  1533. // Limitations:
  1534. // - We may cache the IP and reuse it without checking routability again;
  1535. // the cache should be flushed when network state changes.
  1536. // - Given that the AAAA is requested only when the host has an IPv6
  1537. // route, we don't expect this to often fail with a _valid_ response.
  1538. // However, this remains a possibility and in this case,
  1539. // performDNSQuery will keep awaiting a response which can trigger
  1540. // the "await" logic.
  1541. conn, err := net.DialUDP("udp", nil, &net.UDPAddr{IP: IP, Port: 443})
  1542. if err != nil {
  1543. return errors.Trace(err)
  1544. }
  1545. conn.Close()
  1546. return nil
  1547. }
  1548. func defaultResolverLookupIP(
  1549. ctx context.Context, hostname string, logHostnames bool) ([]net.IP, error) {
  1550. addrs, err := net.DefaultResolver.LookupIPAddr(ctx, hostname)
  1551. if err != nil && !logHostnames {
  1552. // Remove domain names from "net" error messages.
  1553. err = common.RedactNetError(err)
  1554. }
  1555. if err != nil {
  1556. return nil, errors.Trace(err)
  1557. }
  1558. ips := make([]net.IP, len(addrs))
  1559. for i, addr := range addrs {
  1560. ips[i] = addr.IP
  1561. }
  1562. return ips, nil
  1563. }
  1564. // transformDNSPacketConn wraps a *net.UDPConn, intercepting Write calls and
  1565. // applying the specified protocol transform.
  1566. //
  1567. // As transforms operate on strings and DNS requests are binary, the transform
  1568. // should be expressed using hex characters. The DNS packet to be written
  1569. // (input the Write) is converted to hex, transformed, and converted back to
  1570. // binary and then actually written to the UDP socket.
  1571. type transformDNSPacketConn struct {
  1572. *net.UDPConn
  1573. transform transforms.Spec
  1574. seed *prng.Seed
  1575. }
  1576. func (conn *transformDNSPacketConn) Write(b []byte) (int, error) {
  1577. // Limitation: there is no check that a transformed packet remains within
  1578. // the network packet MTU.
  1579. input := hex.EncodeToString(b)
  1580. output, err := conn.transform.ApplyString(conn.seed, input)
  1581. if err != nil {
  1582. return 0, errors.Trace(err)
  1583. }
  1584. packet, err := hex.DecodeString(output)
  1585. if err != nil {
  1586. return 0, errors.Trace(err)
  1587. }
  1588. _, err = conn.UDPConn.Write(packet)
  1589. if err != nil {
  1590. // In the error case, don't report bytes written as the number could
  1591. // exceed the pre-transform length.
  1592. return 0, errors.Trace(err)
  1593. }
  1594. // Report the pre-transform length as bytes written, as the caller may check
  1595. // that the requested len(b) bytes were written.
  1596. return len(b), nil
  1597. }