mirror of
https://github.com/golang/go
synced 2024-11-12 08:20:22 -07:00
crypto/x509: use case-insensitive hostname matching.
Fixes #2792. R=golang-dev, r CC=golang-dev https://golang.org/cl/5590045
This commit is contained in:
parent
2d64bab1de
commit
8efb304440
@ -7,6 +7,7 @@ package x509
|
|||||||
import (
|
import (
|
||||||
"strings"
|
"strings"
|
||||||
"time"
|
"time"
|
||||||
|
"unicode/utf8"
|
||||||
)
|
)
|
||||||
|
|
||||||
type InvalidReason int
|
type InvalidReason int
|
||||||
@ -225,17 +226,51 @@ func matchHostnames(pattern, host string) bool {
|
|||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// toLowerCaseASCII returns a lower-case version of in. See RFC 6125 6.4.1. We use
|
||||||
|
// an explicitly ASCII function to avoid any sharp corners resulting from
|
||||||
|
// performing Unicode operations on DNS labels.
|
||||||
|
func toLowerCaseASCII(in string) string {
|
||||||
|
// If the string is already lower-case then there's nothing to do.
|
||||||
|
isAlreadyLowerCase := true
|
||||||
|
for _, c := range in {
|
||||||
|
if c == utf8.RuneError {
|
||||||
|
// If we get a UTF-8 error then there might be
|
||||||
|
// upper-case ASCII bytes in the invalid sequence.
|
||||||
|
isAlreadyLowerCase = false
|
||||||
|
break
|
||||||
|
}
|
||||||
|
if 'A' <= c && c <= 'Z' {
|
||||||
|
isAlreadyLowerCase = false
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if isAlreadyLowerCase {
|
||||||
|
return in
|
||||||
|
}
|
||||||
|
|
||||||
|
out := []byte(in)
|
||||||
|
for i, c := range out {
|
||||||
|
if 'A' <= c && c <= 'Z' {
|
||||||
|
out[i] += 'a' - 'A'
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return string(out)
|
||||||
|
}
|
||||||
|
|
||||||
// VerifyHostname returns nil if c is a valid certificate for the named host.
|
// VerifyHostname returns nil if c is a valid certificate for the named host.
|
||||||
// Otherwise it returns an error describing the mismatch.
|
// Otherwise it returns an error describing the mismatch.
|
||||||
func (c *Certificate) VerifyHostname(h string) error {
|
func (c *Certificate) VerifyHostname(h string) error {
|
||||||
|
lowered := toLowerCaseASCII(h)
|
||||||
|
|
||||||
if len(c.DNSNames) > 0 {
|
if len(c.DNSNames) > 0 {
|
||||||
for _, match := range c.DNSNames {
|
for _, match := range c.DNSNames {
|
||||||
if matchHostnames(match, h) {
|
if matchHostnames(toLowerCaseASCII(match), lowered) {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// If Subject Alt Name is given, we ignore the common name.
|
// If Subject Alt Name is given, we ignore the common name.
|
||||||
} else if matchHostnames(c.Subject.CommonName, h) {
|
} else if matchHostnames(toLowerCaseASCII(c.Subject.CommonName), lowered) {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -37,6 +37,17 @@ var verifyTests = []verifyTest{
|
|||||||
{"Google", "Thawte", "VeriSign"},
|
{"Google", "Thawte", "VeriSign"},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
leaf: googleLeaf,
|
||||||
|
intermediates: []string{thawteIntermediate},
|
||||||
|
roots: []string{verisignRoot},
|
||||||
|
currentTime: 1302726541,
|
||||||
|
dnsName: "WwW.GooGLE.coM",
|
||||||
|
|
||||||
|
expectedChains: [][]string{
|
||||||
|
{"Google", "Thawte", "VeriSign"},
|
||||||
|
},
|
||||||
|
},
|
||||||
{
|
{
|
||||||
leaf: googleLeaf,
|
leaf: googleLeaf,
|
||||||
intermediates: []string{thawteIntermediate},
|
intermediates: []string{thawteIntermediate},
|
||||||
|
Loading…
Reference in New Issue
Block a user