platform: Function to send the PDR Repo Change event to Host
The PDR Repository Change Event is sent to host informing that
the PDR repository has changed with either some new records added
or some records could have been deleted or some records could have
been modified.
This commit adds a new function to send the repository change event
to host with the changed record handles.
Change-Id: I95d922b81c79442e026a376697c9a044ebc3b30b
Signed-off-by: Pavithra Barithaya <pavithrabarithaya07@gmail.com>
diff --git a/libpldmresponder/platform.cpp b/libpldmresponder/platform.cpp
index 5ffc572..c1aab2b 100644
--- a/libpldmresponder/platform.cpp
+++ b/libpldmresponder/platform.cpp
@@ -1043,6 +1043,92 @@
}
}
+void Handler::sendPDRRepositoryChgEventbyPDRHandles(
+ const std::vector<ChangeEntry>& pdrRecordHandles,
+ const std::vector<uint8_t>& eventDataOps)
+{
+ uint8_t eventDataFormat = FORMAT_IS_PDR_HANDLES;
+ std::vector<uint8_t> numsOfChangeEntries(1);
+ std::vector<std::vector<ChangeEntry>> changeEntries(
+ numsOfChangeEntries.size());
+ for (auto pdrRecordHandle : pdrRecordHandles)
+ {
+ changeEntries[0].push_back(pdrRecordHandle);
+ }
+ if (changeEntries.empty())
+ {
+ return;
+ }
+ numsOfChangeEntries[0] = changeEntries[0].size();
+ size_t maxSize = PLDM_PDR_REPOSITORY_CHG_EVENT_MIN_LENGTH +
+ PLDM_PDR_REPOSITORY_CHANGE_RECORD_MIN_LENGTH +
+ changeEntries[0].size() * sizeof(uint32_t);
+ std::vector<uint8_t> eventDataVec{};
+ eventDataVec.resize(maxSize);
+ auto eventData =
+ reinterpret_cast<struct pldm_pdr_repository_chg_event_data*>(
+ eventDataVec.data());
+ size_t actualSize{};
+ auto firstEntry = changeEntries[0].data();
+ auto rc = encode_pldm_pdr_repository_chg_event_data(
+ eventDataFormat, 1, eventDataOps.data(), numsOfChangeEntries.data(),
+ &firstEntry, eventData, &actualSize, maxSize);
+ if (rc != PLDM_SUCCESS)
+ {
+ error(
+ "Failed to encode the repository change event data with response code '{RC}'",
+ "RC", static_cast<int>(rc));
+ return;
+ }
+ auto instanceId = instanceIdDb->next(eid);
+ std::vector<uint8_t> requestMsg(
+ sizeof(pldm_msg_hdr) + PLDM_PLATFORM_EVENT_MESSAGE_MIN_REQ_BYTES +
+ actualSize);
+ auto request = new (requestMsg.data()) pldm_msg;
+ rc = encode_platform_event_message_req(
+ instanceId, 1, TERMINUS_ID, PLDM_PDR_REPOSITORY_CHG_EVENT,
+ eventDataVec.data(), actualSize, request,
+ actualSize + PLDM_PLATFORM_EVENT_MESSAGE_MIN_REQ_BYTES);
+ if (rc != PLDM_SUCCESS)
+ {
+ instanceIdDb->free(eid, instanceId);
+ error(
+ "Failed to encode the platform event message with response code '{RC}'",
+ "RC", static_cast<unsigned>(rc));
+ return;
+ }
+ auto platformEventMessageResponseHandler = [](mctp_eid_t /*eid*/,
+ const pldm_msg* response,
+ size_t respMsgLen) {
+ if (response == nullptr || !respMsgLen)
+ {
+ error(
+ "Failed to receive response for the PDR repository changed event");
+ return;
+ }
+ uint8_t completionCode{};
+ uint8_t status{};
+ auto responsePtr = reinterpret_cast<const struct pldm_msg*>(response);
+ auto rc = decode_platform_event_message_resp(responsePtr, respMsgLen,
+ &completionCode, &status);
+ if (rc || completionCode)
+ {
+ error(
+ "Failed to decode platform event message with response code '{RC}' and completion code '{CC}'",
+ "RC", static_cast<int>(rc), "CC",
+ static_cast<unsigned>(completionCode));
+ }
+ };
+ rc = handler->registerRequest(
+ eid, instanceId, PLDM_PLATFORM, PLDM_PLATFORM_EVENT_MESSAGE,
+ std::move(requestMsg), std::move(platformEventMessageResponseHandler));
+ if (rc)
+ {
+ error(
+ "Failed to send the PDR repository changed event request after CM");
+ }
+}
+
} // namespace platform
} // namespace responder
} // namespace pldm
diff --git a/libpldmresponder/platform.hpp b/libpldmresponder/platform.hpp
index 8d7a55e..8b9684a 100644
--- a/libpldmresponder/platform.hpp
+++ b/libpldmresponder/platform.hpp
@@ -46,6 +46,8 @@
using EventMap = std::map<EventType, EventHandlers>;
using AssociatedEntityMap = std::map<DbusPath, pldm_entity>;
+using ChangeEntry = uint32_t;
+
class Handler : public CmdHandler
{
public:
@@ -512,6 +514,17 @@
/** @brief Method for setEventreceiver */
void setEventReceiver();
+ /* @brief Send a PLDM event to host firmware containing a list of record
+ * handles of PDRs that the host firmware has to fetch.
+ *
+ * @param[in] pdrRecordHandles - list of PDR record handles
+ * @param[in] eventDataOps - event data operation for PDRRepositoryChgEvent
+ * as in DSP0248 SPEC
+ */
+ void sendPDRRepositoryChgEventbyPDRHandles(
+ const std::vector<uint32_t>& pdrRecordHandles,
+ const std::vector<uint8_t>& eventDataOps);
+
private:
uint8_t eid;
InstanceIdDb* instanceIdDb;