PLDMTOOL : Implement a PLDM requester tool.
Implemented a way for sending PLDM requests for specific PLDM commands.
This tool will interact with MCTP daemon using UNIX domain socket, The
response got from socket will be displayed on the console in raw format.
Tested following PLDM commands:
1) GetPLDMTypes
2) GetPLDMVersion
Tested : Verified the RAW response data.
./pldmtool -c GetPLDMTypes
Encoded request succesfully : RC = 0
Request Message:
08 01 9b 00 04 00 00
Success in creating the socket : RC = 3
Success in connecting to socket : RC = 0
Success in sending message type as pldm to mctp : RC = 0
Write to socket successful : RC = 7
Total length:7
Loopback response message:
08 01 9b 00 04 00 00
On first recv(),response == request : RC = 0
Total length: 14
Shutdown Socket successful : RC = 0
Socket recv() successful : RC = 0
Response Message :
08 01 00 00 04 00 01 00 00 00 00 00 00 00
./pldmtool -c GetPLDMVersion base
PLDM Type requested : base
Encoded request succesfully : RC = 0
Request Message:
08 01 9b 00 03 00 00 00 00 01 00
Success in creating the socket : RC = 3
Success in connecting to socket : RC = 0
Success in sending message type as pldm to mctp : RC = 0
Write to socket successful : RC = 11
Total length:11
Loopback response message:
08 01 9b 00 03 00 00 00 00 01 00
On first recv(),response == request : RC = 0
Total length: 15
Shutdown Socket successful : RC = 0
Socket recv() successful : RC = 0
Response Message:
08 01 00 00 03 00 00 00 00 00 05 f1 f0 f0 00
./pldmtool -h
PLDM requester tool for OpenBMC
Usage: ./pldmtool [OPTIONS] —command... [GetPLDMTypes] [GetPLDMVersion] SUBCOMMA ND
Positionals:
—command TEXT ... REQUIRED
PLDM request command
GetPLDMTypes TEXT Get PLDM Type
GetPLDMVersion TEXT Get PLDM Version
Options:
-h,--help Print this help message and exit
-c TEXT ... REQUIRED PLDM request command
Subcommands:
BASE PLDM Command Type = BASE
BIOS PLDM Command Type = BIOS
OEM PLDM Command Type = OEM
Signed-off-by: Lakshminarayana R. Kammath <lkammath@in.ibm.com>
Change-Id: I758b5f5cf03ad9b91ce47144fe46cd79b41381f3
diff --git a/tool/pldm_base_cmd.cpp b/tool/pldm_base_cmd.cpp
new file mode 100644
index 0000000..aa5b668
--- /dev/null
+++ b/tool/pldm_base_cmd.cpp
@@ -0,0 +1,134 @@
+#include "pldm_base_cmd.hpp"
+
+#include "pldm_cmd_helper.hpp"
+
+#include <string>
+
+constexpr uint8_t PLDM_ENTITY_ID = 8;
+constexpr uint8_t MCTP_MSG_TYPE_PLDM = 1;
+constexpr uint8_t PLDM_LOCAL_INSTANCE_ID = 0;
+
+using namespace std;
+
+/*
+ * Main function that handles the GetPLDMTypes response callback via mctp
+ *
+ */
+void getPLDMTypes(vector<std::string>&& args)
+{
+ // Create and encode the request message
+ vector<uint8_t> requestMsg(sizeof(pldm_msg_hdr) +
+ sizeof(MCTP_MSG_TYPE_PLDM) +
+ sizeof(PLDM_ENTITY_ID));
+ auto request = reinterpret_cast<pldm_msg*>(requestMsg.data());
+
+ // Encode the get_types request message
+ uint8_t instanceId = PLDM_LOCAL_INSTANCE_ID;
+ auto returnCode = encode_get_types_req(instanceId, request);
+ if (returnCode)
+ {
+ cerr << "Failed to encode request msg for GetPLDMType : RC = "
+ << returnCode << endl;
+ return;
+ }
+ cout << "Encoded request succesfully : RC = " << returnCode << endl;
+
+ // Insert the PLDM message type and EID at the begining of the request msg.
+ requestMsg.insert(requestMsg.begin(), MCTP_MSG_TYPE_PLDM);
+ requestMsg.insert(requestMsg.begin(), PLDM_ENTITY_ID);
+
+ cout << "Request Message:" << endl;
+ printBuffer(requestMsg);
+
+ // Create the response message
+ vector<uint8_t> responseMsg;
+
+ // Compares the response with request packet on first socket recv() call.
+ // If above condition is qualified then, reads the actual response from
+ // the socket to output buffer responseMsg.
+ returnCode = mctpSockSendRecv(requestMsg, responseMsg);
+ if (!returnCode)
+ {
+ cout << "Socket recv() successful : RC = " << returnCode << endl;
+ cout << "Response Message : " << endl;
+ printBuffer(responseMsg);
+ }
+ else
+ {
+ cerr << "Failed to recieve from socket : RC = " << returnCode << endl;
+ return;
+ }
+}
+
+/*
+ * Main function that handles the GetPLDMVersion response callback via mctp
+ *
+ */
+void getPLDMVersion(vector<std::string>&& args)
+{
+ // Create a request packet
+ std::vector<uint8_t> requestMsg(sizeof(pldm_msg_hdr) +
+ PLDM_GET_VERSION_REQ_BYTES);
+ auto request = reinterpret_cast<pldm_msg*>(requestMsg.data());
+ uint8_t pldmType = 0x0;
+
+ if (!args[1].c_str())
+ {
+ cout << "Mandatory argument PLDM Command Type not provided!" << endl;
+ cout << "Run pldmtool --help for more information" << endl;
+ return;
+ }
+
+ if (!strcasecmp(args[1].c_str(), "base"))
+ {
+ cout << "PLDM Type requested : " << args[1] << endl;
+ pldmType = PLDM_BASE;
+ }
+ else
+ {
+ cerr << "Unsupported pldm command type OR not supported yet : "
+ << args[1] << endl;
+ return;
+ }
+
+ uint8_t instanceId = PLDM_LOCAL_INSTANCE_ID;
+ uint32_t transferHandle = 0x0;
+ transfer_op_flag opFlag = PLDM_GET_FIRSTPART;
+
+ // encode the get_version request
+ auto returnCode = encode_get_version_req(instanceId, transferHandle, opFlag,
+ pldmType, request);
+ if (returnCode)
+ {
+ cerr << "Failed to encode request msg for GetPLDMVersion. RC = "
+ << returnCode << endl;
+ return;
+ }
+ cout << "Encoded request succesfully : RC = " << returnCode << endl;
+
+ // Insert the PLDM message type and EID at the begining of the request msg.
+ requestMsg.insert(requestMsg.begin(), MCTP_MSG_TYPE_PLDM);
+ requestMsg.insert(requestMsg.begin(), PLDM_ENTITY_ID);
+
+ cout << "Request Message:" << endl;
+ printBuffer(requestMsg);
+
+ // Create the response message
+ vector<uint8_t> responseMsg;
+
+ // Compares the response with request packet on first socket recv() call.
+ // If above condition is qualified then, reads the actual response from
+ // the socket to output buffer responseMsg.
+ returnCode = mctpSockSendRecv(requestMsg, responseMsg);
+ if (!returnCode)
+ {
+ cout << "Socket recv() successful : RC = " << returnCode << endl;
+ cout << "Response Message:" << endl;
+ printBuffer(responseMsg);
+ }
+ else
+ {
+ cerr << "Failed to recieve from socket : RC = " << returnCode << endl;
+ return;
+ }
+}