summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--manager.cpp120
-rw-r--r--manager.hpp18
-rw-r--r--test/TestManager.cpp3
-rw-r--r--utils.hpp44
4 files changed, 150 insertions, 35 deletions
diff --git a/manager.cpp b/manager.cpp
index 9810e14..56e0d0b 100644
--- a/manager.cpp
+++ b/manager.cpp
@@ -10,8 +10,6 @@ namespace // anonymous
constexpr auto SETTINGS_SERVICE = "org.openbmc.settings.Host";
constexpr auto SETTINGS_PATH = "/org/openbmc/settings/host0";
constexpr auto SETTINGS_INTERFACE = "org.openbmc.settings.Host";
-constexpr auto PROPERTY_INTERFACE = "org.freedesktop.DBus.Properties";
-constexpr auto METHOD_GET = "Get";
// TODO: Use new settings in xyz.openbmc_project
const auto MATCH_PROPERTY_CHANGE =
@@ -26,11 +24,20 @@ const auto MATCH_PGOOD_CHANGE =
rules::path("/org/openbmc/control/power0") +
rules::interface("org.freedesktop.DBus.Properties");
-// TODO: consider put the get properties related functions into a common place
constexpr auto POWER_SERVICE = "org.openbmc.control.Power";
constexpr auto POWER_PATH = "/org/openbmc/control/power0";
constexpr auto POWER_INTERFACE = POWER_SERVICE;
constexpr auto PGOOD_STR = "pgood";
+
+constexpr auto SYSTEMD_TIME_SERVICE = "org.freedesktop.timedate1";
+constexpr auto SYSTEMD_TIME_PATH = "/org/freedesktop/timedate1";
+constexpr auto SYSTEMD_TIME_INTERFACE = SYSTEMD_TIME_SERVICE;
+constexpr auto METHOD_SET_NTP = "SetNTP";
+
+constexpr auto OBMC_NETWORK_SERVICE = "org.openbmc.NetworkManager";
+constexpr auto OBMC_NETWORK_PATH = "/org/openbmc/NetworkManager/Interface";
+constexpr auto OBMC_NETWORK_INTERFACE = OBMC_NETWORK_SERVICE;
+constexpr auto METHOD_UPDATE_USE_NTP = "UpdateUseNtpField";
}
namespace phosphor
@@ -64,6 +71,8 @@ Manager::Manager(sdbusplus::bus::bus& bus)
// 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));
+
+ checkDhcpNtp();
}
void Manager::addListener(PropertyChangeListner* listener)
@@ -91,26 +100,28 @@ void Manager::restoreSettings()
void Manager::checkHostOn()
{
- sdbusplus::message::variant<int> pgood = 0;
- auto method = bus.new_method_call(POWER_SERVICE,
- POWER_PATH,
- PROPERTY_INTERFACE,
- METHOD_GET);
- method.append(PROPERTY_INTERFACE, PGOOD_STR);
- auto reply = bus.call(method);
- if (reply)
- {
- reply.read(pgood);
- }
+ int pgood = utils::getProperty<int>(bus,
+ POWER_SERVICE,
+ POWER_PATH,
+ POWER_INTERFACE,
+ PGOOD_STR);
+ hostOn = static_cast<bool>(pgood);
+}
- hostOn = static_cast<bool>(pgood.get<int>());
+void Manager::checkDhcpNtp()
+{
+ std::string useDhcpNtp = utils::getProperty<std::string>(
+ bus,
+ SETTINGS_SERVICE,
+ SETTINGS_PATH,
+ SETTINGS_INTERFACE,
+ PROPERTY_DHCP_NTP);
+ updateDhcpNtpSetting(useDhcpNtp);
}
void Manager::onPropertyChanged(const std::string& key,
const std::string& value)
{
- // TODO: Check dhcp_ntp
-
if (hostOn)
{
// If host is on, set the values as requested time mode/owner.
@@ -127,6 +138,8 @@ void Manager::onPropertyChanged(const std::string& key,
{
listener->onModeChanged(timeMode);
}
+ // When time_mode is updated, update the NTP setting
+ updateNtpSetting(value);
}
else if (key == PROPERTY_TIME_OWNER)
{
@@ -150,13 +163,20 @@ int Manager::onPropertyChanged(sd_bus_message* msg,
std::string ignore;
properties props;
m.read(ignore, props);
+ auto manager = static_cast<Manager*>(userData);
for (const auto& item : props)
{
if (managedProperties.find(item.first) != managedProperties.end())
{
- static_cast<Manager*>(userData)->onPropertyChanged(
+ // For managed properties, notify listeners
+ manager->onPropertyChanged(
item.first, item.second.get<std::string>());
}
+ else if (item.first == PROPERTY_DHCP_NTP)
+ {
+ // For other manager interested properties, handle specifically
+ manager->updateDhcpNtpSetting(item.second.get<std::string>());
+ }
}
return 0;
}
@@ -190,6 +210,46 @@ void Manager::setRequestedOwner(const std::string& owner)
requestedOwner = owner;
}
+void Manager::updateNtpSetting(const std::string& value)
+{
+ bool isNtp = (value == "NTP");
+ auto method = bus.new_method_call(SYSTEMD_TIME_SERVICE,
+ SYSTEMD_TIME_PATH,
+ SYSTEMD_TIME_INTERFACE,
+ METHOD_SET_NTP);
+ method.append(isNtp, false); // isNtp: 'true/false' means Enable/Disable
+ // 'false' meaning no policy-kit
+
+ if (bus.call(method))
+ {
+ log<level::INFO>("Updated NTP setting",
+ entry("ENABLED:%d", isNtp));
+ }
+ else
+ {
+ log<level::ERR>("Failed to update NTP setting");
+ }
+}
+
+void Manager::updateDhcpNtpSetting(const std::string& useDhcpNtp)
+{
+ auto method = bus.new_method_call(OBMC_NETWORK_SERVICE,
+ OBMC_NETWORK_PATH,
+ OBMC_NETWORK_INTERFACE,
+ METHOD_UPDATE_USE_NTP);
+ method.append(useDhcpNtp);
+
+ if (bus.call(method))
+ {
+ log<level::INFO>("Updated use ntp field",
+ entry("USENTPFIELD:%s", useDhcpNtp.c_str()));
+ }
+ else
+ {
+ log<level::ERR>("Failed to update UseNtpField");
+ }
+}
+
void Manager::onPgoodChanged(bool pgood)
{
hostOn = pgood;
@@ -204,6 +264,7 @@ void Manager::onPgoodChanged(bool pgood)
{
listener->onModeChanged(timeMode);
}
+ updateNtpSetting(requestedMode);
setRequestedMode({}); // Clear requested mode
}
if (!requestedOwner.empty())
@@ -257,23 +318,12 @@ void Manager::setCurrentTimeOwner(const std::string& owner)
std::string Manager::getSettings(const char* value) const
{
- sdbusplus::message::variant<std::string> mode;
- auto method = bus.new_method_call(SETTINGS_SERVICE,
- SETTINGS_PATH,
- PROPERTY_INTERFACE,
- METHOD_GET);
- method.append(SETTINGS_INTERFACE, value);
- auto reply = bus.call(method);
- if (reply)
- {
- reply.read(mode);
- }
- else
- {
- log<level::ERR>("Failed to get settings");
- }
-
- return mode.get<std::string>();
+ return utils::getProperty<std::string>(
+ bus,
+ SETTINGS_SERVICE,
+ SETTINGS_PATH,
+ SETTINGS_INTERFACE,
+ value);
}
Mode Manager::convertToMode(const std::string& mode)
diff --git a/manager.hpp b/manager.hpp
index 7edb30f..7c00122 100644
--- a/manager.hpp
+++ b/manager.hpp
@@ -70,6 +70,9 @@ class Manager
/** @brief Check if host is on and update hostOn variable */
void checkHostOn();
+ /** @brief Check if use_dhcp_ntp is used and update NTP setting */
+ void checkDhcpNtp();
+
/** @brief Get setting from settingsd service
*
* @param[in] setting - The string of the setting
@@ -126,6 +129,18 @@ class Manager
*/
void setRequestedOwner(const std::string& owner);
+ /** @brief Update the NTP setting to systemd time service
+ *
+ * @param[in] value - The time mode value, e.g. "NTP" or "MANUAL"
+ */
+ void updateNtpSetting(const std::string& value);
+
+ /** @brief Update dhcp_ntp setting to OpenBMC network service
+ *
+ * @param[in] value - The use_dhcp_ntp value, e.g. "yes" or "no"
+ */
+ void updateDhcpNtpSetting(const std::string& useDhcpNtp);
+
/** @brief The static function called on settings property changed
*
* @param[in] msg - Data associated with subscribed signal
@@ -176,6 +191,9 @@ class Manager
/** @brief The string of time owner property */
static constexpr auto PROPERTY_TIME_OWNER = "time_owner";
+ /** @brief The string of use dhcp ntp property */
+ static constexpr auto PROPERTY_DHCP_NTP = "use_dhcp_ntp";
+
using Updater = std::function<void(const std::string&)>;
/** @brief Map the property string to functions that shall
diff --git a/test/TestManager.cpp b/test/TestManager.cpp
index 935590e..1e4096e 100644
--- a/test/TestManager.cpp
+++ b/test/TestManager.cpp
@@ -135,5 +135,8 @@ TEST_F(TestManager, propertyChange)
ASSERT_DEATH(notifyPropertyChanged("invalid property", "whatever"), "");
}
+// TODO: if gmock is ready, add case to test
+// updateNtpSetting() and updateNetworkSetting()
+
}
}
diff --git a/utils.hpp b/utils.hpp
index 0589613..97b26e7 100644
--- a/utils.hpp
+++ b/utils.hpp
@@ -1,5 +1,7 @@
#pragma once
+#include <phosphor-logging/log.hpp>
+
#include <fstream>
namespace phosphor
@@ -9,6 +11,8 @@ namespace time
namespace utils
{
+using namespace phosphor::logging;
+
/** @brief Read data with type T from file
*
* @param[in] fileName - The name of file to read from
@@ -42,6 +46,46 @@ void writeData(const char* fileName, T&& data)
}
}
+/** @brief The template function to get property from the requested dbus path
+ *
+ * @param[in] bus - The Dbus bus object
+ * @param[in] service - The Dbus service name
+ * @param[in] path - The Dbus object path
+ * @param[in] interface - The Dbus interface
+ * @param[in] propertyName - The property name to get
+ *
+ * @return The value of the property
+ */
+template <typename T>
+T getProperty(sdbusplus::bus::bus& bus,
+ const char* service,
+ const char* path,
+ const char* interface,
+ const char* propertyName)
+{
+ sdbusplus::message::variant<T> value{};
+ auto method = bus.new_method_call(service,
+ path,
+ "org.freedesktop.DBus.Properties",
+ "Get");
+ method.append(interface, propertyName);
+ auto reply = bus.call(method);
+ if (reply)
+ {
+ reply.read(value);
+ }
+ else
+ {
+ // TODO: use elog to throw exception
+ log<level::ERR>("Failed to get property",
+ entry("SERVICE=%s", service),
+ entry("PATH=%s", path),
+ entry("INTERFACE=%s", interface),
+ entry("PROPERTY=%s", propertyName));
+ }
+ return value.template get<T>();
+}
+
}
}
}
OpenPOWER on IntegriCloud