diff --git a/agent/consul/util.go b/agent/consul/util.go index 8bbc247d5..c58891863 100644 --- a/agent/consul/util.go +++ b/agent/consul/util.go @@ -3,7 +3,6 @@ package consul import ( "encoding/binary" "fmt" - "net" "runtime" "strconv" @@ -13,58 +12,6 @@ import ( "github.com/hashicorp/serf/serf" ) -/* - * Contains an entry for each private block: - * 10.0.0.0/8 - * 100.64.0.0/10 - * 127.0.0.0/8 - * 169.254.0.0/16 - * 172.16.0.0/12 - * 192.168.0.0/16 - */ -var privateBlocks []*net.IPNet - -func init() { - // Add each private block - privateBlocks = make([]*net.IPNet, 6) - - _, block, err := net.ParseCIDR("10.0.0.0/8") - if err != nil { - panic(fmt.Sprintf("Bad cidr. Got %v", err)) - } - privateBlocks[0] = block - - _, block, err = net.ParseCIDR("100.64.0.0/10") - if err != nil { - panic(fmt.Sprintf("Bad cidr. Got %v", err)) - } - privateBlocks[1] = block - - _, block, err = net.ParseCIDR("127.0.0.0/8") - if err != nil { - panic(fmt.Sprintf("Bad cidr. Got %v", err)) - } - privateBlocks[2] = block - - _, block, err = net.ParseCIDR("169.254.0.0/16") - if err != nil { - panic(fmt.Sprintf("Bad cidr. Got %v", err)) - } - privateBlocks[3] = block - - _, block, err = net.ParseCIDR("172.16.0.0/12") - if err != nil { - panic(fmt.Sprintf("Bad cidr. Got %v", err)) - } - privateBlocks[4] = block - - _, block, err = net.ParseCIDR("192.168.0.0/16") - if err != nil { - panic(fmt.Sprintf("Bad cidr. Got %v", err)) - } - privateBlocks[5] = block -} - // CanServersUnderstandProtocol checks to see if all the servers in the given // list understand the given protocol version. If there are no servers in the // list then this will return false. @@ -103,149 +50,6 @@ func isConsulNode(m serf.Member) (bool, string) { return true, m.Tags["dc"] } -// Returns if the given IP is in a private block -func isPrivateIP(ipStr string) bool { - ip := net.ParseIP(ipStr) - for _, priv := range privateBlocks { - if priv.Contains(ip) { - return true - } - } - return false -} - -// Returns addresses from interfaces that is up -func activeInterfaceAddresses() ([]net.Addr, error) { - var upAddrs []net.Addr - var loAddrs []net.Addr - - interfaces, err := net.Interfaces() - if err != nil { - return nil, fmt.Errorf("Failed to get interfaces: %v", err) - } - - for _, iface := range interfaces { - // Require interface to be up - if iface.Flags&net.FlagUp == 0 { - continue - } - - addresses, err := iface.Addrs() - if err != nil { - return nil, fmt.Errorf("Failed to get interface addresses: %v", err) - } - - if iface.Flags&net.FlagLoopback != 0 { - loAddrs = append(loAddrs, addresses...) - continue - } - - upAddrs = append(upAddrs, addresses...) - } - - if len(upAddrs) == 0 { - return loAddrs, nil - } - - return upAddrs, nil -} - -// GetPrivateIP is used to return the first private IP address -// associated with an interface on the machine -func GetPrivateIP() (net.IP, error) { - addresses, err := activeInterfaceAddresses() - if err != nil { - return nil, fmt.Errorf("Failed to get interface addresses: %v", err) - } - - return getPrivateIP(addresses) -} - -func getPrivateIP(addresses []net.Addr) (net.IP, error) { - var candidates []net.IP - - // Find private IPv4 address - for _, rawAddr := range addresses { - var ip net.IP - switch addr := rawAddr.(type) { - case *net.IPAddr: - ip = addr.IP - case *net.IPNet: - ip = addr.IP - default: - continue - } - - if ip.To4() == nil { - continue - } - if !isPrivateIP(ip.String()) { - continue - } - candidates = append(candidates, ip) - } - numIps := len(candidates) - switch numIps { - case 0: - return nil, fmt.Errorf("No private IP address found") - case 1: - return candidates[0], nil - default: - return nil, fmt.Errorf("Multiple private IPs found. Please configure one.") - } - -} - -// GetPublicIPv6 is used to return the first public IP address -// associated with an interface on the machine -func GetPublicIPv6() (net.IP, error) { - addresses, err := net.InterfaceAddrs() - if err != nil { - return nil, fmt.Errorf("Failed to get interface addresses: %v", err) - } - - return getPublicIPv6(addresses) -} - -func isUniqueLocalAddress(ip net.IP) bool { - return len(ip) == net.IPv6len && ip[0] == 0xfc && ip[1] == 0x00 -} - -func getPublicIPv6(addresses []net.Addr) (net.IP, error) { - var candidates []net.IP - - // Find public IPv6 address - for _, rawAddr := range addresses { - var ip net.IP - switch addr := rawAddr.(type) { - case *net.IPAddr: - ip = addr.IP - case *net.IPNet: - ip = addr.IP - default: - continue - } - - if ip.To4() != nil { - continue - } - - if ip.IsLinkLocalUnicast() || isUniqueLocalAddress(ip) || ip.IsLoopback() { - continue - } - candidates = append(candidates, ip) - } - numIps := len(candidates) - switch numIps { - case 0: - return nil, fmt.Errorf("No public IPv6 address found") - case 1: - return candidates[0], nil - default: - return nil, fmt.Errorf("Multiple public IPv6 addresses found. Please configure one.") - } -} - // Converts bytes to an integer func bytesToUint64(b []byte) uint64 { return binary.BigEndian.Uint64(b) diff --git a/agent/consul/util_test.go b/agent/consul/util_test.go index a34af4d4e..0c8c37884 100644 --- a/agent/consul/util_test.go +++ b/agent/consul/util_test.go @@ -1,7 +1,6 @@ package consul import ( - "errors" "fmt" "net" "regexp" @@ -14,97 +13,6 @@ import ( "github.com/stretchr/testify/require" ) -func TestGetPrivateIP(t *testing.T) { - t.Parallel() - ip, _, err := net.ParseCIDR("10.1.2.3/32") - if err != nil { - t.Fatalf("failed to parse private cidr: %v", err) - } - - pubIP, _, err := net.ParseCIDR("8.8.8.8/32") - if err != nil { - t.Fatalf("failed to parse public cidr: %v", err) - } - - tests := []struct { - addrs []net.Addr - expected net.IP - err error - }{ - { - addrs: []net.Addr{ - &net.IPAddr{ - IP: ip, - }, - &net.IPAddr{ - IP: pubIP, - }, - }, - expected: ip, - }, - { - addrs: []net.Addr{ - &net.IPAddr{ - IP: pubIP, - }, - }, - err: errors.New("No private IP address found"), - }, - { - addrs: []net.Addr{ - &net.IPAddr{ - IP: ip, - }, - &net.IPAddr{ - IP: ip, - }, - &net.IPAddr{ - IP: pubIP, - }, - }, - err: errors.New("Multiple private IPs found. Please configure one."), - }, - } - - for _, test := range tests { - ip, err := getPrivateIP(test.addrs) - switch { - case test.err != nil && err != nil: - if err.Error() != test.err.Error() { - t.Fatalf("unexpected error: %v != %v", test.err, err) - } - case (test.err == nil && err != nil) || (test.err != nil && err == nil): - t.Fatalf("unexpected error: %v != %v", test.err, err) - default: - if !test.expected.Equal(ip) { - t.Fatalf("unexpected ip: %v != %v", ip, test.expected) - } - } - } -} - -func TestIsPrivateIP(t *testing.T) { - t.Parallel() - if !isPrivateIP("192.168.1.1") { - t.Fatalf("bad") - } - if !isPrivateIP("172.16.45.100") { - t.Fatalf("bad") - } - if !isPrivateIP("10.1.2.3") { - t.Fatalf("bad") - } - if !isPrivateIP("100.115.110.19") { - t.Fatalf("bad") - } - if isPrivateIP("8.8.8.8") { - t.Fatalf("bad") - } - if !isPrivateIP("127.0.0.1") { - t.Fatalf("bad") - } -} - func TestUtil_CanServersUnderstandProtocol(t *testing.T) { t.Parallel() var members []serf.Member @@ -245,100 +153,6 @@ func TestGenerateUUID(t *testing.T) { } } -func TestGetPublicIPv6(t *testing.T) { - t.Parallel() - ip, _, err := net.ParseCIDR("fe80::1/128") - if err != nil { - t.Fatalf("failed to parse link-local cidr: %v", err) - } - - ip2, _, err := net.ParseCIDR("::1/128") - if err != nil { - t.Fatalf("failed to parse loopback cidr: %v", err) - } - - ip3, _, err := net.ParseCIDR("fc00::1/128") - if err != nil { - t.Fatalf("failed to parse ULA cidr: %v", err) - } - - pubIP, _, err := net.ParseCIDR("2001:0db8:85a3::8a2e:0370:7334/128") - if err != nil { - t.Fatalf("failed to parse public cidr: %v", err) - } - - tests := []struct { - addrs []net.Addr - expected net.IP - err error - }{ - { - addrs: []net.Addr{ - &net.IPAddr{ - IP: ip, - }, - &net.IPAddr{ - IP: ip2, - }, - &net.IPAddr{ - IP: ip3, - }, - &net.IPAddr{ - IP: pubIP, - }, - }, - expected: pubIP, - }, - { - addrs: []net.Addr{ - &net.IPAddr{ - IP: ip, - }, - &net.IPAddr{ - IP: ip2, - }, - &net.IPAddr{ - IP: ip3, - }, - }, - err: errors.New("No public IPv6 address found"), - }, - { - addrs: []net.Addr{ - &net.IPAddr{ - IP: ip, - }, - &net.IPAddr{ - IP: ip, - }, - &net.IPAddr{ - IP: pubIP, - }, - &net.IPAddr{ - IP: pubIP, - }, - }, - err: errors.New("Multiple public IPv6 addresses found. Please configure one."), - }, - } - - for _, test := range tests { - ip, err := getPublicIPv6(test.addrs) - switch { - case test.err != nil && err != nil: - if err.Error() != test.err.Error() { - t.Fatalf("unexpected error: %v != %v", test.err, err) - } - case (test.err == nil && err != nil) || (test.err != nil && err == nil): - t.Fatalf("unexpected error: %v != %v", test.err, err) - default: - if !test.expected.Equal(ip) { - t.Fatalf("unexpected ip: %v != %v", ip, test.expected) - } - } - } -} - type testServersProvider []metadata.Server func (p testServersProvider) CheckServers(datacenter string, fn func(*metadata.Server) bool) {