blob: efb4e0f0fc91e2e09deb8698e3fe6e131508db1b [file] [log] [blame]
Alexander Afanasyevc169a812014-05-20 20:37:29 -04001/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
Jeff Thompson7ca11f22013-10-04 19:01:30 -07002/**
Alexander Afanasyev4c9a3d52017-01-03 17:45:19 -08003 * Copyright (c) 2013-2017 Regents of the University of California.
Alexander Afanasyevdfa52c42014-04-24 21:10:11 -07004 *
5 * This file is part of ndn-cxx library (NDN C++ library with eXperimental eXtensions).
Alexander Afanasyevdfa52c42014-04-24 21:10:11 -07006 *
Alexander Afanasyevc169a812014-05-20 20:37:29 -04007 * ndn-cxx library is free software: you can redistribute it and/or modify it under the
8 * terms of the GNU Lesser General Public License as published by the Free Software
9 * Foundation, either version 3 of the License, or (at your option) any later version.
10 *
11 * ndn-cxx library is distributed in the hope that it will be useful, but WITHOUT ANY
12 * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
13 * PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details.
14 *
15 * You should have received copies of the GNU General Public License and GNU Lesser
16 * General Public License along with ndn-cxx, e.g., in COPYING.md file. If not, see
17 * <http://www.gnu.org/licenses/>.
18 *
19 * See AUTHORS.md for complete list of ndn-cxx authors and contributors.
Alexander Afanasyevdfa52c42014-04-24 21:10:11 -070020 *
21 * @author Yingdi Yu <http://irl.cs.ucla.edu/~yingdi/>
22 * @author Jeff Thompson <jefft0@remap.ucla.edu>
Jeff Thompson7ca11f22013-10-04 19:01:30 -070023 */
24
Alexander Afanasyeve2dcdfd2014-02-07 15:53:28 -080025#include "sec-public-info-sqlite3.hpp"
Alexander Afanasyev4c9a3d52017-01-03 17:45:19 -080026#include "identity-certificate.hpp"
27#include "../signature-sha256-with-rsa.hpp"
28#include "../signature-sha256-with-ecdsa.hpp"
29#include "../../data.hpp"
Alexander Afanasyeve2dcdfd2014-02-07 15:53:28 -080030
Yingdi Yu874678f2014-01-22 19:30:34 -080031#include <sqlite3.h>
Jeff Thompson351ac302013-10-19 18:45:00 -070032#include <stdio.h>
Jeff Thompson7ca11f22013-10-04 19:01:30 -070033#include <stdlib.h>
34#include <sstream>
35#include <fstream>
Yingdi Yu0b9c3152014-01-26 16:31:18 -080036#include <boost/filesystem.hpp>
Alexander Afanasyevd409d592014-01-28 18:36:38 -080037
Yingdi Yufc40d872014-02-18 12:56:04 -080038namespace ndn {
Alexander Afanasyev2fa59392016-07-29 17:24:23 -070039namespace security {
Alexander Afanasyev4c9a3d52017-01-03 17:45:19 -080040namespace v1 {
Jeff Thompson7ca11f22013-10-04 19:01:30 -070041
Yingdi Yu5ec0ee32014-06-24 16:26:09 -070042using std::string;
43using std::vector;
44
Alexander Afanasyev07113802015-01-15 19:14:36 -080045const std::string SecPublicInfoSqlite3::SCHEME("pib-sqlite3");
Jeff Thompson7ca11f22013-10-04 19:01:30 -070046
Yingdi Yu41546342014-11-30 23:37:53 -080047static const string INIT_TPM_INFO_TABLE =
48 "CREATE TABLE IF NOT EXISTS "
49 " TpmInfo( "
50 " tpm_locator BLOB NOT NULL,"
51 " PRIMARY KEY (tpm_locator) "
52 " ); ";
Jeff Thompson7ca11f22013-10-04 19:01:30 -070053
Yingdi Yu41546342014-11-30 23:37:53 -080054static const string INIT_ID_TABLE =
55 "CREATE TABLE IF NOT EXISTS "
56 " Identity( "
57 " identity_name BLOB NOT NULL, "
58 " default_identity INTEGER DEFAULT 0, "
59 " PRIMARY KEY (identity_name) "
60 " ); "
61 "CREATE INDEX identity_index ON Identity(identity_name);";
62
63static const string INIT_KEY_TABLE =
64 "CREATE TABLE IF NOT EXISTS "
65 " Key( "
66 " identity_name BLOB NOT NULL, "
67 " key_identifier BLOB NOT NULL, "
68 " key_type INTEGER, "
69 " public_key BLOB, "
70 " default_key INTEGER DEFAULT 0, "
71 " active INTEGER DEFAULT 0, "
72 " PRIMARY KEY (identity_name, key_identifier)"
73 " ); "
74 "CREATE INDEX key_index ON Key(identity_name); ";
75
76
77static const string INIT_CERT_TABLE =
78 "CREATE TABLE IF NOT EXISTS "
79 " Certificate( "
80 " cert_name BLOB NOT NULL, "
81 " cert_issuer BLOB NOT NULL, "
82 " identity_name BLOB NOT NULL, "
83 " key_identifier BLOB NOT NULL, "
84 " not_before TIMESTAMP, "
85 " not_after TIMESTAMP, "
86 " certificate_data BLOB NOT NULL, "
87 " valid_flag INTEGER DEFAULT 1, "
88 " default_cert INTEGER DEFAULT 0, "
89 " PRIMARY KEY (cert_name) "
90 " ); "
91 "CREATE INDEX cert_index ON Certificate(cert_name); "
92 "CREATE INDEX subject ON Certificate(identity_name);";
Jeff Thompson7ca11f22013-10-04 19:01:30 -070093
94/**
Yingdi Yu4b8c6a22014-04-15 23:00:54 -070095 * A utility function to call the normal sqlite3_bind_text where the value and length are
96 * value.c_str() and value.size().
Jeff Thompson7ca11f22013-10-04 19:01:30 -070097 */
Alexander Afanasyevdb4affc2014-07-15 13:37:16 -070098static int
Yingdi Yu41546342014-11-30 23:37:53 -080099sqlite3_bind_string(sqlite3_stmt* statement,
100 int index,
101 const string& value,
102 void(*destructor)(void*))
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700103{
104 return sqlite3_bind_text(statement, index, value.c_str(), value.size(), destructor);
105}
106
Yingdi Yu41546342014-11-30 23:37:53 -0800107static string
108sqlite3_column_string(sqlite3_stmt* statement, int column)
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700109{
Yingdi Yu41546342014-11-30 23:37:53 -0800110 return string(reinterpret_cast<const char*>(sqlite3_column_text(statement, column)),
111 sqlite3_column_bytes(statement, column));
112}
113
114SecPublicInfoSqlite3::SecPublicInfoSqlite3(const std::string& dir)
115 : SecPublicInfo(dir)
116 , m_database(nullptr)
117{
118 boost::filesystem::path identityDir;
Alexander Afanasyev57e00362016-06-23 13:22:54 -0700119 if (dir == "") {
120#ifdef NDN_CXX_HAVE_TESTS
121 if (getenv("TEST_HOME") != nullptr) {
122 identityDir = boost::filesystem::path(getenv("TEST_HOME")) / ".ndn";
123 }
124 else
125#endif // NDN_CXX_HAVE_TESTS
126 if (getenv("HOME") != nullptr) {
127 identityDir = boost::filesystem::path(getenv("HOME")) / ".ndn";
128 }
129 else {
130 identityDir = boost::filesystem::path(".") / ".ndn";
131 }
132 }
133 else {
134 identityDir = boost::filesystem::path(dir);
135 }
Yingdi Yu5ec0ee32014-06-24 16:26:09 -0700136 boost::filesystem::create_directories(identityDir);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700137
Alexander Afanasyev5b60f702014-02-07 12:55:24 -0800138 /// @todo Add define for windows/unix in wscript. The following may completely fail on windows
139 int res = sqlite3_open_v2((identityDir / "ndnsec-public-info.db").c_str(), &m_database,
140 SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE,
Alexander Afanasyev766cea72014-04-24 19:16:42 -0700141#ifdef NDN_CXX_DISABLE_SQLITE3_FS_LOCKING
Alexander Afanasyev44471462014-02-12 11:21:51 -0800142 "unix-dotfile"
Alexander Afanasyev5b60f702014-02-07 12:55:24 -0800143#else
144 0
145#endif
146 );
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700147 if (res != SQLITE_OK)
Spyridon Mastorakis0d2ed2e2015-07-27 19:09:12 -0700148 BOOST_THROW_EXCEPTION(Error("identity DB cannot be opened/created"));
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700149
Yingdi Yu41546342014-11-30 23:37:53 -0800150
Junxiao Shi98acbb02014-12-02 11:00:42 -0700151 BOOST_ASSERT(m_database != nullptr);
152
Yingdi Yu41546342014-11-30 23:37:53 -0800153 initializeTable("TpmInfo", INIT_TPM_INFO_TABLE); // Check if TpmInfo table exists;
154 initializeTable("Identity", INIT_ID_TABLE); // Check if Identity table exists;
155 initializeTable("Key", INIT_KEY_TABLE); // Check if Key table exists;
156 initializeTable("Certificate", INIT_CERT_TABLE); // Check if Certificate table exists;
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700157}
158
Yingdi Yu87581582014-01-14 14:28:39 -0800159SecPublicInfoSqlite3::~SecPublicInfoSqlite3()
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700160{
Junxiao Shi98acbb02014-12-02 11:00:42 -0700161 sqlite3_close(m_database);
162 m_database = nullptr;
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700163}
164
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700165bool
Yingdi Yu41546342014-11-30 23:37:53 -0800166SecPublicInfoSqlite3::doesTableExist(const string& tableName)
167{
168 // Check if the table exists;
169 bool doesTableExist = false;
170 string checkingString =
171 "SELECT name FROM sqlite_master WHERE type='table' AND name='" + tableName + "'";
172
Yingdi Yua90ba482014-12-09 10:54:43 -0800173 sqlite3_stmt* statement = nullptr;
Yingdi Yu41546342014-11-30 23:37:53 -0800174 sqlite3_prepare_v2(m_database, checkingString.c_str(), -1, &statement, 0);
175
176 int result = sqlite3_step(statement);
177 if (result == SQLITE_ROW)
178 doesTableExist = true;
179 sqlite3_finalize(statement);
180
181 return doesTableExist;
182}
183
184bool
185SecPublicInfoSqlite3::initializeTable(const string& tableName, const string& initCommand)
186{
187 // Create the table if it does not exist
188 if (!doesTableExist(tableName)) {
189 char* errorMessage = 0;
190 int result = sqlite3_exec(m_database, initCommand.c_str(), NULL, NULL, &errorMessage);
191
192 if (result != SQLITE_OK && errorMessage != 0) {
193 sqlite3_free(errorMessage);
194 return false;
195 }
196 }
197
198 return true;
199}
200
201void
202SecPublicInfoSqlite3::deleteTable(const string& tableName)
203{
204 string query = "DROP TABLE IF EXISTS " + tableName;
205
Yingdi Yua90ba482014-12-09 10:54:43 -0800206 sqlite3_stmt* statement = nullptr;
Yingdi Yu41546342014-11-30 23:37:53 -0800207 sqlite3_prepare_v2(m_database, query.c_str(), -1, &statement, 0);
208
209 sqlite3_step(statement);
210 sqlite3_finalize(statement);
211}
212
213void
214SecPublicInfoSqlite3::setTpmLocator(const string& tpmLocator)
215{
216 string currentTpm;
217 try {
218 currentTpm = getTpmLocator();
219 }
220 catch (SecPublicInfo::Error&) {
221 setTpmLocatorInternal(tpmLocator, false); // set tpmInfo without resetting
222 return;
223 }
224
225 if (currentTpm == tpmLocator)
226 return; // if the same, nothing will be changed
227
228 setTpmLocatorInternal(tpmLocator, true); // set tpmInfo and reset pib
229}
230
231string
232SecPublicInfoSqlite3::getTpmLocator()
233{
Yingdi Yua90ba482014-12-09 10:54:43 -0800234 sqlite3_stmt* statement = nullptr;
Yingdi Yu41546342014-11-30 23:37:53 -0800235 sqlite3_prepare_v2(m_database, "SELECT tpm_locator FROM TpmInfo", -1, &statement, 0);
236
237 int res = sqlite3_step(statement);
238
239 if (res == SQLITE_ROW) {
240 string tpmLocator = sqlite3_column_string(statement, 0);
241 sqlite3_finalize(statement);
242 return tpmLocator;
243 }
244 else {
245 sqlite3_finalize(statement);
Spyridon Mastorakis0d2ed2e2015-07-27 19:09:12 -0700246 BOOST_THROW_EXCEPTION(SecPublicInfo::Error("TPM info does not exist"));
Yingdi Yu41546342014-11-30 23:37:53 -0800247 }
248}
249
250void
251SecPublicInfoSqlite3::setTpmLocatorInternal(const string& tpmLocator, bool needReset)
252{
Yingdi Yua90ba482014-12-09 10:54:43 -0800253 sqlite3_stmt* statement = nullptr;
Yingdi Yu41546342014-11-30 23:37:53 -0800254
255 if (needReset) {
256 deleteTable("Identity");
257 deleteTable("Key");
258 deleteTable("Certificate");
259
260 initializeTable("Identity", INIT_ID_TABLE);
261 initializeTable("Key", INIT_KEY_TABLE);
262 initializeTable("Certificate", INIT_CERT_TABLE);
263
264 sqlite3_prepare_v2(m_database, "UPDATE TpmInfo SET tpm_locator = ?",
265 -1, &statement, 0);
266 sqlite3_bind_string(statement, 1, tpmLocator, SQLITE_TRANSIENT);
267 }
268 else {
269 // no reset implies there is no tpmLocator record, insert one
270 sqlite3_prepare_v2(m_database, "INSERT INTO TpmInfo (tpm_locator) VALUES (?)",
271 -1, &statement, 0);
272 sqlite3_bind_string(statement, 1, tpmLocator, SQLITE_TRANSIENT);
273 }
274
275 sqlite3_step(statement);
276 sqlite3_finalize(statement);
277}
278
279std::string
280SecPublicInfoSqlite3::getPibLocator()
281{
282 return string("pib-sqlite3:").append(m_location);
283}
284
285bool
Yingdi Yu87581582014-01-14 14:28:39 -0800286SecPublicInfoSqlite3::doesIdentityExist(const Name& identityName)
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700287{
288 bool result = false;
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700289
Yingdi Yua90ba482014-12-09 10:54:43 -0800290 sqlite3_stmt* statement = nullptr;
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700291 sqlite3_prepare_v2(m_database,
292 "SELECT count(*) FROM Identity WHERE identity_name=?",
293 -1, &statement, 0);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700294
Yingdi Yu41546342014-11-30 23:37:53 -0800295 sqlite3_bind_string(statement, 1, identityName.toUri(), SQLITE_TRANSIENT);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700296 int res = sqlite3_step(statement);
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700297
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700298 if (res == SQLITE_ROW) {
299 int countAll = sqlite3_column_int(statement, 0);
300 if (countAll > 0)
301 result = true;
302 }
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700303
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700304 sqlite3_finalize(statement);
305
306 return result;
307}
308
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700309void
Yingdi Yu87581582014-01-14 14:28:39 -0800310SecPublicInfoSqlite3::addIdentity(const Name& identityName)
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700311{
Yingdi Yu05842f22014-04-15 19:21:56 -0700312 if (doesIdentityExist(identityName))
313 return;
314
Yingdi Yua90ba482014-12-09 10:54:43 -0800315 sqlite3_stmt* statement = nullptr;
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700316
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700317 sqlite3_prepare_v2(m_database,
318 "INSERT OR REPLACE INTO Identity (identity_name) values (?)",
319 -1, &statement, 0);
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700320
Yingdi Yu41546342014-11-30 23:37:53 -0800321 sqlite3_bind_string(statement, 1, identityName.toUri(), SQLITE_TRANSIENT);
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700322
Alexander Afanasyev736708b2014-01-06 14:45:34 -0800323 sqlite3_step(statement);
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700324
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700325 sqlite3_finalize(statement);
326}
327
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700328bool
Yingdi Yu87581582014-01-14 14:28:39 -0800329SecPublicInfoSqlite3::revokeIdentity()
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700330{
331 //TODO:
332 return false;
333}
334
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700335bool
Yingdi Yu87581582014-01-14 14:28:39 -0800336SecPublicInfoSqlite3::doesPublicKeyExist(const Name& keyName)
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700337{
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700338 if (keyName.empty())
Spyridon Mastorakis0d2ed2e2015-07-27 19:09:12 -0700339 BOOST_THROW_EXCEPTION(Error("Incorrect key name " + keyName.toUri()));
Yingdi Yu88663af2014-01-15 15:21:38 -0800340
Alexander Afanasyev9c578182014-05-14 17:28:28 -0700341 string keyId = keyName.get(-1).toUri();
Yingdi Yu87581582014-01-14 14:28:39 -0800342 Name identityName = keyName.getPrefix(-1);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700343
Yingdi Yua90ba482014-12-09 10:54:43 -0800344 sqlite3_stmt* statement = nullptr;
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700345 sqlite3_prepare_v2(m_database,
346 "SELECT count(*) FROM Key WHERE identity_name=? AND key_identifier=?",
347 -1, &statement, 0);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700348
Yingdi Yu41546342014-11-30 23:37:53 -0800349 sqlite3_bind_string(statement, 1, identityName.toUri(), SQLITE_TRANSIENT);
350 sqlite3_bind_string(statement, 2, keyId, SQLITE_TRANSIENT);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700351
352 int res = sqlite3_step(statement);
353
354 bool keyIdExist = false;
355 if (res == SQLITE_ROW) {
356 int countAll = sqlite3_column_int(statement, 0);
357 if (countAll > 0)
358 keyIdExist = true;
359 }
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700360
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700361 sqlite3_finalize(statement);
362
363 return keyIdExist;
364}
365
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700366void
Yingdi Yu40b53092014-06-17 17:10:02 -0700367SecPublicInfoSqlite3::addKey(const Name& keyName,
Alexander Afanasyev4c9a3d52017-01-03 17:45:19 -0800368 const PublicKey& publicKeyDer)
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700369{
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700370 if (keyName.empty())
Yingdi Yu2e57a582014-02-20 23:34:43 -0800371 return;
Yingdi Yu88663af2014-01-15 15:21:38 -0800372
Yingdi Yu05842f22014-04-15 19:21:56 -0700373 if (doesPublicKeyExist(keyName))
374 return;
375
Alexander Afanasyev9c578182014-05-14 17:28:28 -0700376 string keyId = keyName.get(-1).toUri();
Yingdi Yu87581582014-01-14 14:28:39 -0800377 Name identityName = keyName.getPrefix(-1);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700378
Yingdi Yu2e57a582014-02-20 23:34:43 -0800379 addIdentity(identityName);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700380
Yingdi Yua90ba482014-12-09 10:54:43 -0800381 sqlite3_stmt* statement = nullptr;
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700382 sqlite3_prepare_v2(m_database,
383 "INSERT OR REPLACE INTO Key \
384 (identity_name, key_identifier, key_type, public_key) \
385 values (?, ?, ?, ?)",
386 -1, &statement, 0);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700387
Yingdi Yu41546342014-11-30 23:37:53 -0800388 sqlite3_bind_string(statement, 1, identityName.toUri(), SQLITE_TRANSIENT);
389 sqlite3_bind_string(statement, 2, keyId, SQLITE_TRANSIENT);
Yingdi Yu99b2a002015-08-12 12:47:44 -0700390 sqlite3_bind_int(statement, 3, static_cast<int>(publicKeyDer.getKeyType()));
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700391 sqlite3_bind_blob(statement, 4,
392 publicKeyDer.get().buf(),
393 publicKeyDer.get().size(),
394 SQLITE_STATIC);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700395
Alexander Afanasyev736708b2014-01-06 14:45:34 -0800396 sqlite3_step(statement);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700397
398 sqlite3_finalize(statement);
399}
400
Alexander Afanasyev4c9a3d52017-01-03 17:45:19 -0800401shared_ptr<PublicKey>
Yingdi Yu87581582014-01-14 14:28:39 -0800402SecPublicInfoSqlite3::getPublicKey(const Name& keyName)
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700403{
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700404 if (keyName.empty())
Spyridon Mastorakis0d2ed2e2015-07-27 19:09:12 -0700405 BOOST_THROW_EXCEPTION(Error("SecPublicInfoSqlite3::getPublicKey Empty keyName"));
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700406
Alexander Afanasyev9c578182014-05-14 17:28:28 -0700407 string keyId = keyName.get(-1).toUri();
Yingdi Yu87581582014-01-14 14:28:39 -0800408 Name identityName = keyName.getPrefix(-1);
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700409
Yingdi Yua90ba482014-12-09 10:54:43 -0800410 sqlite3_stmt* statement = nullptr;
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700411 sqlite3_prepare_v2(m_database,
412 "SELECT public_key FROM Key WHERE identity_name=? AND key_identifier=?",
413 -1, &statement, 0);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700414
Yingdi Yu41546342014-11-30 23:37:53 -0800415 sqlite3_bind_string(statement, 1, identityName.toUri(), SQLITE_TRANSIENT);
416 sqlite3_bind_string(statement, 2, keyId, SQLITE_TRANSIENT);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700417
418 int res = sqlite3_step(statement);
419
Alexander Afanasyev4c9a3d52017-01-03 17:45:19 -0800420 shared_ptr<PublicKey> result;
Yingdi Yua90ba482014-12-09 10:54:43 -0800421 if (res == SQLITE_ROW) {
Alexander Afanasyev4c9a3d52017-01-03 17:45:19 -0800422 result = make_shared<PublicKey>(static_cast<const uint8_t*>(sqlite3_column_blob(statement, 0)),
Alexander Afanasyev2fa59392016-07-29 17:24:23 -0700423 sqlite3_column_bytes(statement, 0));
Yingdi Yua90ba482014-12-09 10:54:43 -0800424 sqlite3_finalize(statement);
425 return result;
426 }
427 else {
428 sqlite3_finalize(statement);
Spyridon Mastorakis0d2ed2e2015-07-27 19:09:12 -0700429 BOOST_THROW_EXCEPTION(Error("SecPublicInfoSqlite3::getPublicKey public key does not exist"));
Yingdi Yua90ba482014-12-09 10:54:43 -0800430 }
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700431}
432
Yingdi Yu40b53092014-06-17 17:10:02 -0700433KeyType
434SecPublicInfoSqlite3::getPublicKeyType(const Name& keyName)
435{
436 if (keyName.empty())
Yingdi Yu99b2a002015-08-12 12:47:44 -0700437 return KeyType::NONE;
Yingdi Yu40b53092014-06-17 17:10:02 -0700438
439 string keyId = keyName.get(-1).toUri();
440 Name identityName = keyName.getPrefix(-1);
441
Yingdi Yua90ba482014-12-09 10:54:43 -0800442 sqlite3_stmt* statement = nullptr;
Yingdi Yu40b53092014-06-17 17:10:02 -0700443 sqlite3_prepare_v2(m_database,
444 "SELECT key_type FROM Key WHERE identity_name=? AND key_identifier=?",
445 -1, &statement, 0);
446
Yingdi Yu41546342014-11-30 23:37:53 -0800447 sqlite3_bind_string(statement, 1, identityName.toUri(), SQLITE_TRANSIENT);
448 sqlite3_bind_string(statement, 2, keyId, SQLITE_TRANSIENT);
Yingdi Yu40b53092014-06-17 17:10:02 -0700449
450 int res = sqlite3_step(statement);
451
Yingdi Yua90ba482014-12-09 10:54:43 -0800452 if (res == SQLITE_ROW) {
453 int typeValue = sqlite3_column_int(statement, 0);
454 sqlite3_finalize(statement);
455 return static_cast<KeyType>(typeValue);
456 }
457 else {
458 sqlite3_finalize(statement);
Yingdi Yu99b2a002015-08-12 12:47:44 -0700459 return KeyType::NONE;
Yingdi Yua90ba482014-12-09 10:54:43 -0800460 }
Yingdi Yu40b53092014-06-17 17:10:02 -0700461}
462
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700463bool
Yingdi Yu87581582014-01-14 14:28:39 -0800464SecPublicInfoSqlite3::doesCertificateExist(const Name& certificateName)
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700465{
Yingdi Yua90ba482014-12-09 10:54:43 -0800466 sqlite3_stmt* statement = nullptr;
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700467 sqlite3_prepare_v2(m_database,
468 "SELECT count(*) FROM Certificate WHERE cert_name=?",
469 -1, &statement, 0);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700470
Yingdi Yu41546342014-11-30 23:37:53 -0800471 sqlite3_bind_string(statement, 1, certificateName.toUri(), SQLITE_TRANSIENT);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700472
473 int res = sqlite3_step(statement);
474
475 bool certExist = false;
476 if (res == SQLITE_ROW) {
477 int countAll = sqlite3_column_int(statement, 0);
478 if (countAll > 0)
479 certExist = true;
480 }
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700481
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700482 sqlite3_finalize(statement);
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700483
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700484 return certExist;
485}
486
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700487void
Alexander Afanasyev4c9a3d52017-01-03 17:45:19 -0800488SecPublicInfoSqlite3::addCertificate(const IdentityCertificate& certificate)
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700489{
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700490 const Name& certificateName = certificate.getName();
Alexander Afanasyev4c9a3d52017-01-03 17:45:19 -0800491 // KeyName is from IdentityCertificate name, so should be qualified.
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700492 Name keyName =
Alexander Afanasyev4c9a3d52017-01-03 17:45:19 -0800493 IdentityCertificate::certificateNameToPublicKeyName(certificate.getName());
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700494
Yingdi Yu40b53092014-06-17 17:10:02 -0700495 addKey(keyName, certificate.getPublicKeyInfo());
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700496
Yingdi Yu05842f22014-04-15 19:21:56 -0700497 if (doesCertificateExist(certificateName))
498 return;
499
Alexander Afanasyev9c578182014-05-14 17:28:28 -0700500 string keyId = keyName.get(-1).toUri();
Yingdi Yu87581582014-01-14 14:28:39 -0800501 Name identity = keyName.getPrefix(-1);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700502
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700503 // Insert the certificate
Yingdi Yua90ba482014-12-09 10:54:43 -0800504 sqlite3_stmt* statement = nullptr;
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700505 sqlite3_prepare_v2(m_database,
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700506 "INSERT OR REPLACE INTO Certificate \
507 (cert_name, cert_issuer, identity_name, key_identifier, \
508 not_before, not_after, certificate_data) \
509 values (?, ?, ?, ?, datetime(?, 'unixepoch'), datetime(?, 'unixepoch'), ?)",
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700510 -1, &statement, 0);
511
Yingdi Yu41546342014-11-30 23:37:53 -0800512 sqlite3_bind_string(statement, 1, certificateName.toUri(), SQLITE_TRANSIENT);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700513
Yingdi Yua90ba482014-12-09 10:54:43 -0800514 try {
515 // this will throw an exception if the signature is not the standard one
516 // or there is no key locator present
517 std::string signerName = certificate.getSignature().getKeyLocator().getName().toUri();
518 sqlite3_bind_string(statement, 2, signerName, SQLITE_TRANSIENT);
519 }
520 catch (tlv::Error&) {
521 return;
522 }
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700523
Yingdi Yu41546342014-11-30 23:37:53 -0800524 sqlite3_bind_string(statement, 3, identity.toUri(), SQLITE_TRANSIENT);
525 sqlite3_bind_string(statement, 4, keyId, SQLITE_STATIC);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700526
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700527 sqlite3_bind_int64(statement, 5,
Yingdi Yua90ba482014-12-09 10:54:43 -0800528 static_cast<sqlite3_int64>(time::toUnixTimestamp(certificate.getNotBefore()).count()));
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700529 sqlite3_bind_int64(statement, 6,
Yingdi Yua90ba482014-12-09 10:54:43 -0800530 static_cast<sqlite3_int64>(time::toUnixTimestamp(certificate.getNotAfter()).count()));
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700531
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700532 sqlite3_bind_blob(statement, 7,
533 certificate.wireEncode().wire(),
534 certificate.wireEncode().size(),
535 SQLITE_TRANSIENT);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700536
Alexander Afanasyev736708b2014-01-06 14:45:34 -0800537 sqlite3_step(statement);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700538
539 sqlite3_finalize(statement);
540}
541
Alexander Afanasyev4c9a3d52017-01-03 17:45:19 -0800542shared_ptr<IdentityCertificate>
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700543SecPublicInfoSqlite3::getCertificate(const Name& certificateName)
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700544{
Yingdi Yua90ba482014-12-09 10:54:43 -0800545 sqlite3_stmt* statement = nullptr;
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700546
547 sqlite3_prepare_v2(m_database,
Yingdi Yu4270f202014-01-28 14:19:16 -0800548 "SELECT certificate_data FROM Certificate WHERE cert_name=?",
549 -1, &statement, 0);
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700550
Yingdi Yu41546342014-11-30 23:37:53 -0800551 sqlite3_bind_string(statement, 1, certificateName.toUri(), SQLITE_TRANSIENT);
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700552
Yingdi Yu4270f202014-01-28 14:19:16 -0800553 int res = sqlite3_step(statement);
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700554
Yingdi Yua90ba482014-12-09 10:54:43 -0800555 if (res == SQLITE_ROW) {
Alexander Afanasyev4c9a3d52017-01-03 17:45:19 -0800556 shared_ptr<IdentityCertificate> certificate = make_shared<IdentityCertificate>();
Yingdi Yua90ba482014-12-09 10:54:43 -0800557 try {
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700558 certificate->wireDecode(Block(static_cast<const uint8_t*>(sqlite3_column_blob(statement, 0)),
Alexander Afanasyevaa0e7da2014-03-17 14:37:33 -0700559 sqlite3_column_bytes(statement, 0)));
Yingdi Yu4270f202014-01-28 14:19:16 -0800560 }
Yingdi Yua90ba482014-12-09 10:54:43 -0800561 catch (tlv::Error&) {
Yingdi Yu2e57a582014-02-20 23:34:43 -0800562 sqlite3_finalize(statement);
Spyridon Mastorakis0d2ed2e2015-07-27 19:09:12 -0700563 BOOST_THROW_EXCEPTION(Error("SecPublicInfoSqlite3::getCertificate certificate cannot be "
564 "decoded"));
Yingdi Yu2e57a582014-02-20 23:34:43 -0800565 }
Yingdi Yua90ba482014-12-09 10:54:43 -0800566
567 sqlite3_finalize(statement);
568 return certificate;
569 }
570 else {
571 sqlite3_finalize(statement);
Spyridon Mastorakis0d2ed2e2015-07-27 19:09:12 -0700572 BOOST_THROW_EXCEPTION(Error("SecPublicInfoSqlite3::getCertificate certificate does not "
573 "exist"));
Yingdi Yua90ba482014-12-09 10:54:43 -0800574 }
Jeff Thompson1975def2013-10-09 17:06:43 -0700575}
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700576
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700577
578Name
Yingdi Yu87581582014-01-14 14:28:39 -0800579SecPublicInfoSqlite3::getDefaultIdentity()
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700580{
Yingdi Yua90ba482014-12-09 10:54:43 -0800581 sqlite3_stmt* statement = nullptr;
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700582 sqlite3_prepare_v2(m_database,
583 "SELECT identity_name FROM Identity WHERE default_identity=1",
584 -1, &statement, 0);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700585
586 int res = sqlite3_step(statement);
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700587
Yingdi Yua90ba482014-12-09 10:54:43 -0800588 if (res == SQLITE_ROW) {
589 Name identity(sqlite3_column_string(statement, 0));
590 sqlite3_finalize(statement);
591 return identity;
592 }
593 else {
594 sqlite3_finalize(statement);
Spyridon Mastorakis0d2ed2e2015-07-27 19:09:12 -0700595 BOOST_THROW_EXCEPTION(Error("SecPublicInfoSqlite3::getDefaultIdentity no default identity"));
Yingdi Yua90ba482014-12-09 10:54:43 -0800596 }
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700597}
598
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700599void
Yingdi Yu87581582014-01-14 14:28:39 -0800600SecPublicInfoSqlite3::setDefaultIdentityInternal(const Name& identityName)
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700601{
Yingdi Yu2e57a582014-02-20 23:34:43 -0800602 addIdentity(identityName);
603
Yingdi Yua90ba482014-12-09 10:54:43 -0800604 sqlite3_stmt* statement = nullptr;
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700605
606 //Reset previous default identity
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700607 sqlite3_prepare_v2(m_database,
608 "UPDATE Identity SET default_identity=0 WHERE default_identity=1",
609 -1, &statement, 0);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700610
611 while (sqlite3_step(statement) == SQLITE_ROW)
Yingdi Yua90ba482014-12-09 10:54:43 -0800612 ;
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700613
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700614 sqlite3_finalize(statement);
615
616 //Set current default identity
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700617 sqlite3_prepare_v2(m_database,
618 "UPDATE Identity SET default_identity=1 WHERE identity_name=?",
619 -1, &statement, 0);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700620
Yingdi Yu41546342014-11-30 23:37:53 -0800621 sqlite3_bind_string(statement, 1, identityName.toUri(), SQLITE_TRANSIENT);
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700622
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700623 sqlite3_step(statement);
624
625 sqlite3_finalize(statement);
626}
627
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700628Name
Yingdi Yu87581582014-01-14 14:28:39 -0800629SecPublicInfoSqlite3::getDefaultKeyNameForIdentity(const Name& identityName)
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700630{
Yingdi Yua90ba482014-12-09 10:54:43 -0800631 sqlite3_stmt* statement = nullptr;
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700632 sqlite3_prepare_v2(m_database,
633 "SELECT key_identifier FROM Key WHERE identity_name=? AND default_key=1",
634 -1, &statement, 0);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700635
Yingdi Yu41546342014-11-30 23:37:53 -0800636 sqlite3_bind_string(statement, 1, identityName.toUri(), SQLITE_TRANSIENT);
Yingdi Yu87581582014-01-14 14:28:39 -0800637
638 int res = sqlite3_step(statement);
Yingdi Yu87581582014-01-14 14:28:39 -0800639
Yingdi Yua90ba482014-12-09 10:54:43 -0800640 if (res == SQLITE_ROW) {
641 Name keyName = identityName;
642 keyName.append(string(reinterpret_cast<const char*>(sqlite3_column_text(statement, 0)),
643 sqlite3_column_bytes(statement, 0)));
644 sqlite3_finalize(statement);
645 return keyName;
646 }
647 else {
648 sqlite3_finalize(statement);
Spyridon Mastorakis0d2ed2e2015-07-27 19:09:12 -0700649 BOOST_THROW_EXCEPTION(Error("SecPublicInfoSqlite3::getDefaultKeyNameForIdentity key not "
650 "found"));
Yingdi Yua90ba482014-12-09 10:54:43 -0800651 }
Yingdi Yu87581582014-01-14 14:28:39 -0800652}
653
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700654void
Yingdi Yu87581582014-01-14 14:28:39 -0800655SecPublicInfoSqlite3::setDefaultKeyNameForIdentityInternal(const Name& keyName)
656{
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700657 if (!doesPublicKeyExist(keyName))
Spyridon Mastorakis0d2ed2e2015-07-27 19:09:12 -0700658 BOOST_THROW_EXCEPTION(Error("Key does not exist:" + keyName.toUri()));
Yingdi Yu88663af2014-01-15 15:21:38 -0800659
Alexander Afanasyev9c578182014-05-14 17:28:28 -0700660 string keyId = keyName.get(-1).toUri();
Yingdi Yu87581582014-01-14 14:28:39 -0800661 Name identityName = keyName.getPrefix(-1);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700662
Yingdi Yua90ba482014-12-09 10:54:43 -0800663 sqlite3_stmt* statement = nullptr;
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700664
665 //Reset previous default Key
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700666 sqlite3_prepare_v2(m_database,
667 "UPDATE Key SET default_key=0 WHERE default_key=1 and identity_name=?",
668 -1, &statement, 0);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700669
Yingdi Yu41546342014-11-30 23:37:53 -0800670 sqlite3_bind_string(statement, 1, identityName.toUri(), SQLITE_TRANSIENT);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700671
672 while (sqlite3_step(statement) == SQLITE_ROW)
Yingdi Yu5ec0ee32014-06-24 16:26:09 -0700673 ;
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700674
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700675 sqlite3_finalize(statement);
676
677 //Set current default Key
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700678 sqlite3_prepare_v2(m_database,
679 "UPDATE Key SET default_key=1 WHERE identity_name=? AND key_identifier=?",
680 -1, &statement, 0);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700681
Yingdi Yu41546342014-11-30 23:37:53 -0800682 sqlite3_bind_string(statement, 1, identityName.toUri(), SQLITE_TRANSIENT);
683 sqlite3_bind_string(statement, 2, keyId, SQLITE_TRANSIENT);
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700684
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700685 sqlite3_step(statement);
686
687 sqlite3_finalize(statement);
688}
689
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700690Name
Yingdi Yu87581582014-01-14 14:28:39 -0800691SecPublicInfoSqlite3::getDefaultCertificateNameForKey(const Name& keyName)
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700692{
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700693 if (keyName.empty())
Spyridon Mastorakis0d2ed2e2015-07-27 19:09:12 -0700694 BOOST_THROW_EXCEPTION(Error("SecPublicInfoSqlite3::getDefaultCertificateNameForKey wrong key"));
Yingdi Yu88663af2014-01-15 15:21:38 -0800695
Alexander Afanasyev9c578182014-05-14 17:28:28 -0700696 string keyId = keyName.get(-1).toUri();
Yingdi Yu87581582014-01-14 14:28:39 -0800697 Name identityName = keyName.getPrefix(-1);
698
Yingdi Yua90ba482014-12-09 10:54:43 -0800699 sqlite3_stmt* statement = nullptr;
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700700 sqlite3_prepare_v2(m_database,
701 "SELECT cert_name FROM Certificate \
702 WHERE identity_name=? AND key_identifier=? AND default_cert=1",
703 -1, &statement, 0);
Yingdi Yu87581582014-01-14 14:28:39 -0800704
Yingdi Yu41546342014-11-30 23:37:53 -0800705 sqlite3_bind_string(statement, 1, identityName.toUri(), SQLITE_TRANSIENT);
706 sqlite3_bind_string(statement, 2, keyId, SQLITE_TRANSIENT);
Yingdi Yu87581582014-01-14 14:28:39 -0800707
708 int res = sqlite3_step(statement);
709
Yingdi Yua90ba482014-12-09 10:54:43 -0800710 if (res == SQLITE_ROW) {
711 Name certName(string(reinterpret_cast<const char*>(sqlite3_column_text(statement, 0)),
712 sqlite3_column_bytes(statement, 0)));
713 sqlite3_finalize(statement);
714 return certName;
715 }
716 else {
717 sqlite3_finalize(statement);
Spyridon Mastorakis0d2ed2e2015-07-27 19:09:12 -0700718 BOOST_THROW_EXCEPTION(Error("certificate not found"));
Yingdi Yua90ba482014-12-09 10:54:43 -0800719 }
Yingdi Yu87581582014-01-14 14:28:39 -0800720}
721
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700722void
Yingdi Yu87581582014-01-14 14:28:39 -0800723SecPublicInfoSqlite3::setDefaultCertificateNameForKeyInternal(const Name& certificateName)
724{
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700725 if (!doesCertificateExist(certificateName))
Spyridon Mastorakis0d2ed2e2015-07-27 19:09:12 -0700726 BOOST_THROW_EXCEPTION(Error("certificate does not exist:" + certificateName.toUri()));
Yingdi Yu88663af2014-01-15 15:21:38 -0800727
Alexander Afanasyev4c9a3d52017-01-03 17:45:19 -0800728 Name keyName = IdentityCertificate::certificateNameToPublicKeyName(certificateName);
Alexander Afanasyev9c578182014-05-14 17:28:28 -0700729 string keyId = keyName.get(-1).toUri();
Yingdi Yu87581582014-01-14 14:28:39 -0800730 Name identityName = keyName.getPrefix(-1);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700731
Yingdi Yua90ba482014-12-09 10:54:43 -0800732 sqlite3_stmt* statement = nullptr;
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700733
734 //Reset previous default Key
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700735 sqlite3_prepare_v2(m_database,
736 "UPDATE Certificate SET default_cert=0 \
737 WHERE default_cert=1 AND identity_name=? AND key_identifier=?",
738 -1, &statement, 0);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700739
Yingdi Yu41546342014-11-30 23:37:53 -0800740 sqlite3_bind_string(statement, 1, identityName.toUri(), SQLITE_TRANSIENT);
741 sqlite3_bind_string(statement, 2, keyId, SQLITE_TRANSIENT);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700742
743 while (sqlite3_step(statement) == SQLITE_ROW)
Yingdi Yu5ec0ee32014-06-24 16:26:09 -0700744 ;
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700745
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700746 sqlite3_finalize(statement);
747
748 //Set current default Key
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700749 sqlite3_prepare_v2(m_database,
750 "UPDATE Certificate SET default_cert=1 \
751 WHERE identity_name=? AND key_identifier=? AND cert_name=?",
752 -1, &statement, 0);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700753
Yingdi Yu41546342014-11-30 23:37:53 -0800754 sqlite3_bind_string(statement, 1, identityName.toUri(), SQLITE_TRANSIENT);
755 sqlite3_bind_string(statement, 2, keyId, SQLITE_TRANSIENT);
756 sqlite3_bind_string(statement, 3, certificateName.toUri(), SQLITE_TRANSIENT);
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700757
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700758 sqlite3_step(statement);
759
760 sqlite3_finalize(statement);
761}
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800762
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800763void
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700764SecPublicInfoSqlite3::getAllIdentities(vector<Name>& nameList, bool isDefault)
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800765{
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700766 sqlite3_stmt* stmt;
767 if (isDefault)
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700768 sqlite3_prepare_v2(m_database,
769 "SELECT identity_name FROM Identity WHERE default_identity=1",
770 -1, &stmt, 0);
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800771 else
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700772 sqlite3_prepare_v2(m_database,
773 "SELECT identity_name FROM Identity WHERE default_identity=0",
774 -1, &stmt, 0);
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800775
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700776 while (sqlite3_step(stmt) == SQLITE_ROW)
Yingdi Yua90ba482014-12-09 10:54:43 -0800777 nameList.push_back(Name(string(reinterpret_cast<const char*>(sqlite3_column_text(stmt, 0)),
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700778 sqlite3_column_bytes(stmt, 0))));
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700779
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700780 sqlite3_finalize(stmt);
Jeff Thompson7ca11f22013-10-04 19:01:30 -0700781}
782
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800783void
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700784SecPublicInfoSqlite3::getAllKeyNames(vector<Name>& nameList, bool isDefault)
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800785{
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700786 sqlite3_stmt* stmt;
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800787
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700788 if (isDefault)
789 sqlite3_prepare_v2(m_database,
790 "SELECT identity_name, key_identifier FROM Key WHERE default_key=1",
791 -1, &stmt, 0);
792 else
793 sqlite3_prepare_v2(m_database,
794 "SELECT identity_name, key_identifier FROM Key WHERE default_key=0",
795 -1, &stmt, 0);
796
Yingdi Yua90ba482014-12-09 10:54:43 -0800797 while (sqlite3_step(stmt) == SQLITE_ROW) {
798 Name keyName(string(reinterpret_cast<const char*>(sqlite3_column_text(stmt, 0)),
799 sqlite3_column_bytes(stmt, 0)));
800 keyName.append(string(reinterpret_cast<const char*>(sqlite3_column_text(stmt, 1)),
801 sqlite3_column_bytes(stmt, 1)));
802 nameList.push_back(keyName);
803 }
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700804 sqlite3_finalize(stmt);
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800805}
806
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800807void
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700808SecPublicInfoSqlite3::getAllKeyNamesOfIdentity(const Name& identity,
809 vector<Name>& nameList,
810 bool isDefault)
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800811{
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700812 sqlite3_stmt* stmt;
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700813
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700814 if (isDefault)
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700815 sqlite3_prepare_v2(m_database,
816 "SELECT key_identifier FROM Key WHERE default_key=1 and identity_name=?",
817 -1, &stmt, 0);
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800818 else
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700819 sqlite3_prepare_v2(m_database,
820 "SELECT key_identifier FROM Key WHERE default_key=0 and identity_name=?",
821 -1, &stmt, 0);
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700822
Yingdi Yu41546342014-11-30 23:37:53 -0800823 sqlite3_bind_string(stmt, 1, identity.toUri(), SQLITE_TRANSIENT);
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800824
Yingdi Yua90ba482014-12-09 10:54:43 -0800825 while (sqlite3_step(stmt) == SQLITE_ROW) {
826 Name keyName(identity);
827 keyName.append(string(reinterpret_cast<const char*>(sqlite3_column_text(stmt, 0)),
828 sqlite3_column_bytes(stmt, 0)));
829 nameList.push_back(keyName);
830 }
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700831 sqlite3_finalize(stmt);
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800832}
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700833
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800834void
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700835SecPublicInfoSqlite3::getAllCertificateNames(vector<Name>& nameList, bool isDefault)
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800836{
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700837 sqlite3_stmt* stmt;
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700838
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700839 if (isDefault)
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700840 sqlite3_prepare_v2(m_database,
841 "SELECT cert_name FROM Certificate WHERE default_cert=1",
842 -1, &stmt, 0);
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800843 else
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700844 sqlite3_prepare_v2(m_database,
845 "SELECT cert_name FROM Certificate WHERE default_cert=0",
846 -1, &stmt, 0);
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800847
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700848 while (sqlite3_step(stmt) == SQLITE_ROW)
Yingdi Yua90ba482014-12-09 10:54:43 -0800849 nameList.push_back(string(reinterpret_cast<const char*>(sqlite3_column_text(stmt, 0)),
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700850 sqlite3_column_bytes(stmt, 0)));
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800851
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700852 sqlite3_finalize(stmt);
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800853}
854
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800855void
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700856SecPublicInfoSqlite3::getAllCertificateNamesOfKey(const Name& keyName,
857 vector<Name>& nameList,
858 bool isDefault)
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800859{
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700860 if (keyName.empty())
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800861 return;
Yingdi Yu88663af2014-01-15 15:21:38 -0800862
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700863 sqlite3_stmt* stmt;
864 if (isDefault)
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700865 sqlite3_prepare_v2(m_database,
866 "SELECT cert_name FROM Certificate \
867 WHERE default_cert=1 and identity_name=? and key_identifier=?",
868 -1, &stmt, 0);
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800869 else
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700870 sqlite3_prepare_v2(m_database,
871 "SELECT cert_name FROM Certificate \
872 WHERE default_cert=0 and identity_name=? and key_identifier=?",
873 -1, &stmt, 0);
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800874
Yingdi Yu87581582014-01-14 14:28:39 -0800875 Name identity = keyName.getPrefix(-1);
Yingdi Yu41546342014-11-30 23:37:53 -0800876 sqlite3_bind_string(stmt, 1, identity.toUri(), SQLITE_TRANSIENT);
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700877
Alexander Afanasyev9c578182014-05-14 17:28:28 -0700878 std::string baseKeyName = keyName.get(-1).toUri();
Yingdi Yu41546342014-11-30 23:37:53 -0800879 sqlite3_bind_string(stmt, 2, baseKeyName, SQLITE_TRANSIENT);
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800880
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700881 while (sqlite3_step(stmt) == SQLITE_ROW)
Yingdi Yua90ba482014-12-09 10:54:43 -0800882 nameList.push_back(string(reinterpret_cast<const char*>(sqlite3_column_text(stmt, 0)),
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700883 sqlite3_column_bytes(stmt, 0)));
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800884
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700885 sqlite3_finalize(stmt);
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800886}
887
888void
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700889SecPublicInfoSqlite3::deleteCertificateInfo(const Name& certName)
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800890{
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700891 if (certName.empty())
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800892 return;
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700893
894 sqlite3_stmt* stmt;
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800895 sqlite3_prepare_v2(m_database, "DELETE FROM Certificate WHERE cert_name=?", -1, &stmt, 0);
Yingdi Yu41546342014-11-30 23:37:53 -0800896 sqlite3_bind_string(stmt, 1, certName.toUri(), SQLITE_TRANSIENT);
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800897 sqlite3_step(stmt);
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700898 sqlite3_finalize(stmt);
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800899}
900
901void
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700902SecPublicInfoSqlite3::deletePublicKeyInfo(const Name& keyName)
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800903{
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700904 if (keyName.empty())
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800905 return;
906
907 string identity = keyName.getPrefix(-1).toUri();
Alexander Afanasyev9c578182014-05-14 17:28:28 -0700908 string keyId = keyName.get(-1).toUri();
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800909
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700910 sqlite3_stmt* stmt;
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700911 sqlite3_prepare_v2(m_database,
912 "DELETE FROM Certificate WHERE identity_name=? and key_identifier=?",
913 -1, &stmt, 0);
Yingdi Yu41546342014-11-30 23:37:53 -0800914 sqlite3_bind_string(stmt, 1, identity, SQLITE_TRANSIENT);
915 sqlite3_bind_string(stmt, 2, keyId, SQLITE_TRANSIENT);
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800916 sqlite3_step(stmt);
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700917 sqlite3_finalize(stmt);
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800918
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700919 sqlite3_prepare_v2(m_database,
920 "DELETE FROM Key WHERE identity_name=? and key_identifier=?",
921 -1, &stmt, 0);
Yingdi Yu41546342014-11-30 23:37:53 -0800922 sqlite3_bind_string(stmt, 1, identity, SQLITE_TRANSIENT);
923 sqlite3_bind_string(stmt, 2, keyId, SQLITE_TRANSIENT);
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800924 sqlite3_step(stmt);
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700925 sqlite3_finalize(stmt);
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800926}
927
928void
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700929SecPublicInfoSqlite3::deleteIdentityInfo(const Name& identityName)
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800930{
931 string identity = identityName.toUri();
932
Alexander Afanasyevfdbfc6d2014-04-14 15:12:11 -0700933 sqlite3_stmt* stmt;
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800934 sqlite3_prepare_v2(m_database, "DELETE FROM Certificate WHERE identity_name=?", -1, &stmt, 0);
Yingdi Yu41546342014-11-30 23:37:53 -0800935 sqlite3_bind_string(stmt, 1, identity, SQLITE_TRANSIENT);
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800936 sqlite3_step(stmt);
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700937 sqlite3_finalize(stmt);
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800938
939 sqlite3_prepare_v2(m_database, "DELETE FROM Key WHERE identity_name=?", -1, &stmt, 0);
Yingdi Yu41546342014-11-30 23:37:53 -0800940 sqlite3_bind_string(stmt, 1, identity, SQLITE_TRANSIENT);
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800941 sqlite3_step(stmt);
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700942 sqlite3_finalize(stmt);
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800943
944 sqlite3_prepare_v2(m_database, "DELETE FROM Identity WHERE identity_name=?", -1, &stmt, 0);
Yingdi Yu41546342014-11-30 23:37:53 -0800945 sqlite3_bind_string(stmt, 1, identity, SQLITE_TRANSIENT);
Yingdi Yu28fd32f2014-01-28 19:03:03 -0800946 sqlite3_step(stmt);
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700947 sqlite3_finalize(stmt);
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800948}
949
Yingdi Yu41546342014-11-30 23:37:53 -0800950std::string
951SecPublicInfoSqlite3::getScheme()
952{
953 return SCHEME;
954}
955
Alexander Afanasyev4c9a3d52017-01-03 17:45:19 -0800956} // namespace v1
Alexander Afanasyev2fa59392016-07-29 17:24:23 -0700957} // namespace security
Alexander Afanasyev0c632112013-12-30 15:59:31 -0800958} // namespace ndn