1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #ifndef CRYPTO_EC_PRIVATE_KEY_H_ 6 #define CRYPTO_EC_PRIVATE_KEY_H_ 7 8 #include <stddef.h> 9 #include <stdint.h> 10 11 #include <memory> 12 #include <string> 13 #include <vector> 14 15 #include "base/macros.h" 16 #include "build/build_config.h" 17 #include "crypto/crypto_export.h" 18 19 #if defined(USE_OPENSSL) 20 // Forward declaration for openssl/*.h 21 typedef struct evp_pkey_st EVP_PKEY; 22 #else 23 // Forward declaration. 24 typedef struct CERTSubjectPublicKeyInfoStr CERTSubjectPublicKeyInfo; 25 typedef struct PK11SlotInfoStr PK11SlotInfo; 26 typedef struct SECKEYPrivateKeyStr SECKEYPrivateKey; 27 typedef struct SECKEYPublicKeyStr SECKEYPublicKey; 28 #endif 29 30 namespace crypto { 31 32 // Encapsulates an elliptic curve (EC) private key. Can be used to generate new 33 // keys, export keys to other formats, or to extract a public key. 34 // TODO(mattm): make this and RSAPrivateKey implement some PrivateKey interface. 35 // (The difference in types of key() and public_key() make this a little 36 // tricky.) 37 class CRYPTO_EXPORT ECPrivateKey { 38 public: 39 ~ECPrivateKey(); 40 41 // Creates a new random instance. Can return nullptr if initialization fails. 42 // The created key will use the NIST P-256 curve. 43 // TODO(mattm): Add a curve parameter. 44 static std::unique_ptr<ECPrivateKey> Create(); 45 46 // Create a new instance by importing an existing private key. The format is 47 // an ASN.1-encoded PrivateKeyInfo block from PKCS #8. This can return 48 // nullptr if initialization fails. 49 static std::unique_ptr<ECPrivateKey> CreateFromPrivateKeyInfo( 50 const std::vector<uint8_t>& input); 51 52 // Creates a new instance by importing an existing key pair. 53 // The key pair is given as an ASN.1-encoded PKCS #8 EncryptedPrivateKeyInfo 54 // block and an X.509 SubjectPublicKeyInfo block. 55 // Returns nullptr if initialization fails. 56 // 57 // This function is deprecated. Use CreateFromPrivateKeyInfo for new code. 58 // See https://crbug.com/603319. 59 static std::unique_ptr<ECPrivateKey> CreateFromEncryptedPrivateKeyInfo( 60 const std::string& password, 61 const std::vector<uint8_t>& encrypted_private_key_info, 62 const std::vector<uint8_t>& subject_public_key_info); 63 64 #if !defined(USE_OPENSSL) 65 // Imports the key pair into |slot| and returns in |public_key| and |key|. 66 // Shortcut for code that needs to keep a reference directly to NSS types 67 // without having to create a ECPrivateKey object and make a copy of them. 68 // TODO(mattm): move this function to some NSS util file. 69 static bool ImportFromEncryptedPrivateKeyInfo( 70 PK11SlotInfo* slot, 71 const std::string& password, 72 const uint8_t* encrypted_private_key_info, 73 size_t encrypted_private_key_info_len, 74 CERTSubjectPublicKeyInfo* decoded_spki, 75 bool permanent, 76 bool sensitive, 77 SECKEYPrivateKey** key, 78 SECKEYPublicKey** public_key); 79 #endif 80 81 // Returns a copy of the object. 82 std::unique_ptr<ECPrivateKey> Copy() const; 83 84 #if defined(USE_OPENSSL) key()85 EVP_PKEY* key() { return key_; } 86 #else key()87 SECKEYPrivateKey* key() { return key_; } public_key()88 SECKEYPublicKey* public_key() { return public_key_; } 89 #endif 90 91 // Exports the private key to a PKCS #8 PrivateKeyInfo block. 92 bool ExportPrivateKey(std::vector<uint8_t>* output) const; 93 94 // Exports the private key as an ASN.1-encoded PKCS #8 EncryptedPrivateKeyInfo 95 // block and the public key as an X.509 SubjectPublicKeyInfo block. 96 // The |password| and |iterations| are used as inputs to the key derivation 97 // function for generating the encryption key. PKCS #5 recommends a minimum 98 // of 1000 iterations, on modern systems a larger value may be preferrable. 99 // 100 // This function is deprecated. Use ExportPrivateKey for new code. See 101 // https://crbug.com/603319. 102 bool ExportEncryptedPrivateKey(const std::string& password, 103 int iterations, 104 std::vector<uint8_t>* output) const; 105 106 // Exports the public key to an X.509 SubjectPublicKeyInfo block. 107 bool ExportPublicKey(std::vector<uint8_t>* output) const; 108 109 // Exports the public key as an EC point in the uncompressed point format. 110 bool ExportRawPublicKey(std::string* output) const; 111 112 private: 113 // Constructor is private. Use one of the Create*() methods above instead. 114 ECPrivateKey(); 115 116 #if defined(USE_OPENSSL) 117 EVP_PKEY* key_; 118 #else 119 SECKEYPrivateKey* key_; 120 SECKEYPublicKey* public_key_; 121 #endif 122 123 DISALLOW_COPY_AND_ASSIGN(ECPrivateKey); 124 }; 125 126 127 } // namespace crypto 128 129 #endif // CRYPTO_EC_PRIVATE_KEY_H_ 130