1*f5c9f8bdSJason M. Bills /* 2*f5c9f8bdSJason M. Bills // Copyright (c) 2018 Intel Corporation 3*f5c9f8bdSJason M. Bills // 4*f5c9f8bdSJason M. Bills // Licensed under the Apache License, Version 2.0 (the "License"); 5*f5c9f8bdSJason M. Bills // you may not use this file except in compliance with the License. 6*f5c9f8bdSJason M. Bills // You may obtain a copy of the License at 7*f5c9f8bdSJason M. Bills // 8*f5c9f8bdSJason M. Bills // http://www.apache.org/licenses/LICENSE-2.0 9*f5c9f8bdSJason M. Bills // 10*f5c9f8bdSJason M. Bills // Unless required by applicable law or agreed to in writing, software 11*f5c9f8bdSJason M. Bills // distributed under the License is distributed on an "AS IS" BASIS, 12*f5c9f8bdSJason M. Bills // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13*f5c9f8bdSJason M. Bills // See the License for the specific language governing permissions and 14*f5c9f8bdSJason M. Bills // limitations under the License. 15*f5c9f8bdSJason M. Bills */ 16*f5c9f8bdSJason M. Bills 17*f5c9f8bdSJason M. Bills #pragma once 18*f5c9f8bdSJason M. Bills 19*f5c9f8bdSJason M. Bills #include "node.hpp" 20*f5c9f8bdSJason M. Bills 21*f5c9f8bdSJason M. Bills #include <boost/system/linux_error.hpp> 22*f5c9f8bdSJason M. Bills 23*f5c9f8bdSJason M. Bills namespace redfish 24*f5c9f8bdSJason M. Bills { 25*f5c9f8bdSJason M. Bills 26*f5c9f8bdSJason M. Bills static constexpr char const *pcieService = "xyz.openbmc_project.PCIe"; 27*f5c9f8bdSJason M. Bills static constexpr char const *pciePath = "/xyz/openbmc_project/PCIe"; 28*f5c9f8bdSJason M. Bills static constexpr char const *pcieDeviceInterface = 29*f5c9f8bdSJason M. Bills "xyz.openbmc_project.PCIe.Device"; 30*f5c9f8bdSJason M. Bills 31*f5c9f8bdSJason M. Bills static inline void getPCIeDeviceList(std::shared_ptr<AsyncResp> asyncResp) 32*f5c9f8bdSJason M. Bills { 33*f5c9f8bdSJason M. Bills auto getPCIeMapCallback = 34*f5c9f8bdSJason M. Bills [asyncResp](const boost::system::error_code ec, 35*f5c9f8bdSJason M. Bills std::vector<std::string> &pcieDevicePaths) { 36*f5c9f8bdSJason M. Bills if (ec) 37*f5c9f8bdSJason M. Bills { 38*f5c9f8bdSJason M. Bills BMCWEB_LOG_DEBUG << "failed to get PCIe device paths ec: " 39*f5c9f8bdSJason M. Bills << ec.message(); 40*f5c9f8bdSJason M. Bills messages::internalError(asyncResp->res); 41*f5c9f8bdSJason M. Bills return; 42*f5c9f8bdSJason M. Bills } 43*f5c9f8bdSJason M. Bills nlohmann::json &pcieDeviceList = 44*f5c9f8bdSJason M. Bills asyncResp->res.jsonValue["PCIeDevices"]; 45*f5c9f8bdSJason M. Bills pcieDeviceList = nlohmann::json::array(); 46*f5c9f8bdSJason M. Bills for (const std::string &pcieDevicePath : pcieDevicePaths) 47*f5c9f8bdSJason M. Bills { 48*f5c9f8bdSJason M. Bills size_t devStart = pcieDevicePath.rfind("/"); 49*f5c9f8bdSJason M. Bills if (devStart == std::string::npos) 50*f5c9f8bdSJason M. Bills { 51*f5c9f8bdSJason M. Bills continue; 52*f5c9f8bdSJason M. Bills } 53*f5c9f8bdSJason M. Bills 54*f5c9f8bdSJason M. Bills std::string devName = pcieDevicePath.substr(devStart + 1); 55*f5c9f8bdSJason M. Bills if (devName.empty()) 56*f5c9f8bdSJason M. Bills { 57*f5c9f8bdSJason M. Bills continue; 58*f5c9f8bdSJason M. Bills } 59*f5c9f8bdSJason M. Bills pcieDeviceList.push_back( 60*f5c9f8bdSJason M. Bills {{"@odata.id", 61*f5c9f8bdSJason M. Bills "/redfish/v1/Systems/system/PCIeDevices/" + devName}}); 62*f5c9f8bdSJason M. Bills } 63*f5c9f8bdSJason M. Bills asyncResp->res.jsonValue["PCIeDevices@odata.count"] = 64*f5c9f8bdSJason M. Bills pcieDeviceList.size(); 65*f5c9f8bdSJason M. Bills }; 66*f5c9f8bdSJason M. Bills crow::connections::systemBus->async_method_call( 67*f5c9f8bdSJason M. Bills std::move(getPCIeMapCallback), "xyz.openbmc_project.ObjectMapper", 68*f5c9f8bdSJason M. Bills "/xyz/openbmc_project/object_mapper", 69*f5c9f8bdSJason M. Bills "xyz.openbmc_project.ObjectMapper", "GetSubTreePaths", 70*f5c9f8bdSJason M. Bills std::string(pciePath) + "/", 1, std::array<std::string, 0>()); 71*f5c9f8bdSJason M. Bills } 72*f5c9f8bdSJason M. Bills 73*f5c9f8bdSJason M. Bills class SystemPCIeDevice : public Node 74*f5c9f8bdSJason M. Bills { 75*f5c9f8bdSJason M. Bills public: 76*f5c9f8bdSJason M. Bills SystemPCIeDevice(CrowApp &app) : 77*f5c9f8bdSJason M. Bills Node(app, "/redfish/v1/Systems/system/PCIeDevices/<str>/", 78*f5c9f8bdSJason M. Bills std::string()) 79*f5c9f8bdSJason M. Bills { 80*f5c9f8bdSJason M. Bills entityPrivileges = { 81*f5c9f8bdSJason M. Bills {boost::beast::http::verb::get, {{"Login"}}}, 82*f5c9f8bdSJason M. Bills {boost::beast::http::verb::head, {{"Login"}}}, 83*f5c9f8bdSJason M. Bills {boost::beast::http::verb::patch, {{"ConfigureManager"}}}, 84*f5c9f8bdSJason M. Bills {boost::beast::http::verb::put, {{"ConfigureManager"}}}, 85*f5c9f8bdSJason M. Bills {boost::beast::http::verb::delete_, {{"ConfigureManager"}}}, 86*f5c9f8bdSJason M. Bills {boost::beast::http::verb::post, {{"ConfigureManager"}}}}; 87*f5c9f8bdSJason M. Bills } 88*f5c9f8bdSJason M. Bills 89*f5c9f8bdSJason M. Bills private: 90*f5c9f8bdSJason M. Bills void doGet(crow::Response &res, const crow::Request &req, 91*f5c9f8bdSJason M. Bills const std::vector<std::string> ¶ms) override 92*f5c9f8bdSJason M. Bills { 93*f5c9f8bdSJason M. Bills std::shared_ptr<AsyncResp> asyncResp = std::make_shared<AsyncResp>(res); 94*f5c9f8bdSJason M. Bills if (params.size() != 1) 95*f5c9f8bdSJason M. Bills { 96*f5c9f8bdSJason M. Bills messages::internalError(asyncResp->res); 97*f5c9f8bdSJason M. Bills return; 98*f5c9f8bdSJason M. Bills } 99*f5c9f8bdSJason M. Bills const std::string &device = params[0]; 100*f5c9f8bdSJason M. Bills 101*f5c9f8bdSJason M. Bills auto getPCIeDeviceCallback = 102*f5c9f8bdSJason M. Bills [asyncResp, 103*f5c9f8bdSJason M. Bills device](const boost::system::error_code ec, 104*f5c9f8bdSJason M. Bills boost::container::flat_map< 105*f5c9f8bdSJason M. Bills std::string, sdbusplus::message::variant<std::string>> 106*f5c9f8bdSJason M. Bills &pcieDevProperties) { 107*f5c9f8bdSJason M. Bills if (ec) 108*f5c9f8bdSJason M. Bills { 109*f5c9f8bdSJason M. Bills BMCWEB_LOG_DEBUG 110*f5c9f8bdSJason M. Bills << "failed to get PCIe Device properties ec: " 111*f5c9f8bdSJason M. Bills << static_cast<int>(ec.value()) << ": " << ec.message(); 112*f5c9f8bdSJason M. Bills if (ec.value() == 113*f5c9f8bdSJason M. Bills boost::system::linux_error::bad_request_descriptor) 114*f5c9f8bdSJason M. Bills { 115*f5c9f8bdSJason M. Bills messages::resourceNotFound(asyncResp->res, "PCIeDevice", 116*f5c9f8bdSJason M. Bills device); 117*f5c9f8bdSJason M. Bills } 118*f5c9f8bdSJason M. Bills else 119*f5c9f8bdSJason M. Bills { 120*f5c9f8bdSJason M. Bills messages::internalError(asyncResp->res); 121*f5c9f8bdSJason M. Bills } 122*f5c9f8bdSJason M. Bills return; 123*f5c9f8bdSJason M. Bills } 124*f5c9f8bdSJason M. Bills 125*f5c9f8bdSJason M. Bills asyncResp->res.jsonValue = { 126*f5c9f8bdSJason M. Bills {"@odata.type", "#PCIeDevice.v1_2_0.PCIeDevice"}, 127*f5c9f8bdSJason M. Bills {"@odata.context", 128*f5c9f8bdSJason M. Bills "/redfish/v1/$metadata#PCIeDevice.v1_2_0.PCIeDevice"}, 129*f5c9f8bdSJason M. Bills {"@odata.id", 130*f5c9f8bdSJason M. Bills "/redfish/v1/Systems/system/PCIeDevices/" + device}, 131*f5c9f8bdSJason M. Bills {"Name", "PCIe Device"}, 132*f5c9f8bdSJason M. Bills {"Id", device}}; 133*f5c9f8bdSJason M. Bills 134*f5c9f8bdSJason M. Bills if (std::string *property = 135*f5c9f8bdSJason M. Bills sdbusplus::message::variant_ns::get_if<std::string>( 136*f5c9f8bdSJason M. Bills &pcieDevProperties["Manufacturer"]); 137*f5c9f8bdSJason M. Bills property) 138*f5c9f8bdSJason M. Bills { 139*f5c9f8bdSJason M. Bills asyncResp->res.jsonValue["Manufacturer"] = *property; 140*f5c9f8bdSJason M. Bills } 141*f5c9f8bdSJason M. Bills 142*f5c9f8bdSJason M. Bills if (std::string *property = 143*f5c9f8bdSJason M. Bills sdbusplus::message::variant_ns::get_if<std::string>( 144*f5c9f8bdSJason M. Bills &pcieDevProperties["DeviceType"]); 145*f5c9f8bdSJason M. Bills property) 146*f5c9f8bdSJason M. Bills { 147*f5c9f8bdSJason M. Bills asyncResp->res.jsonValue["DeviceType"] = *property; 148*f5c9f8bdSJason M. Bills } 149*f5c9f8bdSJason M. Bills 150*f5c9f8bdSJason M. Bills nlohmann::json &pcieFunctionList = 151*f5c9f8bdSJason M. Bills asyncResp->res.jsonValue["Links"]["PCIeFunctions"]; 152*f5c9f8bdSJason M. Bills pcieFunctionList = nlohmann::json::array(); 153*f5c9f8bdSJason M. Bills static constexpr const int maxPciFunctionNum = 8; 154*f5c9f8bdSJason M. Bills for (int functionNum = 0; functionNum < maxPciFunctionNum; 155*f5c9f8bdSJason M. Bills functionNum++) 156*f5c9f8bdSJason M. Bills { 157*f5c9f8bdSJason M. Bills // Check if this function exists by looking for a device ID 158*f5c9f8bdSJason M. Bills std::string devIDProperty = 159*f5c9f8bdSJason M. Bills "Function" + std::to_string(functionNum) + "DeviceId"; 160*f5c9f8bdSJason M. Bills if (std::string *property = 161*f5c9f8bdSJason M. Bills sdbusplus::message::variant_ns::get_if<std::string>( 162*f5c9f8bdSJason M. Bills &pcieDevProperties[devIDProperty]); 163*f5c9f8bdSJason M. Bills property && !property->empty()) 164*f5c9f8bdSJason M. Bills { 165*f5c9f8bdSJason M. Bills pcieFunctionList.push_back( 166*f5c9f8bdSJason M. Bills {{"@odata.id", 167*f5c9f8bdSJason M. Bills "/redfish/v1/Systems/system/PCIeDevices/" + 168*f5c9f8bdSJason M. Bills device + "/PCIeFunctions/" + 169*f5c9f8bdSJason M. Bills std::to_string(functionNum)}}); 170*f5c9f8bdSJason M. Bills } 171*f5c9f8bdSJason M. Bills } 172*f5c9f8bdSJason M. Bills asyncResp->res.jsonValue["Links"]["PCIeFunctions@odata.count"] = 173*f5c9f8bdSJason M. Bills pcieFunctionList.size(); 174*f5c9f8bdSJason M. Bills }; 175*f5c9f8bdSJason M. Bills std::string escapedPath = std::string(pciePath) + "/" + device; 176*f5c9f8bdSJason M. Bills dbus::utility::escapePathForDbus(escapedPath); 177*f5c9f8bdSJason M. Bills crow::connections::systemBus->async_method_call( 178*f5c9f8bdSJason M. Bills std::move(getPCIeDeviceCallback), pcieService, escapedPath, 179*f5c9f8bdSJason M. Bills "org.freedesktop.DBus.Properties", "GetAll", pcieDeviceInterface); 180*f5c9f8bdSJason M. Bills } 181*f5c9f8bdSJason M. Bills }; 182*f5c9f8bdSJason M. Bills 183*f5c9f8bdSJason M. Bills class SystemPCIeFunction : public Node 184*f5c9f8bdSJason M. Bills { 185*f5c9f8bdSJason M. Bills public: 186*f5c9f8bdSJason M. Bills SystemPCIeFunction(CrowApp &app) : 187*f5c9f8bdSJason M. Bills Node( 188*f5c9f8bdSJason M. Bills app, 189*f5c9f8bdSJason M. Bills "/redfish/v1/Systems/system/PCIeDevices/<str>/PCIeFunctions/<str>/", 190*f5c9f8bdSJason M. Bills std::string(), std::string()) 191*f5c9f8bdSJason M. Bills { 192*f5c9f8bdSJason M. Bills entityPrivileges = { 193*f5c9f8bdSJason M. Bills {boost::beast::http::verb::get, {{"Login"}}}, 194*f5c9f8bdSJason M. Bills {boost::beast::http::verb::head, {{"Login"}}}, 195*f5c9f8bdSJason M. Bills {boost::beast::http::verb::patch, {{"ConfigureManager"}}}, 196*f5c9f8bdSJason M. Bills {boost::beast::http::verb::put, {{"ConfigureManager"}}}, 197*f5c9f8bdSJason M. Bills {boost::beast::http::verb::delete_, {{"ConfigureManager"}}}, 198*f5c9f8bdSJason M. Bills {boost::beast::http::verb::post, {{"ConfigureManager"}}}}; 199*f5c9f8bdSJason M. Bills } 200*f5c9f8bdSJason M. Bills 201*f5c9f8bdSJason M. Bills private: 202*f5c9f8bdSJason M. Bills void doGet(crow::Response &res, const crow::Request &req, 203*f5c9f8bdSJason M. Bills const std::vector<std::string> ¶ms) override 204*f5c9f8bdSJason M. Bills { 205*f5c9f8bdSJason M. Bills std::shared_ptr<AsyncResp> asyncResp = std::make_shared<AsyncResp>(res); 206*f5c9f8bdSJason M. Bills if (params.size() != 2) 207*f5c9f8bdSJason M. Bills { 208*f5c9f8bdSJason M. Bills messages::internalError(asyncResp->res); 209*f5c9f8bdSJason M. Bills return; 210*f5c9f8bdSJason M. Bills } 211*f5c9f8bdSJason M. Bills const std::string &device = params[0]; 212*f5c9f8bdSJason M. Bills const std::string &function = params[1]; 213*f5c9f8bdSJason M. Bills 214*f5c9f8bdSJason M. Bills auto getPCIeDeviceCallback = 215*f5c9f8bdSJason M. Bills [asyncResp, device, function]( 216*f5c9f8bdSJason M. Bills const boost::system::error_code ec, 217*f5c9f8bdSJason M. Bills boost::container::flat_map< 218*f5c9f8bdSJason M. Bills std::string, sdbusplus::message::variant<std::string>> 219*f5c9f8bdSJason M. Bills &pcieDevProperties) { 220*f5c9f8bdSJason M. Bills if (ec) 221*f5c9f8bdSJason M. Bills { 222*f5c9f8bdSJason M. Bills BMCWEB_LOG_DEBUG 223*f5c9f8bdSJason M. Bills << "failed to get PCIe Device properties ec: " 224*f5c9f8bdSJason M. Bills << static_cast<int>(ec.value()) << ": " << ec.message(); 225*f5c9f8bdSJason M. Bills if (ec.value() == 226*f5c9f8bdSJason M. Bills boost::system::linux_error::bad_request_descriptor) 227*f5c9f8bdSJason M. Bills { 228*f5c9f8bdSJason M. Bills messages::resourceNotFound(asyncResp->res, "PCIeDevice", 229*f5c9f8bdSJason M. Bills device); 230*f5c9f8bdSJason M. Bills } 231*f5c9f8bdSJason M. Bills else 232*f5c9f8bdSJason M. Bills { 233*f5c9f8bdSJason M. Bills messages::internalError(asyncResp->res); 234*f5c9f8bdSJason M. Bills } 235*f5c9f8bdSJason M. Bills return; 236*f5c9f8bdSJason M. Bills } 237*f5c9f8bdSJason M. Bills 238*f5c9f8bdSJason M. Bills // Check if this function exists by looking for a device ID 239*f5c9f8bdSJason M. Bills std::string devIDProperty = "Function" + function + "DeviceId"; 240*f5c9f8bdSJason M. Bills if (std::string *property = 241*f5c9f8bdSJason M. Bills sdbusplus::message::variant_ns::get_if<std::string>( 242*f5c9f8bdSJason M. Bills &pcieDevProperties[devIDProperty]); 243*f5c9f8bdSJason M. Bills property && property->empty()) 244*f5c9f8bdSJason M. Bills { 245*f5c9f8bdSJason M. Bills messages::resourceNotFound(asyncResp->res, "PCIeFunction", 246*f5c9f8bdSJason M. Bills function); 247*f5c9f8bdSJason M. Bills return; 248*f5c9f8bdSJason M. Bills } 249*f5c9f8bdSJason M. Bills 250*f5c9f8bdSJason M. Bills asyncResp->res.jsonValue = { 251*f5c9f8bdSJason M. Bills {"@odata.type", "#PCIeFunction.v1_2_0.PCIeFunction"}, 252*f5c9f8bdSJason M. Bills {"@odata.context", 253*f5c9f8bdSJason M. Bills "/redfish/v1/$metadata#PCIeFunction.PCIeFunction"}, 254*f5c9f8bdSJason M. Bills {"@odata.id", "/redfish/v1/Systems/system/PCIeDevices/" + 255*f5c9f8bdSJason M. Bills device + "/PCIeFunctions/" + function}, 256*f5c9f8bdSJason M. Bills {"Name", "PCIe Function"}, 257*f5c9f8bdSJason M. Bills {"Id", function}, 258*f5c9f8bdSJason M. Bills {"FunctionId", std::stoi(function)}, 259*f5c9f8bdSJason M. Bills {"Links", 260*f5c9f8bdSJason M. Bills {{"PCIeDevice", 261*f5c9f8bdSJason M. Bills {{"@odata.id", 262*f5c9f8bdSJason M. Bills "/redfish/v1/Systems/system/PCIeDevices/" + 263*f5c9f8bdSJason M. Bills device}}}}}}; 264*f5c9f8bdSJason M. Bills 265*f5c9f8bdSJason M. Bills if (std::string *property = 266*f5c9f8bdSJason M. Bills sdbusplus::message::variant_ns::get_if<std::string>( 267*f5c9f8bdSJason M. Bills &pcieDevProperties["Function" + function + 268*f5c9f8bdSJason M. Bills "DeviceId"]); 269*f5c9f8bdSJason M. Bills property) 270*f5c9f8bdSJason M. Bills { 271*f5c9f8bdSJason M. Bills asyncResp->res.jsonValue["DeviceId"] = *property; 272*f5c9f8bdSJason M. Bills } 273*f5c9f8bdSJason M. Bills 274*f5c9f8bdSJason M. Bills if (std::string *property = 275*f5c9f8bdSJason M. Bills sdbusplus::message::variant_ns::get_if<std::string>( 276*f5c9f8bdSJason M. Bills &pcieDevProperties["Function" + function + 277*f5c9f8bdSJason M. Bills "VendorId"]); 278*f5c9f8bdSJason M. Bills property) 279*f5c9f8bdSJason M. Bills { 280*f5c9f8bdSJason M. Bills asyncResp->res.jsonValue["VendorId"] = *property; 281*f5c9f8bdSJason M. Bills } 282*f5c9f8bdSJason M. Bills 283*f5c9f8bdSJason M. Bills if (std::string *property = 284*f5c9f8bdSJason M. Bills sdbusplus::message::variant_ns::get_if<std::string>( 285*f5c9f8bdSJason M. Bills &pcieDevProperties["Function" + function + 286*f5c9f8bdSJason M. Bills "FunctionType"]); 287*f5c9f8bdSJason M. Bills property) 288*f5c9f8bdSJason M. Bills { 289*f5c9f8bdSJason M. Bills asyncResp->res.jsonValue["FunctionType"] = *property; 290*f5c9f8bdSJason M. Bills } 291*f5c9f8bdSJason M. Bills 292*f5c9f8bdSJason M. Bills if (std::string *property = 293*f5c9f8bdSJason M. Bills sdbusplus::message::variant_ns::get_if<std::string>( 294*f5c9f8bdSJason M. Bills &pcieDevProperties["Function" + function + 295*f5c9f8bdSJason M. Bills "DeviceClass"]); 296*f5c9f8bdSJason M. Bills property) 297*f5c9f8bdSJason M. Bills { 298*f5c9f8bdSJason M. Bills asyncResp->res.jsonValue["DeviceClass"] = *property; 299*f5c9f8bdSJason M. Bills } 300*f5c9f8bdSJason M. Bills 301*f5c9f8bdSJason M. Bills if (std::string *property = 302*f5c9f8bdSJason M. Bills sdbusplus::message::variant_ns::get_if<std::string>( 303*f5c9f8bdSJason M. Bills &pcieDevProperties["Function" + function + 304*f5c9f8bdSJason M. Bills "ClassCode"]); 305*f5c9f8bdSJason M. Bills property) 306*f5c9f8bdSJason M. Bills { 307*f5c9f8bdSJason M. Bills asyncResp->res.jsonValue["ClassCode"] = *property; 308*f5c9f8bdSJason M. Bills } 309*f5c9f8bdSJason M. Bills 310*f5c9f8bdSJason M. Bills if (std::string *property = 311*f5c9f8bdSJason M. Bills sdbusplus::message::variant_ns::get_if<std::string>( 312*f5c9f8bdSJason M. Bills &pcieDevProperties["Function" + function + 313*f5c9f8bdSJason M. Bills "RevisionId"]); 314*f5c9f8bdSJason M. Bills property) 315*f5c9f8bdSJason M. Bills { 316*f5c9f8bdSJason M. Bills asyncResp->res.jsonValue["RevisionId"] = *property; 317*f5c9f8bdSJason M. Bills } 318*f5c9f8bdSJason M. Bills 319*f5c9f8bdSJason M. Bills if (std::string *property = 320*f5c9f8bdSJason M. Bills sdbusplus::message::variant_ns::get_if<std::string>( 321*f5c9f8bdSJason M. Bills &pcieDevProperties["Function" + function + 322*f5c9f8bdSJason M. Bills "SubsystemId"]); 323*f5c9f8bdSJason M. Bills property) 324*f5c9f8bdSJason M. Bills { 325*f5c9f8bdSJason M. Bills asyncResp->res.jsonValue["SubsystemId"] = *property; 326*f5c9f8bdSJason M. Bills } 327*f5c9f8bdSJason M. Bills 328*f5c9f8bdSJason M. Bills if (std::string *property = 329*f5c9f8bdSJason M. Bills sdbusplus::message::variant_ns::get_if<std::string>( 330*f5c9f8bdSJason M. Bills &pcieDevProperties["Function" + function + 331*f5c9f8bdSJason M. Bills "SubsystemVendorId"]); 332*f5c9f8bdSJason M. Bills property) 333*f5c9f8bdSJason M. Bills { 334*f5c9f8bdSJason M. Bills asyncResp->res.jsonValue["SubsystemVendorId"] = *property; 335*f5c9f8bdSJason M. Bills } 336*f5c9f8bdSJason M. Bills }; 337*f5c9f8bdSJason M. Bills std::string escapedPath = std::string(pciePath) + "/" + device; 338*f5c9f8bdSJason M. Bills dbus::utility::escapePathForDbus(escapedPath); 339*f5c9f8bdSJason M. Bills crow::connections::systemBus->async_method_call( 340*f5c9f8bdSJason M. Bills std::move(getPCIeDeviceCallback), pcieService, escapedPath, 341*f5c9f8bdSJason M. Bills "org.freedesktop.DBus.Properties", "GetAll", pcieDeviceInterface); 342*f5c9f8bdSJason M. Bills } 343*f5c9f8bdSJason M. Bills }; 344*f5c9f8bdSJason M. Bills 345*f5c9f8bdSJason M. Bills } // namespace redfish 346