From a9ed73ac221861cb2dd1a5a0fe0d1a9e52bcbbb7 Mon Sep 17 00:00:00 2001 From: retornam Date: Tue, 12 Sep 2023 02:57:40 -0700 Subject: [PATCH] CanonicalName should casefold non-US-ASCII chars (#1470) According to Section 6.2 [1] of RFC 4034,all uppercase US-ASCII letters in the owner name of the RR are replaced by the corresponding lowercase US-ASCII letters. This updates CanonicalName to conform to the RFC. [1] https://www.rfc-editor.org/rfc/rfc4034#section-6.2 Fixes miekg/dns#1434 --- defaults.go | 13 ++++++++++++- labels_test.go | 2 ++ 2 files changed, 14 insertions(+), 1 deletion(-) diff --git a/defaults.go b/defaults.go index c1558b79c..6d7e17605 100644 --- a/defaults.go +++ b/defaults.go @@ -5,6 +5,7 @@ import ( "net" "strconv" "strings" + "unicode" ) const hexDigit = "0123456789abcdef" @@ -330,8 +331,18 @@ func Fqdn(s string) string { // CanonicalName returns the domain name in canonical form. A name in canonical // form is lowercase and fully qualified. See Section 6.2 in RFC 4034. +// According to the RFC all uppercase US-ASCII letters in the owner name of the +// RR areeplaced by the corresponding lowercase US-ASCII letters. func CanonicalName(s string) string { - return strings.ToLower(Fqdn(s)) + var result strings.Builder + for _, ch := range s { + if unicode.IsUpper(ch) && (ch >= 0x00 && ch <= 0x7F) { + result.WriteRune(unicode.ToLower(ch)) + } else { + result.WriteRune(ch) + } + } + return Fqdn(result.String()) } // Copied from the official Go code. diff --git a/labels_test.go b/labels_test.go index dbe9a229f..8cc051c95 100644 --- a/labels_test.go +++ b/labels_test.go @@ -243,6 +243,8 @@ func TestCanonicalName(t *testing.T) { "example.test": "example.test.", "Lower.CASE.test.": "lower.case.test.", "*.Test": "*.test.", + "ÉxamplE.com": "Éxample.com.", + "É.com": "É.com.", } { if got := CanonicalName(s); got != expect { t.Errorf("CanonicalName(%q) = %q, expected %q", s, got, expect)