blob: 3a6cfc79eeb3dbc4ce9e1a94a56d5a87b62e9d35 [file] [log] [blame]
Ed Tanous40e9b922024-09-10 13:50:16 -07001// SPDX-License-Identifier: Apache-2.0
2// SPDX-FileCopyrightText: Copyright OpenBMC Authors
3// SPDX-FileCopyrightText: Copyright 2018 Intel Corporation
James Feist5b4aa862018-08-16 14:07:01 -07004#pragma once
5
Ed Tanous95c63072024-03-26 13:19:52 -07006#include "boost_formatters.hpp"
Nan Zhou80d37e72022-06-21 17:46:14 +00007#include "dbus_singleton.hpp"
Ed Tanous863c1c22022-02-21 21:33:06 -08008#include "logging.hpp"
Nan Zhou80d37e72022-06-21 17:46:14 +00009
Ed Tanous478b7ad2024-07-15 19:11:54 -070010#include <boost/system/error_code.hpp>
George Liua4eb7612023-02-11 15:49:46 +080011#include <sdbusplus/asio/property.hpp>
Nan Zhoud5c80ad2022-07-11 01:16:31 +000012#include <sdbusplus/message/native_types.hpp>
James Feist5b4aa862018-08-16 14:07:01 -070013
Nan Zhou80d37e72022-06-21 17:46:14 +000014#include <array>
Nan Zhoud5c80ad2022-07-11 01:16:31 +000015#include <cstddef>
16#include <cstdint>
Manojkiran Eda17a897d2020-09-12 15:31:58 +053017#include <filesystem>
George Liu21384832022-11-09 11:21:15 +080018#include <functional>
Gunnar Mills1214b7e2020-06-04 10:11:30 -050019#include <regex>
George Liu21384832022-11-09 11:21:15 +080020#include <span>
Nan Zhoud5c80ad2022-07-11 01:16:31 +000021#include <sstream>
Nan Zhou80d37e72022-06-21 17:46:14 +000022#include <string>
George Liu7a1dbc42022-12-07 16:03:22 +080023#include <string_view>
Nan Zhou80d37e72022-06-21 17:46:14 +000024#include <tuple>
Nan Zhoud5c80ad2022-07-11 01:16:31 +000025#include <utility>
Ed Tanous40681292022-02-22 10:11:43 -080026#include <variant>
Nan Zhou80d37e72022-06-21 17:46:14 +000027#include <vector>
Gunnar Mills1214b7e2020-06-04 10:11:30 -050028
James Feist5b4aa862018-08-16 14:07:01 -070029namespace dbus
30{
31
32namespace utility
33{
34
Ed Tanousd1a64812021-12-13 12:14:05 -080035// clang-format off
Ed Tanous40681292022-02-22 10:11:43 -080036using DbusVariantType = std::variant<
Ed Tanousd1a64812021-12-13 12:14:05 -080037 std::vector<std::tuple<std::string, std::string, std::string>>,
38 std::vector<std::string>,
39 std::vector<double>,
40 std::string,
41 int64_t,
42 uint64_t,
43 double,
44 int32_t,
45 uint32_t,
46 int16_t,
47 uint16_t,
48 uint8_t,
49 bool,
Ed Tanousd1a64812021-12-13 12:14:05 -080050 std::vector<uint32_t>,
51 std::vector<uint16_t>,
52 sdbusplus::message::object_path,
Krzysztof Grobelny479e8992021-06-17 13:37:57 +000053 std::tuple<uint64_t, std::vector<std::tuple<std::string, double, uint64_t>>>,
Szymon Dompkef19ab442022-03-07 14:28:06 +010054 std::vector<sdbusplus::message::object_path>,
Ed Tanousd1a64812021-12-13 12:14:05 -080055 std::vector<std::tuple<std::string, std::string>>,
56 std::vector<std::tuple<uint32_t, std::vector<uint32_t>>>,
57 std::vector<std::tuple<uint32_t, size_t>>,
Krzysztof Grobelny479e8992021-06-17 13:37:57 +000058 std::vector<std::tuple<
59 std::vector<std::tuple<sdbusplus::message::object_path, std::string>>,
Ed Tanouse3648032024-10-16 18:06:39 -070060 std::string, std::string, uint64_t>>,
61 std::vector<std::pair<sdbusplus::message::object_path, std::string>>,
Ed Tanous58c71482024-10-19 14:35:07 -070062 std::vector<std::tuple<std::string, uint64_t, std::string, double>>,
63 std::vector<std::tuple<std::string, std::string, uint64_t, std::string>>
Ed Tanousd1a64812021-12-13 12:14:05 -080064 >;
James Feist5b4aa862018-08-16 14:07:01 -070065
Ed Tanousd1a64812021-12-13 12:14:05 -080066// clang-format on
Ed Tanous711ac7a2021-12-20 09:34:41 -080067using DBusPropertiesMap = std::vector<std::pair<std::string, DbusVariantType>>;
Michael Shen80f79a42023-08-24 13:41:53 +000068using DBusInterfacesMap =
69 std::vector<std::pair<std::string, DBusPropertiesMap>>;
Zbigniew Kurzynski755a33c2020-02-28 14:06:37 +010070using ManagedObjectType =
Michael Shen80f79a42023-08-24 13:41:53 +000071 std::vector<std::pair<sdbusplus::message::object_path, DBusInterfacesMap>>;
James Feist5b4aa862018-08-16 14:07:01 -070072
Shantappa Teekappanavar5df6eda2022-01-18 12:29:28 -060073// Map of service name to list of interfaces
74using MapperServiceMap =
75 std::vector<std::pair<std::string, std::vector<std::string>>>;
76
77// Map of object paths to MapperServiceMaps
78using MapperGetSubTreeResponse =
79 std::vector<std::pair<std::string, MapperServiceMap>>;
80
Ed Tanousb9d36b42022-02-26 21:42:46 -080081using MapperGetObject =
82 std::vector<std::pair<std::string, std::vector<std::string>>>;
83
84using MapperGetAncestorsResponse = std::vector<
85 std::pair<std::string,
86 std::vector<std::pair<std::string, std::vector<std::string>>>>>;
87
88using MapperGetSubTreePathsResponse = std::vector<std::string>;
89
George Liua4eb7612023-02-11 15:49:46 +080090using MapperEndPoints = std::vector<std::string>;
91
James Feist5b4aa862018-08-16 14:07:01 -070092inline void escapePathForDbus(std::string& path)
93{
Ed Tanous4b242742023-05-11 09:51:51 -070094 const static std::regex reg("[^A-Za-z0-9_/]");
James Feist5b4aa862018-08-16 14:07:01 -070095 std::regex_replace(path.begin(), path.begin(), path.end(), reg, "_");
96}
97
Ed Tanous863c1c22022-02-21 21:33:06 -080098inline void logError(const boost::system::error_code& ec)
99{
100 if (ec)
101 {
Ed Tanous62598e32023-07-17 17:06:25 -0700102 BMCWEB_LOG_ERROR("DBus error: {}, cannot call method", ec);
Ed Tanous863c1c22022-02-21 21:33:06 -0800103 }
104}
105
James Feist5b4aa862018-08-16 14:07:01 -0700106// gets the string N strings deep into a path
107// i.e. /0th/1st/2nd/3rd
108inline bool getNthStringFromPath(const std::string& path, int index,
109 std::string& result)
110{
Manojkiran Eda17a897d2020-09-12 15:31:58 +0530111 if (index < 0)
James Feist5b4aa862018-08-16 14:07:01 -0700112 {
Manojkiran Eda17a897d2020-09-12 15:31:58 +0530113 return false;
114 }
115
116 std::filesystem::path p1(path);
117 int count = -1;
Patrick Williams89492a12023-05-10 07:51:34 -0500118 for (const auto& element : p1)
Manojkiran Eda17a897d2020-09-12 15:31:58 +0530119 {
120 if (element.has_filename())
James Feist5b4aa862018-08-16 14:07:01 -0700121 {
Manojkiran Eda17a897d2020-09-12 15:31:58 +0530122 ++count;
James Feist5b4aa862018-08-16 14:07:01 -0700123 if (count == index)
124 {
Manojkiran Eda17a897d2020-09-12 15:31:58 +0530125 result = element.stem().string();
James Feist5b4aa862018-08-16 14:07:01 -0700126 break;
127 }
128 }
129 }
Ed Tanousdcf2ebc2022-01-25 10:07:45 -0800130 return count >= index;
James Feist5b4aa862018-08-16 14:07:01 -0700131}
132
Ed Tanousdeae6a72024-11-11 21:58:57 -0800133inline void
134 getAllProperties(const std::string& service, const std::string& objectPath,
135 const std::string& interface,
136 std::function<void(const boost::system::error_code&,
137 const DBusPropertiesMap&)>&& callback)
138{
139 sdbusplus::asio::getAllProperties(*crow::connections::systemBus, service,
140 objectPath, interface,
141 std::move(callback));
142}
143
144template <typename PropertyType>
145inline void getProperty(
146 const std::string& service, const std::string& objectPath,
147 const std::string& interface, const std::string& propertyName,
148 std::function<void(const boost::system::error_code&, const PropertyType&)>&&
149 callback)
150{
151 sdbusplus::asio::getProperty<PropertyType>(
152 *crow::connections::systemBus, service, objectPath, interface,
153 propertyName, std::move(callback));
154}
155
156template <typename PropertyType>
157inline void getProperty(
158 sdbusplus::asio::connection& /*conn*/, const std::string& service,
159 const std::string& objectPath, const std::string& interface,
160 const std::string& propertyName,
161 std::function<void(const boost::system::error_code&, const PropertyType&)>&&
162 callback)
163{
164 getProperty(service, objectPath, interface, propertyName,
165 std::move(callback));
166}
167
168inline void getAllProperties(
169 sdbusplus::asio::connection& /*conn*/, const std::string& service,
170 const std::string& objectPath, const std::string& interface,
171 std::function<void(const boost::system::error_code&,
172 const DBusPropertiesMap&)>&& callback)
173{
174 getAllProperties(service, objectPath, interface, std::move(callback));
175}
176
Ed Tanousd35c2412024-11-18 04:45:30 -0800177inline void checkDbusPathExists(const std::string& path,
178 std::function<void(bool)>&& callback)
Ratan Gupta22c33712019-05-03 21:50:28 +0530179{
Ratan Gupta22c33712019-05-03 21:50:28 +0530180 crow::connections::systemBus->async_method_call(
Ed Tanousd35c2412024-11-18 04:45:30 -0800181 [callback = std::move(callback)](const boost::system::error_code& ec,
182 const MapperGetObject& objectNames) {
Patrick Williamsbd79bce2024-08-16 15:22:20 -0400183 callback(!ec && !objectNames.empty());
184 },
Ratan Gupta22c33712019-05-03 21:50:28 +0530185 "xyz.openbmc_project.ObjectMapper",
186 "/xyz/openbmc_project/object_mapper",
187 "xyz.openbmc_project.ObjectMapper", "GetObject", path,
188 std::array<std::string, 0>());
189}
190
George Liu21384832022-11-09 11:21:15 +0800191inline void
George Liue99073f2022-12-09 11:06:16 +0800192 getSubTree(const std::string& path, int32_t depth,
193 std::span<const std::string_view> interfaces,
George Liu21384832022-11-09 11:21:15 +0800194 std::function<void(const boost::system::error_code&,
195 const MapperGetSubTreeResponse&)>&& callback)
196{
197 crow::connections::systemBus->async_method_call(
198 [callback{std::move(callback)}](
Ed Tanous5e7e2dc2023-02-16 10:37:01 -0800199 const boost::system::error_code& ec,
George Liu21384832022-11-09 11:21:15 +0800200 const MapperGetSubTreeResponse& subtree) { callback(ec, subtree); },
201 "xyz.openbmc_project.ObjectMapper",
202 "/xyz/openbmc_project/object_mapper",
George Liue99073f2022-12-09 11:06:16 +0800203 "xyz.openbmc_project.ObjectMapper", "GetSubTree", path, depth,
204 interfaces);
George Liu21384832022-11-09 11:21:15 +0800205}
206
207inline void getSubTreePaths(
George Liu7a1dbc42022-12-07 16:03:22 +0800208 const std::string& path, int32_t depth,
209 std::span<const std::string_view> interfaces,
George Liu21384832022-11-09 11:21:15 +0800210 std::function<void(const boost::system::error_code&,
211 const MapperGetSubTreePathsResponse&)>&& callback)
212{
213 crow::connections::systemBus->async_method_call(
214 [callback{std::move(callback)}](
Ed Tanous5e7e2dc2023-02-16 10:37:01 -0800215 const boost::system::error_code& ec,
George Liu21384832022-11-09 11:21:15 +0800216 const MapperGetSubTreePathsResponse& subtreePaths) {
Patrick Williamsbd79bce2024-08-16 15:22:20 -0400217 callback(ec, subtreePaths);
218 },
George Liu21384832022-11-09 11:21:15 +0800219 "xyz.openbmc_project.ObjectMapper",
220 "/xyz/openbmc_project/object_mapper",
George Liu7a1dbc42022-12-07 16:03:22 +0800221 "xyz.openbmc_project.ObjectMapper", "GetSubTreePaths", path, depth,
George Liu21384832022-11-09 11:21:15 +0800222 interfaces);
223}
224
Willy Tu8d018362023-04-14 09:14:16 -0700225inline void getAssociatedSubTree(
226 const sdbusplus::message::object_path& associatedPath,
227 const sdbusplus::message::object_path& path, int32_t depth,
228 std::span<const std::string_view> interfaces,
229 std::function<void(const boost::system::error_code&,
230 const MapperGetSubTreeResponse&)>&& callback)
231{
232 crow::connections::systemBus->async_method_call(
233 [callback{std::move(callback)}](
234 const boost::system::error_code& ec,
235 const MapperGetSubTreeResponse& subtree) { callback(ec, subtree); },
236 "xyz.openbmc_project.ObjectMapper",
237 "/xyz/openbmc_project/object_mapper",
238 "xyz.openbmc_project.ObjectMapper", "GetAssociatedSubTree",
239 associatedPath, path, depth, interfaces);
240}
241
242inline void getAssociatedSubTreePaths(
243 const sdbusplus::message::object_path& associatedPath,
244 const sdbusplus::message::object_path& path, int32_t depth,
245 std::span<const std::string_view> interfaces,
246 std::function<void(const boost::system::error_code&,
247 const MapperGetSubTreePathsResponse&)>&& callback)
248{
249 crow::connections::systemBus->async_method_call(
250 [callback{std::move(callback)}](
251 const boost::system::error_code& ec,
252 const MapperGetSubTreePathsResponse& subtreePaths) {
Patrick Williamsbd79bce2024-08-16 15:22:20 -0400253 callback(ec, subtreePaths);
254 },
Willy Tu8d018362023-04-14 09:14:16 -0700255 "xyz.openbmc_project.ObjectMapper",
256 "/xyz/openbmc_project/object_mapper",
257 "xyz.openbmc_project.ObjectMapper", "GetAssociatedSubTreePaths",
258 associatedPath, path, depth, interfaces);
259}
260
Lakshmi Yadlapati64d8e802024-06-26 17:41:19 -0500261inline void getAssociatedSubTreeById(
262 const std::string& id, const std::string& path,
263 std::span<const std::string_view> subtreeInterfaces,
264 std::string_view association,
265 std::span<const std::string_view> endpointInterfaces,
266 std::function<void(const boost::system::error_code&,
267 const MapperGetSubTreeResponse&)>&& callback)
268{
269 crow::connections::systemBus->async_method_call(
270 [callback{std::move(callback)}](
271 const boost::system::error_code& ec,
272 const MapperGetSubTreeResponse& subtree) { callback(ec, subtree); },
273 "xyz.openbmc_project.ObjectMapper",
274 "/xyz/openbmc_project/object_mapper",
275 "xyz.openbmc_project.ObjectMapper", "GetAssociatedSubTreeById", id,
276 path, subtreeInterfaces, association, endpointInterfaces);
277}
278
279inline void getAssociatedSubTreePathsById(
280 const std::string& id, const std::string& path,
281 std::span<const std::string_view> subtreeInterfaces,
282 std::string_view association,
283 std::span<const std::string_view> endpointInterfaces,
284 std::function<void(const boost::system::error_code&,
285 const MapperGetSubTreePathsResponse&)>&& callback)
286{
287 crow::connections::systemBus->async_method_call(
288 [callback{std::move(callback)}](
289 const boost::system::error_code& ec,
290 const MapperGetSubTreePathsResponse& subtreePaths) {
291 callback(ec, subtreePaths);
292 },
293 "xyz.openbmc_project.ObjectMapper",
294 "/xyz/openbmc_project/object_mapper",
295 "xyz.openbmc_project.ObjectMapper", "GetAssociatedSubTreePathsById", id,
296 path, subtreeInterfaces, association, endpointInterfaces);
297}
298
Patrick Williamsbd79bce2024-08-16 15:22:20 -0400299inline void getDbusObject(
300 const std::string& path, std::span<const std::string_view> interfaces,
301 std::function<void(const boost::system::error_code&,
302 const MapperGetObject&)>&& callback)
George Liu2b731192023-01-11 16:27:13 +0800303{
304 crow::connections::systemBus->async_method_call(
305 [callback{std::move(callback)}](const boost::system::error_code& ec,
306 const MapperGetObject& object) {
Patrick Williamsbd79bce2024-08-16 15:22:20 -0400307 callback(ec, object);
308 },
George Liu2b731192023-01-11 16:27:13 +0800309 "xyz.openbmc_project.ObjectMapper",
310 "/xyz/openbmc_project/object_mapper",
311 "xyz.openbmc_project.ObjectMapper", "GetObject", path, interfaces);
312}
313
George Liua4eb7612023-02-11 15:49:46 +0800314inline void getAssociationEndPoints(
315 const std::string& path,
316 std::function<void(const boost::system::error_code&,
317 const MapperEndPoints&)>&& callback)
318{
Ed Tanousdeae6a72024-11-11 21:58:57 -0800319 getProperty<MapperEndPoints>("xyz.openbmc_project.ObjectMapper", path,
320 "xyz.openbmc_project.Association", "endpoints",
321 std::move(callback));
George Liua4eb7612023-02-11 15:49:46 +0800322}
323
Patrick Williamsbd79bce2024-08-16 15:22:20 -0400324inline void getManagedObjects(
325 const std::string& service, const sdbusplus::message::object_path& path,
326 std::function<void(const boost::system::error_code&,
327 const ManagedObjectType&)>&& callback)
George Liuf5892d02023-03-01 10:37:08 +0800328{
329 crow::connections::systemBus->async_method_call(
330 [callback{std::move(callback)}](const boost::system::error_code& ec,
331 const ManagedObjectType& objects) {
Patrick Williamsbd79bce2024-08-16 15:22:20 -0400332 callback(ec, objects);
333 },
George Liuf5892d02023-03-01 10:37:08 +0800334 service, path, "org.freedesktop.DBus.ObjectManager",
335 "GetManagedObjects");
336}
337
James Feist5b4aa862018-08-16 14:07:01 -0700338} // namespace utility
339} // namespace dbus