Aktualizr
C++ SOTA Client
All Classes Namespaces Files Functions Variables Enumerations Enumerator Pages
invstorage.h
1 #ifndef INVSTORAGE_H_
2 #define INVSTORAGE_H_
3 
4 #include <memory>
5 #include <string>
6 #include <utility>
7 
8 #include <boost/filesystem.hpp>
9 #include <boost/optional.hpp>
10 
11 #include "storage_config.h"
12 #include "storage_exception.h"
13 
14 #include "uptane/tuf.h"
15 #include "utilities/types.h"
16 
17 class INvStorage;
18 class FSStorageRead;
19 class SQLStorage;
20 
21 using store_data_t = void (INvStorage::*)(const std::string&);
22 using load_data_t = bool (INvStorage::*)(std::string*);
23 
24 typedef std::vector<std::pair<Uptane::EcuSerial, Uptane::HardwareIdentifier>> EcuSerials;
25 
26 enum class EcuState { kOld = 0, kNotRegistered };
27 
29  MisconfiguredEcu(Uptane::EcuSerial serial_in, Uptane::HardwareIdentifier hardware_id_in, EcuState state_in)
30  : serial(std::move(serial_in)), hardware_id(std::move(hardware_id_in)), state(state_in) {}
31  Uptane::EcuSerial serial;
32  Uptane::HardwareIdentifier hardware_id;
33  EcuState state;
34 };
35 
37  public:
38  class WriteError : public std::runtime_error {
39  public:
40  explicit WriteError(const std::string& what) : std::runtime_error(what) {}
41  };
42  virtual ~StorageTargetWHandle() = default;
43  virtual size_t wfeed(const uint8_t* buf, size_t size) = 0;
44  virtual void wcommit() = 0;
45  virtual void wabort() = 0;
46  uintmax_t getWrittenSize() { return written_size_; }
47 
48  friend std::istream& operator>>(std::istream& is, StorageTargetWHandle& handle) {
49  std::array<uint8_t, 256> arr{};
50  while (!is.eof()) {
51  is.read(reinterpret_cast<char*>(arr.data()), arr.size());
52  handle.wfeed(arr.data(), static_cast<size_t>(is.gcount()));
53  }
54  return is;
55  }
56 
57  protected:
58  uintmax_t written_size_{0};
59 };
60 
62  public:
63  class ReadError : public std::runtime_error {
64  public:
65  explicit ReadError(const std::string& what) : std::runtime_error(what) {}
66  };
67  virtual ~StorageTargetRHandle() = default;
68  virtual bool isPartial() const = 0;
69  virtual std::unique_ptr<StorageTargetWHandle> toWriteHandle() = 0;
70 
71  virtual uintmax_t rsize() const = 0;
72  virtual size_t rread(uint8_t* buf, size_t size) = 0;
73  virtual void rclose() = 0;
74 
75  void writeToFile(const boost::filesystem::path& path) {
76  std::array<uint8_t, 1024> arr{};
77  uintmax_t written = 0;
78  std::ofstream file(path.c_str());
79  if (!file.good()) {
80  throw std::runtime_error(std::string("Error opening file ") + path.string());
81  }
82  while (written < rsize()) {
83  size_t nread = rread(arr.data(), arr.size());
84  file.write(reinterpret_cast<char*>(arr.data()), static_cast<std::streamsize>(nread));
85  written += nread;
86  }
87  file.close();
88  }
89 
90  friend std::ostream& operator<<(std::ostream& os, StorageTargetRHandle& handle) {
91  std::array<uint8_t, 256> arr{};
92  uintmax_t written = 0;
93  while (written < handle.rsize()) {
94  size_t nread = handle.rread(arr.data(), arr.size());
95 
96  os.write(reinterpret_cast<char*>(arr.data()), static_cast<std::streamsize>(nread));
97  written += nread;
98  }
99 
100  return os;
101  }
102 };
103 
104 enum class InstalledVersionUpdateMode { kNone, kCurrent, kPending };
105 
107  SecondaryInfo() : serial(Uptane::EcuSerial::Unknown()), hw_id(Uptane::HardwareIdentifier::Unknown()) {}
108  SecondaryInfo(Uptane::EcuSerial serial_in, Uptane::HardwareIdentifier hw_id_in, std::string type_in,
109  PublicKey pub_key_in, std::string extra_in)
110  : serial(std::move(serial_in)),
111  hw_id(std::move(hw_id_in)),
112  type(std::move(type_in)),
113  pub_key(std::move(pub_key_in)),
114  extra(std::move(extra_in)) {}
115 
116  Uptane::EcuSerial serial;
118  std::string type;
119  PublicKey pub_key;
120 
121  std::string extra;
122 };
123 
124 // Functions loading/storing multiple pieces of data are supposed to do so atomically as far as implementation makes it
125 // possible
126 class INvStorage {
127  public:
128  explicit INvStorage(StorageConfig config) : config_(std::move(config)) {}
129  virtual ~INvStorage() = default;
130  virtual StorageType type() = 0;
131  virtual void storePrimaryKeys(const std::string& public_key, const std::string& private_key) = 0;
132  virtual bool loadPrimaryKeys(std::string* public_key, std::string* private_key) = 0;
133  virtual bool loadPrimaryPublic(std::string* public_key) = 0;
134  virtual bool loadPrimaryPrivate(std::string* private_key) = 0;
135  virtual void clearPrimaryKeys() = 0;
136 
137  virtual void saveSecondaryInfo(const Uptane::EcuSerial& ecu_serial, const std::string& sec_type,
138  const PublicKey& public_key) = 0;
139  virtual void saveSecondaryData(const Uptane::EcuSerial& ecu_serial, const std::string& data) = 0;
140  virtual bool loadSecondaryInfo(const Uptane::EcuSerial& ecu_serial, SecondaryInfo* secondary) = 0;
141  virtual bool loadSecondariesInfo(std::vector<SecondaryInfo>* secondaries) = 0;
142 
143  virtual void storeTlsCreds(const std::string& ca, const std::string& cert, const std::string& pkey) = 0;
144  virtual void storeTlsCa(const std::string& ca) = 0;
145  virtual void storeTlsCert(const std::string& cert) = 0;
146  virtual void storeTlsPkey(const std::string& pkey) = 0;
147  virtual bool loadTlsCreds(std::string* ca, std::string* cert, std::string* pkey) = 0;
148  virtual bool loadTlsCa(std::string* ca) = 0;
149  virtual bool loadTlsCert(std::string* cert) = 0;
150  virtual bool loadTlsPkey(std::string* cert) = 0;
151  virtual void clearTlsCreds() = 0;
152 
153  virtual void storeRoot(const std::string& data, Uptane::RepositoryType repo, Uptane::Version version) = 0;
154  virtual bool loadRoot(std::string* data, Uptane::RepositoryType repo, Uptane::Version version) = 0;
155  bool loadLatestRoot(std::string* data, Uptane::RepositoryType repo) {
156  return loadRoot(data, repo, Uptane::Version());
157  };
158  virtual void storeNonRoot(const std::string& data, Uptane::RepositoryType repo, Uptane::Role role) = 0;
159  virtual bool loadNonRoot(std::string* data, Uptane::RepositoryType repo, Uptane::Role role) = 0;
160  virtual void clearNonRootMeta(Uptane::RepositoryType repo) = 0;
161  virtual void clearMetadata() = 0;
162  virtual void storeDelegation(const std::string& data, Uptane::Role role) = 0;
163  virtual bool loadDelegation(std::string* data, Uptane::Role role) = 0;
164  virtual bool loadAllDelegations(std::vector<std::pair<Uptane::Role, std::string>>& data) const = 0;
165  virtual void deleteDelegation(Uptane::Role role) = 0;
166  virtual void clearDelegations() = 0;
167 
168  virtual void storeDeviceId(const std::string& device_id) = 0;
169  virtual bool loadDeviceId(std::string* device_id) = 0;
170  virtual void clearDeviceId() = 0;
171 
172  virtual void storeEcuSerials(const EcuSerials& serials) = 0;
173  virtual bool loadEcuSerials(EcuSerials* serials) = 0;
174  virtual void clearEcuSerials() = 0;
175 
176  virtual void storeCachedEcuManifest(const Uptane::EcuSerial& ecu_serial, const std::string& manifest) = 0;
177  virtual bool loadCachedEcuManifest(const Uptane::EcuSerial& ecu_serial, std::string* manifest) = 0;
178 
179  virtual void storeMisconfiguredEcus(const std::vector<MisconfiguredEcu>& ecus) = 0;
180  virtual bool loadMisconfiguredEcus(std::vector<MisconfiguredEcu>* ecus) = 0;
181  virtual void clearMisconfiguredEcus() = 0;
182 
183  virtual void storeEcuRegistered() = 0; // should be called after storeDeviceId
184  virtual bool loadEcuRegistered() = 0;
185  virtual void clearEcuRegistered() = 0;
186 
187  virtual void storeNeedReboot() = 0;
188  virtual bool loadNeedReboot(bool* need_reboot) = 0;
189  virtual void clearNeedReboot() = 0;
190 
191  virtual void saveInstalledVersion(const std::string& ecu_serial, const Uptane::Target& target,
192  InstalledVersionUpdateMode update_mode) = 0;
193  virtual bool loadInstalledVersions(const std::string& ecu_serial, boost::optional<Uptane::Target>* current_version,
194  boost::optional<Uptane::Target>* pending_version) = 0;
195  virtual bool loadInstallationLog(const std::string& ecu_serial, std::vector<Uptane::Target>* log,
196  bool only_installed) = 0;
197  virtual bool hasPendingInstall() = 0;
198  virtual void getPendingEcus(std::vector<std::pair<Uptane::EcuSerial, Uptane::Hash>>* pendingEcus) = 0;
199  virtual void clearInstalledVersions() = 0;
200 
201  virtual void saveEcuInstallationResult(const Uptane::EcuSerial& ecu_serial,
202  const data::InstallationResult& result) = 0;
203  virtual bool loadEcuInstallationResults(
204  std::vector<std::pair<Uptane::EcuSerial, data::InstallationResult>>* results) = 0;
205  virtual void storeDeviceInstallationResult(const data::InstallationResult& result, const std::string& raw_report,
206  const std::string& correlation_id) = 0;
207  virtual bool loadDeviceInstallationResult(data::InstallationResult* result, std::string* raw_report,
208  std::string* correlation_id) = 0;
209  virtual void clearInstallationResults() = 0;
210 
211  virtual void saveEcuReportCounter(const Uptane::EcuSerial& ecu_serial, int64_t counter) = 0;
212  virtual bool loadEcuReportCounter(std::vector<std::pair<Uptane::EcuSerial, int64_t>>* results) = 0;
213 
214  virtual bool checkAvailableDiskSpace(uint64_t required_bytes) const = 0;
215  virtual boost::optional<std::pair<uintmax_t, std::string>> checkTargetFile(const Uptane::Target& target) const = 0;
216 
217  // Incremental file API
218  virtual std::unique_ptr<StorageTargetWHandle> allocateTargetFile(const Uptane::Target& target) = 0;
219 
220  virtual std::unique_ptr<StorageTargetRHandle> openTargetFile(const Uptane::Target& target) = 0;
221  virtual std::vector<Uptane::Target> getTargetFiles() = 0;
222  virtual void removeTargetFile(const std::string& target_name) = 0;
223 
224  virtual void cleanUp() = 0;
225 
226  // Special constructors and utilities
227  static std::shared_ptr<INvStorage> newStorage(const StorageConfig& config, bool readonly = false);
228  static void FSSToSQLS(FSStorageRead& fs_storage, SQLStorage& sql_storage);
229  static bool fsReadInstalledVersions(const boost::filesystem::path& filename,
230  std::vector<Uptane::Target>* installed_versions, size_t* current_version);
231 
232  // Not purely virtual
233  void importData(const ImportConfig& import_config);
234  bool loadPrimaryInstalledVersions(boost::optional<Uptane::Target>* current_version,
235  boost::optional<Uptane::Target>* pending_version) {
236  return loadInstalledVersions("", current_version, pending_version);
237  }
238  void savePrimaryInstalledVersion(const Uptane::Target& target, InstalledVersionUpdateMode update_mode) {
239  return saveInstalledVersion("", target, update_mode);
240  }
241  bool loadPrimaryInstallationLog(std::vector<Uptane::Target>* log, bool only_installed) {
242  return loadInstallationLog("", log, only_installed);
243  }
244  void importInstalledVersions(const boost::filesystem::path& base_path);
245 
246  private:
247  void importSimple(const boost::filesystem::path& base_path, store_data_t store_func, load_data_t load_func,
248  const BasedPath& imported_data_path);
249  void importUpdateSimple(const boost::filesystem::path& base_path, store_data_t store_func, load_data_t load_func,
250  const BasedPath& imported_data_path);
251  void importPrimaryKeys(const boost::filesystem::path& base_path, const BasedPath& import_pubkey_path,
252  const BasedPath& import_privkey_path);
253 
254  protected:
255  const StorageConfig config_;
256 };
257 
258 #endif // INVSTORAGE_H_
types.h
data::InstallationResult
Definition: types.h:182
Uptane::Version
Metadata version numbers.
Definition: tuf.h:116
BasedPath
Definition: utils.h:101
StorageConfig
Definition: storage_config.h:15
MisconfiguredEcu
Definition: invstorage.h:28
data
General data structures.
Definition: types.cc:54
Uptane::HardwareIdentifier
Definition: tuf.h:143
StorageTargetWHandle::WriteError
Definition: invstorage.h:38
Uptane::RepositoryType
Definition: tuf.h:20
Uptane::EcuSerial
Definition: tuf.h:174
SecondaryInfo
Definition: invstorage.h:106
PublicKey
Definition: crypto.h:26
StorageTargetRHandle
Definition: invstorage.h:61
result
Results of libaktualizr API calls.
Definition: results.h:13
Uptane::Role
TUF Roles.
Definition: tuf.h:57
Uptane::Target
Definition: tuf.h:238
StorageTargetWHandle
Definition: invstorage.h:36
SQLStorage
Definition: sqlstorage.h:18
FSStorageRead
Definition: fsstorage_read.h:7
INvStorage
Definition: invstorage.h:126
ImportConfig
Definition: storage_config.h:34
StorageTargetRHandle::ReadError
Definition: invstorage.h:63