Aktualizr
C++ SOTA Client
All Classes Namespaces Files Functions Variables Enumerations Enumerator Pages
storage_common_test.cc
1 #include <gtest/gtest.h>
2 
3 #include <memory>
4 #include <string>
5 
6 #include <boost/filesystem.hpp>
7 
8 #include "libaktualizr/types.h"
9 #include "logging/logging.h"
10 #include "storage/sqlstorage.h"
11 #include "utilities/utils.h"
12 
13 StorageType current_storage_type{StorageType::kSqlite};
14 
15 std::unique_ptr<INvStorage> Storage(const boost::filesystem::path &dir) {
16  StorageConfig storage_config;
17  storage_config.type = current_storage_type;
18  storage_config.path = dir;
19 
20  if (storage_config.type == StorageType::kSqlite) {
21  return std::unique_ptr<INvStorage>(new SQLStorage(storage_config, false));
22  } else {
23  throw std::runtime_error("Invalid config type");
24  }
25 }
26 
27 StorageConfig MakeConfig(StorageType type, const boost::filesystem::path &storage_dir) {
28  StorageConfig config;
29 
30  config.type = type;
31  if (config.type == StorageType::kSqlite) {
32  config.sqldb_path = storage_dir / "test.db";
33  } else {
34  throw std::runtime_error("Invalid config type");
35  }
36  return config;
37 }
38 
39 /* Load and store Primary keys. */
40 TEST(storage, load_store_primary_keys) {
41  TemporaryDirectory temp_dir;
42  std::unique_ptr<INvStorage> storage = Storage(temp_dir.Path());
43 
44  storage->storePrimaryKeys("", "");
45  storage->storePrimaryKeys("pr_public", "pr_private");
46 
47  std::string pubkey;
48  std::string privkey;
49 
50  EXPECT_TRUE(storage->loadPrimaryKeys(&pubkey, &privkey));
51  EXPECT_EQ(pubkey, "pr_public");
52  EXPECT_EQ(privkey, "pr_private");
53  storage->clearPrimaryKeys();
54  EXPECT_FALSE(storage->loadPrimaryKeys(nullptr, nullptr));
55 }
56 
57 /* Load and store TLS credentials. */
58 TEST(storage, load_store_tls) {
59  TemporaryDirectory temp_dir;
60  std::unique_ptr<INvStorage> storage = Storage(temp_dir.Path());
61 
62  storage->storeTlsCreds("", "", "");
63  storage->storeTlsCreds("ca", "cert", "priv");
64  std::string ca;
65  std::string cert;
66  std::string priv;
67 
68  EXPECT_TRUE(storage->loadTlsCreds(&ca, &cert, &priv));
69 
70  EXPECT_EQ(ca, "ca");
71  EXPECT_EQ(cert, "cert");
72  EXPECT_EQ(priv, "priv");
73  storage->clearTlsCreds();
74  EXPECT_FALSE(storage->loadTlsCreds(nullptr, nullptr, nullptr));
75 }
76 
77 /* Load and store Uptane metadata. */
78 TEST(storage, load_store_metadata) {
79  TemporaryDirectory temp_dir;
80  std::unique_ptr<INvStorage> storage = Storage(temp_dir.Path());
81 
82  Json::Value root_json;
83  root_json["_type"] = "Root";
84  root_json["consistent_snapshot"] = false;
85  root_json["expires"] = "2038-01-19T03:14:06Z";
86  root_json["keys"]["firstid"]["keytype"] = "ed25519";
87  root_json["keys"]["firstid"]["keyval"]["public"] = "firstval";
88  root_json["keys"]["secondid"]["keytype"] = "ed25519";
89  root_json["keys"]["secondid"]["keyval"]["public"] = "secondval";
90 
91  root_json["roles"]["root"]["threshold"] = 1;
92  root_json["roles"]["root"]["keyids"][0] = "firstid";
93  root_json["roles"]["snapshot"]["threshold"] = 1;
94  root_json["roles"]["snapshot"]["keyids"][0] = "firstid";
95  root_json["roles"]["targets"]["threshold"] = 1;
96  root_json["roles"]["targets"]["keyids"][0] = "firstid";
97  root_json["roles"]["timestamp"]["threshold"] = 1;
98  root_json["roles"]["timestamp"]["keyids"][0] = "firstid";
99 
100  Json::Value meta_root;
101  meta_root["signed"] = root_json;
102  std::string director_root = Utils::jsonToStr(meta_root);
103  std::string image_root = Utils::jsonToStr(meta_root);
104 
105  Json::Value targets_json;
106  targets_json["_type"] = "Targets";
107  targets_json["expires"] = "2038-01-19T03:14:06Z";
108  targets_json["targets"]["file1"]["custom"]["ecu_identifier"] = "ecu1";
109  targets_json["targets"]["file1"]["custom"]["hardware_identifier"] = "hw1";
110  targets_json["targets"]["file1"]["hashes"]["sha256"] = "12ab";
111  targets_json["targets"]["file1"]["length"] = 1;
112  targets_json["targets"]["file2"]["custom"]["ecu_identifier"] = "ecu2";
113  targets_json["targets"]["file2"]["custom"]["hardware_identifier"] = "hw2";
114  targets_json["targets"]["file2"]["hashes"]["sha512"] = "12ab";
115  targets_json["targets"]["file2"]["length"] = 11;
116 
117  Json::Value meta_targets;
118  meta_targets["signed"] = targets_json;
119  std::string director_targets = Utils::jsonToStr(meta_targets);
120  std::string image_targets = Utils::jsonToStr(meta_targets);
121 
122  Json::Value timestamp_json;
123  timestamp_json["signed"]["_type"] = "Timestamp";
124  timestamp_json["signed"]["expires"] = "2038-01-19T03:14:06Z";
125  std::string image_timestamp = Utils::jsonToStr(timestamp_json);
126 
127  Json::Value snapshot_json;
128  snapshot_json["_type"] = "Snapshot";
129  snapshot_json["expires"] = "2038-01-19T03:14:06Z";
130  snapshot_json["meta"]["root.json"]["version"] = 1;
131  snapshot_json["meta"]["targets.json"]["version"] = 2;
132  snapshot_json["meta"]["timestamp.json"]["version"] = 3;
133  snapshot_json["meta"]["snapshot.json"]["version"] = 4;
134 
135  Json::Value meta_snapshot;
136  meta_snapshot["signed"] = snapshot_json;
137  std::string image_snapshot = Utils::jsonToStr(meta_snapshot);
138 
139  storage->storeRoot(director_root, Uptane::RepositoryType::Director(), Uptane::Version(1));
140  storage->storeNonRoot(director_targets, Uptane::RepositoryType::Director(), Uptane::Role::Targets());
141  storage->storeRoot(image_root, Uptane::RepositoryType::Image(), Uptane::Version(1));
142  storage->storeNonRoot(image_targets, Uptane::RepositoryType::Image(), Uptane::Role::Targets());
143  storage->storeNonRoot(image_timestamp, Uptane::RepositoryType::Image(), Uptane::Role::Timestamp());
144  storage->storeNonRoot(image_snapshot, Uptane::RepositoryType::Image(), Uptane::Role::Snapshot());
145 
146  std::string loaded_director_root;
147  std::string loaded_director_targets;
148  std::string loaded_image_root;
149  std::string loaded_image_targets;
150  std::string loaded_image_timestamp;
151  std::string loaded_image_snapshot;
152 
153  EXPECT_TRUE(storage->loadLatestRoot(&loaded_director_root, Uptane::RepositoryType::Director()));
154  EXPECT_TRUE(
155  storage->loadNonRoot(&loaded_director_targets, Uptane::RepositoryType::Director(), Uptane::Role::Targets()));
156  EXPECT_TRUE(storage->loadLatestRoot(&loaded_image_root, Uptane::RepositoryType::Image()));
157  EXPECT_TRUE(storage->loadNonRoot(&loaded_image_targets, Uptane::RepositoryType::Image(), Uptane::Role::Targets()));
158  EXPECT_TRUE(
159  storage->loadNonRoot(&loaded_image_timestamp, Uptane::RepositoryType::Image(), Uptane::Role::Timestamp()));
160  EXPECT_TRUE(storage->loadNonRoot(&loaded_image_snapshot, Uptane::RepositoryType::Image(), Uptane::Role::Snapshot()));
161  EXPECT_EQ(director_root, loaded_director_root);
162  EXPECT_EQ(director_targets, loaded_director_targets);
163  EXPECT_EQ(image_root, loaded_image_root);
164  EXPECT_EQ(image_targets, loaded_image_targets);
165  EXPECT_EQ(image_timestamp, loaded_image_timestamp);
166  EXPECT_EQ(image_snapshot, loaded_image_snapshot);
167 
168  storage->clearNonRootMeta(Uptane::RepositoryType::Director());
169  storage->clearNonRootMeta(Uptane::RepositoryType::Image());
170  EXPECT_FALSE(
171  storage->loadNonRoot(&loaded_director_targets, Uptane::RepositoryType::Director(), Uptane::Role::Targets()));
172  EXPECT_FALSE(
173  storage->loadNonRoot(&loaded_image_timestamp, Uptane::RepositoryType::Image(), Uptane::Role::Timestamp()));
174 }
175 
176 /* Load and store Uptane roots. */
177 TEST(storage, load_store_root) {
178  TemporaryDirectory temp_dir;
179  std::unique_ptr<INvStorage> storage = Storage(temp_dir.Path());
180 
181  Json::Value root_json;
182  root_json["_type"] = "Root";
183  root_json["consistent_snapshot"] = false;
184  root_json["expires"] = "2038-01-19T03:14:06Z";
185  root_json["keys"]["firstid"]["keytype"] = "ed25519";
186  root_json["keys"]["firstid"]["keyval"]["public"] = "firstval";
187  root_json["keys"]["secondid"]["keytype"] = "ed25519";
188  root_json["keys"]["secondid"]["keyval"]["public"] = "secondval";
189 
190  root_json["roles"]["root"]["threshold"] = 1;
191  root_json["roles"]["root"]["keyids"][0] = "firstid";
192  root_json["roles"]["snapshot"]["threshold"] = 1;
193  root_json["roles"]["snapshot"]["keyids"][0] = "firstid";
194  root_json["roles"]["targets"]["threshold"] = 1;
195  root_json["roles"]["targets"]["keyids"][0] = "firstid";
196  root_json["roles"]["timestamp"]["threshold"] = 1;
197  root_json["roles"]["timestamp"]["keyids"][0] = "firstid";
198 
199  Json::Value meta_root;
200  meta_root["signed"] = root_json;
201 
202  std::string loaded_root;
203 
204  storage->storeRoot(Utils::jsonToStr(meta_root), Uptane::RepositoryType::Director(), Uptane::Version(2));
205  EXPECT_TRUE(storage->loadRoot(&loaded_root, Uptane::RepositoryType::Director(), Uptane::Version(2)));
206  EXPECT_EQ(Utils::jsonToStr(meta_root), loaded_root);
207 
208  EXPECT_TRUE(storage->loadLatestRoot(&loaded_root, Uptane::RepositoryType::Director()));
209  EXPECT_EQ(Utils::jsonToStr(meta_root), loaded_root);
210 }
211 
212 /* Load and store the device ID. */
213 TEST(storage, load_store_deviceid) {
214  TemporaryDirectory temp_dir;
215  std::unique_ptr<INvStorage> storage = Storage(temp_dir.Path());
216 
217  storage->storeDeviceId("");
218  storage->storeDeviceId("device_id");
219 
220  std::string device_id;
221 
222  EXPECT_TRUE(storage->loadDeviceId(&device_id));
223 
224  EXPECT_EQ(device_id, "device_id");
225  storage->clearDeviceId();
226  EXPECT_FALSE(storage->loadDeviceId(nullptr));
227 }
228 
229 /* Load and store ECU serials.
230  * Preserve ECU ordering between store and load calls.
231  */
232 TEST(storage, load_store_ecu_serials) {
233  TemporaryDirectory temp_dir;
234  std::unique_ptr<INvStorage> storage = Storage(temp_dir.Path());
235 
236  storage->storeEcuSerials({{Uptane::EcuSerial("a"), Uptane::HardwareIdentifier("")}});
237  EcuSerials serials{{Uptane::EcuSerial("primary"), Uptane::HardwareIdentifier("primary_hw")},
238  {Uptane::EcuSerial("secondary_1"), Uptane::HardwareIdentifier("secondary_hw")},
239  {Uptane::EcuSerial("secondary_2"), Uptane::HardwareIdentifier("secondary_hw")}};
240  storage->storeEcuSerials(serials);
241 
242  EcuSerials serials_out;
243 
244  EXPECT_TRUE(storage->loadEcuSerials(&serials_out));
245 
246  EXPECT_EQ(serials, serials_out);
247  storage->clearEcuSerials();
248  EXPECT_FALSE(storage->loadEcuSerials(nullptr));
249 }
250 
251 /* Load and store a list of misconfigured ECUs. */
252 TEST(storage, load_store_misconfigured_ecus) {
253  TemporaryDirectory temp_dir;
254  std::unique_ptr<INvStorage> storage = Storage(temp_dir.Path());
255 
256  storage->saveMisconfiguredEcu(
257  {Uptane::EcuSerial("primary"), Uptane::HardwareIdentifier("primary_hw"), EcuState::kOld});
258 
259  std::vector<MisconfiguredEcu> ecus_out;
260 
261  EXPECT_TRUE(storage->loadMisconfiguredEcus(&ecus_out));
262 
263  EXPECT_EQ(ecus_out.size(), 1);
264  EXPECT_EQ(ecus_out[0].serial, Uptane::EcuSerial("primary"));
265  EXPECT_EQ(ecus_out[0].hardware_id, Uptane::HardwareIdentifier("primary_hw"));
266  EXPECT_EQ(ecus_out[0].state, EcuState::kOld);
267 
268  storage->clearMisconfiguredEcus();
269  ecus_out.clear();
270  EXPECT_FALSE(storage->loadMisconfiguredEcus(&ecus_out));
271 }
272 
273 /* Load and store a flag indicating successful registration. */
274 TEST(storage, load_store_ecu_registered) {
275  TemporaryDirectory temp_dir;
276  std::unique_ptr<INvStorage> storage = Storage(temp_dir.Path());
277 
278  EXPECT_THROW(storage->storeEcuRegistered(), std::runtime_error);
279  storage->storeDeviceId("test");
280  storage->storeEcuRegistered();
281  storage->storeEcuRegistered();
282 
283  EXPECT_TRUE(storage->loadEcuRegistered());
284 
285  storage->clearEcuRegistered();
286  EXPECT_FALSE(storage->loadEcuRegistered());
287 }
288 
289 /* Load and store installed versions. */
290 TEST(storage, load_store_installed_versions) {
291  TemporaryDirectory temp_dir;
292  std::unique_ptr<INvStorage> storage = Storage(temp_dir.Path());
293 
294  // Test lazy Primary installed version: Primary ECU serial is not defined yet
295  const std::vector<Hash> hashes = {
296  Hash{Hash::Type::kSha256, "2561"},
297  Hash{Hash::Type::kSha512, "5121"},
298  };
299  Uptane::EcuMap primary_ecu{{Uptane::EcuSerial("primary"), Uptane::HardwareIdentifier("primary_hw")}};
300  Uptane::Target t1{"update.bin", primary_ecu, hashes, 1, "corrid"};
301  Json::Value custom;
302  custom["version"] = 42;
303  custom["foo"] = "bar";
304  t1.updateCustom(custom);
305  storage->savePrimaryInstalledVersion(t1, InstalledVersionUpdateMode::kCurrent);
306  {
307  std::vector<Uptane::Target> log;
308  storage->loadPrimaryInstallationLog(&log, true);
309  EXPECT_EQ(log.size(), 1);
310  EXPECT_EQ(log[0].filename(), "update.bin");
311  }
312 
313  EcuSerials serials{{Uptane::EcuSerial("primary"), Uptane::HardwareIdentifier("primary_hw")},
314  {Uptane::EcuSerial("secondary_1"), Uptane::HardwareIdentifier("secondary_hw")},
315  {Uptane::EcuSerial("secondary_2"), Uptane::HardwareIdentifier("secondary_hw")}};
316  storage->storeEcuSerials(serials);
317 
318  {
319  boost::optional<Uptane::Target> current;
320  EXPECT_TRUE(storage->loadInstalledVersions("primary", &current, nullptr));
321  EXPECT_FALSE(storage->hasPendingInstall());
322  EXPECT_TRUE(!!current);
323  EXPECT_EQ(current->filename(), "update.bin");
324  EXPECT_EQ(current->sha256Hash(), "2561");
325  EXPECT_EQ(current->hashes(), hashes);
326  EXPECT_EQ(current->ecus(), primary_ecu);
327  EXPECT_EQ(current->correlation_id(), "corrid");
328  EXPECT_EQ(current->length(), 1);
329  EXPECT_EQ(current->custom_data()["foo"], "bar");
330  EXPECT_EQ(current->custom_data()["version"], 42);
331  }
332 
333  // Set t2 as a pending version
334  Uptane::Target t2{"update2.bin", primary_ecu, {Hash{Hash::Type::kSha256, "2562"}}, 2};
335  storage->savePrimaryInstalledVersion(t2, InstalledVersionUpdateMode::kPending);
336 
337  {
338  boost::optional<Uptane::Target> pending;
339  EXPECT_TRUE(storage->loadInstalledVersions("primary", nullptr, &pending));
340  EXPECT_TRUE(!!pending);
341  EXPECT_TRUE(storage->hasPendingInstall());
342  EXPECT_EQ(pending->filename(), "update2.bin");
343  }
344 
345  // Set t3 as the new pending
346  Uptane::Target t3{"update3.bin", primary_ecu, {Hash{Hash::Type::kSha256, "2563"}}, 3};
347  storage->savePrimaryInstalledVersion(t3, InstalledVersionUpdateMode::kPending);
348 
349  {
350  boost::optional<Uptane::Target> pending;
351  EXPECT_TRUE(storage->loadInstalledVersions("primary", nullptr, &pending));
352  EXPECT_TRUE(!!pending);
353  EXPECT_TRUE(storage->hasPendingInstall());
354  EXPECT_EQ(pending->filename(), "update3.bin");
355  }
356 
357  // Set t3 as current: should replace the pending flag but not create a new
358  // version
359  storage->savePrimaryInstalledVersion(t3, InstalledVersionUpdateMode::kCurrent);
360  {
361  boost::optional<Uptane::Target> current;
362  boost::optional<Uptane::Target> pending;
363  EXPECT_TRUE(storage->loadInstalledVersions("primary", &current, &pending));
364  EXPECT_TRUE(!!current);
365  EXPECT_EQ(current->filename(), "update3.bin");
366  EXPECT_FALSE(!!pending);
367  EXPECT_FALSE(storage->hasPendingInstall());
368 
369  std::vector<Uptane::Target> log;
370  storage->loadInstallationLog("primary", &log, true);
371  EXPECT_EQ(log.size(), 2);
372  EXPECT_EQ(log.back().filename(), "update3.bin");
373  }
374 
375  // Set t1 as current: the log should have grown even though we rolled back
376  {
377  storage->savePrimaryInstalledVersion(t1, InstalledVersionUpdateMode::kCurrent);
378  std::vector<Uptane::Target> log;
379  storage->loadInstallationLog("primary", &log, true);
380  EXPECT_EQ(log.size(), 3);
381  EXPECT_EQ(log.back().filename(), "update.bin");
382  EXPECT_FALSE(storage->hasPendingInstall());
383  }
384 
385  // Set t2 as the new pending and t3 as current afterwards: the pending flag
386  // should disappear
387  storage->savePrimaryInstalledVersion(t2, InstalledVersionUpdateMode::kPending);
388  storage->savePrimaryInstalledVersion(t3, InstalledVersionUpdateMode::kCurrent);
389 
390  {
391  boost::optional<Uptane::Target> current;
392  boost::optional<Uptane::Target> pending;
393  EXPECT_TRUE(storage->loadInstalledVersions("primary", &current, &pending));
394  EXPECT_TRUE(!!current);
395  EXPECT_EQ(current->filename(), "update3.bin");
396  EXPECT_FALSE(!!pending);
397  EXPECT_FALSE(storage->hasPendingInstall());
398 
399  std::vector<Uptane::Target> log;
400  storage->loadInstallationLog("primary", &log, true);
401  EXPECT_EQ(log.size(), 4);
402  EXPECT_EQ(log.back().filename(), "update3.bin");
403  EXPECT_EQ(log[0].custom_data()["foo"], "bar");
404  }
405 
406  // Add a Secondary installed version
407  Uptane::EcuMap secondary_ecu{{Uptane::EcuSerial("secondary1"), Uptane::HardwareIdentifier("secondary_hw")}};
408  Uptane::Target tsec{"secondary.bin", secondary_ecu, {Hash{Hash::Type::kSha256, "256s"}}, 4};
409  storage->saveInstalledVersion("secondary_1", tsec, InstalledVersionUpdateMode::kCurrent);
410 
411  {
412  EXPECT_TRUE(storage->loadInstalledVersions("primary", nullptr, nullptr));
413  EXPECT_TRUE(storage->loadInstalledVersions("secondary_1", nullptr, nullptr));
414 
415  std::vector<Uptane::Target> log;
416  storage->loadInstallationLog("secondary_1", &log, true);
417  EXPECT_EQ(log.size(), 1);
418  EXPECT_EQ(log.back().filename(), "secondary.bin");
419  }
420 }
421 
422 /*
423  * Load and store an ECU installation result in an SQL database.
424  * Load and store a device installation result in an SQL database.
425  */
426 TEST(storage, load_store_installation_results) {
427  TemporaryDirectory temp_dir;
428  std::unique_ptr<INvStorage> storage = Storage(temp_dir.Path());
429 
430  EcuSerials serials{{Uptane::EcuSerial("primary"), Uptane::HardwareIdentifier("primary_hw")},
431  {Uptane::EcuSerial("secondary_1"), Uptane::HardwareIdentifier("secondary_hw")},
432  {Uptane::EcuSerial("secondary_2"), Uptane::HardwareIdentifier("secondary_hw")}};
433  storage->storeEcuSerials(serials);
434 
435  storage->saveEcuInstallationResult(Uptane::EcuSerial("secondary_2"), data::InstallationResult());
436  storage->saveEcuInstallationResult(Uptane::EcuSerial("primary"), data::InstallationResult());
437  storage->saveEcuInstallationResult(Uptane::EcuSerial("primary"),
439 
440  std::vector<std::pair<Uptane::EcuSerial, data::InstallationResult>> res;
441  EXPECT_TRUE(storage->loadEcuInstallationResults(&res));
442  EXPECT_EQ(res.size(), 2);
443  EXPECT_EQ(res.at(0).first.ToString(), "primary");
444  EXPECT_EQ(res.at(0).second.result_code.num_code, data::ResultCode::Numeric::kGeneralError);
445  EXPECT_EQ(res.at(1).first.ToString(), "secondary_2");
446  EXPECT_EQ(res.at(1).second.result_code.num_code, data::ResultCode::Numeric::kOk);
447 
448  storage->storeDeviceInstallationResult(data::InstallationResult(data::ResultCode::Numeric::kGeneralError, ""), "raw",
449  "corrid");
450 
451  data::InstallationResult dev_res;
452  std::string report;
453  std::string correlation_id;
454  EXPECT_TRUE(storage->loadDeviceInstallationResult(&dev_res, &report, &correlation_id));
455  EXPECT_EQ(dev_res.result_code.num_code, data::ResultCode::Numeric::kGeneralError);
456  EXPECT_EQ(report, "raw");
457  EXPECT_EQ(correlation_id, "corrid");
458  EXPECT_TRUE(storage->storeDeviceInstallationRawReport("user's raw report"));
459 
460  storage->clearInstallationResults();
461  res.clear();
462  EXPECT_FALSE(storage->loadEcuInstallationResults(&res));
463  EXPECT_EQ(res.size(), 0);
464  EXPECT_FALSE(storage->loadDeviceInstallationResult(&dev_res, &report, &correlation_id));
465  EXPECT_FALSE(storage->storeDeviceInstallationRawReport(
466  "This call will return a negative value since the installation report was cleaned!"));
467 }
468 
469 TEST(storage, downloaded_files_info) {
470  TemporaryDirectory temp_dir;
471  std::unique_ptr<INvStorage> storage = Storage(temp_dir.Path());
472 
473  storage->storeTargetFilename("target1", "file1");
474  storage->storeTargetFilename("target2", "file2");
475  ASSERT_EQ(storage->getTargetFilename("target1"), "file1");
476  ASSERT_EQ(storage->getTargetFilename("target2"), "file2");
477 
478  auto names = storage->getAllTargetNames();
479  ASSERT_EQ(names.size(), 2);
480  ASSERT_EQ(names.at(0), "target1");
481  ASSERT_EQ(names.at(1), "target2");
482 
483  storage->deleteTargetInfo("target1");
484  names = storage->getAllTargetNames();
485  ASSERT_EQ(names.size(), 1);
486  ASSERT_EQ(names.at(0), "target2");
487 }
488 
489 TEST(storage, load_store_secondary_info) {
490  TemporaryDirectory temp_dir;
491  std::unique_ptr<INvStorage> storage = Storage(temp_dir.Path());
492 
493  // note: this can be done before the ECU is known
494  storage->saveSecondaryData(Uptane::EcuSerial("secondary_2"), "data2");
495 
496  EcuSerials serials{{Uptane::EcuSerial("primary"), Uptane::HardwareIdentifier("primary_hw")},
497  {Uptane::EcuSerial("secondary_1"), Uptane::HardwareIdentifier("secondary_hw")},
498  {Uptane::EcuSerial("secondary_2"), Uptane::HardwareIdentifier("secondary_hw")}};
499  storage->storeEcuSerials(serials);
500 
501  storage->saveSecondaryInfo(Uptane::EcuSerial("secondary_1"), "ip", PublicKey("key1", KeyType::kED25519));
502 
503  EXPECT_THROW(storage->saveSecondaryInfo(Uptane::EcuSerial("primary"), "ip", PublicKey("key0", KeyType::kRSA2048)),
504  std::runtime_error);
505 
506  std::vector<SecondaryInfo> sec_infos;
507  EXPECT_TRUE(storage->loadSecondariesInfo(&sec_infos));
508 
509  ASSERT_EQ(sec_infos.size(), 2);
510  EXPECT_EQ(sec_infos[0].serial.ToString(), "secondary_1");
511  EXPECT_EQ(sec_infos[0].hw_id.ToString(), "secondary_hw");
512  EXPECT_EQ(sec_infos[0].type, "ip");
513  EXPECT_EQ(sec_infos[0].pub_key.Value(), "key1");
514  EXPECT_EQ(sec_infos[0].pub_key.Type(), KeyType::kED25519);
515  EXPECT_EQ(sec_infos[1].pub_key.Type(), KeyType::kUnknown);
516  EXPECT_EQ(sec_infos[1].type, "");
517  EXPECT_EQ(sec_infos[1].extra, "data2");
518 
519  // test update of data
520  storage->saveSecondaryInfo(Uptane::EcuSerial("secondary_1"), "ip", PublicKey("key2", KeyType::kED25519));
521  storage->saveSecondaryData(Uptane::EcuSerial("secondary_1"), "data1");
522  EXPECT_TRUE(storage->loadSecondariesInfo(&sec_infos));
523 
524  ASSERT_EQ(sec_infos.size(), 2);
525  EXPECT_EQ(sec_infos[0].pub_key.Value(), "key2");
526  EXPECT_EQ(sec_infos[0].extra, "data1");
527 }
528 
529 /* Import keys and credentials from file into storage. */
530 TEST(storage, import_data) {
531  TemporaryDirectory temp_dir;
532  std::unique_ptr<INvStorage> storage = Storage(temp_dir.Path());
533  boost::filesystem::create_directories(temp_dir / "import");
534 
535  ImportConfig import_config;
536  import_config.base_path = temp_dir.Path() / "import";
537  import_config.uptane_private_key_path = utils::BasedPath("private");
538  import_config.uptane_public_key_path = utils::BasedPath("public");
539  import_config.tls_cacert_path = utils::BasedPath("ca");
540  import_config.tls_clientcert_path = utils::BasedPath("cert");
541  import_config.tls_pkey_path = utils::BasedPath("pkey");
542 
543  Utils::writeFile(import_config.uptane_private_key_path.get(import_config.base_path).string(),
544  std::string("uptane_private_1"));
545  Utils::writeFile(import_config.uptane_public_key_path.get(import_config.base_path).string(),
546  std::string("uptane_public_1"));
547  Utils::writeFile(import_config.tls_cacert_path.get(import_config.base_path).string(), std::string("tls_cacert_1"));
548  Utils::writeFile(import_config.tls_clientcert_path.get(import_config.base_path).string(), std::string("tls_cert_1"));
549  Utils::writeFile(import_config.tls_pkey_path.get(import_config.base_path).string(), std::string("tls_pkey_1"));
550 
551  // Initially the storage is empty
552  EXPECT_FALSE(storage->loadPrimaryPublic(nullptr));
553  EXPECT_FALSE(storage->loadPrimaryPrivate(nullptr));
554  EXPECT_FALSE(storage->loadTlsCa(nullptr));
555  EXPECT_FALSE(storage->loadTlsCert(nullptr));
556  EXPECT_FALSE(storage->loadTlsPkey(nullptr));
557 
558  storage->importData(import_config);
559 
560  std::string primary_public;
561  std::string primary_private;
562  std::string tls_ca;
563  std::string tls_cert;
564  std::string tls_pkey;
565 
566  // the data has been imported
567  EXPECT_TRUE(storage->loadPrimaryPublic(&primary_public));
568  EXPECT_TRUE(storage->loadPrimaryPrivate(&primary_private));
569  EXPECT_TRUE(storage->loadTlsCa(&tls_ca));
570  EXPECT_TRUE(storage->loadTlsCert(&tls_cert));
571  EXPECT_TRUE(storage->loadTlsPkey(&tls_pkey));
572 
573  EXPECT_EQ(primary_private, "uptane_private_1");
574  EXPECT_EQ(primary_public, "uptane_public_1");
575  EXPECT_EQ(tls_ca, "tls_cacert_1");
576  EXPECT_EQ(tls_cert, "tls_cert_1");
577  EXPECT_EQ(tls_pkey, "tls_pkey_1");
578 
579  Utils::writeFile(import_config.uptane_private_key_path.get(import_config.base_path).string(),
580  std::string("uptane_private_2"));
581  Utils::writeFile(import_config.uptane_public_key_path.get(import_config.base_path).string(),
582  std::string("uptane_public_2"));
583  Utils::writeFile(import_config.tls_cacert_path.get(import_config.base_path).string(), std::string("tls_cacert_2"));
584  Utils::writeFile(import_config.tls_clientcert_path.get(import_config.base_path).string(), std::string("tls_cert_2"));
585  Utils::writeFile(import_config.tls_pkey_path.get(import_config.base_path).string(), std::string("tls_pkey_2"));
586 
587  storage->importData(import_config);
588 
589  EXPECT_TRUE(storage->loadPrimaryPublic(&primary_public));
590  EXPECT_TRUE(storage->loadPrimaryPrivate(&primary_private));
591  EXPECT_TRUE(storage->loadTlsCa(&tls_ca));
592  EXPECT_TRUE(storage->loadTlsCert(&tls_cert));
593  EXPECT_TRUE(storage->loadTlsPkey(&tls_pkey));
594 
595  // only root cert is being updated
596  EXPECT_EQ(primary_private, "uptane_private_1");
597  EXPECT_EQ(primary_public, "uptane_public_1");
598  EXPECT_EQ(tls_ca, "tls_cacert_2");
599  EXPECT_EQ(tls_cert, "tls_cert_1");
600  EXPECT_EQ(tls_pkey, "tls_pkey_1");
601 }
602 
603 #ifndef __NO_MAIN__
604 int main(int argc, char **argv) {
605  ::testing::InitGoogleTest(&argc, argv);
606  logger_init();
607  logger_set_threshold(boost::log::trivial::trace);
608 
609  std::cout << "Running tests for SQLStorage" << std::endl;
610  current_storage_type = StorageType::kSqlite;
611  int res_sql = RUN_ALL_TESTS();
612 
613  return res_sql; // 0 indicates success
614 }
615 #endif
Metadata version numbers.
Definition: tuf.h:120
The Hash class The hash of a file or Uptane metadata.
Definition: types.h:157
The BasedPath class Can represent an absolute or relative path, only readable through the BasePath::g...
Definition: types.h:29