diff options
Diffstat (limited to 'src/lib/pubkey/pkcs8.cpp')
-rw-r--r-- | src/lib/pubkey/pkcs8.cpp | 82 |
1 files changed, 69 insertions, 13 deletions
diff --git a/src/lib/pubkey/pkcs8.cpp b/src/lib/pubkey/pkcs8.cpp index 92157a196..1a021a283 100644 --- a/src/lib/pubkey/pkcs8.cpp +++ b/src/lib/pubkey/pkcs8.cpp @@ -44,19 +44,39 @@ secure_vector<byte> PKCS8_extract(DataSource& source, secure_vector<byte> PKCS8_decode( DataSource& source, std::function<std::string ()> get_passphrase, - AlgorithmIdentifier& pk_alg_id) + AlgorithmIdentifier& pk_alg_id, + bool is_encrypted) { AlgorithmIdentifier pbe_alg_id; secure_vector<byte> key_data, key; - bool is_encrypted = true; try { if(ASN1::maybe_BER(source) && !PEM_Code::matches(source)) - key_data = PKCS8_extract(source, pbe_alg_id); + { + if ( is_encrypted ) + { + key_data = PKCS8_extract(source, pbe_alg_id); + } + else + { + // todo read more efficiently + while ( !source.end_of_data() ) + { + byte b; + size_t read = source.read_byte( b ); + if ( read ) + { + key_data.push_back( b ); + } + } + } + } else { std::string label; key_data = PEM_Code::decode(source, label); + + // todo remove autodetect for pem as well? if(label == "PRIVATE KEY") is_encrypted = false; else if(label == "ENCRYPTED PRIVATE KEY") @@ -189,15 +209,18 @@ std::string PEM_encode(const Private_Key& key, "ENCRYPTED PRIVATE KEY"); } +namespace { + /* -* Extract a private key and return it +* Extract a private key (encrypted/unencrypted) and return it */ Private_Key* load_key(DataSource& source, RandomNumberGenerator& rng, - std::function<std::string ()> get_pass) + std::function<std::string ()> get_pass, + bool is_encrypted) { AlgorithmIdentifier alg_id; - secure_vector<byte> pkcs8_key = PKCS8_decode(source, get_pass, alg_id); + secure_vector<byte> pkcs8_key = PKCS8_decode(source, get_pass, alg_id, is_encrypted); const std::string alg_name = OIDS::lookup(alg_id.oid); if(alg_name == "" || alg_name == alg_id.oid.as_string()) @@ -207,29 +230,51 @@ Private_Key* load_key(DataSource& source, return make_private_key(alg_id, pkcs8_key, rng); } +} + /* -* Extract a private key and return it +* Extract an encrypted private key and return it */ -Private_Key* load_key(const std::string& fsname, +Private_Key* load_key(DataSource& source, RandomNumberGenerator& rng, std::function<std::string ()> get_pass) { - DataSource_Stream source(fsname, true); - return PKCS8::load_key(source, rng, get_pass); + return load_key(source, rng, get_pass, true); } /* -* Extract a private key and return it +* Extract an encrypted private key and return it */ Private_Key* load_key(DataSource& source, RandomNumberGenerator& rng, const std::string& pass) { - return PKCS8::load_key(source, rng, [pass]() { return pass; }); + return load_key(source, rng, [pass]() { return pass; }, true); + } + +/* +* Extract an unencrypted private key and return it +*/ +Private_Key* load_key(DataSource& source, + RandomNumberGenerator& rng) + { + return load_key(source, rng, []() -> std::string { + throw PKCS8_Exception( "Internal error: Attempt to read password for unencrypted key" );}, false); + } + +/* +* Extract an encrypted private key and return it +*/ +Private_Key* load_key(const std::string& fsname, + RandomNumberGenerator& rng, + std::function<std::string ()> get_pass) + { + DataSource_Stream source(fsname, true); + return load_key(source, rng, get_pass, true); } /* -* Extract a private key and return it +* Extract an encrypted private key and return it */ Private_Key* load_key(const std::string& fsname, RandomNumberGenerator& rng, @@ -239,6 +284,17 @@ Private_Key* load_key(const std::string& fsname, } /* +* Extract an unencrypted private key and return it +*/ +Private_Key* load_key(const std::string& fsname, + RandomNumberGenerator& rng) + { + DataSource_Stream source(fsname, true); + return load_key(source, rng, []() -> std::string { + throw PKCS8_Exception( "Internal error: Attempt to read password for unencrypted key" );}, false); + } + +/* * Make a copy of this private key */ Private_Key* copy_key(const Private_Key& key, |