host-bmc: Process host TL PDR

Process host TL PDR and build TLPDRMap for easy lookup based on
PLDMTerminusHandle, the parsing of the host state sensors is done
after the TL PDR's are processed.

Tested:

Tested on Rainier simics and sensor event from host is handled
and the D-Bus object is updated.

Change-Id: I3b5903c4e6a071465ac84cedb9723019dc6d06fa
Signed-off-by: Tom Joseph <tomjoseph@in.ibm.com>
Signed-off-by: Sampa Misra <sampmisr@in.ibm.com>
diff --git a/host-bmc/host_pdr_handler.cpp b/host-bmc/host_pdr_handler.cpp
index f8594d6..31065a4 100644
--- a/host-bmc/host_pdr_handler.cpp
+++ b/host-bmc/host_pdr_handler.cpp
@@ -106,6 +106,8 @@
                                     PLDM_GET_PDR_REQ_BYTES);
     auto request = reinterpret_cast<pldm_msg*>(requestMsg.data());
     bool merged = false;
+    PDRList stateSensorPDRs{};
+    TLPDRMap tlpdrInfo{};
 
     uint32_t nextRecordHandle{};
     uint32_t recordHandle{};
@@ -189,16 +191,19 @@
                 }
                 else
                 {
-                    if (pdrHdr->type == PLDM_STATE_SENSOR_PDR)
+                    if (pdrHdr->type == PLDM_TERMINUS_LOCATOR_PDR)
                     {
-                        const auto& [terminusHandle, sensorID, sensorInfo] =
-                            responder::pdr_utils::parseStateSensorPDR(pdr);
-                        SensorEntry sensorEntry{};
-                        // TODO: Lookup Terminus ID from the Terminus Locator
-                        // PDR with terminusHandle
-                        sensorEntry.terminusID = 0;
-                        sensorEntry.sensorID = sensorID;
-                        sensorMap.emplace(sensorEntry, std::move(sensorInfo));
+                        auto tlpdr =
+                            reinterpret_cast<const pldm_terminus_locator_pdr*>(
+                                pdr.data());
+                        tlpdrInfo.emplace(
+                            static_cast<pdr::TerminusHandle>(
+                                tlpdr->terminus_handle),
+                            static_cast<pdr::TerminusID>(tlpdr->tid));
+                    }
+                    else if (pdrHdr->type == PLDM_STATE_SENSOR_PDR)
+                    {
+                        stateSensorPDRs.emplace_back(pdr);
                     }
                     pldm_pdr_add(repo, pdr.data(), respCount, 0, true);
                 }
@@ -217,6 +222,8 @@
         }
     } while (recordHandle);
 
+    parseStateSensorPDRs(stateSensorPDRs, tlpdrInfo);
+
     if (merged)
     {
         // We have merged host's entity association PDRs with our own. Send an
@@ -371,4 +378,27 @@
     }
 }
 
+void HostPDRHandler::parseStateSensorPDRs(const PDRList& stateSensorPDRs,
+                                          const TLPDRMap& tlpdrInfo)
+{
+    for (const auto& pdr : stateSensorPDRs)
+    {
+        SensorEntry sensorEntry{};
+        const auto& [terminusHandle, sensorID, sensorInfo] =
+            responder::pdr_utils::parseStateSensorPDR(pdr);
+        sensorEntry.sensorID = sensorID;
+        try
+        {
+            sensorEntry.terminusID = tlpdrInfo.at(terminusHandle);
+        }
+        // If there is no mapping for terminusHandle assign the reserved TID
+        // value of 0xFF to indicate that.
+        catch (const std::out_of_range& e)
+        {
+            sensorEntry.terminusID = PLDM_TID_RESERVED;
+        }
+        sensorMap.emplace(sensorEntry, std::move(sensorInfo));
+    }
+}
+
 } // namespace pldm