summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--redfish-core/include/redfish.hpp2
-rw-r--r--redfish-core/lib/hypervisor_system.hpp219
2 files changed, 221 insertions, 0 deletions
diff --git a/redfish-core/include/redfish.hpp b/redfish-core/include/redfish.hpp
index 0f02288311..aad28ac000 100644
--- a/redfish-core/include/redfish.hpp
+++ b/redfish-core/include/redfish.hpp
@@ -211,6 +211,8 @@ class RedfishService
std::make_unique<HypervisorInterfaceCollection>(app));
nodes.emplace_back(std::make_unique<HypervisorInterface>(app));
nodes.emplace_back(std::make_unique<HypervisorSystem>(app));
+ nodes.emplace_back(std::make_unique<HypervisorActionsReset>(app));
+ nodes.emplace_back(std::make_unique<HypervisorResetActionInfo>(app));
nodes.emplace_back(std::make_unique<TelemetryService>(app));
nodes.emplace_back(
diff --git a/redfish-core/lib/hypervisor_system.hpp b/redfish-core/lib/hypervisor_system.hpp
index 4ec88fd51f..3367a14612 100644
--- a/redfish-core/lib/hypervisor_system.hpp
+++ b/redfish-core/lib/hypervisor_system.hpp
@@ -94,6 +94,61 @@ inline void getHypervisorState(const std::shared_ptr<AsyncResp>& aResp)
}
/**
+ * @brief Populate Actions if any are valid for hypervisor object
+ *
+ * The hypervisor state object is optional so this function will only set the
+ * Action if the object is found
+ *
+ * @param[in] aResp Shared pointer for completing asynchronous calls.
+ *
+ * @return None.
+ */
+inline void getHypervisorActions(const std::shared_ptr<AsyncResp>& aResp)
+{
+ BMCWEB_LOG_DEBUG << "Get hypervisor actions.";
+ crow::connections::systemBus->async_method_call(
+ [aResp](
+ const boost::system::error_code ec,
+ const std::vector<std::pair<std::string, std::vector<std::string>>>&
+ objInfo) {
+ if (ec)
+ {
+ BMCWEB_LOG_DEBUG << "DBUS response error " << ec;
+ // This is an optional D-Bus object so just return if
+ // error occurs
+ return;
+ }
+
+ if (objInfo.size() == 0)
+ {
+ // As noted above, this is an optional interface so just return
+ // if there is no instance found
+ return;
+ }
+
+ if (objInfo.size() > 1)
+ {
+ // More then one hypervisor object is not supported and is an
+ // error
+ messages::internalError(aResp->res);
+ return;
+ }
+
+ // Object present so system support limited ComputerSystem Action
+ aResp->res.jsonValue["Actions"]["#ComputerSystem.Reset"] = {
+ {"target",
+ "/redfish/v1/Systems/hypervisor/Actions/ComputerSystem.Reset"},
+ {"@Redfish.ActionInfo",
+ "/redfish/v1/Systems/hypervisor/ResetActionInfo"}};
+ },
+ "xyz.openbmc_project.ObjectMapper",
+ "/xyz/openbmc_project/object_mapper",
+ "xyz.openbmc_project.ObjectMapper", "GetObject",
+ "/xyz/openbmc_project/state/hypervisor0",
+ std::array<const char*, 1>{"xyz.openbmc_project.State.Host"});
+}
+
+/**
* Hypervisor Systems derived class for delivering Computer Systems Schema.
*/
class HypervisorSystem : public Node
@@ -142,6 +197,7 @@ class HypervisorSystem : public Node
{"@odata.id", "/redfish/v1/Systems/hypervisor/"
"EthernetInterfaces"}};
getHypervisorState(asyncResp);
+ getHypervisorActions(asyncResp);
// TODO: Add "SystemType" : "hypervisor"
},
"xyz.openbmc_project.Settings",
@@ -954,4 +1010,167 @@ class HypervisorInterface : public Node
res.result(boost::beast::http::status::accepted);
}
};
+
+/**
+ * HypervisorResetActionInfo derived class for delivering Computer Systems
+ * ResetType AllowableValues using ResetInfo schema.
+ */
+class HypervisorResetActionInfo : public Node
+{
+ public:
+ /*
+ * Default Constructor
+ */
+ HypervisorResetActionInfo(App& app) :
+ Node(app, "/redfish/v1/Systems/hypervisor/ResetActionInfo/")
+ {
+ entityPrivileges = {
+ {boost::beast::http::verb::get, {{"Login"}}},
+ {boost::beast::http::verb::head, {{"Login"}}},
+ {boost::beast::http::verb::patch, {{"ConfigureComponents"}}},
+ {boost::beast::http::verb::put, {{"ConfigureComponents"}}},
+ {boost::beast::http::verb::delete_, {{"ConfigureComponents"}}},
+ {boost::beast::http::verb::post, {{"ConfigureComponents"}}}};
+ }
+
+ private:
+ /**
+ * Functions triggers appropriate requests on DBus
+ */
+ void doGet(crow::Response& res, const crow::Request&,
+ const std::vector<std::string>&) override
+ {
+ std::shared_ptr<AsyncResp> asyncResp = std::make_shared<AsyncResp>(res);
+
+ // Only return action info if hypervisor D-Bus object present
+ crow::connections::systemBus->async_method_call(
+ [asyncResp](const boost::system::error_code ec,
+ const std::vector<std::pair<
+ std::string, std::vector<std::string>>>& objInfo) {
+ if (ec)
+ {
+ BMCWEB_LOG_DEBUG << "DBUS response error " << ec;
+
+ // No hypervisor objects found by mapper
+ if (ec.value() == boost::system::errc::io_error)
+ {
+ messages::resourceNotFound(asyncResp->res, "hypervisor",
+ "ResetActionInfo");
+ return;
+ }
+
+ messages::internalError(asyncResp->res);
+ return;
+ }
+
+ // One and only one hypervisor instance supported
+ if (objInfo.size() != 1)
+ {
+ messages::internalError(asyncResp->res);
+ return;
+ }
+
+ // The hypervisor object only support the ability to turn On
+ // The system object Action should be utilized for other
+ // operations
+ asyncResp->res.jsonValue = {
+ {"@odata.type", "#ActionInfo.v1_1_2.ActionInfo"},
+ {"@odata.id",
+ "/redfish/v1/Systems/hypervisor/ResetActionInfo"},
+ {"Name", "Reset Action Info"},
+ {"Id", "ResetActionInfo"},
+ {"Parameters",
+ {{{"Name", "ResetType"},
+ {"Required", true},
+ {"DataType", "String"},
+ {"AllowableValues", {"On"}}}}}};
+ },
+ "xyz.openbmc_project.ObjectMapper",
+ "/xyz/openbmc_project/object_mapper",
+ "xyz.openbmc_project.ObjectMapper", "GetObject",
+ "/xyz/openbmc_project/state/hypervisor0",
+ std::array<const char*, 1>{"xyz.openbmc_project.State.Host"});
+ }
+};
+
+/**
+ * HypervisorActionsReset class supports the POST method for Reset action.
+ * The class sends data directly to D-Bus.
+ */
+class HypervisorActionsReset : public Node
+{
+ public:
+ HypervisorActionsReset(App& app) :
+ Node(app,
+ "/redfish/v1/Systems/hypervisor/Actions/ComputerSystem.Reset/")
+ {
+ entityPrivileges = {
+ {boost::beast::http::verb::post, {{"ConfigureComponents"}}}};
+ }
+
+ private:
+ /**
+ * Function handles POST method request.
+ * Analyzes POST body message before sends Reset request data to D-Bus.
+ */
+ void doPost(crow::Response& res, const crow::Request& req,
+ const std::vector<std::string>&) override
+ {
+ std::shared_ptr<AsyncResp> asyncResp = std::make_shared<AsyncResp>(res);
+
+ std::optional<std::string> resetType;
+ if (!json_util::readJson(req, res, "ResetType", resetType))
+ {
+ // readJson adds appropriate error to response
+ return;
+ }
+
+ if (!resetType)
+ {
+ messages::actionParameterMissing(
+ asyncResp->res, "ComputerSystem.Reset", "ResetType");
+ return;
+ }
+
+ // Hypervisor object only support On operation
+ if (resetType != "On")
+ {
+ messages::propertyValueNotInList(asyncResp->res, *resetType,
+ "ResetType");
+ return;
+ }
+
+ std::string command = "xyz.openbmc_project.State.Host.Transition.On";
+
+ crow::connections::systemBus->async_method_call(
+ [asyncResp, resetType](const boost::system::error_code ec) {
+ if (ec)
+ {
+ BMCWEB_LOG_ERROR << "D-Bus responses error: " << ec;
+ if (ec.value() == boost::asio::error::invalid_argument)
+ {
+ messages::actionParameterNotSupported(
+ asyncResp->res, *resetType, "Reset");
+ return;
+ }
+
+ if (ec.value() == boost::asio::error::host_unreachable)
+ {
+ messages::resourceNotFound(asyncResp->res, "Actions",
+ "Reset");
+ return;
+ }
+
+ messages::internalError(asyncResp->res);
+ return;
+ }
+ messages::success(asyncResp->res);
+ },
+ "xyz.openbmc_project.State.Hypervisor",
+ "/xyz/openbmc_project/state/hypervisor0",
+ "org.freedesktop.DBus.Properties", "Set",
+ "xyz.openbmc_project.State.Host", "RequestedHostTransition",
+ std::variant<std::string>{std::move(command)});
+ }
+};
} // namespace redfish