control: Associate identifier with target holds
Create a zone method that associates a unique identifier to a target
hold so that if more than one hold exists, the highest target is always
used between all actions that could have set a target hold on the zone.
Change-Id: I7699769a2e271c8a63a0a0a05aef6b0888ce180a
Signed-off-by: Matthew Barth <msbarth@us.ibm.com>
diff --git a/control/json/actions/count_state_target.cpp b/control/json/actions/count_state_target.cpp
index 9f2ba5e..1017ae6 100644
--- a/control/json/actions/count_state_target.cpp
+++ b/control/json/actions/count_state_target.cpp
@@ -64,7 +64,6 @@
}
if (numAtState >= _count)
{
- zone.setTarget(_target);
break;
}
}
@@ -74,9 +73,9 @@
}
}
- // Update zone's active fan control allowed based on action results
- zone.setActiveAllow(ActionBase::getName() + std::to_string(_id),
- !(numAtState >= _count));
+ // Update zone's target hold based on action results
+ zone.setTargetHold(ActionBase::getName() + std::to_string(_id), _target,
+ (numAtState >= _count));
}
void CountStateTarget::setCount(const json& jsonObj)
diff --git a/control/json/actions/missing_owner_target.cpp b/control/json/actions/missing_owner_target.cpp
index 68f6614..8d8a605 100644
--- a/control/json/actions/missing_owner_target.cpp
+++ b/control/json/actions/missing_owner_target.cpp
@@ -49,12 +49,8 @@
[&intf = group.getInterface()](const auto& member) {
return !Manager::hasOwner(member, intf);
});
- if (isMissingOwner)
- {
- zone.setTarget(_target);
- }
- // Update group's fan control active allowed based on action results
- zone.setActiveAllow(group.getName(), !isMissingOwner);
+ // Update zone's target hold based on action results
+ zone.setTargetHold(group.getName(), _target, isMissingOwner);
}
}
diff --git a/control/json/zone.cpp b/control/json/zone.cpp
index 6d2744f..d59fe26 100644
--- a/control/json/zone.cpp
+++ b/control/json/zone.cpp
@@ -143,6 +143,36 @@
}
}
+void Zone::setTargetHold(const std::string& ident, uint64_t target, bool hold)
+{
+ if (!hold)
+ {
+ _holds.erase(ident);
+ }
+ else
+ {
+ _holds[ident] = target;
+ _isActive = false;
+ }
+
+ auto itHoldMax = std::max_element(_holds.begin(), _holds.end(),
+ [](const auto& aHold, const auto& bHold) {
+ return aHold.second < bHold.second;
+ });
+ if (itHoldMax == _holds.end())
+ {
+ _isActive = true;
+ }
+ else
+ {
+ _target = itHoldMax->second;
+ for (auto& fan : _fans)
+ {
+ fan->setTarget(_target);
+ }
+ }
+}
+
void Zone::setActiveAllow(const std::string& ident, bool isActiveAllow)
{
_active[ident] = isActiveAllow;
diff --git a/control/json/zone.hpp b/control/json/zone.hpp
index b47e051..d6ee3e2 100644
--- a/control/json/zone.hpp
+++ b/control/json/zone.hpp
@@ -216,6 +216,18 @@
void setTarget(uint64_t target);
/**
+ * Sets and holds all fans in the zone to the target given or releases a
+ * target hold resulting in the fans being held at the highest remaining
+ * hold target if other hold targets had been requested. When no hold
+ * targets exist, the zone returns to being active.
+ *
+ * @param[in] ident - Unique identifier for a target hold
+ * @param[in] target - Target to hold fans at
+ * @param[in] hold - Whether to hold(true) or release(false) a target hold
+ */
+ void setTargetHold(const std::string& ident, uint64_t target, bool hold);
+
+ /**
* @brief Sets the automatic fan control allowed active state
*
* @param[in] ident - An identifier that affects the active state
@@ -434,6 +446,9 @@
/* Map of active fan control allowed by a string identifier */
std::map<std::string, bool> _active;
+ /* Map of target holds by a string identifier */
+ std::unordered_map<std::string, uint64_t> _holds;
+
/* Interface to property mapping of their associated set property handler
* function */
static const std::map<