13c50c82aSKamalkumar Patel #include "platform_config.hpp" 23c50c82aSKamalkumar Patel 389644441SRiya Dixit #include <phosphor-logging/lg2.hpp> 489644441SRiya Dixit 589644441SRiya Dixit PHOSPHOR_LOG2_USING; 689644441SRiya Dixit 73c50c82aSKamalkumar Patel namespace pldm 83c50c82aSKamalkumar Patel { 93c50c82aSKamalkumar Patel namespace responder 103c50c82aSKamalkumar Patel { 113c50c82aSKamalkumar Patel 123c50c82aSKamalkumar Patel namespace platform_config 133c50c82aSKamalkumar Patel { 143c50c82aSKamalkumar Patel /** @brief callback function invoked when interfaces get added from 153c50c82aSKamalkumar Patel * Entity manager 163c50c82aSKamalkumar Patel * 173c50c82aSKamalkumar Patel * @param[in] msg - Data associated with subscribed signal 183c50c82aSKamalkumar Patel */ 193c50c82aSKamalkumar Patel void Handler::systemCompatibleCallback(sdbusplus::message_t& msg) 203c50c82aSKamalkumar Patel { 213c50c82aSKamalkumar Patel sdbusplus::message::object_path path; 223c50c82aSKamalkumar Patel 233c50c82aSKamalkumar Patel pldm::utils::InterfaceMap interfaceMap; 243c50c82aSKamalkumar Patel 253c50c82aSKamalkumar Patel msg.read(path, interfaceMap); 263c50c82aSKamalkumar Patel 273c50c82aSKamalkumar Patel if (!interfaceMap.contains(compatibleInterface)) 283c50c82aSKamalkumar Patel { 293c50c82aSKamalkumar Patel return; 303c50c82aSKamalkumar Patel } 313c50c82aSKamalkumar Patel // Get the "Name" property value of the 323c50c82aSKamalkumar Patel // "xyz.openbmc_project.Inventory.Decorator.Compatible" interface 333c50c82aSKamalkumar Patel const auto& properties = interfaceMap.at(compatibleInterface); 343c50c82aSKamalkumar Patel 353c50c82aSKamalkumar Patel if (!properties.contains(namesProperty)) 363c50c82aSKamalkumar Patel { 373c50c82aSKamalkumar Patel return; 383c50c82aSKamalkumar Patel } 393c50c82aSKamalkumar Patel auto names = 403c50c82aSKamalkumar Patel std::get<pldm::utils::Interfaces>(properties.at(namesProperty)); 413c50c82aSKamalkumar Patel 423c50c82aSKamalkumar Patel if (!names.empty()) 433c50c82aSKamalkumar Patel { 44*0a422696SKamalkumar Patel std::optional<std::string> sysType = getSysSpecificJsonDir(sysDirPath, 45*0a422696SKamalkumar Patel names); 46*0a422696SKamalkumar Patel if (sysType.has_value()) 47*0a422696SKamalkumar Patel { 48*0a422696SKamalkumar Patel systemType = sysType.value(); 49*0a422696SKamalkumar Patel } 5062dd8ff2SArchana Kakani if (sysTypeCallback) 5162dd8ff2SArchana Kakani { 5246f352edSArchana Kakani sysTypeCallback(systemType, true); 5362dd8ff2SArchana Kakani } 543c50c82aSKamalkumar Patel } 553c50c82aSKamalkumar Patel 563c50c82aSKamalkumar Patel if (!systemType.empty()) 573c50c82aSKamalkumar Patel { 583c50c82aSKamalkumar Patel systemCompatibleMatchCallBack.reset(); 593c50c82aSKamalkumar Patel } 603c50c82aSKamalkumar Patel } 613c50c82aSKamalkumar Patel 623c50c82aSKamalkumar Patel /** @brief Method to get the system type information 633c50c82aSKamalkumar Patel * 643c50c82aSKamalkumar Patel * @return - the system type information 653c50c82aSKamalkumar Patel */ 663c50c82aSKamalkumar Patel std::optional<std::filesystem::path> Handler::getPlatformName() 673c50c82aSKamalkumar Patel { 683c50c82aSKamalkumar Patel if (!systemType.empty()) 693c50c82aSKamalkumar Patel { 703c50c82aSKamalkumar Patel return fs::path{systemType}; 713c50c82aSKamalkumar Patel } 723c50c82aSKamalkumar Patel 733c50c82aSKamalkumar Patel namespace fs = std::filesystem; 742edc34bbSKamalkumar Patel static const std::string entityMangerService = 752edc34bbSKamalkumar Patel "xyz.openbmc_project.EntityManager"; 763c50c82aSKamalkumar Patel 773c50c82aSKamalkumar Patel static constexpr auto searchpath = "/xyz/openbmc_project/"; 783c50c82aSKamalkumar Patel int depth = 0; 793c50c82aSKamalkumar Patel std::vector<std::string> systemCompatible = {compatibleInterface}; 802edc34bbSKamalkumar Patel 812edc34bbSKamalkumar Patel try 822edc34bbSKamalkumar Patel { 833c50c82aSKamalkumar Patel pldm::utils::GetSubTreeResponse response = 843c50c82aSKamalkumar Patel pldm::utils::DBusHandler().getSubtree(searchpath, depth, 853c50c82aSKamalkumar Patel systemCompatible); 863c50c82aSKamalkumar Patel auto& bus = pldm::utils::DBusHandler::getBus(); 873c50c82aSKamalkumar Patel 883c50c82aSKamalkumar Patel for (const auto& [objectPath, serviceMap] : response) 893c50c82aSKamalkumar Patel { 903c50c82aSKamalkumar Patel try 913c50c82aSKamalkumar Patel { 922edc34bbSKamalkumar Patel auto record = std::find_if( 932edc34bbSKamalkumar Patel serviceMap.begin(), serviceMap.end(), 942edc34bbSKamalkumar Patel [](auto map) { return map.first == entityMangerService; }); 952edc34bbSKamalkumar Patel 962edc34bbSKamalkumar Patel if (record != serviceMap.end()) 972edc34bbSKamalkumar Patel { 983c50c82aSKamalkumar Patel auto method = bus.new_method_call( 992edc34bbSKamalkumar Patel entityMangerService.c_str(), objectPath.c_str(), 1002edc34bbSKamalkumar Patel "org.freedesktop.DBus.Properties", "Get"); 1012edc34bbSKamalkumar Patel method.append(compatibleInterface, namesProperty); 1022edc34bbSKamalkumar Patel auto propSystemList = 1032edc34bbSKamalkumar Patel bus.call(method, dbusTimeout).unpack<PropertyValue>(); 1042edc34bbSKamalkumar Patel auto systemList = 1052edc34bbSKamalkumar Patel std::get<std::vector<std::string>>(propSystemList); 1062edc34bbSKamalkumar Patel 1073c50c82aSKamalkumar Patel if (!systemList.empty()) 1083c50c82aSKamalkumar Patel { 109*0a422696SKamalkumar Patel std::optional<std::string> sysType = 110*0a422696SKamalkumar Patel getSysSpecificJsonDir(sysDirPath, systemList); 1112edc34bbSKamalkumar Patel // once systemtype received,then resetting a callback 1122edc34bbSKamalkumar Patel systemCompatibleMatchCallBack.reset(); 113*0a422696SKamalkumar Patel if (sysType.has_value()) 114*0a422696SKamalkumar Patel { 115*0a422696SKamalkumar Patel systemType = sysType.value(); 116*0a422696SKamalkumar Patel } 1173c50c82aSKamalkumar Patel return fs::path{systemType}; 1183c50c82aSKamalkumar Patel } 1193c50c82aSKamalkumar Patel } 1202edc34bbSKamalkumar Patel } 1213c50c82aSKamalkumar Patel catch (const std::exception& e) 1223c50c82aSKamalkumar Patel { 1233c50c82aSKamalkumar Patel error( 12489644441SRiya Dixit "Failed to get Names property at '{PATH}' on interface '{INTERFACE}', error - {ERROR}", 1252edc34bbSKamalkumar Patel "PATH", objectPath, "INTERFACE", compatibleInterface, 1262edc34bbSKamalkumar Patel "ERROR", e); 1273c50c82aSKamalkumar Patel } 1283c50c82aSKamalkumar Patel } 1292edc34bbSKamalkumar Patel } 1302edc34bbSKamalkumar Patel catch (const std::exception& e) 1312edc34bbSKamalkumar Patel { 13289644441SRiya Dixit error( 13389644441SRiya Dixit "Failed to make a d-bus call to get platform name, error - {ERROR}", 1342edc34bbSKamalkumar Patel "ERROR", e); 1352edc34bbSKamalkumar Patel } 1363c50c82aSKamalkumar Patel return std::nullopt; 1373c50c82aSKamalkumar Patel } 1383c50c82aSKamalkumar Patel 139*0a422696SKamalkumar Patel std::optional<std::string> 140*0a422696SKamalkumar Patel Handler::getSysSpecificJsonDir(const fs::path& dirPath, 141*0a422696SKamalkumar Patel const std::vector<std::string>& dirNames) 142*0a422696SKamalkumar Patel { 143*0a422696SKamalkumar Patel // The current setup assumes that the BIOS and PDR configurations always 144*0a422696SKamalkumar Patel // come from the same system type. If, in the future, we need to use BIOS 145*0a422696SKamalkumar Patel // and PDR configurations from different system types, we should create 146*0a422696SKamalkumar Patel // separate system type folders for each and update the logic to support 147*0a422696SKamalkumar Patel // this. 148*0a422696SKamalkumar Patel 149*0a422696SKamalkumar Patel if (dirPath.empty()) 150*0a422696SKamalkumar Patel { 151*0a422696SKamalkumar Patel return std::nullopt; 152*0a422696SKamalkumar Patel } 153*0a422696SKamalkumar Patel 154*0a422696SKamalkumar Patel for (const auto& dirEntry : std::filesystem::directory_iterator{dirPath}) 155*0a422696SKamalkumar Patel { 156*0a422696SKamalkumar Patel if (dirEntry.is_directory()) 157*0a422696SKamalkumar Patel { 158*0a422696SKamalkumar Patel const auto sysDir = dirEntry.path().filename().string(); 159*0a422696SKamalkumar Patel if (std::find(dirNames.begin(), dirNames.end(), sysDir) != 160*0a422696SKamalkumar Patel dirNames.end()) 161*0a422696SKamalkumar Patel { 162*0a422696SKamalkumar Patel return sysDir; 163*0a422696SKamalkumar Patel } 164*0a422696SKamalkumar Patel } 165*0a422696SKamalkumar Patel } 166*0a422696SKamalkumar Patel 167*0a422696SKamalkumar Patel return std::nullopt; 168*0a422696SKamalkumar Patel } 169*0a422696SKamalkumar Patel 17062dd8ff2SArchana Kakani void Handler::registerSystemTypeCallback(SystemTypeCallback callback) 17162dd8ff2SArchana Kakani { 17262dd8ff2SArchana Kakani sysTypeCallback = callback; 17362dd8ff2SArchana Kakani } 17462dd8ff2SArchana Kakani 1753c50c82aSKamalkumar Patel } // namespace platform_config 1763c50c82aSKamalkumar Patel 1773c50c82aSKamalkumar Patel } // namespace responder 1783c50c82aSKamalkumar Patel 1793c50c82aSKamalkumar Patel } // namespace pldm 180