network.go 1.7 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465
  1. package goupnp
  2. import (
  3. "net"
  4. "github.com/tailscale/goupnp/httpu"
  5. )
  6. // httpuClient creates a HTTPU client that multiplexes to all multicast-capable
  7. // IPv4 addresses on the host. Returns a function to clean up once the client is
  8. // no longer required.
  9. func httpuClient() (*httpu.MultiClient, error) {
  10. addrs, err := localIPv4MCastAddrs()
  11. if err != nil {
  12. return nil, ctxError(err, "requesting host IPv4 addresses")
  13. }
  14. delegates := make([]httpu.ClientInterface, 0, len(addrs))
  15. for _, addr := range addrs {
  16. c, err := httpu.NewHTTPUClientAddr(addr)
  17. if err != nil {
  18. return nil, ctxErrorf(err, "creating HTTPU client for address %s", addr)
  19. }
  20. delegates = append(delegates, c)
  21. }
  22. return httpu.NewMultiClient(delegates), nil
  23. }
  24. // localIPv2MCastAddrs returns the set of IPv4 addresses on multicast-able
  25. // network interfaces.
  26. func localIPv4MCastAddrs() ([]string, error) {
  27. ifaces, err := net.Interfaces()
  28. if err != nil {
  29. return nil, ctxError(err, "requesting host interfaces")
  30. }
  31. // Find the set of addresses to listen on.
  32. var addrs []string
  33. for _, iface := range ifaces {
  34. if iface.Flags&net.FlagMulticast == 0 || iface.Flags&net.FlagLoopback != 0 || iface.Flags&net.FlagUp == 0 {
  35. // Does not support multicast or is a loopback address.
  36. continue
  37. }
  38. ifaceAddrs, err := iface.Addrs()
  39. if err != nil {
  40. return nil, ctxErrorf(err,
  41. "finding addresses on interface %s", iface.Name)
  42. }
  43. for _, netAddr := range ifaceAddrs {
  44. addr, ok := netAddr.(*net.IPNet)
  45. if !ok {
  46. // Not an IPNet address.
  47. continue
  48. }
  49. if addr.IP.To4() == nil {
  50. // Not IPv4.
  51. continue
  52. }
  53. addrs = append(addrs, addr.IP.String())
  54. }
  55. }
  56. return addrs, nil
  57. }