From 5ac9daca088ab4f378d7df849f6c7d28bea86071 Mon Sep 17 00:00:00 2001 From: Sean Liao Date: Sun, 26 Oct 2025 22:34:45 +0000 Subject: [PATCH] publicsuffix: don't treat ip addresses as domain names While IP addresses are not domain names and probably shouldn't be passed to these functions at all, it seems wrong to have it handle IPv4 and IPv6 differently. Fixes golang/go#32979 Change-Id: Id321a08b552c11d990c3966636b64793f762143f Reviewed-on: https://go-review.googlesource.com/c/net/+/715100 Reviewed-by: Michael Pratt LUCI-TryBot-Result: Go LUCI Reviewed-by: Damien Neil --- publicsuffix/list.go | 5 +++++ publicsuffix/list_test.go | 10 ++++++++++ 2 files changed, 15 insertions(+) diff --git a/publicsuffix/list.go b/publicsuffix/list.go index 047cb30e..7ab8b3cf 100644 --- a/publicsuffix/list.go +++ b/publicsuffix/list.go @@ -51,6 +51,7 @@ package publicsuffix // import "golang.org/x/net/publicsuffix" import ( "fmt" "net/http/cookiejar" + "net/netip" "strings" ) @@ -84,6 +85,10 @@ func (list) String() string { // domains like "foo.appspot.com" can be found at // https://wiki.mozilla.org/Public_Suffix_List/Use_Cases func PublicSuffix(domain string) (publicSuffix string, icann bool) { + if _, err := netip.ParseAddr(domain); err == nil { + return domain, false + } + lo, hi := uint32(0), uint32(numTLD) s, suffix, icannNode, wildcard := domain, len(domain), false, false loop: diff --git a/publicsuffix/list_test.go b/publicsuffix/list_test.go index 7a1bb0fe..7648fdb5 100644 --- a/publicsuffix/list_test.go +++ b/publicsuffix/list_test.go @@ -5,6 +5,7 @@ package publicsuffix import ( + "net/netip" "sort" "strings" "testing" @@ -85,6 +86,11 @@ var publicSuffixTestCases = []struct { // Empty string. {"", "", false}, + // IP addresses don't have a domain hierarchy + {"192.0.2.0", "192.0.2.0", false}, + {"::ffff:192.0.2.0", "::ffff:192.0.2.0", false}, + {"2001:db8::", "2001:db8::", false}, + // The .ao rules are: // ao // ed.ao @@ -332,6 +338,10 @@ type slowPublicSuffixRule struct { // This function returns the public suffix, not the registrable domain, and so // it stops after step 6. func slowPublicSuffix(domain string) (string, bool) { + if _, err := netip.ParseAddr(domain); err == nil { + return domain, false + } + match := func(rulePart, domainPart string) bool { switch rulePart[0] { case '*':