dial.go 23 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743
  1. // Copyright 2010 The Go Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style
  3. // license that can be found in the LICENSE file.
  4. package net
  5. import (
  6. "context"
  7. "internal/nettrace"
  8. "syscall"
  9. "time"
  10. )
  11. // defaultTCPKeepAlive is a default constant value for TCPKeepAlive times
  12. // See golang.org/issue/31510
  13. const (
  14. defaultTCPKeepAlive = 15 * time.Second
  15. )
  16. // A Dialer contains options for connecting to an address.
  17. //
  18. // The zero value for each field is equivalent to dialing
  19. // without that option. Dialing with the zero value of Dialer
  20. // is therefore equivalent to just calling the Dial function.
  21. //
  22. // It is safe to call Dialer's methods concurrently.
  23. type Dialer struct {
  24. // Timeout is the maximum amount of time a dial will wait for
  25. // a connect to complete. If Deadline is also set, it may fail
  26. // earlier.
  27. //
  28. // The default is no timeout.
  29. //
  30. // When using TCP and dialing a host name with multiple IP
  31. // addresses, the timeout may be divided between them.
  32. //
  33. // With or without a timeout, the operating system may impose
  34. // its own earlier timeout. For instance, TCP timeouts are
  35. // often around 3 minutes.
  36. Timeout time.Duration
  37. // Deadline is the absolute point in time after which dials
  38. // will fail. If Timeout is set, it may fail earlier.
  39. // Zero means no deadline, or dependent on the operating system
  40. // as with the Timeout option.
  41. Deadline time.Time
  42. // LocalAddr is the local address to use when dialing an
  43. // address. The address must be of a compatible type for the
  44. // network being dialed.
  45. // If nil, a local address is automatically chosen.
  46. LocalAddr Addr
  47. // DualStack previously enabled RFC 6555 Fast Fallback
  48. // support, also known as "Happy Eyeballs", in which IPv4 is
  49. // tried soon if IPv6 appears to be misconfigured and
  50. // hanging.
  51. //
  52. // Deprecated: Fast Fallback is enabled by default. To
  53. // disable, set FallbackDelay to a negative value.
  54. DualStack bool
  55. // FallbackDelay specifies the length of time to wait before
  56. // spawning a RFC 6555 Fast Fallback connection. That is, this
  57. // is the amount of time to wait for IPv6 to succeed before
  58. // assuming that IPv6 is misconfigured and falling back to
  59. // IPv4.
  60. //
  61. // If zero, a default delay of 300ms is used.
  62. // A negative value disables Fast Fallback support.
  63. FallbackDelay time.Duration
  64. // KeepAlive specifies the interval between keep-alive
  65. // probes for an active network connection.
  66. // If zero, keep-alive probes are sent with a default value
  67. // (currently 15 seconds), if supported by the protocol and operating
  68. // system. Network protocols or operating systems that do
  69. // not support keep-alives ignore this field.
  70. // If negative, keep-alive probes are disabled.
  71. KeepAlive time.Duration
  72. // Resolver optionally specifies an alternate resolver to use.
  73. Resolver *Resolver
  74. // Cancel is an optional channel whose closure indicates that
  75. // the dial should be canceled. Not all types of dials support
  76. // cancellation.
  77. //
  78. // Deprecated: Use DialContext instead.
  79. Cancel <-chan struct{}
  80. // If Control is not nil, it is called after creating the network
  81. // connection but before actually dialing.
  82. //
  83. // Network and address parameters passed to Control method are not
  84. // necessarily the ones passed to Dial. For example, passing "tcp" to Dial
  85. // will cause the Control function to be called with "tcp4" or "tcp6".
  86. Control func(network, address string, c syscall.RawConn) error
  87. }
  88. func (d *Dialer) dualStack() bool { return d.FallbackDelay >= 0 }
  89. func minNonzeroTime(a, b time.Time) time.Time {
  90. if a.IsZero() {
  91. return b
  92. }
  93. if b.IsZero() || a.Before(b) {
  94. return a
  95. }
  96. return b
  97. }
  98. // deadline returns the earliest of:
  99. // - now+Timeout
  100. // - d.Deadline
  101. // - the context's deadline
  102. // Or zero, if none of Timeout, Deadline, or context's deadline is set.
  103. func (d *Dialer) deadline(ctx context.Context, now time.Time) (earliest time.Time) {
  104. if d.Timeout != 0 { // including negative, for historical reasons
  105. earliest = now.Add(d.Timeout)
  106. }
  107. if d, ok := ctx.Deadline(); ok {
  108. earliest = minNonzeroTime(earliest, d)
  109. }
  110. return minNonzeroTime(earliest, d.Deadline)
  111. }
  112. func (d *Dialer) resolver() *Resolver {
  113. if d.Resolver != nil {
  114. return d.Resolver
  115. }
  116. return DefaultResolver
  117. }
  118. // partialDeadline returns the deadline to use for a single address,
  119. // when multiple addresses are pending.
  120. func partialDeadline(now, deadline time.Time, addrsRemaining int) (time.Time, error) {
  121. if deadline.IsZero() {
  122. return deadline, nil
  123. }
  124. timeRemaining := deadline.Sub(now)
  125. if timeRemaining <= 0 {
  126. return time.Time{}, errTimeout
  127. }
  128. // Tentatively allocate equal time to each remaining address.
  129. timeout := timeRemaining / time.Duration(addrsRemaining)
  130. // If the time per address is too short, steal from the end of the list.
  131. const saneMinimum = 2 * time.Second
  132. if timeout < saneMinimum {
  133. if timeRemaining < saneMinimum {
  134. timeout = timeRemaining
  135. } else {
  136. timeout = saneMinimum
  137. }
  138. }
  139. return now.Add(timeout), nil
  140. }
  141. func (d *Dialer) fallbackDelay() time.Duration {
  142. if d.FallbackDelay > 0 {
  143. return d.FallbackDelay
  144. } else {
  145. return 300 * time.Millisecond
  146. }
  147. }
  148. func parseNetwork(ctx context.Context, network string, needsProto bool) (afnet string, proto int, err error) {
  149. i := last(network, ':')
  150. if i < 0 { // no colon
  151. switch network {
  152. case "tcp", "tcp4", "tcp6":
  153. case "udp", "udp4", "udp6":
  154. case "ip", "ip4", "ip6":
  155. if needsProto {
  156. return "", 0, UnknownNetworkError(network)
  157. }
  158. case "unix", "unixgram", "unixpacket":
  159. default:
  160. return "", 0, UnknownNetworkError(network)
  161. }
  162. return network, 0, nil
  163. }
  164. afnet = network[:i]
  165. switch afnet {
  166. case "ip", "ip4", "ip6":
  167. protostr := network[i+1:]
  168. proto, i, ok := dtoi(protostr)
  169. if !ok || i != len(protostr) {
  170. proto, err = lookupProtocol(ctx, protostr)
  171. if err != nil {
  172. return "", 0, err
  173. }
  174. }
  175. return afnet, proto, nil
  176. }
  177. return "", 0, UnknownNetworkError(network)
  178. }
  179. // resolveAddrList resolves addr using hint and returns a list of
  180. // addresses. The result contains at least one address when error is
  181. // nil.
  182. func (r *Resolver) resolveAddrList(ctx context.Context, op, network, addr string, hint Addr) (addrList, error) {
  183. afnet, _, err := parseNetwork(ctx, network, true)
  184. if err != nil {
  185. return nil, err
  186. }
  187. if op == "dial" && addr == "" {
  188. return nil, errMissingAddress
  189. }
  190. switch afnet {
  191. case "unix", "unixgram", "unixpacket":
  192. addr, err := ResolveUnixAddr(afnet, addr)
  193. if err != nil {
  194. return nil, err
  195. }
  196. if op == "dial" && hint != nil && addr.Network() != hint.Network() {
  197. return nil, &AddrError{Err: "mismatched local address type", Addr: hint.String()}
  198. }
  199. return addrList{addr}, nil
  200. }
  201. addrs, err := r.internetAddrList(ctx, afnet, addr)
  202. if err != nil || op != "dial" || hint == nil {
  203. return addrs, err
  204. }
  205. var (
  206. tcp *TCPAddr
  207. udp *UDPAddr
  208. ip *IPAddr
  209. wildcard bool
  210. )
  211. switch hint := hint.(type) {
  212. case *TCPAddr:
  213. tcp = hint
  214. wildcard = tcp.isWildcard()
  215. case *UDPAddr:
  216. udp = hint
  217. wildcard = udp.isWildcard()
  218. case *IPAddr:
  219. ip = hint
  220. wildcard = ip.isWildcard()
  221. }
  222. naddrs := addrs[:0]
  223. for _, addr := range addrs {
  224. if addr.Network() != hint.Network() {
  225. return nil, &AddrError{Err: "mismatched local address type", Addr: hint.String()}
  226. }
  227. switch addr := addr.(type) {
  228. case *TCPAddr:
  229. if !wildcard && !addr.isWildcard() && !addr.IP.matchAddrFamily(tcp.IP) {
  230. continue
  231. }
  232. naddrs = append(naddrs, addr)
  233. case *UDPAddr:
  234. if !wildcard && !addr.isWildcard() && !addr.IP.matchAddrFamily(udp.IP) {
  235. continue
  236. }
  237. naddrs = append(naddrs, addr)
  238. case *IPAddr:
  239. if !wildcard && !addr.isWildcard() && !addr.IP.matchAddrFamily(ip.IP) {
  240. continue
  241. }
  242. naddrs = append(naddrs, addr)
  243. }
  244. }
  245. if len(naddrs) == 0 {
  246. return nil, &AddrError{Err: errNoSuitableAddress.Error(), Addr: hint.String()}
  247. }
  248. return naddrs, nil
  249. }
  250. // Dial connects to the address on the named network.
  251. //
  252. // Known networks are "tcp", "tcp4" (IPv4-only), "tcp6" (IPv6-only),
  253. // "udp", "udp4" (IPv4-only), "udp6" (IPv6-only), "ip", "ip4"
  254. // (IPv4-only), "ip6" (IPv6-only), "unix", "unixgram" and
  255. // "unixpacket".
  256. //
  257. // For TCP and UDP networks, the address has the form "host:port".
  258. // The host must be a literal IP address, or a host name that can be
  259. // resolved to IP addresses.
  260. // The port must be a literal port number or a service name.
  261. // If the host is a literal IPv6 address it must be enclosed in square
  262. // brackets, as in "[2001:db8::1]:80" or "[fe80::1%zone]:80".
  263. // The zone specifies the scope of the literal IPv6 address as defined
  264. // in RFC 4007.
  265. // The functions JoinHostPort and SplitHostPort manipulate a pair of
  266. // host and port in this form.
  267. // When using TCP, and the host resolves to multiple IP addresses,
  268. // Dial will try each IP address in order until one succeeds.
  269. //
  270. // Examples:
  271. // Dial("tcp", "golang.org:http")
  272. // Dial("tcp", "192.0.2.1:http")
  273. // Dial("tcp", "198.51.100.1:80")
  274. // Dial("udp", "[2001:db8::1]:domain")
  275. // Dial("udp", "[fe80::1%lo0]:53")
  276. // Dial("tcp", ":80")
  277. //
  278. // For IP networks, the network must be "ip", "ip4" or "ip6" followed
  279. // by a colon and a literal protocol number or a protocol name, and
  280. // the address has the form "host". The host must be a literal IP
  281. // address or a literal IPv6 address with zone.
  282. // It depends on each operating system how the operating system
  283. // behaves with a non-well known protocol number such as "0" or "255".
  284. //
  285. // Examples:
  286. // Dial("ip4:1", "192.0.2.1")
  287. // Dial("ip6:ipv6-icmp", "2001:db8::1")
  288. // Dial("ip6:58", "fe80::1%lo0")
  289. //
  290. // For TCP, UDP and IP networks, if the host is empty or a literal
  291. // unspecified IP address, as in ":80", "0.0.0.0:80" or "[::]:80" for
  292. // TCP and UDP, "", "0.0.0.0" or "::" for IP, the local system is
  293. // assumed.
  294. //
  295. // For Unix networks, the address must be a file system path.
  296. func Dial(network, address string) (Conn, error) {
  297. var d Dialer
  298. return d.Dial(network, address)
  299. }
  300. // DialTimeout acts like Dial but takes a timeout.
  301. //
  302. // The timeout includes name resolution, if required.
  303. // When using TCP, and the host in the address parameter resolves to
  304. // multiple IP addresses, the timeout is spread over each consecutive
  305. // dial, such that each is given an appropriate fraction of the time
  306. // to connect.
  307. //
  308. // See func Dial for a description of the network and address
  309. // parameters.
  310. func DialTimeout(network, address string, timeout time.Duration) (Conn, error) {
  311. d := Dialer{Timeout: timeout}
  312. return d.Dial(network, address)
  313. }
  314. // sysDialer contains a Dial's parameters and configuration.
  315. type sysDialer struct {
  316. Dialer
  317. network, address string
  318. }
  319. // Dial connects to the address on the named network.
  320. //
  321. // See func Dial for a description of the network and address
  322. // parameters.
  323. //
  324. // Dial uses context.Background internally; to specify the context, use
  325. // DialContext.
  326. func (d *Dialer) Dial(network, address string) (Conn, error) {
  327. return d.DialContext(context.Background(), network, address)
  328. }
  329. // DialContext connects to the address on the named network using
  330. // the provided context.
  331. //
  332. // The provided Context must be non-nil. If the context expires before
  333. // the connection is complete, an error is returned. Once successfully
  334. // connected, any expiration of the context will not affect the
  335. // connection.
  336. //
  337. // When using TCP, and the host in the address parameter resolves to multiple
  338. // network addresses, any dial timeout (from d.Timeout or ctx) is spread
  339. // over each consecutive dial, such that each is given an appropriate
  340. // fraction of the time to connect.
  341. // For example, if a host has 4 IP addresses and the timeout is 1 minute,
  342. // the connect to each single address will be given 15 seconds to complete
  343. // before trying the next one.
  344. //
  345. // See func Dial for a description of the network and address
  346. // parameters.
  347. func (d *Dialer) DialContext(ctx context.Context, network, address string) (Conn, error) {
  348. if ctx == nil {
  349. panic("nil context")
  350. }
  351. deadline := d.deadline(ctx, time.Now())
  352. if !deadline.IsZero() {
  353. if d, ok := ctx.Deadline(); !ok || deadline.Before(d) {
  354. subCtx, cancel := context.WithDeadline(ctx, deadline)
  355. defer cancel()
  356. ctx = subCtx
  357. }
  358. }
  359. if oldCancel := d.Cancel; oldCancel != nil {
  360. subCtx, cancel := context.WithCancel(ctx)
  361. defer cancel()
  362. go func() {
  363. select {
  364. case <-oldCancel:
  365. cancel()
  366. case <-subCtx.Done():
  367. }
  368. }()
  369. ctx = subCtx
  370. }
  371. // Shadow the nettrace (if any) during resolve so Connect events don't fire for DNS lookups.
  372. resolveCtx := ctx
  373. if trace, _ := ctx.Value(nettrace.TraceKey{}).(*nettrace.Trace); trace != nil {
  374. shadow := *trace
  375. shadow.ConnectStart = nil
  376. shadow.ConnectDone = nil
  377. resolveCtx = context.WithValue(resolveCtx, nettrace.TraceKey{}, &shadow)
  378. }
  379. addrs, err := d.resolver().resolveAddrList(resolveCtx, "dial", network, address, d.LocalAddr)
  380. if err != nil {
  381. return nil, &OpError{Op: "dial", Net: network, Source: nil, Addr: nil, Err: err}
  382. }
  383. sd := &sysDialer{
  384. Dialer: *d,
  385. network: network,
  386. address: address,
  387. }
  388. var primaries, fallbacks addrList
  389. if d.dualStack() && network == "tcp" {
  390. primaries, fallbacks = addrs.partition(isIPv4)
  391. } else {
  392. primaries = addrs
  393. }
  394. var c Conn
  395. if len(fallbacks) > 0 {
  396. c, err = sd.dialParallel(ctx, primaries, fallbacks)
  397. } else {
  398. c, err = sd.dialSerial(ctx, primaries)
  399. }
  400. if err != nil {
  401. return nil, err
  402. }
  403. if tc, ok := c.(*TCPConn); ok && d.KeepAlive >= 0 {
  404. setKeepAlive(tc.fd, true)
  405. ka := d.KeepAlive
  406. if d.KeepAlive == 0 {
  407. ka = defaultTCPKeepAlive
  408. }
  409. setKeepAlivePeriod(tc.fd, ka)
  410. testHookSetKeepAlive(ka)
  411. }
  412. return c, nil
  413. }
  414. // dialParallel races two copies of dialSerial, giving the first a
  415. // head start. It returns the first established connection and
  416. // closes the others. Otherwise it returns an error from the first
  417. // primary address.
  418. func (sd *sysDialer) dialParallel(ctx context.Context, primaries, fallbacks addrList) (Conn, error) {
  419. if len(fallbacks) == 0 {
  420. return sd.dialSerial(ctx, primaries)
  421. }
  422. returned := make(chan struct{})
  423. defer close(returned)
  424. type dialResult struct {
  425. Conn
  426. error
  427. primary bool
  428. done bool
  429. }
  430. results := make(chan dialResult) // unbuffered
  431. startRacer := func(ctx context.Context, primary bool) {
  432. ras := primaries
  433. if !primary {
  434. ras = fallbacks
  435. }
  436. c, err := sd.dialSerial(ctx, ras)
  437. select {
  438. case results <- dialResult{Conn: c, error: err, primary: primary, done: true}:
  439. case <-returned:
  440. if c != nil {
  441. c.Close()
  442. }
  443. }
  444. }
  445. var primary, fallback dialResult
  446. // Start the main racer.
  447. primaryCtx, primaryCancel := context.WithCancel(ctx)
  448. defer primaryCancel()
  449. go startRacer(primaryCtx, true)
  450. // Start the timer for the fallback racer.
  451. fallbackTimer := time.NewTimer(sd.fallbackDelay())
  452. defer fallbackTimer.Stop()
  453. for {
  454. select {
  455. case <-fallbackTimer.C:
  456. fallbackCtx, fallbackCancel := context.WithCancel(ctx)
  457. defer fallbackCancel()
  458. go startRacer(fallbackCtx, false)
  459. case res := <-results:
  460. if res.error == nil {
  461. return res.Conn, nil
  462. }
  463. if res.primary {
  464. primary = res
  465. } else {
  466. fallback = res
  467. }
  468. if primary.done && fallback.done {
  469. return nil, primary.error
  470. }
  471. if res.primary && fallbackTimer.Stop() {
  472. // If we were able to stop the timer, that means it
  473. // was running (hadn't yet started the fallback), but
  474. // we just got an error on the primary path, so start
  475. // the fallback immediately (in 0 nanoseconds).
  476. fallbackTimer.Reset(0)
  477. }
  478. }
  479. }
  480. }
  481. // dialSerial connects to a list of addresses in sequence, returning
  482. // either the first successful connection, or the first error.
  483. func (sd *sysDialer) dialSerial(ctx context.Context, ras addrList) (Conn, error) {
  484. var firstErr error // The error from the first address is most relevant.
  485. for i, ra := range ras {
  486. select {
  487. case <-ctx.Done():
  488. return nil, &OpError{Op: "dial", Net: sd.network, Source: sd.LocalAddr, Addr: ra, Err: mapErr(ctx.Err())}
  489. default:
  490. }
  491. dialCtx := ctx
  492. if deadline, hasDeadline := ctx.Deadline(); hasDeadline {
  493. partialDeadline, err := partialDeadline(time.Now(), deadline, len(ras)-i)
  494. if err != nil {
  495. // Ran out of time.
  496. if firstErr == nil {
  497. firstErr = &OpError{Op: "dial", Net: sd.network, Source: sd.LocalAddr, Addr: ra, Err: err}
  498. }
  499. break
  500. }
  501. if partialDeadline.Before(deadline) {
  502. var cancel context.CancelFunc
  503. dialCtx, cancel = context.WithDeadline(ctx, partialDeadline)
  504. defer cancel()
  505. }
  506. }
  507. c, err := sd.dialSingle(dialCtx, ra)
  508. if err == nil {
  509. return c, nil
  510. }
  511. if firstErr == nil {
  512. firstErr = err
  513. }
  514. }
  515. if firstErr == nil {
  516. firstErr = &OpError{Op: "dial", Net: sd.network, Source: nil, Addr: nil, Err: errMissingAddress}
  517. }
  518. return nil, firstErr
  519. }
  520. // dialSingle attempts to establish and returns a single connection to
  521. // the destination address.
  522. func (sd *sysDialer) dialSingle(ctx context.Context, ra Addr) (c Conn, err error) {
  523. trace, _ := ctx.Value(nettrace.TraceKey{}).(*nettrace.Trace)
  524. if trace != nil {
  525. raStr := ra.String()
  526. if trace.ConnectStart != nil {
  527. trace.ConnectStart(sd.network, raStr)
  528. }
  529. if trace.ConnectDone != nil {
  530. defer func() { trace.ConnectDone(sd.network, raStr, err) }()
  531. }
  532. }
  533. la := sd.LocalAddr
  534. switch ra := ra.(type) {
  535. case *TCPAddr:
  536. la, _ := la.(*TCPAddr)
  537. c, err = sd.dialTCP(ctx, la, ra)
  538. case *UDPAddr:
  539. la, _ := la.(*UDPAddr)
  540. c, err = sd.dialUDP(ctx, la, ra)
  541. case *IPAddr:
  542. la, _ := la.(*IPAddr)
  543. c, err = sd.dialIP(ctx, la, ra)
  544. case *UnixAddr:
  545. la, _ := la.(*UnixAddr)
  546. c, err = sd.dialUnix(ctx, la, ra)
  547. default:
  548. return nil, &OpError{Op: "dial", Net: sd.network, Source: la, Addr: ra, Err: &AddrError{Err: "unexpected address type", Addr: sd.address}}
  549. }
  550. if err != nil {
  551. return nil, &OpError{Op: "dial", Net: sd.network, Source: la, Addr: ra, Err: err} // c is non-nil interface containing nil pointer
  552. }
  553. return c, nil
  554. }
  555. // ListenConfig contains options for listening to an address.
  556. type ListenConfig struct {
  557. // If Control is not nil, it is called after creating the network
  558. // connection but before binding it to the operating system.
  559. //
  560. // Network and address parameters passed to Control method are not
  561. // necessarily the ones passed to Listen. For example, passing "tcp" to
  562. // Listen will cause the Control function to be called with "tcp4" or "tcp6".
  563. Control func(network, address string, c syscall.RawConn) error
  564. // KeepAlive specifies the keep-alive period for network
  565. // connections accepted by this listener.
  566. // If zero, keep-alives are enabled if supported by the protocol
  567. // and operating system. Network protocols or operating systems
  568. // that do not support keep-alives ignore this field.
  569. // If negative, keep-alives are disabled.
  570. KeepAlive time.Duration
  571. }
  572. // Listen announces on the local network address.
  573. //
  574. // See func Listen for a description of the network and address
  575. // parameters.
  576. func (lc *ListenConfig) Listen(ctx context.Context, network, address string) (Listener, error) {
  577. addrs, err := DefaultResolver.resolveAddrList(ctx, "listen", network, address, nil)
  578. if err != nil {
  579. return nil, &OpError{Op: "listen", Net: network, Source: nil, Addr: nil, Err: err}
  580. }
  581. sl := &sysListener{
  582. ListenConfig: *lc,
  583. network: network,
  584. address: address,
  585. }
  586. var l Listener
  587. la := addrs.first(isIPv4)
  588. switch la := la.(type) {
  589. case *TCPAddr:
  590. l, err = sl.listenTCP(ctx, la)
  591. case *UnixAddr:
  592. l, err = sl.listenUnix(ctx, la)
  593. default:
  594. return nil, &OpError{Op: "listen", Net: sl.network, Source: nil, Addr: la, Err: &AddrError{Err: "unexpected address type", Addr: address}}
  595. }
  596. if err != nil {
  597. return nil, &OpError{Op: "listen", Net: sl.network, Source: nil, Addr: la, Err: err} // l is non-nil interface containing nil pointer
  598. }
  599. return l, nil
  600. }
  601. // ListenPacket announces on the local network address.
  602. //
  603. // See func ListenPacket for a description of the network and address
  604. // parameters.
  605. func (lc *ListenConfig) ListenPacket(ctx context.Context, network, address string) (PacketConn, error) {
  606. addrs, err := DefaultResolver.resolveAddrList(ctx, "listen", network, address, nil)
  607. if err != nil {
  608. return nil, &OpError{Op: "listen", Net: network, Source: nil, Addr: nil, Err: err}
  609. }
  610. sl := &sysListener{
  611. ListenConfig: *lc,
  612. network: network,
  613. address: address,
  614. }
  615. var c PacketConn
  616. la := addrs.first(isIPv4)
  617. switch la := la.(type) {
  618. case *UDPAddr:
  619. c, err = sl.listenUDP(ctx, la)
  620. case *IPAddr:
  621. c, err = sl.listenIP(ctx, la)
  622. case *UnixAddr:
  623. c, err = sl.listenUnixgram(ctx, la)
  624. default:
  625. return nil, &OpError{Op: "listen", Net: sl.network, Source: nil, Addr: la, Err: &AddrError{Err: "unexpected address type", Addr: address}}
  626. }
  627. if err != nil {
  628. return nil, &OpError{Op: "listen", Net: sl.network, Source: nil, Addr: la, Err: err} // c is non-nil interface containing nil pointer
  629. }
  630. return c, nil
  631. }
  632. // sysListener contains a Listen's parameters and configuration.
  633. type sysListener struct {
  634. ListenConfig
  635. network, address string
  636. }
  637. // Listen announces on the local network address.
  638. //
  639. // The network must be "tcp", "tcp4", "tcp6", "unix" or "unixpacket".
  640. //
  641. // For TCP networks, if the host in the address parameter is empty or
  642. // a literal unspecified IP address, Listen listens on all available
  643. // unicast and anycast IP addresses of the local system.
  644. // To only use IPv4, use network "tcp4".
  645. // The address can use a host name, but this is not recommended,
  646. // because it will create a listener for at most one of the host's IP
  647. // addresses.
  648. // If the port in the address parameter is empty or "0", as in
  649. // "127.0.0.1:" or "[::1]:0", a port number is automatically chosen.
  650. // The Addr method of Listener can be used to discover the chosen
  651. // port.
  652. //
  653. // See func Dial for a description of the network and address
  654. // parameters.
  655. //
  656. // Listen uses context.Background internally; to specify the context, use
  657. // ListenConfig.Listen.
  658. func Listen(network, address string) (Listener, error) {
  659. var lc ListenConfig
  660. return lc.Listen(context.Background(), network, address)
  661. }
  662. // ListenPacket announces on the local network address.
  663. //
  664. // The network must be "udp", "udp4", "udp6", "unixgram", or an IP
  665. // transport. The IP transports are "ip", "ip4", or "ip6" followed by
  666. // a colon and a literal protocol number or a protocol name, as in
  667. // "ip:1" or "ip:icmp".
  668. //
  669. // For UDP and IP networks, if the host in the address parameter is
  670. // empty or a literal unspecified IP address, ListenPacket listens on
  671. // all available IP addresses of the local system except multicast IP
  672. // addresses.
  673. // To only use IPv4, use network "udp4" or "ip4:proto".
  674. // The address can use a host name, but this is not recommended,
  675. // because it will create a listener for at most one of the host's IP
  676. // addresses.
  677. // If the port in the address parameter is empty or "0", as in
  678. // "127.0.0.1:" or "[::1]:0", a port number is automatically chosen.
  679. // The LocalAddr method of PacketConn can be used to discover the
  680. // chosen port.
  681. //
  682. // See func Dial for a description of the network and address
  683. // parameters.
  684. //
  685. // ListenPacket uses context.Background internally; to specify the context, use
  686. // ListenConfig.ListenPacket.
  687. func ListenPacket(network, address string) (PacketConn, error) {
  688. var lc ListenConfig
  689. return lc.ListenPacket(context.Background(), network, address)
  690. }