Save properties to persistent storage when host is on
1. When host is on, set properties as requested properties instead
of notify listeners;
2. When host becomes off, and requested properties are not empty, notify
the listners and reset the requested properties.
Add unit tests.
Change-Id: I9359c801c698df0c6e5eab43e12427bb5a6da611
Signed-off-by: Lei YU <mine260309@gmail.com>
diff --git a/manager.cpp b/manager.cpp
index 5a3d928..9810e14 100644
--- a/manager.cpp
+++ b/manager.cpp
@@ -1,4 +1,5 @@
#include "manager.hpp"
+#include "utils.hpp"
#include <phosphor-logging/log.hpp>
@@ -12,9 +13,6 @@
constexpr auto PROPERTY_INTERFACE = "org.freedesktop.DBus.Properties";
constexpr auto METHOD_GET = "Get";
-constexpr auto PROPERTY_TIME_MODE = "time_mode";
-constexpr auto PROPERTY_TIME_OWNER = "time_owner";
-
// TODO: Use new settings in xyz.openbmc_project
const auto MATCH_PROPERTY_CHANGE =
rules::type::signal() +
@@ -58,9 +56,14 @@
propertyChangeMatch(bus, MATCH_PROPERTY_CHANGE, onPropertyChanged, this),
pgoodChangeMatch(bus, MATCH_PGOOD_CHANGE, onPgoodChanged, this)
{
- setCurrentTimeMode(getSettings(PROPERTY_TIME_MODE));
- setCurrentTimeOwner(getSettings(PROPERTY_TIME_OWNER));
checkHostOn();
+
+ // Restore settings from persistent storage
+ restoreSettings();
+
+ // Check the settings daemon to process the new settings
+ onPropertyChanged(PROPERTY_TIME_MODE, getSettings(PROPERTY_TIME_MODE));
+ onPropertyChanged(PROPERTY_TIME_OWNER, getSettings(PROPERTY_TIME_OWNER));
}
void Manager::addListener(PropertyChangeListner* listener)
@@ -72,6 +75,20 @@
listeners.insert(listener);
}
+void Manager::restoreSettings()
+{
+ auto mode = utils::readData<std::string>(modeFile);
+ if (!mode.empty())
+ {
+ timeMode = convertToMode(mode);
+ }
+ auto owner = utils::readData<std::string>(ownerFile);
+ if (!owner.empty())
+ {
+ timeOwner = convertToOwner(owner);
+ }
+}
+
void Manager::checkHostOn()
{
sdbusplus::message::variant<int> pgood = 0;
@@ -92,28 +109,32 @@
void Manager::onPropertyChanged(const std::string& key,
const std::string& value)
{
- // TODO: Check pgood
- // If it's off, notify listners;
- // If it's on, hold the values and store in persistent storage
- // as requested time mode/owner.
- // And when pgood turns back to off, notify the listners.
-
// TODO: Check dhcp_ntp
- if (key == PROPERTY_TIME_MODE)
+ if (hostOn)
{
- setCurrentTimeMode(value);
- for (const auto& listener : listeners)
- {
- listener->onModeChanged(timeMode);
- }
+ // If host is on, set the values as requested time mode/owner.
+ // And when host becomes off, notify the listners.
+ setPropertyAsRequested(key, value);
}
- else if (key == PROPERTY_TIME_OWNER)
+ else
{
- setCurrentTimeOwner(value);
- for (const auto& listener : listeners)
+ // If host is off, notify listners
+ if (key == PROPERTY_TIME_MODE)
{
- listener->onOwnerChanged(timeOwner);
+ setCurrentTimeMode(value);
+ for (const auto listener : listeners)
+ {
+ listener->onModeChanged(timeMode);
+ }
+ }
+ else if (key == PROPERTY_TIME_OWNER)
+ {
+ setCurrentTimeOwner(value);
+ for (const auto listener : listeners)
+ {
+ listener->onOwnerChanged(timeOwner);
+ }
}
}
}
@@ -133,18 +154,67 @@
{
if (managedProperties.find(item.first) != managedProperties.end())
{
- static_cast<Manager*>(userData)
- ->onPropertyChanged(item.first, item.second.get<std::string>());
+ static_cast<Manager*>(userData)->onPropertyChanged(
+ item.first, item.second.get<std::string>());
}
}
return 0;
}
+void Manager::setPropertyAsRequested(const std::string& key,
+ const std::string& value)
+{
+ if (key == PROPERTY_TIME_MODE)
+ {
+ setRequestedMode(value);
+ }
+ else if (key == PROPERTY_TIME_OWNER)
+ {
+ setRequestedOwner(value);
+ }
+ else
+ {
+ // The key shall be already the supported one
+ // TODO: use elog API
+ assert(false);
+ }
+}
+
+void Manager::setRequestedMode(const std::string& mode)
+{
+ requestedMode = mode;
+}
+
+void Manager::setRequestedOwner(const std::string& owner)
+{
+ requestedOwner = owner;
+}
+
void Manager::onPgoodChanged(bool pgood)
{
hostOn = pgood;
- // TODO: if host is off, check requested time_mode/owner:
- // and notify the listeners if any.
+ if (hostOn)
+ {
+ return;
+ }
+ if (!requestedMode.empty())
+ {
+ setCurrentTimeMode(requestedMode);
+ for (const auto& listener : listeners)
+ {
+ listener->onModeChanged(timeMode);
+ }
+ setRequestedMode({}); // Clear requested mode
+ }
+ if (!requestedOwner.empty())
+ {
+ setCurrentTimeOwner(requestedOwner);
+ for (const auto& listener : listeners)
+ {
+ listener->onOwnerChanged(timeOwner);
+ }
+ setRequestedOwner({}); // Clear requested owner
+ }
}
int Manager::onPgoodChanged(sd_bus_message* msg,
@@ -174,6 +244,7 @@
log<level::INFO>("Time mode is changed",
entry("MODE=%s", mode.c_str()));
timeMode = convertToMode(mode);
+ utils::writeData(modeFile, mode);
}
void Manager::setCurrentTimeOwner(const std::string& owner)
@@ -181,6 +252,7 @@
log<level::INFO>("Time owner is changed",
entry("OWNER=%s", owner.c_str()));
timeOwner = convertToOwner(owner);
+ utils::writeData(ownerFile, owner);
}
std::string Manager::getSettings(const char* value) const