OpenCores
URL https://opencores.org/ocsvn/openrisc/openrisc/trunk

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [gnu-dev/] [or1k-gcc/] [libgo/] [go/] [crypto/] [x509/] [pkcs1.go] - Rev 833

Go to most recent revision | Compare with Previous | Blame | View Log

// Copyright 2011 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

package x509

import (
        "crypto/rsa"
        "encoding/asn1"
        "errors"
        "math/big"
)

// pkcs1PrivateKey is a structure which mirrors the PKCS#1 ASN.1 for an RSA private key.
type pkcs1PrivateKey struct {
        Version int
        N       *big.Int
        E       int
        D       *big.Int
        P       *big.Int
        Q       *big.Int
        // We ignore these values, if present, because rsa will calculate them.
        Dp   *big.Int `asn1:"optional"`
        Dq   *big.Int `asn1:"optional"`
        Qinv *big.Int `asn1:"optional"`

        AdditionalPrimes []pkcs1AdditionalRSAPrime `asn1:"optional"`
}

type pkcs1AdditionalRSAPrime struct {
        Prime *big.Int

        // We ignore these values because rsa will calculate them.
        Exp   *big.Int
        Coeff *big.Int
}

// ParsePKCS1PrivateKey returns an RSA private key from its ASN.1 PKCS#1 DER encoded form.
func ParsePKCS1PrivateKey(der []byte) (key *rsa.PrivateKey, err error) {
        var priv pkcs1PrivateKey
        rest, err := asn1.Unmarshal(der, &priv)
        if len(rest) > 0 {
                err = asn1.SyntaxError{Msg: "trailing data"}
                return
        }
        if err != nil {
                return
        }

        if priv.Version > 1 {
                return nil, errors.New("x509: unsupported private key version")
        }

        if priv.N.Sign() <= 0 || priv.D.Sign() <= 0 || priv.P.Sign() <= 0 || priv.Q.Sign() <= 0 {
                return nil, errors.New("private key contains zero or negative value")
        }

        key = new(rsa.PrivateKey)
        key.PublicKey = rsa.PublicKey{
                E: priv.E,
                N: priv.N,
        }

        key.D = priv.D
        key.Primes = make([]*big.Int, 2+len(priv.AdditionalPrimes))
        key.Primes[0] = priv.P
        key.Primes[1] = priv.Q
        for i, a := range priv.AdditionalPrimes {
                if a.Prime.Sign() <= 0 {
                        return nil, errors.New("private key contains zero or negative prime")
                }
                key.Primes[i+2] = a.Prime
                // We ignore the other two values because rsa will calculate
                // them as needed.
        }

        err = key.Validate()
        if err != nil {
                return nil, err
        }
        key.Precompute()

        return
}

// MarshalPKCS1PrivateKey converts a private key to ASN.1 DER encoded form.
func MarshalPKCS1PrivateKey(key *rsa.PrivateKey) []byte {
        key.Precompute()

        version := 0
        if len(key.Primes) > 2 {
                version = 1
        }

        priv := pkcs1PrivateKey{
                Version: version,
                N:       key.N,
                E:       key.PublicKey.E,
                D:       key.D,
                P:       key.Primes[0],
                Q:       key.Primes[1],
                Dp:      key.Precomputed.Dp,
                Dq:      key.Precomputed.Dq,
                Qinv:    key.Precomputed.Qinv,
        }

        priv.AdditionalPrimes = make([]pkcs1AdditionalRSAPrime, len(key.Precomputed.CRTValues))
        for i, values := range key.Precomputed.CRTValues {
                priv.AdditionalPrimes[i].Prime = key.Primes[2+i]
                priv.AdditionalPrimes[i].Exp = values.Exp
                priv.AdditionalPrimes[i].Coeff = values.Coeff
        }

        b, _ := asn1.Marshal(priv)
        return b
}

// rsaPublicKey reflects the ASN.1 structure of a PKCS#1 public key.
type rsaPublicKey struct {
        N *big.Int
        E int
}

Go to most recent revision | Compare with Previous | Blame | View Log

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.