appcommands: support multi-host set/get fw version
Support multi-host set/get fw version in IPMI set/get system info command
Test case:
Get bios version from different host success.
Signed-off-by: Bonnie Lo <Bonnie_Lo@wiwynn.com>
Change-Id: Id2e1598bbe8f7d834fe3c31710384a7dbbe537e0
diff --git a/src/appcommands.cpp b/src/appcommands.cpp
index a4aa3cc..e0ae4ed 100644
--- a/src/appcommands.cpp
+++ b/src/appcommands.cpp
@@ -51,6 +51,11 @@
int sendBicCmd(uint8_t, uint8_t, uint8_t, std::vector<uint8_t>&,
std::vector<uint8_t>&);
+static inline auto responseSystemInfoParamterNotSupportCommand()
+{
+ return response(IPMI_CC_SYSTEM_INFO_PARAMETER_NOT_SUPPORTED);
+}
+
void printGUID(uint8_t* guid, off_t offset)
{
std::cout << "Read GUID from offset : " << offset << " :\n";
@@ -247,7 +252,7 @@
return;
}
-static int platSetSysFWVer(uint8_t* ver)
+static int platSetSysFWVer(uint8_t* ver, const std::string key)
{
std::stringstream ss;
int i;
@@ -265,23 +270,39 @@
ss << (char)ver[i];
}
- appData[KEY_SYSFW_VER] = ss.str();
+ appData[key] = ss.str();
flush_app_data();
return 0;
}
-static int platGetSysFWVer(uint8_t* ver)
+static int platGetSysFWVer(std::vector<uint8_t>& respData,
+ const std::string key)
{
- std::string str = appData[KEY_SYSFW_VER].get<std::string>();
- int len;
+ int len = -1;
- *ver++ = 0; // byte 1: Set selector not supported
- *ver++ = 0; // byte 2: Only ASCII supported
+ if (!appData.contains(std::string(key)))
+ {
+ return -1;
+ }
+ std::string str = appData[key].get<std::string>();
+
+ respData.push_back(0); // byte 1: Set selector not supported
+ respData.push_back(0); // byte 2: Only ASCII supported
len = str.length();
- *ver++ = len;
- memcpy(ver, str.data(), len);
+ respData.push_back(len); // byte 3: Size of version
+
+ for (auto c : str)
+ {
+ respData.push_back(c);
+ }
+
+ // Remaining byte fill to 0
+ for (int i = 0; i < SIZE_SYSFW_VER - (len + 3); i++)
+ {
+ respData.push_back(0);
+ }
return (len + 3);
}
@@ -289,16 +310,20 @@
//----------------------------------------------------------------------
// Set Sys Info Params (IPMI/Sec 22.14a) (CMD_APP_SET_SYS_INFO_PARAMS)
//----------------------------------------------------------------------
-ipmi_ret_t ipmiAppSetSysInfoParams(ipmi_netfn_t, ipmi_cmd_t,
- ipmi_request_t request, ipmi_response_t,
- ipmi_data_len_t data_len, ipmi_context_t)
+ipmi::RspType<uint8_t> ipmiAppSetSysInfoParams(ipmi::Context::ptr ctx,
+ std::vector<uint8_t> req)
{
- uint8_t* req = reinterpret_cast<uint8_t*>(request);
uint8_t param = req[0];
- uint8_t req_len = *data_len;
+ uint8_t req_len = req.size();
+ std::optional<size_t> hostId = findHost(ctx->hostIdx);
- *data_len = 0;
+ if (!hostId)
+ {
+ phosphor::logging::log<phosphor::logging::level::ERR>(
+ "Invalid Host Id received");
+ return ipmi::responseInvalidCommand();
+ }
switch (param)
{
@@ -306,10 +331,13 @@
sysInfoParams.set_in_prog = req[1];
break;
case SYS_INFO_PARAM_SYSFW_VER:
+ {
memcpy(sysInfoParams.sysfw_ver, &req[1], SIZE_SYSFW_VER);
- if (platSetSysFWVer(sysInfoParams.sysfw_ver))
- return IPMI_CC_SYSTEM_INFO_PARAMETER_NOT_SUPPORTED;
+ std::string version_key = KEY_SYSFW_VER + std::to_string(*hostId);
+ if (platSetSysFWVer(sysInfoParams.sysfw_ver, version_key))
+ return ipmi::responseSystemInfoParamterNotSupportCommand();
break;
+ }
case SYS_INFO_PARAM_SYS_NAME:
memcpy(sysInfoParams.sys_name, &req[1], SIZE_SYS_NAME);
break;
@@ -351,89 +379,100 @@
memcpy(sysInfoParams.last_boot_time, &req[1], SIZE_LAST_BOOT_TIME);
break;
default:
- return IPMI_CC_SYSTEM_INFO_PARAMETER_NOT_SUPPORTED;
+ return ipmi::responseSystemInfoParamterNotSupportCommand();
break;
}
- return IPMI_CC_OK;
+ return ipmi::responseSuccess();
}
//----------------------------------------------------------------------
// Get Sys Info Params (IPMI/Sec 22.14b) (CMD_APP_GET_SYS_INFO_PARAMS)
//----------------------------------------------------------------------
-ipmi_ret_t ipmiAppGetSysInfoParams(ipmi_netfn_t, ipmi_cmd_t,
- ipmi_request_t request,
- ipmi_response_t response,
- ipmi_data_len_t data_len, ipmi_context_t)
+ipmi::RspType<std::vector<uint8_t>>
+ ipmiAppGetSysInfoParams(ipmi::Context::ptr ctx, uint8_t, uint8_t param,
+ uint8_t, uint8_t)
{
- uint8_t* req = reinterpret_cast<uint8_t*>(request);
- uint8_t* res = reinterpret_cast<uint8_t*>(response);
-
- uint8_t param = req[1];
int len;
+ std::vector<uint8_t> respData;
+ respData.push_back(1); // Parameter revision
- *res++ = 1; // Parameter revision
- *data_len = 1;
+ std::optional<size_t> hostId = findHost(ctx->hostIdx);
+
+ if (!hostId)
+ {
+ phosphor::logging::log<phosphor::logging::level::ERR>(
+ "Invalid Host Id received");
+ return ipmi::responseInvalidCommand();
+ }
switch (param)
{
case SYS_INFO_PARAM_SET_IN_PROG:
- *res++ = sysInfoParams.set_in_prog;
- *data_len += 1;
+ respData.push_back(sysInfoParams.set_in_prog);
break;
case SYS_INFO_PARAM_SYSFW_VER:
- if ((len = platGetSysFWVer(res)) < 0)
- return IPMI_CC_SYSTEM_INFO_PARAMETER_NOT_SUPPORTED;
- *data_len += SIZE_SYSFW_VER;
+ {
+ std::string version_key = KEY_SYSFW_VER + std::to_string(*hostId);
+ if ((platGetSysFWVer(respData, version_key)) < 0)
+ return ipmi::responseSystemInfoParamterNotSupportCommand();
break;
+ }
case SYS_INFO_PARAM_SYS_NAME:
- memcpy(res, sysInfoParams.sys_name, SIZE_SYS_NAME);
- *data_len += SIZE_SYS_NAME;
+ respData.insert(respData.end(), std::begin(sysInfoParams.sys_name),
+ std::end(sysInfoParams.sys_name));
break;
case SYS_INFO_PARAM_PRI_OS_NAME:
- memcpy(res, sysInfoParams.pri_os_name, SIZE_OS_NAME);
- *data_len += SIZE_OS_NAME;
+ respData.insert(respData.end(),
+ std::begin(sysInfoParams.pri_os_name),
+ std::end(sysInfoParams.pri_os_name));
break;
case SYS_INFO_PARAM_PRESENT_OS_NAME:
- memcpy(res, sysInfoParams.present_os_name, SIZE_OS_NAME);
- *data_len += SIZE_OS_NAME;
+ respData.insert(respData.end(),
+ std::begin(sysInfoParams.present_os_name),
+ std::end(sysInfoParams.present_os_name));
break;
case SYS_INFO_PARAM_PRESENT_OS_VER:
- memcpy(res, sysInfoParams.present_os_ver, SIZE_OS_VER);
- *data_len += SIZE_OS_VER;
+ respData.insert(respData.end(),
+ std::begin(sysInfoParams.present_os_ver),
+ std::end(sysInfoParams.present_os_ver));
break;
case SYS_INFO_PARAM_BMC_URL:
- memcpy(res, sysInfoParams.bmc_url, SIZE_BMC_URL);
- *data_len += SIZE_BMC_URL;
+ respData.insert(respData.end(), std::begin(sysInfoParams.bmc_url),
+ std::end(sysInfoParams.bmc_url));
break;
case SYS_INFO_PARAM_OS_HV_URL:
- memcpy(res, sysInfoParams.os_hv_url, SIZE_OS_HV_URL);
- *data_len += SIZE_OS_HV_URL;
+ respData.insert(respData.end(), std::begin(sysInfoParams.os_hv_url),
+ std::end(sysInfoParams.os_hv_url));
break;
case SYS_INFO_PARAM_BIOS_CURRENT_BOOT_LIST:
len = appData[KEY_BIOS_BOOT_LEN].get<uint8_t>();
- memcpy(res, sysInfoParams.bios_current_boot_list, len);
- *data_len += len;
+ respData.insert(respData.end(),
+ std::begin(sysInfoParams.bios_current_boot_list),
+ std::begin(sysInfoParams.bios_current_boot_list) +
+ len);
break;
case SYS_INFO_PARAM_BIOS_FIXED_BOOT_DEVICE:
- memcpy(res, sysInfoParams.bios_fixed_boot_device,
- SIZE_BIOS_FIXED_BOOT_DEVICE);
- *data_len += SIZE_BIOS_FIXED_BOOT_DEVICE;
+ respData.insert(respData.end(),
+ std::begin(sysInfoParams.bios_fixed_boot_device),
+ std::end(sysInfoParams.bios_fixed_boot_device));
break;
case SYS_INFO_PARAM_BIOS_RSTR_DFLT_SETTING:
- memcpy(res, sysInfoParams.bios_rstr_dflt_setting,
- SIZE_BIOS_RSTR_DFLT_SETTING);
- *data_len += SIZE_BIOS_RSTR_DFLT_SETTING;
+ respData.insert(respData.end(),
+ std::begin(sysInfoParams.bios_rstr_dflt_setting),
+ std::end(sysInfoParams.bios_rstr_dflt_setting));
break;
case SYS_INFO_PARAM_LAST_BOOT_TIME:
- memcpy(res, sysInfoParams.last_boot_time, SIZE_LAST_BOOT_TIME);
- *data_len += SIZE_LAST_BOOT_TIME;
+ respData.insert(respData.end(),
+ std::begin(sysInfoParams.last_boot_time),
+ std::end(sysInfoParams.last_boot_time));
break;
default:
- return IPMI_CC_SYSTEM_INFO_PARAMETER_NOT_SUPPORTED;
+ return ipmi::responseSystemInfoParamterNotSupportCommand();
break;
}
- return IPMI_CC_OK;
+
+ return ipmi::responseSuccess(respData);
}
void registerAPPFunctions()
@@ -470,12 +509,13 @@
ipmiAppGetSysGUID,
PRIVILEGE_USER); // Get System GUID
#endif
- ipmiPrintAndRegister(NETFUN_APP, CMD_APP_SET_SYS_INFO_PARAMS, NULL,
- ipmiAppSetSysInfoParams,
- PRIVILEGE_USER); // Set Sys Info Params
- ipmiPrintAndRegister(NETFUN_APP, CMD_APP_GET_SYS_INFO_PARAMS, NULL,
- ipmiAppGetSysInfoParams,
- PRIVILEGE_USER); // Get Sys Info Params
+ ipmi::registerHandler(ipmi::prioOpenBmcBase, ipmi::netFnApp,
+ ipmi::app::cmdSetSystemInfoParameters,
+ ipmi::Privilege::User, ipmiAppSetSysInfoParams);
+
+ ipmi::registerHandler(ipmi::prioOpenBmcBase, ipmi::netFnApp,
+ ipmi::app::cmdGetSystemInfoParameters,
+ ipmi::Privilege::User, ipmiAppGetSysInfoParams);
return;
}
diff --git a/src/usb-dbg.cpp b/src/usb-dbg.cpp
index 9a718b7..19adbe8 100644
--- a/src/usb-dbg.cpp
+++ b/src/usb-dbg.cpp
@@ -795,7 +795,7 @@
return 0;
}
-static int getBiosVer(std::string& ver)
+static int getBiosVer(std::string& ver, size_t hostPosition)
{
nlohmann::json appObj;
@@ -804,9 +804,11 @@
{
file >> appObj;
file.close();
- if (appObj.find(KEY_SYSFW_VER) != appObj.end())
+ std::string version_key = KEY_SYSFW_VER + std::to_string(hostPosition);
+
+ if (appObj.find(version_key) != appObj.end())
{
- ver = appObj[KEY_SYSFW_VER].get<std::string>();
+ ver = appObj[version_key].get<std::string>();
return 0;
}
}
@@ -1025,7 +1027,7 @@
{
// BIOS ver
std::string biosVer;
- if (getBiosVer(biosVer) == 0)
+ if (getBiosVer(biosVer, hostPosition) == 0)
{
frame_info.append("BIOS_FW_ver:", 0);
frame_info.append(biosVer.c_str(), 1);