diff options
author | Jack Lloyd <[email protected]> | 2017-12-04 14:00:47 -0500 |
---|---|---|
committer | Jack Lloyd <[email protected]> | 2017-12-04 14:00:47 -0500 |
commit | 697fdc8fcb7f4ada4699ccad80def4673270d133 (patch) | |
tree | 5b2ec8652a20d7e0c0b74f328958818fafaa14b4 /src/lib/x509/x509_obj.cpp | |
parent | d3c1f3ba1a9d03ff8e84f0044ee3854804fac86b (diff) |
Support uninitialized certificate objects
Issued raised by @securitykernel on Slack, there was no non-hacky
way to decode a list of certificate objects because creating an
uninitialized one wasn't allowed. However after #884 that got much
closer to being viable, this is the last pieces.
Diffstat (limited to 'src/lib/x509/x509_obj.cpp')
-rw-r--r-- | src/lib/x509/x509_obj.cpp | 95 |
1 files changed, 34 insertions, 61 deletions
diff --git a/src/lib/x509/x509_obj.cpp b/src/lib/x509/x509_obj.cpp index dad27d6ff..019bac0b1 100644 --- a/src/lib/x509/x509_obj.cpp +++ b/src/lib/x509/x509_obj.cpp @@ -47,45 +47,10 @@ Pss_params decode_pss_params(const std::vector<uint8_t>& encoded_pss_params) } /* -* Create a generic X.509 object -*/ -X509_Object::X509_Object(DataSource& stream, const std::string& labels) - { - init(stream, labels); - } - -#if defined(BOTAN_TARGET_OS_HAS_FILESYSTEM) -/* -* Create a generic X.509 object -*/ -X509_Object::X509_Object(const std::string& file, const std::string& labels) - { - DataSource_Stream stream(file, true); - init(stream, labels); - } -#endif - -/* -* Create a generic X.509 object -*/ -X509_Object::X509_Object(const std::vector<uint8_t>& vec, const std::string& labels) - { - DataSource_Memory stream(vec.data(), vec.size()); - init(stream, labels); - } - -/* * Read a PEM or BER X.509 object */ -void X509_Object::init(DataSource& in, const std::string& labels) +void X509_Object::load_data(DataSource& in) { - m_PEM_labels_allowed = split_on(labels, '/'); - if(m_PEM_labels_allowed.size() < 1) - throw Invalid_Argument("Bad labels argument to X509_Object"); - - m_PEM_label_pref = m_PEM_labels_allowed[0]; - std::sort(m_PEM_labels_allowed.begin(), m_PEM_labels_allowed.end()); - try { if(ASN1::maybe_BER(in) && !PEM_Code::matches(in)) { @@ -97,9 +62,21 @@ void X509_Object::init(DataSource& in, const std::string& labels) std::string got_label; DataSource_Memory ber(PEM_Code::decode(in, got_label)); - if(!std::binary_search(m_PEM_labels_allowed.begin(), - m_PEM_labels_allowed.end(), got_label)) - throw Decoding_Error("Invalid PEM label: " + got_label); + if(got_label != PEM_label()) + { + bool is_alternate = false; + for(std::string alt_label : alternate_PEM_labels()) + { + if(got_label == alt_label) + { + is_alternate = true; + break; + } + } + + if(!is_alternate) + throw Decoding_Error("Unexpected PEM label for " + PEM_label() + " of " + got_label); + } BER_Decoder dec(ber); decode_from(dec); @@ -107,7 +84,7 @@ void X509_Object::init(DataSource& in, const std::string& labels) } catch(Decoding_Error& e) { - throw Decoding_Error(m_PEM_label_pref + " decoding failed: " + e.what()); + throw Decoding_Error(PEM_label() + " decoding failed: " + e.what()); } } @@ -135,6 +112,18 @@ void X509_Object::decode_from(BER_Decoder& from) .decode(m_sig_algo) .decode(m_sig, BIT_STRING) .end_cons(); + + try { + force_decode(); + } + catch(Decoding_Error& e) + { + throw Decoding_Error(PEM_label() + " decoding failed", e.what()); + } + catch(Invalid_Argument& e) + { + throw Decoding_Error(PEM_label() + " decoding failed", e.what()); + } } /* @@ -152,7 +141,7 @@ std::vector<uint8_t> X509_Object::BER_encode() const */ std::string X509_Object::PEM_encode() const { - return PEM_Code::encode(BER_encode(), m_PEM_label_pref); + return PEM_Code::encode(BER_encode(), PEM_label()); } /* @@ -199,7 +188,7 @@ std::string X509_Object::hash_used_for_signature() const bool X509_Object::check_signature(const Public_Key* pub_key) const { if(!pub_key) - throw Exception("No key provided for " + m_PEM_label_pref + " signature check"); + throw Exception("No key provided for " + PEM_label() + " signature check"); std::unique_ptr<const Public_Key> key(pub_key); return check_signature(*key); } @@ -280,31 +269,15 @@ std::vector<uint8_t> X509_Object::make_signed(PK_Signer* signer, const AlgorithmIdentifier& algo, const secure_vector<uint8_t>& tbs_bits) { + const std::vector<uint8_t> signature = signer->sign_message(tbs_bits, rng); + return DER_Encoder() .start_cons(SEQUENCE) .raw_bytes(tbs_bits) .encode(algo) - .encode(signer->sign_message(tbs_bits, rng), BIT_STRING) + .encode(signature, BIT_STRING) .end_cons() .get_contents_unlocked(); } -/* -* Try to decode the actual information -*/ -void X509_Object::do_decode() - { - try { - force_decode(); - } - catch(Decoding_Error& e) - { - throw Decoding_Error(m_PEM_label_pref + " decoding failed", e.what()); - } - catch(Invalid_Argument& e) - { - throw Decoding_Error(m_PEM_label_pref + " decoding failed", e.what()); - } - } - } |