mirror of
https://github.com/golang/go
synced 2024-09-29 20:14:29 -06:00
crypto/x509: abstract SAN parsing function
We'll need this for handling name constraints during verification. Change-Id: I4ef19d9489fb2a9ae9a62699d81cef92a21fda28 Reviewed-on: https://go-review.googlesource.com/62692 Run-TryBot: Adam Langley <agl@golang.org> TryBot-Result: Gobot Gobot <gobot@golang.org> Reviewed-by: David Crawshaw <crawshaw@golang.org>
This commit is contained in:
parent
3079b0ad89
commit
c4d63a0d34
@ -1042,7 +1042,7 @@ func parsePublicKey(algo PublicKeyAlgorithm, keyData *publicKeyInfo) (interface{
|
||||
}
|
||||
}
|
||||
|
||||
func parseSANExtension(value []byte) (dnsNames, emailAddresses []string, ipAddresses []net.IP, err error) {
|
||||
func forEachSAN(extension []byte, callback func(tag int, data []byte) error) error {
|
||||
// RFC 5280, 4.2.1.6
|
||||
|
||||
// SubjectAltName ::= GeneralNames
|
||||
@ -1060,16 +1060,14 @@ func parseSANExtension(value []byte) (dnsNames, emailAddresses []string, ipAddre
|
||||
// iPAddress [7] OCTET STRING,
|
||||
// registeredID [8] OBJECT IDENTIFIER }
|
||||
var seq asn1.RawValue
|
||||
var rest []byte
|
||||
if rest, err = asn1.Unmarshal(value, &seq); err != nil {
|
||||
return
|
||||
rest, err := asn1.Unmarshal(extension, &seq)
|
||||
if err != nil {
|
||||
return err
|
||||
} else if len(rest) != 0 {
|
||||
err = errors.New("x509: trailing data after X.509 extension")
|
||||
return
|
||||
return errors.New("x509: trailing data after X.509 extension")
|
||||
}
|
||||
if !seq.IsCompound || seq.Tag != 16 || seq.Class != 0 {
|
||||
err = asn1.StructuralError{Msg: "bad SAN sequence"}
|
||||
return
|
||||
return asn1.StructuralError{Msg: "bad SAN sequence"}
|
||||
}
|
||||
|
||||
rest = seq.Bytes
|
||||
@ -1077,24 +1075,36 @@ func parseSANExtension(value []byte) (dnsNames, emailAddresses []string, ipAddre
|
||||
var v asn1.RawValue
|
||||
rest, err = asn1.Unmarshal(rest, &v)
|
||||
if err != nil {
|
||||
return
|
||||
return err
|
||||
}
|
||||
switch v.Tag {
|
||||
case 1:
|
||||
emailAddresses = append(emailAddresses, string(v.Bytes))
|
||||
case 2:
|
||||
dnsNames = append(dnsNames, string(v.Bytes))
|
||||
case 7:
|
||||
switch len(v.Bytes) {
|
||||
case net.IPv4len, net.IPv6len:
|
||||
ipAddresses = append(ipAddresses, v.Bytes)
|
||||
default:
|
||||
err = errors.New("x509: certificate contained IP address of length " + strconv.Itoa(len(v.Bytes)))
|
||||
return
|
||||
}
|
||||
|
||||
if err := callback(v.Tag, v.Bytes); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func parseSANExtension(value []byte) (dnsNames, emailAddresses []string, ipAddresses []net.IP, err error) {
|
||||
err = forEachSAN(value, func(tag int, data []byte) error {
|
||||
switch tag {
|
||||
case 1:
|
||||
emailAddresses = append(emailAddresses, string(data))
|
||||
case 2:
|
||||
dnsNames = append(dnsNames, string(data))
|
||||
case 7:
|
||||
switch len(data) {
|
||||
case net.IPv4len, net.IPv6len:
|
||||
ipAddresses = append(ipAddresses, data)
|
||||
default:
|
||||
return errors.New("x509: certificate contained IP address of length " + strconv.Itoa(len(data)))
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
})
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user