Simplified Guard class and supporting functions

Signed-off-by: Zane Shelley <zshelle@us.ibm.com>
Change-Id: I7a4b2298198c7aa9434c08dfa949081ed6437a53
diff --git a/analyzer/analyzer_main.cpp b/analyzer/analyzer_main.cpp
index c8de857..05d9f42 100644
--- a/analyzer/analyzer_main.cpp
+++ b/analyzer/analyzer_main.cpp
@@ -162,7 +162,7 @@
                    util::pdbg::getPath(rootCause.getChip()),
                    rootCause.toUint32(), __attn(rootCause.getAttnType()));
 
-        // Perform service actions based on the root cause.
+        // Resolve any service actions required by the root cause.
         RasDataParser rasData{};
         ServiceData servData{rootCause, isoData.queryCheckstop()};
         rasData.getResolution(rootCause)->resolve(servData);
@@ -170,7 +170,19 @@
         // Create and commit a PEL.
         uint32_t logId = std::get<1>(createPel(isoData, servData));
 
-        // Populate dump parameters
+        // Write guard records to persistent storage.
+        // TODO: The PEL ID will be required, but interface is still unknown.
+        for (const auto& guard : servData.getGuardList())
+        {
+            guard.apply();
+        }
+
+        // Gather/return information needed for dump.
+        // TODO: Need ID from root cause. At the moment, HUID does not exist in
+        //       devtree. Will need a better ID definition.
+        // TODO: HW dump is default, but some attentions may require something
+        //       different. Will need to investigate adding that information to
+        //       the RAS data files.
         o_dumpParameters.logId    = logId;
         o_dumpParameters.unitId   = 0;
         o_dumpParameters.dumpType = attn::DumpType::Hardware;
diff --git a/analyzer/create_pel.cpp b/analyzer/create_pel.cpp
index 2106b36..558af52 100644
--- a/analyzer/create_pel.cpp
+++ b/analyzer/create_pel.cpp
@@ -27,7 +27,6 @@
 {
     FFDC_SIGNATURES    = 0x01,
     FFDC_REGISTER_DUMP = 0x02,
-    FFDC_GUARD         = 0x03,
 
     // For the callout section, the value of '0xCA' is required per the
     // phosphor-logging openpower-pel extention spec.
@@ -95,24 +94,6 @@
 
 //------------------------------------------------------------------------------
 
-void __addGuardList(const ServiceData& i_servData,
-                    std::vector<util::FFDCFile>& io_userDataFiles)
-{
-    // Get the JSON output for the guard list.
-    nlohmann::json json;
-    i_servData.getGuardList(json);
-
-    // Create a new entry for the user data section containing the guard list.
-    io_userDataFiles.emplace_back(util::FFDCFormat::JSON, FFDC_GUARD,
-                                  FFDC_VERSION1);
-
-    // Use a file stream to write the JSON to file.
-    std::ofstream o{io_userDataFiles.back().getPath()};
-    o << json;
-}
-
-//------------------------------------------------------------------------------
-
 void __captureSignatureList(const libhei::IsolationData& i_isoData,
                             std::vector<util::FFDCFile>& io_userDataFiles)
 {
@@ -283,9 +264,6 @@
     // Add the list of callouts to the PEL.
     __addCalloutList(i_servData, userDataFiles);
 
-    // Add the list of guard requests to the PEL.
-    __addGuardList(i_servData, userDataFiles);
-
     // Capture the complete signature list.
     __captureSignatureList(i_isoData, userDataFiles);
 
diff --git a/analyzer/guard.cpp b/analyzer/guard.cpp
new file mode 100644
index 0000000..2acd2c1
--- /dev/null
+++ b/analyzer/guard.cpp
@@ -0,0 +1,17 @@
+#include <analyzer/guard.hpp>
+#include <util/trace.hpp>
+
+namespace analyzer
+{
+
+//------------------------------------------------------------------------------
+
+void Guard::apply() const
+{
+    // TODO
+    trace::err("Guard::apply() currently not supported");
+}
+
+//------------------------------------------------------------------------------
+
+} // namespace analyzer
diff --git a/analyzer/guard.hpp b/analyzer/guard.hpp
new file mode 100644
index 0000000..d3cabdd
--- /dev/null
+++ b/analyzer/guard.hpp
@@ -0,0 +1,60 @@
+#pragma once
+
+#include <map>
+#include <string>
+
+namespace analyzer
+{
+
+/**
+ * @brief A service event requiring hardware to be guarded.
+ */
+class Guard
+{
+  public:
+    /** Supported guard types. */
+    enum class Type
+    {
+        NONE,      ///< Do not guard
+        FATAL,     ///< Guard on fatal error (cannot recover resource)
+        NON_FATAL, ///< Guard on non-fatal error (can recover resource)
+    };
+
+  public:
+    /**
+     * @brief Constructor from components.
+     * @param i_path The hardware path to guard.
+     * @param i_type The guard type.
+     */
+    Guard(const std::string& i_path, Type i_type) :
+        iv_path(i_path), iv_type(i_type)
+    {}
+
+  private:
+    /** The hardware path to guard. */
+    const std::string iv_path;
+
+    /** The guard type. */
+    const Type iv_type;
+
+  public:
+    /** @brief Writes guard record to persistent storage. */
+    void apply() const;
+
+    /** @return A string representation of the guard type enum. */
+    std::string getString() const
+    {
+        // clang-format off
+        static const std::map<Type, std::string> m =
+        {
+            {Type::NONE,      "NONE"},
+            {Type::FATAL,     "FATAL"},
+            {Type::NON_FATAL, "NON_FATAL"},
+        };
+        // clang-format on
+
+        return m.at(iv_type);
+    }
+};
+
+} // namespace analyzer
diff --git a/analyzer/meson.build b/analyzer/meson.build
index ebeed4d..fe2858d 100644
--- a/analyzer/meson.build
+++ b/analyzer/meson.build
@@ -2,6 +2,7 @@
 analyzer_src = files(
     'analyzer_main.cpp',
     'create_pel.cpp',
+    'guard.cpp',
     'hei_user_interface.cpp',
     'initialize_isolator.cpp',
     'ras-data/ras-data-parser.cpp',
diff --git a/analyzer/resolution.cpp b/analyzer/resolution.cpp
index cce581f..fe407b6 100644
--- a/analyzer/resolution.cpp
+++ b/analyzer/resolution.cpp
@@ -23,8 +23,9 @@
         }
     }
 
-    // Get the location code for this target.
-    auto locCode = util::pdbg::getLocationCode(trgt);
+    // Get the location code and entity path for this target.
+    auto locCode    = util::pdbg::getLocationCode(trgt);
+    auto entityPath = util::pdbg::getPhysDevPath(trgt);
 
     // Add the actual callout to the service data.
     nlohmann::json callout;
@@ -32,22 +33,8 @@
     callout["Priority"]     = iv_priority.getUserDataString();
     io_sd.addCallout(callout);
 
-    // Add entity path to gard list.
-    auto entityPath = util::pdbg::getPhysDevPath(trgt);
-    if (entityPath.empty())
-    {
-        trace::err("Unable to find entity path for %s", path.c_str());
-    }
-    else
-    {
-        Guard::Type guard = Guard::NONE;
-        if (iv_guard)
-        {
-            guard = io_sd.queryCheckstop() ? Guard::FATAL : Guard::NON_FATAL;
-        }
-
-        io_sd.addGuard(std::make_shared<Guard>(entityPath, guard));
-    }
+    // Add the guard info to the service data.
+    io_sd.addGuard(entityPath, iv_guard);
 }
 
 //------------------------------------------------------------------------------
diff --git a/analyzer/service_data.hpp b/analyzer/service_data.hpp
index c9f9c41..3664550 100644
--- a/analyzer/service_data.hpp
+++ b/analyzer/service_data.hpp
@@ -1,6 +1,7 @@
 #pragma once
 
 #include <analyzer/callout.hpp>
+#include <analyzer/guard.hpp>
 #include <hei_main.hpp>
 #include <nlohmann/json.hpp>
 
@@ -8,54 +9,6 @@
 {
 
 /**
- * @brief A service event requiring hardware to be guarded.
- */
-class Guard
-{
-  public:
-    /** Supported guard types. */
-    enum Type
-    {
-        NONE,      ///< Do not guard
-        FATAL,     ///< Guard on fatal error (cannot recover resource)
-        NON_FATAL, ///< Guard on non-fatal error (can recover resource)
-    };
-
-  public:
-    /**
-     * @brief Constructor from components.
-     * @param i_path The hardware path to guard.
-     * @param i_type The guard type.
-     */
-    Guard(const std::string& i_path, Type i_type) :
-        iv_path(i_path), iv_type(i_type)
-    {}
-
-  private:
-    /** The hardware path to guard. */
-    const std::string iv_path;
-
-    /** The guard type. */
-    const Type iv_type;
-
-  public:
-    void getJson(nlohmann::json& j) const
-    {
-        // clang-format off
-        static const std::map<Type, std::string> m =
-        {
-            {NONE,      "NONE"},
-            {FATAL,     "FATAL"},
-            {NON_FATAL, "NON_FATAL"},
-        };
-        // clang-format on
-
-        nlohmann::json c = {{"Path", iv_path}, {"Type", m.at(iv_type)}};
-        j.emplace_back(c);
-    }
-};
-
-/**
  * @brief Data regarding required service actions based on the hardware error
  *        analysis.
  */
@@ -93,9 +46,9 @@
     nlohmann::json iv_calloutList = nlohmann::json::array();
 
     /** The list of hardware guard requests. Some information will be added to
-     * the PEL, but the actual guard record will be created after submitting the
-     * PEL. */
-    std::vector<std::shared_ptr<Guard>> iv_guardList;
+     *  the PEL, but the actual guard record will be created after submitting
+     *  the PEL. */
+    std::vector<Guard> iv_guardList;
 
   public:
     /** @return The signature of the root cause attention. */
@@ -120,10 +73,23 @@
         iv_calloutList.push_back(i_callout);
     }
 
-    /** Add a guard request to the list. */
-    void addGuard(const std::shared_ptr<Guard>& i_guard)
+    /**
+     * @brief  Add a guard request to the guard list.
+     * @param  i_path  Entity path for the target part.
+     * @param  i_guard True, if the part should be guarded. False, otherwise.
+     */
+    void addGuard(const std::string& i_path, bool i_guard)
     {
-        iv_guardList.push_back(i_guard);
+        Guard::Type guardType = Guard::Type::NONE;
+        if (i_guard)
+        {
+            // The guard type is dependent on the presence of a system checkstop
+            // attention.
+            guardType =
+                queryCheckstop() ? Guard::Type::FATAL : Guard::Type::NON_FATAL;
+        }
+
+        iv_guardList.emplace_back(i_path, guardType);
     }
 
     /** @brief Accessor to iv_calloutList. */
@@ -132,19 +98,10 @@
         return iv_calloutList;
     }
 
-    /**
-     * @brief Iterates the guard list and returns the json attached to each
-     *        guard request in the list.
-     * @param o_json The returned json data.
-     */
-    void getGuardList(nlohmann::json& o_json) const
+    /** @brief Accessor to iv_guardList. */
+    const std::vector<Guard>& getGuardList() const
     {
-        o_json.clear(); // Ensure we are starting with a clean list.
-
-        for (const auto& g : iv_guardList)
-        {
-            g->getJson(o_json);
-        }
+        return iv_guardList;
     }
 };