package x509
import (
)
const ecPrivKeyVersion = 1
type ecPrivateKey struct {
Version int
PrivateKey []byte
NamedCurveOID asn1.ObjectIdentifier `asn1:"optional,explicit,tag:0"`
PublicKey asn1.BitString `asn1:"optional,explicit,tag:1"`
}
func ( []byte) (*ecdsa.PrivateKey, error) {
return parseECPrivateKey(nil, )
}
func ( *ecdsa.PrivateKey) ([]byte, error) {
, := oidFromNamedCurve(.Curve)
if ! {
return nil, errors.New("x509: unknown elliptic curve")
}
return marshalECPrivateKeyWithOID(, )
}
func ( *ecdsa.PrivateKey, asn1.ObjectIdentifier) ([]byte, error) {
, := .Bytes()
if != nil {
return nil,
}
, := .PublicKey.Bytes()
if != nil {
return nil,
}
return asn1.Marshal(ecPrivateKey{
Version: 1,
PrivateKey: ,
NamedCurveOID: ,
PublicKey: asn1.BitString{Bytes: },
})
}
func ( *ecdh.PrivateKey) ([]byte, error) {
return asn1.Marshal(ecPrivateKey{
Version: 1,
PrivateKey: .Bytes(),
PublicKey: asn1.BitString{Bytes: .PublicKey().Bytes()},
})
}
func ( *asn1.ObjectIdentifier, []byte) ( *ecdsa.PrivateKey, error) {
var ecPrivateKey
if , := asn1.Unmarshal(, &); != nil {
if , := asn1.Unmarshal(, &pkcs8{}); == nil {
return nil, errors.New("x509: failed to parse private key (use ParsePKCS8PrivateKey instead for this key format)")
}
if , := asn1.Unmarshal(, &pkcs1PrivateKey{}); == nil {
return nil, errors.New("x509: failed to parse private key (use ParsePKCS1PrivateKey instead for this key format)")
}
return nil, errors.New("x509: failed to parse EC private key: " + .Error())
}
if .Version != ecPrivKeyVersion {
return nil, fmt.Errorf("x509: unknown EC private key version %d", .Version)
}
var elliptic.Curve
if != nil {
= namedCurveFromOID(*)
} else {
= namedCurveFromOID(.NamedCurveOID)
}
if == nil {
return nil, errors.New("x509: unknown elliptic curve")
}
:= (.Params().N.BitLen() + 7) / 8
:= make([]byte, )
for len(.PrivateKey) > len() {
if .PrivateKey[0] != 0 {
return nil, errors.New("x509: invalid private key length")
}
.PrivateKey = .PrivateKey[1:]
}
copy([len()-len(.PrivateKey):], .PrivateKey)
return ecdsa.ParseRawPrivateKey(, )
}