Support Processors and its collection for ProcessorType Accelerator

Interface- phosphor-dbus-interfaces/blob/master/xyz/openbmc_project/
Inventory/Item/Accelerator.interface.yaml

Redfish schema Status/state is mapped to two properties-
Functional and Present
    xyz.openbmc_project.State.Decorator.OperationalStatus
    xyz.openbmc_project.Inventory.Item

Tested:
-- ran Redfish-Service-Validator, All 6 GPUs shows Success
-- ran GET on Processors Collection
curl -k -H "X-Auth-Token: $bmc_token" -X GET
 https://${bmc}/redfish/v1/Systems/system/Processors

{
  "@odata.context": "/redfish/v1/$metadata#ProcessorCollection.ProcessorCollection",
  "@odata.id": "/redfish/v1/Systems/system/Processors/",
  "@odata.type": "#ProcessorCollection.ProcessorCollection",
  "Members": [
    {
      "@odata.id": "/redfish/v1/Systems/system/Processors/cpu0"
    },
    {
      "@odata.id": "/redfish/v1/Systems/system/Processors/cpu1"
    },
    {
      "@odata.id": "/redfish/v1/Systems/system/Processors/gv100card0"
    },
    {
      "@odata.id": "/redfish/v1/Systems/system/Processors/gv100card1"
    },
    {
      "@odata.id": "/redfish/v1/Systems/system/Processors/gv100card2"
    },
    {
      "@odata.id": "/redfish/v1/Systems/system/Processors/gv100card3"
    },
    {
      "@odata.id": "/redfish/v1/Systems/system/Processors/gv100card4"
    },
    {
      "@odata.id": "/redfish/v1/Systems/system/Processors/gv100card5"
    }
  ],
  "Members@odata.count": 8,
  "Name": "Processor Collection"

 curl -k -H "X-Auth-Token: $bmc_token" -X GET
 https://${bmc}/redfish/v1/Systems/system/Processors/gv100card0
{
  "@odata.context": "/redfish/v1/$metadata#Processor.Processor",
  "@odata.id": "/redfish/v1/Systems/system/Processors/gv100card0",
  "@odata.type": "#Processor.v1_3_1.Processor",
  "Id": "gv100card0",
  "Name": "Processor",
  "ProcessorType": "Accelerator",
  "Status": {
    "Health": "OK",
    "State": "Absent"
  }

Change-Id: I5315df80d88d3a04de4b62435a200a718a10cd4c
Signed-off-by: Alpana Kumari <alpankum@in.ibm.com>
diff --git a/redfish-core/lib/cpudimm.hpp b/redfish-core/lib/cpudimm.hpp
index 4245595..572156d 100644
--- a/redfish-core/lib/cpudimm.hpp
+++ b/redfish-core/lib/cpudimm.hpp
@@ -25,7 +25,7 @@
 
 void getResourceList(std::shared_ptr<AsyncResp> aResp,
                      const std::string &subclass,
-                     const std::string &collectionName)
+                     const std::vector<const char *> &collectionName)
 {
     BMCWEB_LOG_DEBUG << "Get available system cpu/mem resources.";
     crow::connections::systemBus->async_method_call(
@@ -60,8 +60,7 @@
         "xyz.openbmc_project.ObjectMapper",
         "/xyz/openbmc_project/object_mapper",
         "xyz.openbmc_project.ObjectMapper", "GetSubTree",
-        "/xyz/openbmc_project/inventory", int32_t(0),
-        std::array<const char *, 1>{collectionName.c_str()});
+        "/xyz/openbmc_project/inventory", int32_t(0), collectionName);
 }
 
 void getCpuDataByService(std::shared_ptr<AsyncResp> aResp,
@@ -156,9 +155,75 @@
         service, objPath, "org.freedesktop.DBus.Properties", "GetAll", "");
 }
 
-void getCpuData(std::shared_ptr<AsyncResp> aResp, const std::string &cpuId)
+void getAcceleratorDataByService(std::shared_ptr<AsyncResp> aResp,
+                                 const std::string &acclrtrId,
+                                 const std::string &service,
+                                 const std::string &objPath)
+{
+    BMCWEB_LOG_DEBUG
+        << "Get available system Accelerator resources by service.";
+    crow::connections::systemBus->async_method_call(
+        [acclrtrId, aResp{std::move(aResp)}](
+            const boost::system::error_code ec,
+            const boost::container::flat_map<
+                std::string, std::variant<std::string, uint32_t, uint16_t>>
+                &properties) {
+            if (ec)
+            {
+                BMCWEB_LOG_DEBUG << "DBUS response error";
+                messages::internalError(aResp->res);
+                return;
+            }
+            aResp->res.jsonValue["Id"] = acclrtrId;
+            aResp->res.jsonValue["Name"] = "Processor";
+            const std::string *accPresent = nullptr;
+            const std::string *accFunctional = nullptr;
+            std::string state = "";
+
+            for (const auto &property : properties)
+            {
+                if (property.first == "Functional")
+                {
+                    accFunctional = std::get_if<std::string>(&property.second);
+                }
+                else if (property.first == "Present")
+                {
+                    accPresent = std::get_if<std::string>(&property.second);
+                }
+            }
+
+            if (!accPresent || !accFunctional)
+            {
+                BMCWEB_LOG_DEBUG << "Required properties missing in DBUS "
+                                    "response";
+                messages::internalError(aResp->res);
+                return;
+            }
+
+            if ((*accPresent == "Present") && (*accFunctional == "Functional"))
+            {
+                state = "Enabled";
+            }
+            else if (*accPresent == "Present")
+            {
+                state = "UnavailableOffline";
+            }
+            else
+            {
+                state = "Absent";
+            }
+            aResp->res.jsonValue["Status"]["State"] = state;
+            aResp->res.jsonValue["Status"]["Health"] = "OK";
+            aResp->res.jsonValue["ProcessorType"] = "Accelerator";
+        },
+        service, objPath, "org.freedesktop.DBus.Properties", "GetAll", "");
+}
+
+void getCpuData(std::shared_ptr<AsyncResp> aResp, const std::string &cpuId,
+                const std::vector<const char *> inventoryItems)
 {
     BMCWEB_LOG_DEBUG << "Get available system cpu resources.";
+
     crow::connections::systemBus->async_method_call(
         [cpuId, aResp{std::move(aResp)}](
             const boost::system::error_code ec,
@@ -178,8 +243,19 @@
                 {
                     for (const auto &service : object.second)
                     {
-                        getCpuDataByService(aResp, cpuId, service.first,
-                                            object.first);
+                        for (const auto &inventory : service.second)
+                            if (inventory ==
+                                "xyz.openbmc_project.Inventory.Item.Cpu")
+                            {
+                                getCpuDataByService(aResp, cpuId, service.first,
+                                                    object.first);
+                            }
+                            else if (inventory == "xyz.openbmc_project."
+                                                  "Inventory.Item.Accelerator")
+                            {
+                                getAcceleratorDataByService(
+                                    aResp, cpuId, service.first, object.first);
+                            }
                         return;
                     }
                 }
@@ -191,8 +267,7 @@
         "xyz.openbmc_project.ObjectMapper",
         "/xyz/openbmc_project/object_mapper",
         "xyz.openbmc_project.ObjectMapper", "GetSubTree",
-        "/xyz/openbmc_project/inventory", int32_t(0),
-        std::array<const char *, 1>{"xyz.openbmc_project.Inventory.Item.Cpu"});
+        "/xyz/openbmc_project/inventory", int32_t(0), inventoryItems);
 };
 
 void getDimmDataByService(std::shared_ptr<AsyncResp> aResp,
@@ -340,7 +415,8 @@
         auto asyncResp = std::make_shared<AsyncResp>(res);
 
         getResourceList(asyncResp, "Processors",
-                        "xyz.openbmc_project.Inventory.Item.Cpu");
+                        {"xyz.openbmc_project.Inventory.Item.Cpu",
+                         "xyz.openbmc_project.Inventory.Item.Accelerator"});
     }
 };
 
@@ -378,16 +454,18 @@
             res.end();
             return;
         }
-        const std::string &cpuId = params[0];
+        const std::string &processorId = params[0];
         res.jsonValue["@odata.type"] = "#Processor.v1_3_1.Processor";
         res.jsonValue["@odata.context"] =
             "/redfish/v1/$metadata#Processor.Processor";
         res.jsonValue["@odata.id"] =
-            "/redfish/v1/Systems/system/Processors/" + cpuId;
+            "/redfish/v1/Systems/system/Processors/" + processorId;
 
         auto asyncResp = std::make_shared<AsyncResp>(res);
 
-        getCpuData(asyncResp, cpuId);
+        getCpuData(asyncResp, processorId,
+                   {"xyz.openbmc_project.Inventory.Item.Cpu",
+                    "xyz.openbmc_project.Inventory.Item.Accelerator"});
     }
 };
 
@@ -424,7 +502,7 @@
         auto asyncResp = std::make_shared<AsyncResp>(res);
 
         getResourceList(asyncResp, "Memory",
-                        "xyz.openbmc_project.Inventory.Item.Dimm");
+                        {"xyz.openbmc_project.Inventory.Item.Dimm"});
     }
 };