diff options
author | Abhishek Patel <Abhishek.Patel@ibm.com> | 2021-06-22 01:32:02 +0300 |
---|---|---|
committer | Ed Tanous <ed@tanous.net> | 2021-07-20 17:59:50 +0300 |
commit | b4bec66b24755cf87e924d56219c60e9506f196b (patch) | |
tree | e30e2921e5ddca0ce12a0c02a17b7cc6530c2e38 /redfish-core/lib/redfish_util.hpp | |
parent | 11a2f0f0186983d5939351c276c60b054c059c5a (diff) | |
download | bmcweb-b4bec66b24755cf87e924d56219c60e9506f196b.tar.xz |
Move getPortInfo to Redfish Utility
Plan to use getPortInfo() to get the SSH SerialConsole in the
ComputerSystem.
This commit moves the getPortInfo functionality into the redfish
utility.
Tested: manually tested on Witherspoon system, there is no change in
output. Run Redfish validator, no error found.
Before:
"HTTPS": {
"Certificates": {
"@odata.id": "/redfish/v1/Managers/bmc/NetworkProtocol/HTTPS/
Certificates"
},
"Port": 443,
"ProtocolEnabled": true
},
"IPMI": {
"Port": 623,
"ProtocolEnabled": true
},
"SSH": {
"Port": 22,
"ProtocolEnabled": true
}
After:
"HTTPS": {
"Certificates": {
"@odata.id": "/redfish/v1/Managers/bmc/NetworkProtocol/HTTPS/
Certificates"
},
"Port": 443,
"ProtocolEnabled": true
},
"IPMI": {
"Port": 623,
"ProtocolEnabled": true
},
"SSH": {
"Port": 22,
"ProtocolEnabled": true
}
Change-Id: I126827fbbecec59adcf630b88e31bc5ff8151588
Signed-off-by: Abhishek Patel <Abhishek.Patel@ibm.com>
Diffstat (limited to 'redfish-core/lib/redfish_util.hpp')
-rw-r--r-- | redfish-core/lib/redfish_util.hpp | 164 |
1 files changed, 164 insertions, 0 deletions
diff --git a/redfish-core/lib/redfish_util.hpp b/redfish-core/lib/redfish_util.hpp index 5494a23838..60626a5128 100644 --- a/redfish-core/lib/redfish_util.hpp +++ b/redfish-core/lib/redfish_util.hpp @@ -19,6 +19,34 @@ namespace redfish { +enum NetworkProtocolUnitStructFields +{ + NET_PROTO_UNIT_NAME, + NET_PROTO_UNIT_DESC, + NET_PROTO_UNIT_LOAD_STATE, + NET_PROTO_UNIT_ACTIVE_STATE, + NET_PROTO_UNIT_SUB_STATE, + NET_PROTO_UNIT_DEVICE, + NET_PROTO_UNIT_OBJ_PATH, + NET_PROTO_UNIT_ALWAYS_0, + NET_PROTO_UNIT_ALWAYS_EMPTY, + NET_PROTO_UNIT_ALWAYS_ROOT_PATH +}; + +enum NetworkProtocolListenResponseElements +{ + NET_PROTO_LISTEN_TYPE, + NET_PROTO_LISTEN_STREAM +}; + +/** + * @brief D-Bus Unit structure returned in array from ListUnits Method + */ +using UnitStruct = + std::tuple<std::string, std::string, std::string, std::string, std::string, + std::string, sdbusplus::message::object_path, uint32_t, + std::string, sdbusplus::message::object_path>; + template <typename CallbackFunc> void getMainChassisId(std::shared_ptr<bmcweb::AsyncResp> asyncResp, CallbackFunc&& callback) @@ -59,5 +87,141 @@ void getMainChassisId(std::shared_ptr<bmcweb::AsyncResp> asyncResp, "xyz.openbmc_project.Inventory.Item.Board", "xyz.openbmc_project.Inventory.Item.Chassis"}); } + +template <typename CallbackFunc> +void getPortStatusAndPath(const std::string& serviceName, + CallbackFunc&& callback) +{ + crow::connections::systemBus->async_method_call( + [serviceName, + callback{std::move(callback)}](const boost::system::error_code ec, + const std::vector<UnitStruct>& r) { + if (ec) + { + BMCWEB_LOG_ERROR << ec; + // return error code + callback(ec, "", false); + return; + } + + for (const UnitStruct& unit : r) + { + // Only traverse through <xyz>.socket units + const std::string& unitName = + std::get<NET_PROTO_UNIT_NAME>(unit); + + // find "." into unitsName + size_t lastCharPos = unitName.rfind('.'); + if (lastCharPos == std::string::npos) + { + continue; + } + + // is unitsName end with ".socket" + std::string unitNameEnd = unitName.substr(lastCharPos); + if (unitNameEnd.compare(".socket") != 0) + { + continue; + } + + // find "@" into unitsName + if (size_t atCharPos = unitName.rfind('@'); + atCharPos != std::string::npos) + { + lastCharPos = atCharPos; + } + + // unitsName without "@eth(x).socket", only <xyz> + // unitsName without ".socket", only <xyz> + std::string unitNameStr = unitName.substr(0, lastCharPos); + + // We are interested in services, which starts with + // mapped service name + if (unitNameStr != serviceName) + { + continue; + } + + const std::string& socketPath = + std::get<NET_PROTO_UNIT_OBJ_PATH>(unit); + const std::string& unitState = + std::get<NET_PROTO_UNIT_SUB_STATE>(unit); + + bool isProtocolEnabled = + ((unitState == "running") || (unitState == "listening")); + // We found service, return from inner loop. + callback(ec, socketPath, isProtocolEnabled); + return; + } + + // no service foudn, throw error + boost::system::error_code ec1 = + boost::system::errc::make_error_code( + boost::system::errc::no_such_process); + // return error code + callback(ec1, "", false); + BMCWEB_LOG_ERROR << ec1; + }, + "org.freedesktop.systemd1", "/org/freedesktop/systemd1", + "org.freedesktop.systemd1.Manager", "ListUnits"); +} + +template <typename CallbackFunc> +void getPortNumber(const std::string& socketPath, CallbackFunc&& callback) +{ + crow::connections::systemBus->async_method_call( + [callback{std::move(callback)}]( + const boost::system::error_code ec, + const std::variant< + std::vector<std::tuple<std::string, std::string>>>& resp) { + if (ec) + { + BMCWEB_LOG_ERROR << ec; + callback(ec, 0); + return; + } + const std::vector< + std::tuple<std::string, std::string>>* responsePtr = + std::get_if<std::vector<std::tuple<std::string, std::string>>>( + &resp); + if (responsePtr == nullptr || responsePtr->size() < 1) + { + // Network Protocol Listen Response Elements is empty + boost::system::error_code ec1 = + boost::system::errc::make_error_code( + boost::system::errc::bad_message); + // return error code + callback(ec1, 0); + BMCWEB_LOG_ERROR << ec1; + return; + } + const std::string& listenStream = + std::get<NET_PROTO_LISTEN_STREAM>((*responsePtr)[0]); + const char* pa = &listenStream[listenStream.rfind(':') + 1]; + int port{0}; + if (auto [p, ec2] = std::from_chars(pa, nullptr, port); + ec2 != std::errc()) + { + // there is only two possibility invalid_argument and + // result_out_of_range + boost::system::error_code ec3 = + boost::system::errc::make_error_code( + boost::system::errc::invalid_argument); + if (ec2 == std::errc::result_out_of_range) + { + ec3 = boost::system::errc::make_error_code( + boost::system::errc::result_out_of_range); + } + // return error code + callback(ec3, 0); + BMCWEB_LOG_ERROR << ec3; + } + callback(ec, port); + }, + "org.freedesktop.systemd1", socketPath, + "org.freedesktop.DBus.Properties", "Get", + "org.freedesktop.systemd1.Socket", "Listen"); +} + } // namespace redfish #endif |