1 // SPDX-License-Identifier: Apache-2.0
2 // SPDX-FileCopyrightText: Copyright OpenBMC Authors
3
4 #include "dbus_utility.hpp"
5
6 #include "boost_formatters.hpp"
7 #include "dbus_singleton.hpp"
8 #include "logging.hpp"
9
10 #include <boost/system/error_code.hpp>
11 #include <sdbusplus/asio/connection.hpp>
12 #include <sdbusplus/asio/property.hpp>
13 #include <sdbusplus/message/native_types.hpp>
14
15 #include <array>
16 #include <cstdint>
17 #include <functional>
18 #include <regex>
19 #include <span>
20 #include <string>
21 #include <string_view>
22 #include <utility>
23
24 namespace dbus
25 {
26
27 namespace utility
28 {
29
escapePathForDbus(std::string & path)30 void escapePathForDbus(std::string& path)
31 {
32 const static std::regex reg("[^A-Za-z0-9_/]");
33 std::regex_replace(path.begin(), path.begin(), path.end(), reg, "_");
34 }
35
logError(const boost::system::error_code & ec)36 void logError(const boost::system::error_code& ec)
37 {
38 if (ec)
39 {
40 BMCWEB_LOG_ERROR("DBus error: {}, cannot call method", ec);
41 }
42 }
43
getAllProperties(const std::string & service,const std::string & objectPath,const std::string & interface,std::function<void (const boost::system::error_code &,const DBusPropertiesMap &)> && callback)44 void getAllProperties(const std::string& service, const std::string& objectPath,
45 const std::string& interface,
46 std::function<void(const boost::system::error_code&,
47 const DBusPropertiesMap&)>&& callback)
48 {
49 sdbusplus::asio::getAllProperties(*crow::connections::systemBus, service,
50 objectPath, interface,
51 std::move(callback));
52 }
53
getAllProperties(sdbusplus::asio::connection &,const std::string & service,const std::string & objectPath,const std::string & interface,std::function<void (const boost::system::error_code &,const DBusPropertiesMap &)> && callback)54 void getAllProperties(sdbusplus::asio::connection& /*conn*/,
55 const std::string& service, const std::string& objectPath,
56 const std::string& interface,
57 std::function<void(const boost::system::error_code&,
58 const DBusPropertiesMap&)>&& callback)
59 {
60 getAllProperties(service, objectPath, interface, std::move(callback));
61 }
62
checkDbusPathExists(const std::string & path,std::function<void (bool)> && callback)63 void checkDbusPathExists(const std::string& path,
64 std::function<void(bool)>&& callback)
65 {
66 dbus::utility::async_method_call(
67 [callback = std::move(callback)](const boost::system::error_code& ec,
68 const MapperGetObject& objectNames) {
69 callback(!ec && !objectNames.empty());
70 },
71 "xyz.openbmc_project.ObjectMapper",
72 "/xyz/openbmc_project/object_mapper",
73 "xyz.openbmc_project.ObjectMapper", "GetObject", path,
74 std::array<std::string, 0>());
75 }
76
getSubTree(const std::string & path,int32_t depth,std::span<const std::string_view> interfaces,std::function<void (const boost::system::error_code &,const MapperGetSubTreeResponse &)> && callback)77 void getSubTree(const std::string& path, int32_t depth,
78 std::span<const std::string_view> interfaces,
79 std::function<void(const boost::system::error_code&,
80 const MapperGetSubTreeResponse&)>&& callback)
81 {
82 dbus::utility::async_method_call(
83 [callback = std::move(callback)](
84 const boost::system::error_code& ec,
85 const MapperGetSubTreeResponse& subtree) { callback(ec, subtree); },
86 "xyz.openbmc_project.ObjectMapper",
87 "/xyz/openbmc_project/object_mapper",
88 "xyz.openbmc_project.ObjectMapper", "GetSubTree", path, depth,
89 interfaces);
90 }
91
getSubTreePaths(const std::string & path,int32_t depth,std::span<const std::string_view> interfaces,std::function<void (const boost::system::error_code &,const MapperGetSubTreePathsResponse &)> && callback)92 void getSubTreePaths(
93 const std::string& path, int32_t depth,
94 std::span<const std::string_view> interfaces,
95 std::function<void(const boost::system::error_code&,
96 const MapperGetSubTreePathsResponse&)>&& callback)
97 {
98 dbus::utility::async_method_call(
99 [callback = std::move(callback)](
100 const boost::system::error_code& ec,
101 const MapperGetSubTreePathsResponse& subtreePaths) {
102 callback(ec, subtreePaths);
103 },
104 "xyz.openbmc_project.ObjectMapper",
105 "/xyz/openbmc_project/object_mapper",
106 "xyz.openbmc_project.ObjectMapper", "GetSubTreePaths", path, depth,
107 interfaces);
108 }
109
getAssociatedSubTree(const sdbusplus::message::object_path & associatedPath,const sdbusplus::message::object_path & path,int32_t depth,std::span<const std::string_view> interfaces,std::function<void (const boost::system::error_code &,const MapperGetSubTreeResponse &)> && callback)110 void getAssociatedSubTree(
111 const sdbusplus::message::object_path& associatedPath,
112 const sdbusplus::message::object_path& path, int32_t depth,
113 std::span<const std::string_view> interfaces,
114 std::function<void(const boost::system::error_code&,
115 const MapperGetSubTreeResponse&)>&& callback)
116 {
117 dbus::utility::async_method_call(
118 [callback = std::move(callback)](
119 const boost::system::error_code& ec,
120 const MapperGetSubTreeResponse& subtree) { callback(ec, subtree); },
121 "xyz.openbmc_project.ObjectMapper",
122 "/xyz/openbmc_project/object_mapper",
123 "xyz.openbmc_project.ObjectMapper", "GetAssociatedSubTree",
124 associatedPath, path, depth, interfaces);
125 }
126
getAssociatedSubTreePaths(const sdbusplus::message::object_path & associatedPath,const sdbusplus::message::object_path & path,int32_t depth,std::span<const std::string_view> interfaces,std::function<void (const boost::system::error_code &,const MapperGetSubTreePathsResponse &)> && callback)127 void getAssociatedSubTreePaths(
128 const sdbusplus::message::object_path& associatedPath,
129 const sdbusplus::message::object_path& path, int32_t depth,
130 std::span<const std::string_view> interfaces,
131 std::function<void(const boost::system::error_code&,
132 const MapperGetSubTreePathsResponse&)>&& callback)
133 {
134 dbus::utility::async_method_call(
135 [callback = std::move(callback)](
136 const boost::system::error_code& ec,
137 const MapperGetSubTreePathsResponse& subtreePaths) {
138 callback(ec, subtreePaths);
139 },
140 "xyz.openbmc_project.ObjectMapper",
141 "/xyz/openbmc_project/object_mapper",
142 "xyz.openbmc_project.ObjectMapper", "GetAssociatedSubTreePaths",
143 associatedPath, path, depth, interfaces);
144 }
145
getAssociatedSubTreeById(const std::string & id,const std::string & path,std::span<const std::string_view> subtreeInterfaces,std::string_view association,std::span<const std::string_view> endpointInterfaces,std::function<void (const boost::system::error_code &,const MapperGetSubTreeResponse &)> && callback)146 void getAssociatedSubTreeById(
147 const std::string& id, const std::string& path,
148 std::span<const std::string_view> subtreeInterfaces,
149 std::string_view association,
150 std::span<const std::string_view> endpointInterfaces,
151 std::function<void(const boost::system::error_code&,
152 const MapperGetSubTreeResponse&)>&& callback)
153 {
154 dbus::utility::async_method_call(
155 [callback = std::move(callback)](
156 const boost::system::error_code& ec,
157 const MapperGetSubTreeResponse& subtree) { callback(ec, subtree); },
158 "xyz.openbmc_project.ObjectMapper",
159 "/xyz/openbmc_project/object_mapper",
160 "xyz.openbmc_project.ObjectMapper", "GetAssociatedSubTreeById", id,
161 path, subtreeInterfaces, association, endpointInterfaces);
162 }
163
getAssociatedSubTreePathsById(const std::string & id,const std::string & path,std::span<const std::string_view> subtreeInterfaces,std::string_view association,std::span<const std::string_view> endpointInterfaces,std::function<void (const boost::system::error_code &,const MapperGetSubTreePathsResponse &)> && callback)164 void getAssociatedSubTreePathsById(
165 const std::string& id, const std::string& path,
166 std::span<const std::string_view> subtreeInterfaces,
167 std::string_view association,
168 std::span<const std::string_view> endpointInterfaces,
169 std::function<void(const boost::system::error_code&,
170 const MapperGetSubTreePathsResponse&)>&& callback)
171 {
172 dbus::utility::async_method_call(
173 [callback = std::move(callback)](
174 const boost::system::error_code& ec,
175 const MapperGetSubTreePathsResponse& subtreePaths) {
176 callback(ec, subtreePaths);
177 },
178 "xyz.openbmc_project.ObjectMapper",
179 "/xyz/openbmc_project/object_mapper",
180 "xyz.openbmc_project.ObjectMapper", "GetAssociatedSubTreePathsById", id,
181 path, subtreeInterfaces, association, endpointInterfaces);
182 }
183
getDbusObject(const std::string & path,std::span<const std::string_view> interfaces,std::function<void (const boost::system::error_code &,const MapperGetObject &)> && callback)184 void getDbusObject(const std::string& path,
185 std::span<const std::string_view> interfaces,
186 std::function<void(const boost::system::error_code&,
187 const MapperGetObject&)>&& callback)
188 {
189 dbus::utility::async_method_call(
190 [callback = std::move(callback)](const boost::system::error_code& ec,
191 const MapperGetObject& object) {
192 callback(ec, object);
193 },
194 "xyz.openbmc_project.ObjectMapper",
195 "/xyz/openbmc_project/object_mapper",
196 "xyz.openbmc_project.ObjectMapper", "GetObject", path, interfaces);
197 }
198
getAssociationEndPoints(const std::string & path,std::function<void (const boost::system::error_code &,const MapperEndPoints &)> && callback)199 void getAssociationEndPoints(
200 const std::string& path,
201 std::function<void(const boost::system::error_code&,
202 const MapperEndPoints&)>&& callback)
203 {
204 getProperty<MapperEndPoints>("xyz.openbmc_project.ObjectMapper", path,
205 "xyz.openbmc_project.Association", "endpoints",
206 std::move(callback));
207 }
208
getManagedObjects(const std::string & service,const sdbusplus::message::object_path & path,std::function<void (const boost::system::error_code &,const ManagedObjectType &)> && callback)209 void getManagedObjects(const std::string& service,
210 const sdbusplus::message::object_path& path,
211 std::function<void(const boost::system::error_code&,
212 const ManagedObjectType&)>&& callback)
213 {
214 dbus::utility::async_method_call(
215 [callback = std::move(callback)](const boost::system::error_code& ec,
216 const ManagedObjectType& objects) {
217 callback(ec, objects);
218 },
219 service, path, "org.freedesktop.DBus.ObjectManager",
220 "GetManagedObjects");
221 }
222
223 } // namespace utility
224 } // namespace dbus
225