Add a termination error display option in peltool

By using the new parameter -t, peltool will display only
termination errors,it will show from 1 to x termination
errors as they exist in the log.

Signed-off-by: Miguel Gomez <mgomez@mx1.ibm.com>
Change-Id: Ib14f569028ef95725076829e7fd7c455c630e8d1
diff --git a/extensions/openpower-pels/tools/peltool.cpp b/extensions/openpower-pels/tools/peltool.cpp
index 427216a..7d0842f 100644
--- a/extensions/openpower-pels/tools/peltool.cpp
+++ b/extensions/openpower-pels/tools/peltool.cpp
@@ -41,6 +41,8 @@
 namespace message = openpower::pels::message;
 namespace pv = openpower::pels::pel_values;
 
+const uint8_t critSysTermSeverity = 0x51;
+
 using PELFunc = std::function<void(const PEL&, bool hexDump)>;
 message::Registry registry(getPELReadOnlyDataPath() / message::registryFileName,
                            false);
@@ -267,6 +269,8 @@
  * @param[in] itr - std::map iterator of <uint32_t, BCDTime>
  * @param[in] hidden - Boolean to include hidden PELs
  * @param[in] includeInfo - Boolean to include informational PELs
+ * @param[in] critSysTerm - Boolean to include critical error and system
+ * termination PELs
  * @param[in] fullPEL - Boolean to print full JSON representation of PEL
  * @param[in] foundPEL - Boolean to check if any PEL is present
  * @param[in] scrubRegex - SRC regex object
@@ -275,8 +279,8 @@
  * @return std::string - JSON string of PEL entry (empty if fullPEL is true)
  */
 template <typename T>
-std::string genPELJSON(T itr, bool hidden, bool includeInfo, bool fullPEL,
-                       bool& foundPEL,
+std::string genPELJSON(T itr, bool hidden, bool includeInfo, bool critSysTerm,
+                       bool fullPEL, bool& foundPEL,
                        const std::optional<std::regex>& scrubRegex,
                        const std::vector<std::string>& plugins, bool hexDump)
 {
@@ -309,6 +313,10 @@
         {
             return listStr;
         }
+        if (critSysTerm && pel.userHeader().severity() != critSysTermSeverity)
+        {
+            return listStr;
+        }
         std::bitset<16> actionFlags{pel.userHeader().actionFlags()};
         if (!hidden && actionFlags.test(hiddenFlagBit))
         {
@@ -422,12 +430,15 @@
  * @param[in] order - Boolean to print in reverse orser
  * @param[in] hidden - Boolean to include hidden PELs
  * @param[in] includeInfo - Boolean to include informational PELs
+ * @param[in] critSysTerm - Boolean to include critical error and system
+ * termination PELs
  * @param[in] fullPEL - Boolean to print full PEL into a JSON array
  * @param[in] scrubRegex - SRC regex object
  * @param[in] hexDump - Boolean to print hexdump of PEL instead of JSON
  */
-void printPELs(bool order, bool hidden, bool includeInfo, bool fullPEL,
-               const std::optional<std::regex>& scrubRegex, bool hexDump)
+void printPELs(bool order, bool hidden, bool includeInfo, bool critSysTerm,
+               bool fullPEL, const std::optional<std::regex>& scrubRegex,
+               bool hexDump)
 {
     std::string listStr;
     std::map<uint32_t, BCDTime> PELs;
@@ -452,10 +463,11 @@
     {
         plugins = getPlugins();
     }
-    auto buildJSON = [&listStr, &hidden, &includeInfo, &fullPEL, &foundPEL,
-                      &scrubRegex, &plugins, &hexDump](const auto& i) {
-        listStr += genPELJSON(i, hidden, includeInfo, fullPEL, foundPEL,
-                              scrubRegex, plugins, hexDump);
+    auto buildJSON = [&listStr, &hidden, &includeInfo, &critSysTerm, &fullPEL,
+                      &foundPEL, &scrubRegex, &plugins,
+                      &hexDump](const auto& i) {
+        listStr += genPELJSON(i, hidden, includeInfo, critSysTerm, fullPEL,
+                              foundPEL, scrubRegex, plugins, hexDump);
     };
     if (order)
     {
@@ -643,9 +655,10 @@
  * @brief Print number of PELs
  * @param[in] hidden - Bool to include hidden logs
  * @param[in] includeInfo - Bool to include informational logs
+ * @param[in] critSysTerm - Bool to include CritSysTerm
  * @param[in] scrubRegex - SRC regex object
  */
-void printPELCount(bool hidden, bool includeInfo,
+void printPELCount(bool hidden, bool includeInfo, bool critSysTerm,
                    const std::optional<std::regex>& scrubRegex)
 {
     std::size_t count = 0;
@@ -670,6 +683,10 @@
         {
             continue;
         }
+        if (critSysTerm && pel.userHeader().severity() != critSysTermSeverity)
+        {
+            continue;
+        }
         std::bitset<16> actionFlags{pel.userHeader().actionFlags()};
         if (!hidden && actionFlags.test(hiddenFlagBit))
         {
@@ -786,6 +803,7 @@
     bool listPELDescOrd = false;
     bool hidden = false;
     bool includeInfo = false;
+    bool critSysTerm = false;
     bool deleteAll = false;
     bool showPELCount = false;
     bool fullPEL = false;
@@ -802,6 +820,8 @@
     app.add_flag("-r", listPELDescOrd, "Reverse order of output");
     app.add_flag("-h", hidden, "Include hidden PELs");
     app.add_flag("-f,--info", includeInfo, "Include informational PELs");
+    app.add_flag("-t, --termination", critSysTerm,
+                 "List only critical system terminating PELs");
     app.add_option("-d, --delete", idToDelete, "Delete a PEL based on its ID");
     app.add_flag("-D, --delete-all", deleteAll, "Delete all PELs");
     app.add_option("-s, --scrub", scrubFile,
@@ -848,8 +868,8 @@
         {
             scrubRegex = genRegex(scrubFile);
         }
-        printPELs(listPELDescOrd, hidden, includeInfo, fullPEL, scrubRegex,
-                  hexDump);
+        printPELs(listPELDescOrd, hidden, includeInfo, critSysTerm, fullPEL,
+                  scrubRegex, hexDump);
     }
     else if (showPELCount)
     {
@@ -857,7 +877,7 @@
         {
             scrubRegex = genRegex(scrubFile);
         }
-        printPELCount(hidden, includeInfo, scrubRegex);
+        printPELCount(hidden, includeInfo, critSysTerm, scrubRegex);
     }
     else if (!idToDelete.empty())
     {