8 #include <botan/certstor_sql.h>
9 #include <botan/ber_dec.h>
10 #include <botan/der_enc.h>
11 #include <botan/internal/filesystem.h>
12 #include <botan/pkcs8.h>
13 #include <botan/data_src.h>
14 #include <botan/hash.h>
15 #include <botan/hex.h>
20 const std::string& passwd,
22 const std::string& table_prefix) :
28 m_database->create_table(
"CREATE TABLE IF NOT EXISTS " +
29 m_prefix +
"certificates ( \
30 fingerprint BLOB PRIMARY KEY, \
33 priv_fingerprint BLOB, \
34 certificate BLOB UNIQUE NOT NULL\
36 m_database->create_table(
"CREATE TABLE IF NOT EXISTS " + m_prefix +
"keys (\
37 fingerprint BLOB PRIMARY KEY, \
38 key BLOB UNIQUE NOT NULL \
40 m_database->create_table(
"CREATE TABLE IF NOT EXISTS " + m_prefix +
"revoked (\
41 fingerprint BLOB PRIMARY KEY, \
42 reason BLOB NOT NULL, \
48 std::shared_ptr<const X509_Certificate>
52 std::shared_ptr<SQL_Database::Statement> stmt;
58 stmt = m_database->new_statement(
"SELECT certificate FROM " + m_prefix +
"certificates WHERE subject_dn == ?1");
63 stmt = m_database->new_statement(
"SELECT certificate FROM " + m_prefix +
"certificates WHERE\
64 subject_dn == ?1 AND (key_id == NULL OR key_id == ?2)");
69 std::shared_ptr<const X509_Certificate> cert;
72 auto blob = stmt->get_blob(0);
73 cert = std::make_shared<X509_Certificate>(
74 std::vector<uint8_t>(blob.first,blob.first + blob.second));
81 std::shared_ptr<const X509_Certificate>
87 std::shared_ptr<const X509_Certificate>
93 std::shared_ptr<const X509_CRL>
98 for(
auto crl: all_crls)
100 if(!crl.get_revoked().empty() && crl.issuer_dn() == subject.
issuer_dn())
101 return std::shared_ptr<X509_CRL>(
new X509_CRL(crl));
104 return std::shared_ptr<X509_CRL>();
109 std::vector<X509_DN> ret;
110 auto stmt = m_database->new_statement(
"SELECT subject_dn FROM " + m_prefix +
"certificates");
114 auto blob = stmt->get_blob(0);
132 auto stmt = m_database->new_statement(
"INSERT OR REPLACE INTO " +
133 m_prefix +
"certificates (\
139 ) VALUES ( ?1, ?2, ?3, ?4, ?5 )");
145 stmt->bind(4,std::vector<uint8_t>());
160 auto stmt = m_database->new_statement(
"DELETE FROM " + m_prefix +
"certificates WHERE fingerprint == ?1");
171 auto stmt = m_database->new_statement(
"SELECT key FROM " + m_prefix +
"keys "
172 "JOIN " + m_prefix +
"certificates ON " +
173 m_prefix +
"keys.fingerprint == " + m_prefix +
"certificates.priv_fingerprint "
174 "WHERE " + m_prefix +
"certificates.fingerprint == ?1");
177 std::shared_ptr<const Private_Key> key;
180 auto blob = stmt->get_blob(0);
188 std::vector<std::shared_ptr<const X509_Certificate>>
192 auto stmt = m_database->new_statement(
"SELECT certificate FROM " + m_prefix +
"certificates WHERE priv_fingerprint == ?1");
196 std::vector<std::shared_ptr<const X509_Certificate>> certs;
199 auto blob = stmt->get_blob(0);
200 certs.push_back(std::make_shared<X509_Certificate>(
201 std::vector<uint8_t>(blob.first,blob.first + blob.second)));
216 auto stmt1 = m_database->new_statement(
217 "INSERT OR REPLACE INTO " + m_prefix +
"keys ( fingerprint, key ) VALUES ( ?1, ?2 )");
220 stmt1->bind(2,pkcs8.data(),pkcs8.size());
223 auto stmt2 = m_database->new_statement(
224 "UPDATE " + m_prefix +
"certificates SET priv_fingerprint = ?1 WHERE fingerprint == ?2");
236 auto stmt = m_database->new_statement(
"DELETE FROM " + m_prefix +
"keys WHERE fingerprint == ?1");
247 auto stmt1 = m_database->new_statement(
248 "INSERT OR REPLACE INTO " + m_prefix +
"revoked ( fingerprint, reason, time ) VALUES ( ?1, ?2, ?3 )");
269 auto stmt = m_database->new_statement(
"DELETE FROM " + m_prefix +
"revoked WHERE fingerprint == ?1");
277 auto stmt = m_database->new_statement(
278 "SELECT certificate,reason,time FROM " + m_prefix +
"revoked "
279 "JOIN " + m_prefix +
"certificates ON " +
280 m_prefix +
"certificates.fingerprint == " + m_prefix +
"revoked.fingerprint");
282 std::map<X509_DN,std::vector<CRL_Entry>> crls;
285 auto blob = stmt->get_blob(0);
287 std::vector<uint8_t>(blob.first,blob.first + blob.second));
288 auto code =
static_cast<CRL_Code>(stmt->get_size_t(1));
291 auto i = crls.find(cert.issuer_dn());
294 crls.insert(std::make_pair(cert.issuer_dn(),std::vector<CRL_Entry>({ent})));
298 i->second.push_back(ent);
302 std::vector<X509_CRL> ret;
303 X509_Time t(std::chrono::system_clock::now());
307 ret.push_back(
X509_CRL(p.first,t,t,p.second));
std::shared_ptr< const X509_Certificate > find_cert_by_pubkey_sha1(const std::vector< uint8_t > &key_hash) const override
std::vector< uint8_t > get_contents_unlocked()
bool insert_cert(const X509_Certificate &cert)
std::string fingerprint(const std::string &alg="SHA") const
void encode_into(class DER_Encoder &to) const override
secure_vector< uint8_t > BER_encode(const Private_Key &key)
std::vector< std::shared_ptr< const X509_Certificate > > find_certs_for_key(const Private_Key &key) const
Returns all certificates for private key "key".
void encode_into(class DER_Encoder &) const override
Private_Key * load_key(DataSource &source, RandomNumberGenerator &rng, std::function< std::string()> get_pass)
void encode_into(DER_Encoder &) const override
DER encode a X509_Time.
void decode_from(class BER_Decoder &) override
std::string fingerprint(const std::string &hash_name="SHA-1") const
Certificate_Store_In_SQL(const std::shared_ptr< SQL_Database > db, const std::string &passwd, RandomNumberGenerator &rng, const std::string &table_prefix="")
bool time_is_set() const
Return if the time has been set somehow.
void remove_key(const Private_Key &key)
Removes "key" from the store.
std::vector< X509_CRL > generate_crls() const
RandomNumberGenerator & m_rng
secure_vector< uint8_t > m_prefix
virtual std::shared_ptr< const X509_Certificate > find_cert(const X509_DN &subject_dn, const std::vector< uint8_t > &key_id) const override
bool insert_key(const X509_Certificate &cert, const Private_Key &key)
void revoke_cert(const X509_Certificate &, CRL_Code, const X509_Time &time=X509_Time())
Marks "cert" as revoked starting from "time".
bool remove_cert(const X509_Certificate &cert)
X509_DN issuer_dn() const
virtual std::shared_ptr< const X509_CRL > find_crl_for(const X509_Certificate &issuer) const override
std::vector< uint8_t > subject_key_id() const
std::shared_ptr< const Private_Key > find_key(const X509_Certificate &) const
Returns the private key for "cert" or an empty shared_ptr if none was found.
void affirm_cert(const X509_Certificate &)
Reverses the revokation for "cert".
X509_DN subject_dn() const
virtual std::vector< X509_DN > all_subjects() const override
std::shared_ptr< const X509_Certificate > find_cert_by_raw_subject_dn_sha256(const std::vector< uint8_t > &subject_hash) const override