blob: ca943949f9ab189e617347b4b346ae351783d15c [file] [log] [blame]
Tomáš Pecka991e4d52021-01-11 10:03:14 +01001#include <sdbus-c++/sdbus-c++.h>
2#include "dbus_rauc_server.h"
3#include "utils/log-init.h"
4
5using namespace std::literals;
6
7namespace {
8const std::string interfaceManager = "de.pengutronix.rauc.Installer";
9const std::string objectPathManager = "/";
10}
11
12/** @brief Create a dbus server on the connection */
13DBusRAUCServer::DBusRAUCServer(sdbus::IConnection& connection, std::string primarySlot, const std::map<std::string, velia::system::RAUC::SlotProperties>& status)
14 : m_manager(sdbus::createObject(connection, objectPathManager))
15 , m_primarySlot(std::move(primarySlot))
16{
17 for (const auto& [slotName, slotStatus] : status) {
18 std::map<std::string, sdbus::Variant> m;
19 for (auto it = slotStatus.begin(); it != slotStatus.end(); ++it) {
20 // NOTE: I wanted a for-range loop over the map with structured binding [key, val] but this did not compile with clang++.
21 // According to http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2017/p0588r1.html:
22 // "If a lambda-expression [...] captures a structured binding (explicitly or implicitly), the program is ill-formed."
23
24 const auto& k = it->first;
25 std::visit([&k, &m](auto&& arg) { m.insert(std::make_pair(k, sdbus::Variant(arg))); }, it->second);
26 }
27 m_status.emplace_back(slotName, m);
28 }
29
30 // create manager object
31 m_manager->registerMethod("GetSlotStatus").onInterface(interfaceManager).implementedAs([this]() { return m_status; });
32 m_manager->registerMethod("GetPrimary").onInterface(interfaceManager).implementedAs([this]() { return m_primarySlot; });
33 m_manager->finishRegistration();
34}