chassishandler: add AC failed bit support for chassis status

PFail property is provided by power control service,
true means the booting is from AC power loss.

Tested:
Remove the AC cable and reconnect it to power on the system
ipmitool chassis status will return:
Last Power Event     : ac-failed

Change-Id: I3743f15da259491052ee8fc869205438e79046f8
Signed-off-by: Yong Li <yong.b.li@linux.intel.com>
diff --git a/chassishandler.cpp b/chassishandler.cpp
index f17fa9d..0d2265f 100644
--- a/chassishandler.cpp
+++ b/chassishandler.cpp
@@ -865,6 +865,37 @@
     return std::make_optional(powerGood);
 }
 
+/*
+ * getACFailStatus
+ * helper function for Get Chassis Status Command
+ * return - bool value for ACFail (false on error)
+ */
+bool getACFailStatus()
+{
+    constexpr const char* powerControlObj =
+        "/xyz/openbmc_project/Chassis/Control/Power0";
+    constexpr const char* powerControlIntf =
+        "xyz.openbmc_project.Chassis.Control.Power";
+    bool acFail = false;
+    std::shared_ptr<sdbusplus::asio::connection> bus = getSdBus();
+    try
+    {
+        auto service =
+            ipmi::getService(*bus, powerControlIntf, powerControlObj);
+
+        ipmi::Value variant = ipmi::getDbusProperty(
+            *bus, service, powerControlObj, powerControlIntf, "PFail");
+        acFail = std::get<bool>(variant);
+    }
+    catch (const std::exception& e)
+    {
+        log<level::ERR>("Failed to fetch PFail property",
+                        entry("ERROR=%s", e.what()),
+                        entry("PATH=%s", powerControlObj),
+                        entry("INTERFACE=%s", powerControlIntf));
+    }
+    return acFail;
+}
 } // namespace power_policy
 
 static std::optional<bool> getButtonEnabled(const std::string& buttonPath,
@@ -960,13 +991,14 @@
         resetButtonDisabled = *resetButtonReading;
     }
 
+    bool powerDownAcFailed = power_policy::getACFailStatus();
+
     // This response has a lot of hard-coded, unsupported fields
     // They are set to false or 0
     constexpr bool powerOverload = false;
     constexpr bool chassisInterlock = false;
     constexpr bool powerFault = false;
     constexpr bool powerControlFault = false;
-    constexpr bool powerDownAcFailed = false;
     constexpr bool powerDownOverload = false;
     constexpr bool powerDownInterlock = false;
     constexpr bool powerDownPowerFault = false;