crit-service: start bmc quiesce target on fail

This target will be monitored by the BMC state target and used to tell
external clients when the BMC is in a bad state due to a critical
service failing

Signed-off-by: Andrew Geissler <geissonator@yahoo.com>
Change-Id: Ibf0460bef9b3ac2a96e8a294e6de122463530713
diff --git a/systemd_target_signal.cpp b/systemd_target_signal.cpp
index cc3cf4c..88b1aad 100644
--- a/systemd_target_signal.cpp
+++ b/systemd_target_signal.cpp
@@ -39,6 +39,30 @@
     }
 }
 
+void SystemdTargetLogging::startBmcQuiesceTarget()
+{
+    auto method = this->bus.new_method_call(
+        "org.freedesktop.systemd1", "/org/freedesktop/systemd1",
+        "org.freedesktop.systemd1.Manager", "StartUnit");
+
+    // TODO: Enhance when needed to support multiple-bmc instance systems
+    method.append("obmc-bmc-service-quiesce@0.target");
+    method.append("replace");
+    try
+    {
+        this->bus.call_noreply(method);
+    }
+    catch (const sdbusplus::exception::exception& e)
+    {
+        error("Failed to start BMC quiesce target, exception:{ERROR}", "ERROR",
+              e);
+        // just continue, this is error path anyway so we're just doing what
+        // we can
+    }
+
+    return;
+}
+
 void SystemdTargetLogging::logError(const std::string& errorLog,
                                     const std::string& result,
                                     const std::string& unit)
@@ -94,6 +118,8 @@
 
             // Generate a BMC dump when a critical service fails
             createBmcDump();
+            // Enter BMC Quiesce when a critical service fails
+            startBmcQuiesceTarget();
             return (std::string{
                 "xyz.openbmc_project.State.Error.CriticalServiceFailure"});
         }