Use net.IP.IsLoopback() to match loopback addresses
- changed the `MatchLocalhost` function in remotes/docker/registry.go - Make use of SplitHostPort to split host and port number - Added additional tests for modified code in remotes/docker/registry_test.go - Note: this does not handle mathcing of IP addresses in octal, decimal or hex format or a mix of these. Fixes: #5129 Signed-off-by: Madhav Jivrajani <madhav.jiv@gmail.com>
This commit is contained in:
		| @@ -17,7 +17,10 @@ | |||||||
| package docker | package docker | ||||||
|  |  | ||||||
| import ( | import ( | ||||||
|  | 	"net" | ||||||
| 	"net/http" | 	"net/http" | ||||||
|  |  | ||||||
|  | 	"github.com/pkg/errors" | ||||||
| ) | ) | ||||||
|  |  | ||||||
| // HostCapabilities represent the capabilities of the registry | // HostCapabilities represent the capabilities of the registry | ||||||
| @@ -201,12 +204,41 @@ func MatchAllHosts(string) (bool, error) { | |||||||
|  |  | ||||||
| // MatchLocalhost is a host match function which returns true for | // MatchLocalhost is a host match function which returns true for | ||||||
| // localhost. | // localhost. | ||||||
|  | // | ||||||
|  | // Note: this does not handle matching of ip addresses in octal, | ||||||
|  | // decimal or hex form. | ||||||
| func MatchLocalhost(host string) (bool, error) { | func MatchLocalhost(host string) (bool, error) { | ||||||
| 	for _, s := range []string{"localhost", "127.0.0.1", "[::1]"} { | 	switch { | ||||||
| 		if len(host) >= len(s) && host[0:len(s)] == s && (len(host) == len(s) || host[len(s)] == ':') { | 	case host == "::1": | ||||||
|  | 		return true, nil | ||||||
|  | 	case host == "[::1]": | ||||||
| 		return true, nil | 		return true, nil | ||||||
| 	} | 	} | ||||||
| 	} | 	h, p, err := net.SplitHostPort(host) | ||||||
| 	return host == "::1", nil |  | ||||||
|  |  | ||||||
|  | 	// addrError helps distinguish between errors of form | ||||||
|  | 	// "no colon in address" and "too many colons in address". | ||||||
|  | 	// The former is fine as the host string need not have a | ||||||
|  | 	// port. Latter needs to be handled. | ||||||
|  | 	addrError := &net.AddrError{ | ||||||
|  | 		Err:  "missing port in address", | ||||||
|  | 		Addr: host, | ||||||
|  | 	} | ||||||
|  | 	if err != nil { | ||||||
|  | 		if err.Error() != addrError.Error() { | ||||||
|  | 			return false, err | ||||||
|  | 		} | ||||||
|  | 		// host string without any port specified | ||||||
|  | 		h = host | ||||||
|  | 	} else if len(p) == 0 { | ||||||
|  | 		return false, errors.New("invalid host name format") | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	// use ipv4 dotted decimal for further checking | ||||||
|  | 	if h == "localhost" { | ||||||
|  | 		h = "127.0.0.1" | ||||||
|  | 	} | ||||||
|  | 	ip := net.ParseIP(h) | ||||||
|  |  | ||||||
|  | 	return ip.IsLoopback(), nil | ||||||
| } | } | ||||||
|   | |||||||
| @@ -52,14 +52,19 @@ func TestMatchLocalhost(t *testing.T) { | |||||||
| 		match bool | 		match bool | ||||||
| 	}{ | 	}{ | ||||||
| 		{"", false}, | 		{"", false}, | ||||||
| 		{"127.1.1.1", false}, | 		{"127.1.1.1", true}, | ||||||
| 		{"127.0.0.1", true}, | 		{"127.0.0.1", true}, | ||||||
|  | 		{"127.256.0.1", false}, // test MatchLocalhost does not panic on invalid ip | ||||||
|  | 		{"127.23.34.52", true}, | ||||||
| 		{"127.0.0.1:5000", true}, | 		{"127.0.0.1:5000", true}, | ||||||
| 		{"registry.org", false}, | 		{"registry.org", false}, | ||||||
|  | 		{"126.example.com", false}, | ||||||
| 		{"localhost", true}, | 		{"localhost", true}, | ||||||
| 		{"localhost:5000", true}, | 		{"localhost:5000", true}, | ||||||
| 		{"[127:0:0:1]", false}, | 		{"[127:0:0:1]", false}, | ||||||
| 		{"[::1]", true}, | 		{"[::1]", true}, | ||||||
|  | 		{"[::1]:", false},     // invalid ip | ||||||
|  | 		{"127.0.1.1:", false}, // invalid ip | ||||||
| 		{"[::1]:5000", true}, | 		{"[::1]:5000", true}, | ||||||
| 		{"::1", true}, | 		{"::1", true}, | ||||||
| 	} { | 	} { | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user
	 Madhav Jivrajani
					Madhav Jivrajani