OpenPOWER: Limit User-Requested System Dumps
System dumps can be several gigabytes in size. To conserve space,
only one dump is stored at a time. When a new dump is requested,
the existing dump will be discarded while creating a new one.
In the case of system-generated dumps, which are triggered by
critical errors, it is permissible to initiate a new dump even
if an existing dump is already present in the host memory
This commit adds a restriction on initiating new user-requested system
dumps while a system dump is in progress or if one is already stored
in host memory.
New user-requested system dumps will be allowed once the existing
dump is deleted or offloaded.
This change applies only to user-requested dumps and does not impact
system generated dumps.
Test:
- Initiate system dump when another dump in progress and verified
a Unavailable was returned
- Force a system generated system dump when one dump is present
a Unavailable was returned
Signed-off-by: Dhruvaraj Subhashchandran <dhruvaraj@in.ibm.com>
Change-Id: I4598912b0761669859f84a43ab4c60f47664b1e6
diff --git a/dump-extensions/openpower-dumps/dump_manager_system.cpp b/dump-extensions/openpower-dumps/dump_manager_system.cpp
index fad4947..949c87c 100644
--- a/dump-extensions/openpower-dumps/dump_manager_system.cpp
+++ b/dump-extensions/openpower-dumps/dump_manager_system.cpp
@@ -4,6 +4,7 @@
#include "dump_utils.hpp"
#include "op_dump_consts.hpp"
+#include "op_dump_util.hpp"
#include "system_dump_entry.hpp"
#include "xyz/openbmc_project/Common/error.hpp"
@@ -140,6 +141,14 @@
lg2::warning(
"System dump accepts not more than 2 additional parameters");
}
+ using Unavailable =
+ sdbusplus::xyz::openbmc_project::Common::Error::Unavailable;
+
+ if (openpower::dump::util::isSystemDumpInProgress(bus))
+ {
+ lg2::error("Another dump in progress or available to offload");
+ elog<Unavailable>();
+ }
using NotAllowed =
sdbusplus::xyz::openbmc_project::Common::Error::NotAllowed;
diff --git a/dump-extensions/openpower-dumps/op_dump_util.cpp b/dump-extensions/openpower-dumps/op_dump_util.cpp
index e8b2497..c56b902 100644
--- a/dump-extensions/openpower-dumps/op_dump_util.cpp
+++ b/dump-extensions/openpower-dumps/op_dump_util.cpp
@@ -1,5 +1,6 @@
#include "op_dump_util.hpp"
+#include "dump_utils.hpp"
#include "xyz/openbmc_project/Common/error.hpp"
#include "xyz/openbmc_project/Dump/Create/error.hpp"
@@ -52,6 +53,60 @@
return isEnabled;
}
+BIOSAttrValueType readBIOSAttribute(const std::string& attrName,
+ sdbusplus::bus::bus& bus)
+{
+ std::tuple<std::string, BIOSAttrValueType, BIOSAttrValueType> attrVal;
+ auto method = bus.new_method_call(
+ "xyz.openbmc_project.BIOSConfigManager",
+ "/xyz/openbmc_project/bios_config/manager",
+ "xyz.openbmc_project.BIOSConfig.Manager", "GetAttribute");
+ method.append(attrName);
+ try
+ {
+ auto result = bus.call(method);
+ result.read(std::get<0>(attrVal), std::get<1>(attrVal),
+ std::get<2>(attrVal));
+ }
+ catch (const sdbusplus::exception::SdBusError& e)
+ {
+ lg2::error("Failed to read BIOS Attribute: {ATTRIBUTE_NAME}",
+ "ATTRIBUTE_NAME", attrName);
+ throw;
+ }
+ return std::get<1>(attrVal);
+}
+
+bool isSystemDumpInProgress(sdbusplus::bus::bus& bus)
+{
+ try
+ {
+ auto dumpInProgress = std::get<std::string>(
+ readBIOSAttribute("pvm_sys_dump_active"), bus);
+ if (dumpInProgress == "Enabled")
+ {
+ lg2::info("A system dump is already in progress");
+ return true;
+ }
+ }
+ catch (const std::bad_variant_access& ex)
+ {
+ lg2::error("Failed to read pvm_sys_dump_active property value due "
+ "to bad variant access error:{ERROR}",
+ "ERROR", ex);
+ return false;
+ }
+ catch (const std::exception& ex)
+ {
+ lg2::error("Failed to read pvm_sys_dump_active error:{ERROR}", "ERROR",
+ ex);
+ return false;
+ }
+
+ lg2::info("Another system dump is not in progress");
+ return false;
+}
+
} // namespace util
} // namespace dump
} // namespace openpower
diff --git a/dump-extensions/openpower-dumps/op_dump_util.hpp b/dump-extensions/openpower-dumps/op_dump_util.hpp
index 80c84a3..695fcd5 100644
--- a/dump-extensions/openpower-dumps/op_dump_util.hpp
+++ b/dump-extensions/openpower-dumps/op_dump_util.hpp
@@ -19,6 +19,28 @@
*/
bool isOPDumpsEnabled(sdbusplus::bus::bus& bus);
+using BIOSAttrValueType = std::variant<int64_t, std::string>;
+
+/** @brief Read a BIOS attribute value
+ *
+ * @param[in] attrName - Name of the BIOS attribute
+ * @param[in] bus - D-Bus handle
+ *
+ * @return The value of the BIOS attribute as a variant of possible types
+ *
+ * @throws sdbusplus::exception::SdBusError if failed to read the attribute
+ */
+BIOSAttrValueType readBIOSAttribute(const std::string& attrName,
+ sdbusplus::bus::bus& bus);
+
+/** @brief Check whether a system is in progress or available to offload.
+ *
+ * @param[in] bus - D-Bus handle
+ *
+ * @return true - A dump is in progress or available to offload
+ * false - No dump in progress
+ */
+bool isSystemDumpInProgress(sdbusplus::bus::bus& bus);
} // namespace util
} // namespace dump
} // namespace openpower