redfish: oem: add stepwise configuration GET
Add stepwise configuration information into the oem
redfish configuration. Also move the basic configuration
information into the above loop to not set it multiple
times. Only implemented GET thus far, PATCH will be in
follow-on commit.
Tested-by: Navigated to redfish/v1/Managers/bmc/ and saw
Stepwise configuration.
Change-Id: Id4fdf7b6c6708edc56c1ede717b79c50de2b1c94
Signed-off-by: James Feist <james.feist@linux.intel.com>
diff --git a/include/dbus_utility.hpp b/include/dbus_utility.hpp
index e527e90..8677cc8 100644
--- a/include/dbus_utility.hpp
+++ b/include/dbus_utility.hpp
@@ -26,8 +26,8 @@
using DbusVariantType = sdbusplus::message::variant<
std::vector<std::tuple<std::string, std::string, std::string>>,
- std::vector<std::string>, std::string, int64_t, uint64_t, double, int32_t,
- uint32_t, int16_t, uint16_t, uint8_t, bool>;
+ std::vector<std::string>, std::vector<double>, std::string, int64_t,
+ uint64_t, double, int32_t, uint32_t, int16_t, uint16_t, uint8_t, bool>;
using ManagedObjectType = std::vector<
std::pair<sdbusplus::message::object_path,
diff --git a/redfish-core/lib/managers.hpp b/redfish-core/lib/managers.hpp
index daa441d..99a3e8b 100644
--- a/redfish-core/lib/managers.hpp
+++ b/redfish-core/lib/managers.hpp
@@ -112,6 +112,8 @@
"xyz.openbmc_project.Configuration.Pid";
static constexpr const char* pidZoneConfigurationIface =
"xyz.openbmc_project.Configuration.Pid.Zone";
+static constexpr const char* stepwiseConfigurationIface =
+ "xyz.openbmc_project.Configuration.Stepwise";
static void asyncPopulatePid(const std::string& connection,
const std::string& path,
@@ -144,6 +146,13 @@
pids["@odata.id"] =
"/redfish/v1/Managers/bmc#/Oem/OpenBmc/Fan/PidControllers";
+ nlohmann::json& stepwise = configRoot["StepwiseControllers"];
+ stepwise["@odata.type"] = "#OemManager.StepwiseControllers";
+ stepwise["@odata.context"] =
+ "/redfish/v1/$metadata#OemManager.StepwiseControllers";
+ stepwise["@odata.id"] =
+ "/redfish/v1/Managers/bmc#/Oem/OpenBmc/Fan/StepwiseControllers";
+
nlohmann::json& zones = configRoot["FanZones"];
zones["@odata.id"] =
"/redfish/v1/Managers/bmc#/Oem/OpenBmc/Fan/FanZones";
@@ -162,7 +171,8 @@
for (const auto& intfPair : pathPair.second)
{
if (intfPair.first != pidConfigurationIface &&
- intfPair.first != pidZoneConfigurationIface)
+ intfPair.first != pidZoneConfigurationIface &&
+ intfPair.first != stepwiseConfigurationIface)
{
continue;
}
@@ -179,11 +189,13 @@
if (namePtr == nullptr)
{
BMCWEB_LOG_ERROR << "Pid Name Field illegal";
+ messages::internalError(asyncResp->res);
return;
}
std::string name = *namePtr;
dbus::utility::escapePathForDbus(name);
+ nlohmann::json* config = nullptr;
if (intfPair.first == pidZoneConfigurationIface)
{
std::string chassis;
@@ -201,8 +213,83 @@
zone["@odata.type"] = "#OemManager.FanZone";
zone["@odata.context"] =
"/redfish/v1/$metadata#OemManager.FanZone";
+ config = &zone;
}
+ else if (intfPair.first == stepwiseConfigurationIface)
+ {
+ nlohmann::json& controller = stepwise[name];
+ config = &controller;
+
+ controller["@odata.id"] =
+ "/redfish/v1/Managers/bmc#/Oem/"
+ "OpenBmc/Fan/StepwiseControllers/" +
+ std::string(name);
+ controller["@odata.type"] =
+ "#OemManager.StepwiseController";
+
+ controller["@odata.context"] =
+ "/redfish/v1/"
+ "$metadata#OemManager.StepwiseController";
+ }
+
+ // pid and fans are off the same configuration
+ else if (intfPair.first == pidConfigurationIface)
+ {
+ const std::string* classPtr = nullptr;
+ auto findClass = intfPair.second.find("Class");
+ if (findClass != intfPair.second.end())
+ {
+ classPtr = sdbusplus::message::variant_ns::get_if<
+ std::string>(&findClass->second);
+ }
+ if (classPtr == nullptr)
+ {
+ BMCWEB_LOG_ERROR << "Pid Class Field illegal";
+ messages::internalError(asyncResp->res);
+ return;
+ }
+ bool isFan = *classPtr == "fan";
+ nlohmann::json& element =
+ isFan ? fans[name] : pids[name];
+ config = &element;
+ if (isFan)
+ {
+ element["@odata.id"] =
+ "/redfish/v1/Managers/bmc#/Oem/"
+ "OpenBmc/Fan/FanControllers/" +
+ std::string(name);
+ element["@odata.type"] =
+ "#OemManager.FanController";
+
+ element["@odata.context"] =
+ "/redfish/v1/"
+ "$metadata#OemManager.FanController";
+ }
+ else
+ {
+ element["@odata.id"] =
+ "/redfish/v1/Managers/bmc#/Oem/"
+ "OpenBmc/Fan/PidControllers/" +
+ std::string(name);
+ element["@odata.type"] =
+ "#OemManager.PidController";
+ element["@odata.context"] =
+ "/redfish/v1/$metadata"
+ "#OemManager.PidController";
+ }
+ }
+ else
+ {
+ BMCWEB_LOG_ERROR << "Unexpected configuration";
+ messages::internalError(asyncResp->res);
+ return;
+ }
+
+ // used for making maps out of 2 vectors
+ const std::vector<double>* keys = nullptr;
+ const std::vector<double>* values = nullptr;
+
for (const auto& propertyPair : intfPair.second)
{
if (propertyPair.first == "Type" ||
@@ -225,54 +312,76 @@
messages::internalError(asyncResp->res);
return;
}
- zones[name][propertyPair.first] = *ptr;
+ (*config)[propertyPair.first] = *ptr;
+ }
+
+ if (intfPair.first == stepwiseConfigurationIface)
+ {
+ if (propertyPair.first == "Reading" ||
+ propertyPair.first == "Output")
+ {
+ const std::vector<double>* ptr =
+ sdbusplus::message::variant_ns::get_if<
+ std::vector<double>>(
+ &propertyPair.second);
+
+ if (ptr == nullptr)
+ {
+ BMCWEB_LOG_ERROR << "Field Illegal "
+ << propertyPair.first;
+ messages::internalError(asyncResp->res);
+ return;
+ }
+
+ if (propertyPair.first == "Reading")
+ {
+ keys = ptr;
+ }
+ else
+ {
+ values = ptr;
+ }
+ if (keys && values)
+ {
+ if (keys->size() != values->size())
+ {
+ BMCWEB_LOG_ERROR
+ << "Reading and Output size don't "
+ "match ";
+ messages::internalError(asyncResp->res);
+ return;
+ }
+ nlohmann::json& steps = (*config)["Steps"];
+ steps = nlohmann::json::array();
+ for (size_t ii = 0; ii < keys->size(); ii++)
+ {
+ steps.push_back(
+ {{"Target", (*keys)[ii]},
+ {"Output", (*values)[ii]}});
+ }
+ }
+ }
+ if (propertyPair.first == "NegativeHysteresis" ||
+ propertyPair.first == "PositiveHysteresis")
+ {
+ const double* ptr =
+ sdbusplus::message::variant_ns::get_if<
+ double>(&propertyPair.second);
+ if (ptr == nullptr)
+ {
+ BMCWEB_LOG_ERROR << "Field Illegal "
+ << propertyPair.first;
+ messages::internalError(asyncResp->res);
+ return;
+ }
+ (*config)[propertyPair.first] = *ptr;
+ }
}
// pid and fans are off the same configuration
- if (intfPair.first == pidConfigurationIface)
+ if (intfPair.first == pidConfigurationIface ||
+ intfPair.first == stepwiseConfigurationIface)
{
- const std::string* classPtr = nullptr;
- auto findClass = intfPair.second.find("Class");
- if (findClass != intfPair.second.end())
- {
- classPtr =
- sdbusplus::message::variant_ns::get_if<
- std::string>(&findClass->second);
- }
- if (classPtr == nullptr)
- {
- BMCWEB_LOG_ERROR << "Pid Class Field illegal";
- messages::internalError(asyncResp->res);
- return;
- }
- bool isFan = *classPtr == "fan";
- nlohmann::json& element =
- isFan ? fans[name] : pids[name];
- if (isFan)
- {
- element["@odata.id"] =
- "/redfish/v1/Managers/bmc#/Oem/"
- "OpenBmc/Fan/FanControllers/" +
- std::string(name);
- element["@odata.type"] =
- "#OemManager.FanController";
-
- element["@odata.context"] =
- "/redfish/v1/"
- "$metadata#OemManager.FanController";
- }
- else
- {
- element["@odata.id"] =
- "/redfish/v1/Managers/bmc#/Oem/"
- "OpenBmc/Fan/PidControllers/" +
- std::string(name);
- element["@odata.type"] =
- "#OemManager.PidController";
- element["@odata.context"] =
- "/redfish/v1/$metadata"
- "#OemManager.PidController";
- }
if (propertyPair.first == "Zones")
{
@@ -288,7 +397,7 @@
messages::internalError(asyncResp->res);
return;
}
- auto& data = element[propertyPair.first];
+ auto& data = (*config)[propertyPair.first];
data = nlohmann::json::array();
for (std::string itemCopy : *inputs)
{
@@ -310,7 +419,7 @@
else if (propertyPair.first == "Inputs" ||
propertyPair.first == "Outputs")
{
- auto& data = element[propertyPair.first];
+ auto& data = (*config)[propertyPair.first];
const std::vector<std::string>* inputs =
sdbusplus::message::variant_ns::get_if<
std::vector<std::string>>(
@@ -347,7 +456,7 @@
messages::internalError(asyncResp->res);
return;
}
- element[propertyPair.first] = *ptr;
+ (*config)[propertyPair.first] = *ptr;
}
}
}
@@ -654,7 +763,8 @@
// this list is alphabetical, so we
// should have found the objMgr by now
if (interface == pidConfigurationIface ||
- interface == pidZoneConfigurationIface)
+ interface == pidZoneConfigurationIface ||
+ interface == stepwiseConfigurationIface)
{
auto findObjMgr =
objectMgrPaths.find(connectionGroup.first);
@@ -678,9 +788,9 @@
"xyz.openbmc_project.ObjectMapper",
"/xyz/openbmc_project/object_mapper",
"xyz.openbmc_project.ObjectMapper", "GetSubTree", "/", 0,
- std::array<const char*, 3>{pidConfigurationIface,
- pidZoneConfigurationIface,
- objectManagerIface});
+ std::array<const char*, 4>{
+ pidConfigurationIface, pidZoneConfigurationIface,
+ objectManagerIface, stepwiseConfigurationIface});
}
void doGet(crow::Response& res, const crow::Request& req,