191ac8d3aSPatrick Venture #include "fru-fault-monitor.hpp" 291ac8d3aSPatrick Venture 391ac8d3aSPatrick Venture #include "elog-errors.hpp" 491ac8d3aSPatrick Venture 591ac8d3aSPatrick Venture #include <phosphor-logging/elog.hpp> 6*e9fb5c6aSGeorge Liu #include <phosphor-logging/lg2.hpp> 791ac8d3aSPatrick Venture #include <sdbusplus/exception.hpp> 84b062010SGeorge Liu #include <xyz/openbmc_project/Led/Fru/Monitor/error.hpp> 94b062010SGeorge Liu #include <xyz/openbmc_project/Led/Mapper/error.hpp> 103c6f29a0SDhruvaraj Subhashchandran 1159b86cd7SDhruvaraj Subhashchandran namespace phosphor 1259b86cd7SDhruvaraj Subhashchandran { 1359b86cd7SDhruvaraj Subhashchandran namespace led 1459b86cd7SDhruvaraj Subhashchandran { 1559b86cd7SDhruvaraj Subhashchandran namespace fru 1659b86cd7SDhruvaraj Subhashchandran { 1759b86cd7SDhruvaraj Subhashchandran namespace fault 1859b86cd7SDhruvaraj Subhashchandran { 1959b86cd7SDhruvaraj Subhashchandran namespace monitor 2059b86cd7SDhruvaraj Subhashchandran { 2159b86cd7SDhruvaraj Subhashchandran 223c6f29a0SDhruvaraj Subhashchandran using namespace phosphor::logging; 233c6f29a0SDhruvaraj Subhashchandran 243c6f29a0SDhruvaraj Subhashchandran constexpr auto MAPPER_BUSNAME = "xyz.openbmc_project.ObjectMapper"; 253c6f29a0SDhruvaraj Subhashchandran constexpr auto MAPPER_OBJ_PATH = "/xyz/openbmc_project/object_mapper"; 263c6f29a0SDhruvaraj Subhashchandran constexpr auto MAPPER_IFACE = "xyz.openbmc_project.ObjectMapper"; 273c6f29a0SDhruvaraj Subhashchandran constexpr auto OBJMGR_IFACE = "org.freedesktop.DBus.ObjectManager"; 283c6f29a0SDhruvaraj Subhashchandran constexpr auto LED_GROUPS = "/xyz/openbmc_project/led/groups/"; 293c6f29a0SDhruvaraj Subhashchandran constexpr auto LOG_PATH = "/xyz/openbmc_project/logging"; 30891c4769SDhruvaraj Subhashchandran constexpr auto LOG_IFACE = "xyz.openbmc_project.Logging.Entry"; 313c6f29a0SDhruvaraj Subhashchandran 3291ac8d3aSPatrick Venture using AssociationList = 3391ac8d3aSPatrick Venture std::vector<std::tuple<std::string, std::string, std::string>>; 34a41d282aSPatrick Williams using Attributes = std::variant<bool, AssociationList>; 35aebfde81SDhruvaraj Subhashchandran using PropertyName = std::string; 36b2f253b7SMatt Spinler using PropertyMap = std::map<PropertyName, Attributes>; 37b2f253b7SMatt Spinler using InterfaceName = std::string; 38b2f253b7SMatt Spinler using InterfaceMap = std::map<InterfaceName, PropertyMap>; 39aebfde81SDhruvaraj Subhashchandran 40891c4769SDhruvaraj Subhashchandran using Service = std::string; 41891c4769SDhruvaraj Subhashchandran using Path = std::string; 42891c4769SDhruvaraj Subhashchandran using Interface = std::string; 43891c4769SDhruvaraj Subhashchandran using Interfaces = std::vector<Interface>; 44891c4769SDhruvaraj Subhashchandran using MapperResponseType = std::map<Path, std::map<Service, Interfaces>>; 45891c4769SDhruvaraj Subhashchandran 463c6f29a0SDhruvaraj Subhashchandran using MethodErr = 473c6f29a0SDhruvaraj Subhashchandran sdbusplus::xyz::openbmc_project::Led::Mapper::Error::MethodError; 483c6f29a0SDhruvaraj Subhashchandran using ObjectNotFoundErr = 493c6f29a0SDhruvaraj Subhashchandran sdbusplus::xyz::openbmc_project::Led::Mapper::Error::ObjectNotFoundError; 5091ac8d3aSPatrick Venture using InventoryPathErr = sdbusplus::xyz::openbmc_project::Led::Fru::Monitor:: 5191ac8d3aSPatrick Venture Error::InventoryPathError; 523c6f29a0SDhruvaraj Subhashchandran 5391ac8d3aSPatrick Venture std::string getService(sdbusplus::bus::bus& bus, const std::string& path) 543c6f29a0SDhruvaraj Subhashchandran { 5591ac8d3aSPatrick Venture auto mapper = bus.new_method_call(MAPPER_BUSNAME, MAPPER_OBJ_PATH, 563c6f29a0SDhruvaraj Subhashchandran MAPPER_IFACE, "GetObject"); 573c6f29a0SDhruvaraj Subhashchandran mapper.append(path.c_str(), std::vector<std::string>({OBJMGR_IFACE})); 583c6f29a0SDhruvaraj Subhashchandran 593c6f29a0SDhruvaraj Subhashchandran std::map<std::string, std::vector<std::string>> mapperResponse; 60151122aaSWilliam A. Kennington III try 61151122aaSWilliam A. Kennington III { 62d78de14dSGeorge Liu auto mapperResponseMsg = bus.call(mapper); 633c6f29a0SDhruvaraj Subhashchandran mapperResponseMsg.read(mapperResponse); 64151122aaSWilliam A. Kennington III } 657152edcfSPatrick Williams catch (const sdbusplus::exception::exception& e) 66151122aaSWilliam A. Kennington III { 67*e9fb5c6aSGeorge Liu lg2::error( 68*e9fb5c6aSGeorge Liu "Failed to parse getService mapper response, ERROR = {ERROR}", 69*e9fb5c6aSGeorge Liu "ERROR", e); 70151122aaSWilliam A. Kennington III using namespace xyz::openbmc_project::Led::Mapper; 7191ac8d3aSPatrick Venture elog<ObjectNotFoundErr>(ObjectNotFoundError::METHOD_NAME("GetObject"), 72151122aaSWilliam A. Kennington III ObjectNotFoundError::PATH(path.c_str()), 7391ac8d3aSPatrick Venture ObjectNotFoundError::INTERFACE(OBJMGR_IFACE)); 74151122aaSWilliam A. Kennington III } 753c6f29a0SDhruvaraj Subhashchandran if (mapperResponse.empty()) 763c6f29a0SDhruvaraj Subhashchandran { 773c6f29a0SDhruvaraj Subhashchandran using namespace xyz::openbmc_project::Led::Mapper; 7891ac8d3aSPatrick Venture elog<ObjectNotFoundErr>(ObjectNotFoundError::METHOD_NAME("GetObject"), 793c6f29a0SDhruvaraj Subhashchandran ObjectNotFoundError::PATH(path.c_str()), 8091ac8d3aSPatrick Venture ObjectNotFoundError::INTERFACE(OBJMGR_IFACE)); 813c6f29a0SDhruvaraj Subhashchandran } 823c6f29a0SDhruvaraj Subhashchandran 833c6f29a0SDhruvaraj Subhashchandran return mapperResponse.cbegin()->first; 843c6f29a0SDhruvaraj Subhashchandran } 853c6f29a0SDhruvaraj Subhashchandran 8691ac8d3aSPatrick Venture void action(sdbusplus::bus::bus& bus, const std::string& path, bool assert) 8759b86cd7SDhruvaraj Subhashchandran { 883c6f29a0SDhruvaraj Subhashchandran std::string service; 893c6f29a0SDhruvaraj Subhashchandran try 903c6f29a0SDhruvaraj Subhashchandran { 91e77b8345SMatt Spinler std::string groups{LED_GROUPS}; 92e77b8345SMatt Spinler groups.pop_back(); 93e77b8345SMatt Spinler service = getService(bus, groups); 943c6f29a0SDhruvaraj Subhashchandran } 953c6f29a0SDhruvaraj Subhashchandran catch (MethodErr& e) 963c6f29a0SDhruvaraj Subhashchandran { 973c6f29a0SDhruvaraj Subhashchandran commit<MethodErr>(); 983c6f29a0SDhruvaraj Subhashchandran return; 993c6f29a0SDhruvaraj Subhashchandran } 1003c6f29a0SDhruvaraj Subhashchandran catch (ObjectNotFoundErr& e) 1013c6f29a0SDhruvaraj Subhashchandran { 1023c6f29a0SDhruvaraj Subhashchandran commit<ObjectNotFoundErr>(); 1033c6f29a0SDhruvaraj Subhashchandran return; 1043c6f29a0SDhruvaraj Subhashchandran } 1053c6f29a0SDhruvaraj Subhashchandran 1063c6f29a0SDhruvaraj Subhashchandran auto pos = path.rfind("/"); 1073c6f29a0SDhruvaraj Subhashchandran if (pos == std::string::npos) 1083c6f29a0SDhruvaraj Subhashchandran { 1093c6f29a0SDhruvaraj Subhashchandran using namespace xyz::openbmc_project::Led::Fru::Monitor; 11091ac8d3aSPatrick Venture report<InventoryPathErr>(InventoryPathError::PATH(path.c_str())); 1113c6f29a0SDhruvaraj Subhashchandran return; 1123c6f29a0SDhruvaraj Subhashchandran } 1133c6f29a0SDhruvaraj Subhashchandran auto unit = path.substr(pos + 1); 1143c6f29a0SDhruvaraj Subhashchandran 11591ac8d3aSPatrick Venture std::string ledPath = LED_GROUPS + unit + '_' + LED_FAULT; 1163c6f29a0SDhruvaraj Subhashchandran 11791ac8d3aSPatrick Venture auto method = bus.new_method_call(service.c_str(), ledPath.c_str(), 11891ac8d3aSPatrick Venture "org.freedesktop.DBus.Properties", "Set"); 1193c6f29a0SDhruvaraj Subhashchandran method.append("xyz.openbmc_project.Led.Group"); 1203c6f29a0SDhruvaraj Subhashchandran method.append("Asserted"); 1213c6f29a0SDhruvaraj Subhashchandran 122a41d282aSPatrick Williams method.append(std::variant<bool>(assert)); 12308d613e7SAdriana Kobylak 12408d613e7SAdriana Kobylak try 12508d613e7SAdriana Kobylak { 1263c6f29a0SDhruvaraj Subhashchandran bus.call_noreply(method); 12708d613e7SAdriana Kobylak } 1287152edcfSPatrick Williams catch (const sdbusplus::exception::exception& e) 12908d613e7SAdriana Kobylak { 13008d613e7SAdriana Kobylak // Log an info message, system may not have all the LED Groups defined 131*e9fb5c6aSGeorge Liu lg2::info("Failed to Assert LED Group, ERROR = {ERROR}", "ERROR", e); 13208d613e7SAdriana Kobylak } 1333c6f29a0SDhruvaraj Subhashchandran 13459b86cd7SDhruvaraj Subhashchandran return; 13559b86cd7SDhruvaraj Subhashchandran } 13659b86cd7SDhruvaraj Subhashchandran 1373eedbe44SPatrick Williams void Add::created(sdbusplus::message::message& msg) 13859b86cd7SDhruvaraj Subhashchandran { 1393eedbe44SPatrick Williams auto bus = msg.get_bus(); 1403c6f29a0SDhruvaraj Subhashchandran 141b2f253b7SMatt Spinler sdbusplus::message::object_path objectPath; 142b2f253b7SMatt Spinler InterfaceMap interfaces; 143151122aaSWilliam A. Kennington III try 144151122aaSWilliam A. Kennington III { 145b2f253b7SMatt Spinler msg.read(objectPath, interfaces); 146151122aaSWilliam A. Kennington III } 1477152edcfSPatrick Williams catch (const sdbusplus::exception::exception& e) 148151122aaSWilliam A. Kennington III { 149*e9fb5c6aSGeorge Liu lg2::error("Failed to parse created message, ERROR = {ERROR}", "ERROR", 150*e9fb5c6aSGeorge Liu e); 151151122aaSWilliam A. Kennington III return; 152151122aaSWilliam A. Kennington III } 1533c6f29a0SDhruvaraj Subhashchandran 154b2f253b7SMatt Spinler std::size_t found = objectPath.str.find(ELOG_ENTRY); 1553c6f29a0SDhruvaraj Subhashchandran if (found == std::string::npos) 1563c6f29a0SDhruvaraj Subhashchandran { 1573c6f29a0SDhruvaraj Subhashchandran // Not a new error entry skip 1583eedbe44SPatrick Williams return; 1593c6f29a0SDhruvaraj Subhashchandran } 160a6e48929SAndrew Geissler auto iter = interfaces.find("xyz.openbmc_project.Association.Definitions"); 161b2f253b7SMatt Spinler if (iter == interfaces.end()) 1623c6f29a0SDhruvaraj Subhashchandran { 1633eedbe44SPatrick Williams return; 1643c6f29a0SDhruvaraj Subhashchandran } 1653c6f29a0SDhruvaraj Subhashchandran 1663d2b0d62SMatt Spinler // Nothing else shows when a specific error log 1673d2b0d62SMatt Spinler // has been created. Do it here. 168*e9fb5c6aSGeorge Liu // TODO:(phosphor-logging#25): support sdbusplus::message::object_path 169*e9fb5c6aSGeorge Liu // directly. 170*e9fb5c6aSGeorge Liu lg2::info("{PATH} created", "PATH", objectPath.str); 1713d2b0d62SMatt Spinler 172a6e48929SAndrew Geissler auto attr = iter->second.find("Associations"); 173aebfde81SDhruvaraj Subhashchandran if (attr == iter->second.end()) 1743c6f29a0SDhruvaraj Subhashchandran { 1753eedbe44SPatrick Williams return; 1763c6f29a0SDhruvaraj Subhashchandran } 1773c6f29a0SDhruvaraj Subhashchandran 1785ebebeffSPatrick Williams auto& assocs = std::get<AssociationList>(attr->second); 1793c6f29a0SDhruvaraj Subhashchandran if (assocs.empty()) 1803c6f29a0SDhruvaraj Subhashchandran { 1813c6f29a0SDhruvaraj Subhashchandran // No associations skip 1823eedbe44SPatrick Williams return; 1833c6f29a0SDhruvaraj Subhashchandran } 1843c6f29a0SDhruvaraj Subhashchandran 1853c6f29a0SDhruvaraj Subhashchandran for (const auto& item : assocs) 1863c6f29a0SDhruvaraj Subhashchandran { 1873c6f29a0SDhruvaraj Subhashchandran if (std::get<1>(item).compare(CALLOUT_REV_ASSOCIATION) == 0) 1883c6f29a0SDhruvaraj Subhashchandran { 1893eedbe44SPatrick Williams removeWatches.emplace_back( 1903c6f29a0SDhruvaraj Subhashchandran std::make_unique<Remove>(bus, std::get<2>(item))); 191891c4769SDhruvaraj Subhashchandran action(bus, std::get<2>(item), true); 1923c6f29a0SDhruvaraj Subhashchandran } 1933c6f29a0SDhruvaraj Subhashchandran } 194aebfde81SDhruvaraj Subhashchandran 1953eedbe44SPatrick Williams return; 19659b86cd7SDhruvaraj Subhashchandran } 19759b86cd7SDhruvaraj Subhashchandran 19891122927SMatt Spinler void getLoggingSubTree(sdbusplus::bus::bus& bus, MapperResponseType& subtree) 199891c4769SDhruvaraj Subhashchandran { 200891c4769SDhruvaraj Subhashchandran auto depth = 0; 20191ac8d3aSPatrick Venture auto mapperCall = bus.new_method_call(MAPPER_BUSNAME, MAPPER_OBJ_PATH, 20291ac8d3aSPatrick Venture MAPPER_IFACE, "GetSubTree"); 203891c4769SDhruvaraj Subhashchandran mapperCall.append("/"); 204891c4769SDhruvaraj Subhashchandran mapperCall.append(depth); 205891c4769SDhruvaraj Subhashchandran mapperCall.append(std::vector<Interface>({LOG_IFACE})); 206891c4769SDhruvaraj Subhashchandran 20791122927SMatt Spinler try 20891122927SMatt Spinler { 209891c4769SDhruvaraj Subhashchandran auto mapperResponseMsg = bus.call(mapperCall); 21091122927SMatt Spinler mapperResponseMsg.read(subtree); 211151122aaSWilliam A. Kennington III } 2127152edcfSPatrick Williams catch (const sdbusplus::exception::exception& e) 213151122aaSWilliam A. Kennington III { 214*e9fb5c6aSGeorge Liu lg2::error( 215*e9fb5c6aSGeorge Liu "Failed to parse existing callouts subtree message, ERROR = {ERROR}", 216*e9fb5c6aSGeorge Liu "ERROR", e); 21791122927SMatt Spinler } 21891122927SMatt Spinler } 21991122927SMatt Spinler 22091122927SMatt Spinler void Add::processExistingCallouts(sdbusplus::bus::bus& bus) 22191122927SMatt Spinler { 22291122927SMatt Spinler MapperResponseType mapperResponse; 22391122927SMatt Spinler 22491122927SMatt Spinler getLoggingSubTree(bus, mapperResponse); 225891c4769SDhruvaraj Subhashchandran if (mapperResponse.empty()) 226891c4769SDhruvaraj Subhashchandran { 227fc30e0c1SDhruvaraj Subhashchandran // No errors to process. 228891c4769SDhruvaraj Subhashchandran return; 229891c4769SDhruvaraj Subhashchandran } 230891c4769SDhruvaraj Subhashchandran 231891c4769SDhruvaraj Subhashchandran for (const auto& elem : mapperResponse) 232891c4769SDhruvaraj Subhashchandran { 23391ac8d3aSPatrick Venture auto method = bus.new_method_call( 23491ac8d3aSPatrick Venture elem.second.begin()->first.c_str(), elem.first.c_str(), 23591ac8d3aSPatrick Venture "org.freedesktop.DBus.Properties", "Get"); 236a6e48929SAndrew Geissler method.append("xyz.openbmc_project.Association.Definitions"); 237a6e48929SAndrew Geissler method.append("Associations"); 238891c4769SDhruvaraj Subhashchandran auto reply = bus.call(method); 239891c4769SDhruvaraj Subhashchandran if (reply.is_method_error()) 240891c4769SDhruvaraj Subhashchandran { 241891c4769SDhruvaraj Subhashchandran // do not stop, continue with next elog 242*e9fb5c6aSGeorge Liu lg2::error("Error in getting associations"); 243891c4769SDhruvaraj Subhashchandran continue; 244891c4769SDhruvaraj Subhashchandran } 245891c4769SDhruvaraj Subhashchandran 246a41d282aSPatrick Williams std::variant<AssociationList> assoc; 247151122aaSWilliam A. Kennington III try 248151122aaSWilliam A. Kennington III { 249891c4769SDhruvaraj Subhashchandran reply.read(assoc); 250151122aaSWilliam A. Kennington III } 2517152edcfSPatrick Williams catch (const sdbusplus::exception::exception& e) 252151122aaSWilliam A. Kennington III { 253*e9fb5c6aSGeorge Liu lg2::error( 254*e9fb5c6aSGeorge Liu "Failed to parse existing callouts associations message, ERROR = {ERROR}", 255*e9fb5c6aSGeorge Liu "ERROR", e); 256151122aaSWilliam A. Kennington III continue; 257151122aaSWilliam A. Kennington III } 2585ebebeffSPatrick Williams auto& assocs = std::get<AssociationList>(assoc); 259891c4769SDhruvaraj Subhashchandran if (assocs.empty()) 260891c4769SDhruvaraj Subhashchandran { 261891c4769SDhruvaraj Subhashchandran // no associations, skip 262891c4769SDhruvaraj Subhashchandran continue; 263891c4769SDhruvaraj Subhashchandran } 264891c4769SDhruvaraj Subhashchandran 265891c4769SDhruvaraj Subhashchandran for (const auto& item : assocs) 266891c4769SDhruvaraj Subhashchandran { 267891c4769SDhruvaraj Subhashchandran if (std::get<1>(item).compare(CALLOUT_REV_ASSOCIATION) == 0) 268891c4769SDhruvaraj Subhashchandran { 269891c4769SDhruvaraj Subhashchandran removeWatches.emplace_back( 270891c4769SDhruvaraj Subhashchandran std::make_unique<Remove>(bus, std::get<2>(item))); 271891c4769SDhruvaraj Subhashchandran action(bus, std::get<2>(item), true); 272891c4769SDhruvaraj Subhashchandran } 273891c4769SDhruvaraj Subhashchandran } 274891c4769SDhruvaraj Subhashchandran } 275891c4769SDhruvaraj Subhashchandran } 276891c4769SDhruvaraj Subhashchandran 2773eedbe44SPatrick Williams void Remove::removed(sdbusplus::message::message& msg) 27859b86cd7SDhruvaraj Subhashchandran { 2793eedbe44SPatrick Williams auto bus = msg.get_bus(); 2803c6f29a0SDhruvaraj Subhashchandran 2813eedbe44SPatrick Williams action(bus, inventoryPath, false); 2823eedbe44SPatrick Williams return; 28359b86cd7SDhruvaraj Subhashchandran } 28459b86cd7SDhruvaraj Subhashchandran 28559b86cd7SDhruvaraj Subhashchandran } // namespace monitor 28659b86cd7SDhruvaraj Subhashchandran } // namespace fault 28759b86cd7SDhruvaraj Subhashchandran } // namespace fru 28859b86cd7SDhruvaraj Subhashchandran } // namespace led 28959b86cd7SDhruvaraj Subhashchandran } // namespace phosphor 290