utils_solaris.go 2.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102
  1. // +build solaris
  2. package netutils
  3. import (
  4. "fmt"
  5. "net"
  6. "os/exec"
  7. "strings"
  8. "github.com/docker/libnetwork/ipamutils"
  9. "github.com/vishvananda/netlink"
  10. )
  11. var (
  12. networkGetRoutesFct func(netlink.Link, int) ([]netlink.Route, error)
  13. )
  14. // CheckRouteOverlaps checks whether the passed network overlaps with any existing routes
  15. func CheckRouteOverlaps(toCheck *net.IPNet) error {
  16. return nil
  17. }
  18. // ElectInterfaceAddresses looks for an interface on the OS with the specified name
  19. // and returns its IPv4 and IPv6 addresses in CIDR form. If the interface does not exist,
  20. // it chooses from a predifined list the first IPv4 address which does not conflict
  21. // with other interfaces on the system.
  22. func ElectInterfaceAddresses(name string) (*net.IPNet, []*net.IPNet, error) {
  23. var (
  24. v4Net *net.IPNet
  25. )
  26. out, err := exec.Command("/usr/sbin/ipadm", "show-addr",
  27. "-p", "-o", "addrobj,addr").Output()
  28. if err != nil {
  29. fmt.Println("failed to list interfaces on system")
  30. return nil, nil, err
  31. }
  32. alist := strings.Fields(string(out))
  33. for _, a := range alist {
  34. linkandaddr := strings.SplitN(a, ":", 2)
  35. if len(linkandaddr) != 2 {
  36. fmt.Println("failed to check interfaces on system: ", a)
  37. continue
  38. }
  39. gw := fmt.Sprintf("%s_gw0", name)
  40. link := strings.Split(linkandaddr[0], "/")[0]
  41. addr := linkandaddr[1]
  42. if gw != link {
  43. continue
  44. }
  45. _, ipnet, err := net.ParseCIDR(addr)
  46. if err != nil {
  47. fmt.Println("failed to parse address: ", addr)
  48. continue
  49. }
  50. v4Net = ipnet
  51. break
  52. }
  53. if v4Net == nil {
  54. v4Net, err = FindAvailableNetwork(ipamutils.PredefinedBroadNetworks)
  55. if err != nil {
  56. return nil, nil, err
  57. }
  58. }
  59. return v4Net, nil, nil
  60. }
  61. // FindAvailableNetwork returns a network from the passed list which does not
  62. // overlap with existing interfaces in the system
  63. func FindAvailableNetwork(list []*net.IPNet) (*net.IPNet, error) {
  64. out, err := exec.Command("/usr/sbin/ipadm", "show-addr",
  65. "-p", "-o", "addr").Output()
  66. if err != nil {
  67. fmt.Println("failed to list interfaces on system")
  68. return nil, err
  69. }
  70. ipaddrs := strings.Fields(string(out))
  71. inuse := []*net.IPNet{}
  72. for _, ip := range ipaddrs {
  73. _, ipnet, err := net.ParseCIDR(ip)
  74. if err != nil {
  75. fmt.Println("failed to check interfaces on system: ", ip)
  76. continue
  77. }
  78. inuse = append(inuse, ipnet)
  79. }
  80. for _, avail := range list {
  81. is_avail := true
  82. for _, ipnet := range inuse {
  83. if NetworkOverlaps(avail, ipnet) {
  84. is_avail = false
  85. break
  86. }
  87. }
  88. if is_avail {
  89. return avail, nil
  90. }
  91. }
  92. return nil, fmt.Errorf("no available network")
  93. }