1 #include "settings.hpp"
2 
3 #include <ipmid/utils.hpp>
4 #include <phosphor-logging/elog-errors.hpp>
5 #include <phosphor-logging/log.hpp>
6 #include <sdbusplus/message/types.hpp>
7 #include <xyz/openbmc_project/Common/error.hpp>
8 
9 namespace settings
10 {
11 
12 using namespace phosphor::logging;
13 using namespace sdbusplus::error::xyz::openbmc_project::common;
14 
15 constexpr auto mapperService = "xyz.openbmc_project.ObjectMapper";
16 constexpr auto mapperPath = "/xyz/openbmc_project/object_mapper";
17 constexpr auto mapperIntf = "xyz.openbmc_project.ObjectMapper";
18 
19 Objects::Objects(sdbusplus::bus_t& bus, const std::vector<Interface>& filter) :
20     bus(bus)
21 {
22     auto depth = 0;
23 
24     auto mapperCall = bus.new_method_call(mapperService, mapperPath, mapperIntf,
25                                           "GetSubTree");
26     mapperCall.append(root);
27     mapperCall.append(depth);
28     mapperCall.append(filter);
29 
30     using Interfaces = std::vector<Interface>;
31     using MapperResponse = std::map<Path, std::map<Service, Interfaces>>;
32     MapperResponse result;
33     try
34     {
35         auto response = bus.call(mapperCall);
36         response.read(result);
37     }
38     catch (const std::exception& e)
39     {
40         log<level::ERR>("Error in mapper GetSubTree",
41                         entry("ERROR=%s", e.what()));
42         elog<InternalFailure>();
43     }
44 
45     for (auto& iter : result)
46     {
47         const auto& path = iter.first;
48         for (auto& interface : iter.second.begin()->second)
49         {
50             auto found = map.find(interface);
51             if (map.end() != found)
52             {
53                 auto& paths = found->second;
54                 paths.push_back(path);
55             }
56             else
57             {
58                 map.emplace(std::move(interface), std::vector<Path>({path}));
59             }
60         }
61     }
62 }
63 
64 Service Objects::service(const Path& path, const Interface& interface) const
65 {
66     using Interfaces = std::vector<Interface>;
67     auto mapperCall = bus.new_method_call(mapperService, mapperPath, mapperIntf,
68                                           "GetObject");
69     mapperCall.append(path);
70     mapperCall.append(Interfaces({interface}));
71 
72     std::map<Service, Interfaces> result;
73     try
74     {
75         auto response = bus.call(mapperCall);
76         response.read(result);
77         return result.begin()->first;
78     }
79     catch (const std::exception& e)
80     {
81         log<level::ERR>("Invalid response from mapper",
82                         entry("ERROR=%s", e.what()));
83         elog<InternalFailure>();
84     }
85 }
86 
87 } // namespace settings
88