platform-mc: Support multi-handlers for polled events

platform-mc only supports one event handler for the polled events.
Update the code to allow multiple event handlers.

Change-Id: Icfb531ce89a49bb417ca94bd608442f9323810b4
Signed-off-by: Thu Nguyen <thu@os.amperecomputing.com>
diff --git a/oem/ampere/oem_ampere.hpp b/oem/ampere/oem_ampere.hpp
index 8fb926e..d054175 100644
--- a/oem/ampere/oem_ampere.hpp
+++ b/oem/ampere/oem_ampere.hpp
@@ -101,11 +101,11 @@
         /* Support handle the polled event with Ampere OEM CPER event class */
         platformManager->registerPolledEventHandler(
             0xFA,
-            [platformManager](pldm_tid_t tid, uint16_t eventId,
-                              const uint8_t* eventData, size_t eventDataSize) {
+            {[platformManager](pldm_tid_t tid, uint16_t eventId,
+                               const uint8_t* eventData, size_t eventDataSize) {
                 return platformManager->handlePolledCperEvent(
                     tid, eventId, eventData, eventDataSize);
-            });
+            }});
     }
 
   private:
diff --git a/platform-mc/event_manager.cpp b/platform-mc/event_manager.cpp
index 139438b..80ee6fc 100644
--- a/platform-mc/event_manager.cpp
+++ b/platform-mc/event_manager.cpp
@@ -518,6 +518,33 @@
     return PLDM_SUCCESS;
 }
 
+void EventManager::callPolledEventHandlers(pldm_tid_t tid, uint8_t eventClass,
+                                           uint16_t eventId,
+                                           std::vector<uint8_t>& eventMessage)
+{
+    try
+    {
+        const auto& handlers = eventHandlers.at(eventClass);
+        for (const auto& handler : handlers)
+        {
+            auto rc =
+                handler(tid, eventId, eventMessage.data(), eventMessage.size());
+            if (rc != PLDM_SUCCESS)
+            {
+                lg2::error(
+                    "Failed to handle platform event msg for terminus {TID}, event {EVENTID} return {RET}",
+                    "TID", tid, "EVENTID", eventId, "RET", rc);
+            }
+        }
+    }
+    catch (const std::out_of_range& e)
+    {
+        lg2::error(
+            "Failed to handle platform event msg for terminus {TID}, event {EVENTID} error - {ERROR}",
+            "TID", tid, "EVENTID", eventId, "ERROR", e);
+    }
+}
+
 exec::task<int> EventManager::pollForPlatformEventTask(
     pldm_tid_t tid, uint32_t pollDataTransferHandle)
 {
@@ -582,9 +609,8 @@
             /* Handle the polled event after finish ACK it */
             if (eventHandlers.contains(polledEventClass))
             {
-                eventHandlers.at(
-                    polledEventClass)(polledEventTid, polledEventId,
-                                      eventMessage.data(), eventMessage.size());
+                callPolledEventHandlers(polledEventTid, polledEventClass,
+                                        polledEventId, eventMessage);
             }
             eventMessage.clear();
 
diff --git a/platform-mc/event_manager.hpp b/platform-mc/event_manager.hpp
index 08ec3bc..21199e0 100644
--- a/platform-mc/event_manager.hpp
+++ b/platform-mc/event_manager.hpp
@@ -19,7 +19,8 @@
 using HandlerFunc =
     std::function<int(pldm_tid_t tid, uint16_t eventId,
                       const uint8_t* eventData, size_t eventDataSize)>;
-using EventMap = std::map<EventType, HandlerFunc>;
+using HandlerFuncs = std::vector<HandlerFunc>;
+using EventMap = std::map<EventType, HandlerFuncs>;
 
 /**
  * @brief EventManager
@@ -46,19 +47,19 @@
         // Default response handler for PollForPlatFormEventMessage
         registerPolledEventHandler(
             PLDM_MESSAGE_POLL_EVENT,
-            [this](pldm_tid_t tid, uint16_t eventId, const uint8_t* eventData,
-                   size_t eventDataSize) {
+            {[this](pldm_tid_t tid, uint16_t eventId, const uint8_t* eventData,
+                    size_t eventDataSize) {
                 return this->handlePlatformEvent(tid, eventId,
                                                  PLDM_MESSAGE_POLL_EVENT,
                                                  eventData, eventDataSize);
-            });
+            }});
         registerPolledEventHandler(
             PLDM_CPER_EVENT,
-            [this](pldm_tid_t tid, uint16_t eventId, const uint8_t* eventData,
-                   size_t eventDataSize) {
+            {[this](pldm_tid_t tid, uint16_t eventId, const uint8_t* eventData,
+                    size_t eventDataSize) {
                 return this->handlePlatformEvent(tid, eventId, PLDM_CPER_EVENT,
                                                  eventData, eventDataSize);
-            });
+            }});
     };
 
     /** @brief Handle platform event
@@ -111,9 +112,15 @@
      *         PollForPlatFormEventMessage
      */
     void registerPolledEventHandler(uint8_t eventClass,
-                                    pldm::platform_mc::HandlerFunc function)
+                                    pldm::platform_mc::HandlerFuncs handlers)
     {
-        eventHandlers.insert_or_assign(eventClass, std::move(function));
+        auto [iter, inserted] = eventHandlers.try_emplace(
+            eventClass, pldm::platform_mc::HandlerFuncs{});
+
+        for (const auto& handler : handlers)
+        {
+            iter->second.emplace_back(handler);
+        }
     }
 
   protected:
@@ -202,6 +209,18 @@
         uint32_t nextDataTransferHandle, uint8_t* transferOperationFlag,
         uint32_t* dataTransferHandle, uint32_t* eventIdToAcknowledge);
 
+    /** @brief Helper function to call the event handler for polled events
+     *
+     *  @param[in] tid - terminus ID
+     *  @param[out] eventClass - Event class
+     *  @param[out] eventId - Event ID
+     *  @param[in] eventMessage - event data of response message
+     *
+     */
+    void callPolledEventHandlers(pldm_tid_t tid, uint8_t eventClass,
+                                 uint16_t eventId,
+                                 std::vector<uint8_t>& eventMessage);
+
     /** @brief Reference of terminusManager */
     TerminusManager& terminusManager;
 
diff --git a/platform-mc/manager.hpp b/platform-mc/manager.hpp
index 7def32b..29d924a 100644
--- a/platform-mc/manager.hpp
+++ b/platform-mc/manager.hpp
@@ -204,10 +204,9 @@
      *
      */
     void registerPolledEventHandler(uint8_t eventClass,
-                                    pldm::platform_mc::HandlerFunc handlerFunc)
+                                    pldm::platform_mc::HandlerFuncs handlers)
     {
-        eventManager.registerPolledEventHandler(eventClass,
-                                                std::move(handlerFunc));
+        eventManager.registerPolledEventHandler(eventClass, handlers);
     }
 
   private: