From 17d1fe23b704cacb1cdd9b58156f354626b36f8c Mon Sep 17 00:00:00 2001 From: Matthew Barth Date: Thu, 11 May 2017 15:00:36 -0500 Subject: Add setting zone speed action Enable an action to be defined that sets the zone to a given speed when a number of properties are set to a given value Change-Id: I5252a20a24bdb14dee63080f2c08b080c82ad7e8 Signed-off-by: Matthew Barth --- control/actions.hpp | 50 ++++++++++++++++++++++++++++++++++++++++++++++++++ control/functor.hpp | 13 +++++++++++++ control/types.hpp | 18 ++++++++++++++++-- control/zone.cpp | 42 ++++++++++++++++++++++++------------------ control/zone.hpp | 16 +++++++++++++++- 5 files changed, 118 insertions(+), 21 deletions(-) create mode 100644 control/actions.hpp (limited to 'control') diff --git a/control/actions.hpp b/control/actions.hpp new file mode 100644 index 0000000..eb857b6 --- /dev/null +++ b/control/actions.hpp @@ -0,0 +1,50 @@ +#pragma once + +#include + +namespace phosphor +{ +namespace fan +{ +namespace control +{ +namespace action +{ + +/** + * @brief An action to set the speed on a zone + * @details The zone is set to the given speed when a defined number of + * properties in the group are set to the given state + * + * @param[in] count - Number of properties + * @param[in] state - Value the property(s) needed to be set at + * @param[in] speed - Speed to set the zone to + * + * @return Lambda function + * A lambda function to set the zone speed when the number of properties + * within the group are at a certain value + */ +auto count_state_before_speed(size_t count, bool state, uint64_t speed) +{ + return [=](auto& zone, auto& group) + { + size_t numAtState = std::count_if( + group.begin(), + group.end(), + [&zone, &state](auto const& entry) + { + return zone.getPropertyValue( + entry.first, + std::get(entry.second)) == state; + }); + if (numAtState >= count) + { + zone.setSpeed(speed); + } + }; +} + +} // namespace action +} // namespace control +} // namespace fan +} // namespace phosphor diff --git a/control/functor.hpp b/control/functor.hpp index f2f3a78..2b36445 100644 --- a/control/functor.hpp +++ b/control/functor.hpp @@ -26,6 +26,19 @@ auto make_handler(T&& handler) return Handler(std::forward(handler)); } +/** + * @brief Create an action function object + * + * @param[in] action - The action being created + * + * @return - The created action function object + */ +template +auto make_action(T&& action) +{ + return Action(std::forward(action)); +} + /** * @struct Property Changed * @brief A match filter functor for Dbus property value changed signals diff --git a/control/types.hpp b/control/types.hpp index bbbac61..c610ed9 100644 --- a/control/types.hpp +++ b/control/types.hpp @@ -19,17 +19,31 @@ constexpr auto fanNamePos = 0; constexpr auto sensorListPos = 1; using FanDefinition = std::tuple>; +constexpr auto intfPos = 0; +constexpr auto propPos = 1; +using Group = std::map>; using Handler = std::function; +using Action = std::function; constexpr auto signaturePos = 0; constexpr auto handlerObjPos = 1; using PropertyChange = std::tuple; -using SetSpeedEvent = std::vector; + +constexpr auto groupPos = 0; +constexpr auto actionPos = 1; +constexpr auto propChangeListPos = 2; +using SetSpeedEvent = std::tuple>; + +constexpr auto eventGroupPos = 0; +constexpr auto eventHandlerPos = 1; +constexpr auto eventActionPos = 2; +using EventData = std::tuple; constexpr auto zoneObjPos = 0; -using SignalEvent = std::tuple; +constexpr auto eventDataPos = 1; +using SignalEvent = std::tuple; constexpr auto zoneNumPos = 0; constexpr auto fullSpeedPos = 1; diff --git a/control/zone.cpp b/control/zone.cpp index 28b81f9..3a35b24 100644 --- a/control/zone.cpp +++ b/control/zone.cpp @@ -36,20 +36,24 @@ Zone::Zone(sdbusplus::bus::bus& bus, _fans.emplace_back(std::make_unique(bus, def)); } - // Setup signal trigger for property changes - for (auto& event : std::get(def)) - { - for (auto& prop : event) - { - _signalEvents.emplace_back( - std::make_unique(this, - std::get(prop) - )); - _matches.emplace_back(bus, - std::get(prop).c_str(), - signalHandler, - _signalEvents.back().get()); - } + // Setup signal trigger for set speed events + for (auto& event : std::get(def)) + { + for (auto& prop : std::get(event)) + { + _signalEvents.emplace_back( + std::make_unique(this, + EventData + { + std::get(event), + std::get(prop), + std::get(event) + })); + _matches.emplace_back(bus, + std::get(prop).c_str(), + signalHandler, + _signalEvents.back().get()); + } } } @@ -70,18 +74,20 @@ int Zone::signalHandler(sd_bus_message* msg, auto& signalEvent = *static_cast(data); std::get(signalEvent)->handleEvent( sdbpMsg, - std::get(signalEvent)); + std::get(signalEvent)); return 0; } void Zone::handleEvent(sdbusplus::message::message& msg, - const Handler& handler) + const EventData& eventData) { // Handle the callback - handler(_bus, msg, *this); + std::get(eventData)(_bus, msg, *this); + // Perform the action + std::get(eventData)(*this, + std::get(eventData)); } - } } } diff --git a/control/zone.hpp b/control/zone.hpp index 601c002..d8f3fe4 100644 --- a/control/zone.hpp +++ b/control/zone.hpp @@ -71,6 +71,20 @@ class Zone _properties[object][property] = value; }; + /** + * @brief Get the value of an object's property + * + * @param[in] object - Name of the object containing the property + * @param[in] property - Property name + * + * @return - The property value + */ + inline auto getPropertyValue(const std::string& object, + const std::string& property) + { + return _properties[object][property]; + }; + private: /** @@ -126,7 +140,7 @@ class Zone * @param[in] eventData - The event's data */ void handleEvent(sdbusplus::message::message& msg, - const Handler& handler); + const EventData& eventData); }; } -- cgit v1.2.1