Fix for mapper errors during logging service restart

There was a race condition while calling mapper from led monitoring after
error logs started persisting, to avoid such errors the callout information is
now extracted from the message received as part of interface added signal.

Resolves openbmc/openbmc#1853

Change-Id: Ie913992bdcb3b1cb93677d64331db34202f8ae72
Signed-off-by: Dhruvaraj Subhashchandran <dhruvaraj@in.ibm.com>
diff --git a/elog-errors.hpp b/elog-errors.hpp
index 1cc6f4a..95c80e7 100644
--- a/elog-errors.hpp
+++ b/elog-errors.hpp
@@ -9,28 +9,6 @@
 #include <phosphor-logging/log.hpp>
 #include <phosphor-logging/elog.hpp>
 
-namespace sdbusplus
-{
-namespace xyz
-{
-namespace openbmc_project
-{
-namespace Led
-{
-namespace Fru
-{
-namespace Monitor
-{
-namespace Error
-{
-    struct AssociationRetrieveError;
-} // namespace Error
-} // namespace Monitor
-} // namespace Fru
-} // namespace Led
-} // namespace openbmc_project
-} // namespace xyz
-} // namespace sdbusplus
 
 namespace sdbusplus
 {
@@ -174,72 +152,6 @@
 {
 namespace Led
 {
-namespace Fru
-{
-namespace Monitor
-{
-namespace _AssociationRetrieveError
-{
-
-struct ELOG_ENTRY_PATH
-{
-    static constexpr auto str = "ELOG_ENTRY_PATH=%s";
-    static constexpr auto str_short = "ELOG_ENTRY_PATH";
-    using type = std::tuple<std::decay_t<decltype(str)>,const char*>;
-    explicit constexpr ELOG_ENTRY_PATH(const char* a) : _entry(entry(str, a)) {};
-    type _entry;
-};
-
-}  // namespace _AssociationRetrieveError
-
-struct AssociationRetrieveError : public sdbusplus::exception_t
-{
-    static constexpr auto errName = "xyz.openbmc_project.Led.Fru.Monitor.AssociationRetrieveError";
-    static constexpr auto errDesc = "Error in retrieving the associations from elog entry.";
-    static constexpr auto L = level::INFO;
-    using ELOG_ENTRY_PATH = _AssociationRetrieveError::ELOG_ENTRY_PATH;
-    using metadata_types = std::tuple<ELOG_ENTRY_PATH>;
-
-    const char* name() const noexcept
-    {
-        return errName;
-    }
-
-    const char* description() const noexcept
-    {
-        return errDesc;
-    }
-
-    const char* what() const noexcept
-    {
-        return errName;
-    }
-};
-
-} // namespace Monitor
-} // namespace Fru
-} // namespace Led
-} // namespace openbmc_project
-} // namespace xyz
-
-
-namespace details
-{
-
-template <>
-struct map_exception_type<sdbusplus::xyz::openbmc_project::Led::Fru::Monitor::Error::AssociationRetrieveError>
-{
-    using type = xyz::openbmc_project::Led::Fru::Monitor::AssociationRetrieveError;
-};
-
-}
-
-namespace xyz
-{
-namespace openbmc_project
-{
-namespace Led
-{
 namespace Mapper
 {
 namespace _MethodError
diff --git a/fault-monitor/fru-fault-monitor.cpp b/fault-monitor/fru-fault-monitor.cpp
index 8bf27f2..dc2f231 100644
--- a/fault-monitor/fru-fault-monitor.cpp
+++ b/fault-monitor/fru-fault-monitor.cpp
@@ -26,13 +26,17 @@
 
 using AssociationList = std::vector<std::tuple<
                         std::string, std::string, std::string>>;
+using Attributes = sdbusplus::message::variant<bool,AssociationList>;
+using AttributeName = std::string;
+using AttributeMap = std::map<AttributeName, Attributes>;
+using PropertyName = std::string;
+using PropertyMap = std::map<PropertyName, AttributeMap>;
+using LogEntryMsg = std::pair<sdbusplus::message::object_path, PropertyMap>;
+
 using MethodErr  =
     sdbusplus::xyz::openbmc_project::Led::Mapper::Error::MethodError;
 using ObjectNotFoundErr =
     sdbusplus::xyz::openbmc_project::Led::Mapper::Error::ObjectNotFoundError;
-using AssociationRetrieveErr =
-    sdbusplus::xyz::openbmc_project::
-    Led::Fru::Monitor::Error::AssociationRetrieveError;
 using InventoryPathErr =
     sdbusplus::xyz::openbmc_project::
     Led::Fru::Monitor::Error::InventoryPathError;
@@ -121,9 +125,9 @@
 {
     auto bus = msg.get_bus();
 
-    sdbusplus::message::object_path obPath;
-    msg.read(obPath);
-    std::string objectPath(std::move(obPath));
+    LogEntryMsg logEntry;
+    msg.read(logEntry);
+    std::string objectPath(std::move(logEntry.first));
 
     std::size_t found = objectPath.find(ELOG_ENTRY);
     if (found == std::string::npos)
@@ -131,44 +135,22 @@
         //Not a new error entry skip
         return;
     }
+    log<level::ERR>(objectPath.c_str());
 
-    std::string service;
-    try
+    auto iter = logEntry.second.find("org.openbmc.Associations");
+    if (iter == logEntry.second.end())
     {
-        service = getService(bus, LOG_PATH);
-    }
-    catch (MethodErr& e)
-    {
-        commit<MethodErr>();
-        return;
-    }
-    catch (ObjectNotFoundErr& e)
-    {
-        commit<ObjectNotFoundErr>();
         return;
     }
 
-    auto method =  bus.new_method_call(service.c_str(), objectPath.c_str(),
-                                       "org.freedesktop.DBus.Properties",
-                                       "Get");
-
-    method.append("org.openbmc.Associations");
-    method.append("associations");
-    auto reply = bus.call(method);
-    if (reply.is_method_error())
+    auto attr = iter->second.find("associations");
+    if (attr == iter->second.end())
     {
-        using namespace xyz::openbmc_project::Led::Fru::Monitor;
-        report<AssociationRetrieveErr>(
-            AssociationRetrieveError::ELOG_ENTRY_PATH(
-                objectPath.c_str()));
         return;
     }
 
-    sdbusplus::message::variant<AssociationList> assoc;
-    reply.read(assoc);
-
-    auto assocs =
-        sdbusplus::message::variant_ns::get<AssociationList>(assoc);
+    auto& assocs =
+        sdbusplus::message::variant_ns::get<AssociationList>(attr->second);
     if (assocs.empty())
     {
         //No associations skip
@@ -181,9 +163,10 @@
         {
             action(bus, std::get<2>(item), true);
             removeWatches.emplace_back(
-                    std::make_unique<Remove>(bus, std::get<2>(item)));
+                std::make_unique<Remove>(bus, std::get<2>(item)));
         }
     }
+
     return;
 }
 
diff --git a/xyz/openbmc_project/Led/Fru/Monitor.errors.yaml b/xyz/openbmc_project/Led/Fru/Monitor.errors.yaml
index bb77f45..e949513 100644
--- a/xyz/openbmc_project/Led/Fru/Monitor.errors.yaml
+++ b/xyz/openbmc_project/Led/Fru/Monitor.errors.yaml
@@ -1,7 +1,3 @@
 #xyz.openbmc_project.Led.Fru.Monitor.InventoryPathError
 - name: InventoryPathError
   description: Invalid Inventory Path.
-
-#xyz.openbmc_project.Led.Fru.Monitor.AssociationRetrieveError
-- name: AssociationRetrieveError
-  description: Error in retrieving the associations from elog entry.
diff --git a/xyz/openbmc_project/Led/Fru/Monitor.metadata.yaml b/xyz/openbmc_project/Led/Fru/Monitor.metadata.yaml
index bd59e5f..57e0fd5 100644
--- a/xyz/openbmc_project/Led/Fru/Monitor.metadata.yaml
+++ b/xyz/openbmc_project/Led/Fru/Monitor.metadata.yaml
@@ -2,8 +2,3 @@
   meta:
     - str: "PATH=%s"
       type: string
-
-- name: AssociationRetrieveError
-  meta:
-    - str: "ELOG_ENTRY_PATH=%s"
-      type: string