github.com/haraldrudell/parl@v0.4.176/parlca/rsa-private.go (about)

     1  /*
     2  © 2022–present Harald Rudell <harald.rudell@gmail.com> (https://haraldrudell.github.io/haraldrudell/)
     3  ISC License
     4  */
     5  
     6  package parlca
     7  
     8  import (
     9  	"crypto/rand"
    10  	"crypto/rsa"
    11  	"crypto/x509"
    12  	"encoding/pem"
    13  
    14  	"github.com/haraldrudell/parl"
    15  	"github.com/haraldrudell/parl/perrors"
    16  )
    17  
    18  const (
    19  	rsaDefaultBits = 2048
    20  )
    21  
    22  type RsaPrivateKey struct {
    23  	// Decrypt(rand io.Reader, ciphertext []byte, opts crypto.DecrypterOpts) (plaintext []byte, err error)
    24  	// Equal(x crypto.PrivateKey) bool
    25  	// Precompute()
    26  	// Public() crypto.PublicKey
    27  	// Sign(rand io.Reader, digest []byte, opts crypto.SignerOpts) ([]byte, error)
    28  	// Size() int
    29  	// Validate() error
    30  	rsa.PrivateKey
    31  }
    32  
    33  func NewRsa() (privateKey parl.PrivateKey, err error) {
    34  	return NewRsaBits(rsaDefaultBits)
    35  }
    36  
    37  func NewRsaBits(bits int) (privateKey parl.PrivateKey, err error) {
    38  	var rsaPrivateKey *rsa.PrivateKey
    39  	if rsaPrivateKey, err = rsa.GenerateKey(rand.Reader, bits); perrors.IsPF(&err, "rsa.GenerateKey: %w", err) {
    40  		return
    41  	}
    42  	privateKey = &RsaPrivateKey{PrivateKey: *rsaPrivateKey}
    43  	return
    44  }
    45  
    46  func (key *RsaPrivateKey) Algo() (algo x509.PublicKeyAlgorithm) {
    47  	return x509.RSA
    48  }
    49  
    50  func (key *RsaPrivateKey) DER() (bytes parl.PrivateKeyDer, err error) {
    51  	if bytes, err = x509.MarshalPKCS8PrivateKey(&key.PrivateKey); err != nil {
    52  		err = perrors.Errorf("x509.MarshalPKCS8PrivateKey: '%w'", err)
    53  	}
    54  	return
    55  }
    56  
    57  func (key *RsaPrivateKey) DERe() (privateKeyDer parl.PrivateKeyDer) {
    58  	var err error
    59  	if privateKeyDer, err = key.DER(); err != nil {
    60  		panic(err)
    61  	}
    62  	return
    63  }
    64  
    65  func (key *RsaPrivateKey) PEM() (pemBytes parl.PemBytes, err error) {
    66  	block := pem.Block{
    67  		Type: pemPrivateKeyType,
    68  	}
    69  	if block.Bytes, err = key.DER(); err != nil {
    70  		return
    71  	}
    72  	pemBytes = append([]byte(PemText(block.Bytes)), pem.EncodeToMemory(&block)...)
    73  	return
    74  }
    75  
    76  func (key *RsaPrivateKey) PEMe() (pemBytes parl.PemBytes) {
    77  	var err error
    78  	if pemBytes, err = key.PEM(); err != nil {
    79  		panic(err)
    80  	}
    81  	return
    82  }
    83  
    84  func (key *RsaPrivateKey) PublicKey() (publicKey parl.PublicKey) {
    85  	return &RsaPublicKey{PublicKey: key.PrivateKey.PublicKey}
    86  }
    87  
    88  func (key *RsaPrivateKey) Validate() (err error) {
    89  	if key.PrivateKey.D == nil {
    90  		return perrors.New("rsa priovate key uninitialized")
    91  	}
    92  	return key.PrivateKey.Validate()
    93  }