blob: 4068923749ccefb9b75af2d504b56336b247c832 [file] [log] [blame]
Brad Bishop6e9cfdb2017-06-08 11:59:58 -04001#pragma once
2
Brad Bishop6e9cfdb2017-06-08 11:59:58 -04003#include <phosphor-logging/elog-errors.hpp>
Matthew Barth9e80c872020-05-26 10:50:29 -05004#include <phosphor-logging/elog.hpp>
5#include <phosphor-logging/log.hpp>
6#include <sdbusplus/bus.hpp>
7#include <sdbusplus/bus/match.hpp>
8#include <sdbusplus/message.hpp>
Brad Bishop6e9cfdb2017-06-08 11:59:58 -04009#include <xyz/openbmc_project/Common/error.hpp>
10
Patrick Williamsfbf47032023-07-17 12:27:34 -050011#include <format>
12
Brad Bishop6e9cfdb2017-06-08 11:59:58 -040013namespace phosphor
14{
15namespace fan
16{
17namespace util
18{
19namespace detail
20{
21namespace errors = sdbusplus::xyz::openbmc_project::Common::Error;
22} // namespace detail
23
Matt Spinlerba7b5fe2018-04-25 15:26:10 -050024/**
25 * @class DBusError
26 *
27 * The base class for the exceptions thrown on fails in the various
28 * SDBusPlus calls. Used so that a single catch statement can catch
29 * any type of these exceptions.
30 *
31 * None of these exceptions will log anything when they are created,
32 * it is up to the handler to do that if desired.
33 */
34class DBusError : public std::runtime_error
35{
Matthew Barth9e80c872020-05-26 10:50:29 -050036 public:
Patrick Williams61b73292023-05-10 07:50:12 -050037 explicit DBusError(const std::string& msg) : std::runtime_error(msg) {}
Matt Spinlerba7b5fe2018-04-25 15:26:10 -050038};
39
40/**
41 * @class DBusMethodError
42 *
43 * Thrown on a DBus Method call failure
44 */
45class DBusMethodError : public DBusError
46{
Matthew Barth9e80c872020-05-26 10:50:29 -050047 public:
48 DBusMethodError(const std::string& busName, const std::string& path,
49 const std::string& interface, const std::string& method) :
Patrick Williamsfbf47032023-07-17 12:27:34 -050050 DBusError(std::format("DBus method failed: {} {} {} {}", busName, path,
Matt Spinler23f87572021-01-20 14:20:30 -060051 interface, method)),
Matthew Barth9e80c872020-05-26 10:50:29 -050052 busName(busName), path(path), interface(interface), method(method)
53 {}
Matt Spinlerba7b5fe2018-04-25 15:26:10 -050054
Matthew Barth9e80c872020-05-26 10:50:29 -050055 const std::string busName;
56 const std::string path;
57 const std::string interface;
58 const std::string method;
Matt Spinlerba7b5fe2018-04-25 15:26:10 -050059};
60
61/**
62 * @class DBusServiceError
63 *
64 * Thrown when a service lookup fails. Usually this points to
65 * the object path not being present in D-Bus.
66 */
67class DBusServiceError : public DBusError
68{
Matthew Barth9e80c872020-05-26 10:50:29 -050069 public:
70 DBusServiceError(const std::string& path, const std::string& interface) :
Matt Spinler23f87572021-01-20 14:20:30 -060071 DBusError(
Patrick Williamsfbf47032023-07-17 12:27:34 -050072 std::format("DBus service lookup failed: {} {}", path, interface)),
Matt Spinler23f87572021-01-20 14:20:30 -060073 path(path), interface(interface)
Matthew Barth9e80c872020-05-26 10:50:29 -050074 {}
Matt Spinlerba7b5fe2018-04-25 15:26:10 -050075
Matthew Barth9e80c872020-05-26 10:50:29 -050076 const std::string path;
77 const std::string interface;
Matt Spinlerba7b5fe2018-04-25 15:26:10 -050078};
79
Matthew Barth88923a02018-05-11 10:14:44 -050080/**
81 * @class DBusPropertyError
82 *
83 * Thrown when a set/get property fails.
84 */
85class DBusPropertyError : public DBusError
86{
Matthew Barth9e80c872020-05-26 10:50:29 -050087 public:
Matt Spinler23f87572021-01-20 14:20:30 -060088 DBusPropertyError(const std::string& msg, const std::string& busName,
Matthew Barth9e80c872020-05-26 10:50:29 -050089 const std::string& path, const std::string& interface,
90 const std::string& property) :
Patrick Williamsfbf47032023-07-17 12:27:34 -050091 DBusError(msg + std::format(": {} {} {} {}", busName, path, interface,
Matt Spinler23f87572021-01-20 14:20:30 -060092 property)),
Matthew Barth9e80c872020-05-26 10:50:29 -050093 busName(busName), path(path), interface(interface), property(property)
94 {}
Matthew Barth88923a02018-05-11 10:14:44 -050095
Matthew Barth9e80c872020-05-26 10:50:29 -050096 const std::string busName;
97 const std::string path;
98 const std::string interface;
99 const std::string property;
Matthew Barth88923a02018-05-11 10:14:44 -0500100};
101
Brad Bishop1e4922a2017-07-12 22:56:49 -0400102/** @brief Alias for PropertiesChanged signal callbacks. */
Matthew Barth9e80c872020-05-26 10:50:29 -0500103template <typename... T>
Patrick Williamsc21d0b32020-05-13 17:55:14 -0500104using Properties = std::map<std::string, std::variant<T...>>;
Brad Bishop1e4922a2017-07-12 22:56:49 -0400105
Brad Bishop6e9cfdb2017-06-08 11:59:58 -0400106/** @class SDBusPlus
107 * @brief DBus access delegate implementation for sdbusplus.
108 */
109class SDBusPlus
110{
Matthew Barth9e80c872020-05-26 10:50:29 -0500111 public:
112 /** @brief Get the bus connection. */
113 static auto& getBus() __attribute__((pure))
114 {
115 static auto bus = sdbusplus::bus::new_default();
116 return bus;
117 }
Brad Bishop6e9cfdb2017-06-08 11:59:58 -0400118
Matthew Barth9e80c872020-05-26 10:50:29 -0500119 /** @brief Invoke a method. */
120 template <typename... Args>
Patrick Williamscb356d42022-07-22 19:26:53 -0500121 static auto callMethod(sdbusplus::bus_t& bus, const std::string& busName,
Matthew Barth9e80c872020-05-26 10:50:29 -0500122 const std::string& path,
123 const std::string& interface,
124 const std::string& method, Args&&... args)
125 {
126 auto reqMsg = bus.new_method_call(busName.c_str(), path.c_str(),
127 interface.c_str(), method.c_str());
128 reqMsg.append(std::forward<Args>(args)...);
129 try
Brad Bishop6e9cfdb2017-06-08 11:59:58 -0400130 {
Matthew Barth9e80c872020-05-26 10:50:29 -0500131 auto respMsg = bus.call(reqMsg);
132 if (respMsg.is_method_error())
Brad Bishop6e9cfdb2017-06-08 11:59:58 -0400133 {
Matt Spinlerba7b5fe2018-04-25 15:26:10 -0500134 throw DBusMethodError{busName, path, interface, method};
Brad Bishop6e9cfdb2017-06-08 11:59:58 -0400135 }
Matthew Barth7c48d102018-05-09 14:52:36 -0500136 return respMsg;
137 }
Patrick Williamscb356d42022-07-22 19:26:53 -0500138 catch (const sdbusplus::exception_t&)
Matthew Barth9e80c872020-05-26 10:50:29 -0500139 {
140 throw DBusMethodError{busName, path, interface, method};
141 }
142 }
143
144 /** @brief Invoke a method. */
145 template <typename... Args>
146 static auto callMethod(const std::string& busName, const std::string& path,
147 const std::string& interface,
148 const std::string& method, Args&&... args)
149 {
150 return callMethod(getBus(), busName, path, interface, method,
151 std::forward<Args>(args)...);
152 }
153
154 /** @brief Invoke a method and read the response. */
155 template <typename Ret, typename... Args>
156 static auto
Patrick Williamscb356d42022-07-22 19:26:53 -0500157 callMethodAndRead(sdbusplus::bus_t& bus, const std::string& busName,
Matthew Barth9e80c872020-05-26 10:50:29 -0500158 const std::string& path, const std::string& interface,
159 const std::string& method, Args&&... args)
160 {
Patrick Williamscb356d42022-07-22 19:26:53 -0500161 sdbusplus::message_t respMsg = callMethod<Args...>(
Matthew Barth9e80c872020-05-26 10:50:29 -0500162 bus, busName, path, interface, method, std::forward<Args>(args)...);
163 Ret resp;
164 respMsg.read(resp);
165 return resp;
166 }
167
168 /** @brief Invoke a method and read the response. */
169 template <typename Ret, typename... Args>
Patrick Williamsdfddd642024-08-16 15:21:51 -0400170 static auto callMethodAndRead(
171 const std::string& busName, const std::string& path,
172 const std::string& interface, const std::string& method, Args&&... args)
Matthew Barth9e80c872020-05-26 10:50:29 -0500173 {
174 return callMethodAndRead<Ret>(getBus(), busName, path, interface,
175 method, std::forward<Args>(args)...);
176 }
177
178 /** @brief Get subtree from the mapper without checking response. */
Patrick Williamscb356d42022-07-22 19:26:53 -0500179 static auto getSubTreeRaw(sdbusplus::bus_t& bus, const std::string& path,
Matthew Barth9e80c872020-05-26 10:50:29 -0500180 const std::string& interface, int32_t depth)
181 {
182 using namespace std::literals::string_literals;
183
184 using Path = std::string;
185 using Intf = std::string;
186 using Serv = std::string;
187 using Intfs = std::vector<Intf>;
188 using Objects = std::map<Path, std::map<Serv, Intfs>>;
189 Intfs intfs = {interface};
190
Patrick Williamsdfddd642024-08-16 15:21:51 -0400191 return callMethodAndRead<Objects>(
192 bus, "xyz.openbmc_project.ObjectMapper"s,
193 "/xyz/openbmc_project/object_mapper"s,
194 "xyz.openbmc_project.ObjectMapper"s, "GetSubTree"s, path, depth,
195 intfs);
Matthew Barth9e80c872020-05-26 10:50:29 -0500196 }
197
Mike Capps7a401a22021-07-12 13:59:31 -0400198 /** @brief Get subtree from the mapper without checking response,
199 * (multiple interfaces version). */
Patrick Williamscb356d42022-07-22 19:26:53 -0500200 static auto getSubTreeRaw(sdbusplus::bus_t& bus, const std::string& path,
Mike Capps7a401a22021-07-12 13:59:31 -0400201 const std::vector<std::string>& intfs,
202 int32_t depth)
203 {
204 using namespace std::literals::string_literals;
205
206 using Path = std::string;
207 using Intf = std::string;
208 using Serv = std::string;
209 using Intfs = std::vector<Intf>;
210 using Objects = std::map<Path, std::map<Serv, Intfs>>;
211
Patrick Williamsdfddd642024-08-16 15:21:51 -0400212 return callMethodAndRead<Objects>(
213 bus, "xyz.openbmc_project.ObjectMapper"s,
214 "/xyz/openbmc_project/object_mapper"s,
215 "xyz.openbmc_project.ObjectMapper"s, "GetSubTree"s, path, depth,
216 intfs);
Mike Capps7a401a22021-07-12 13:59:31 -0400217 }
218
Matthew Barth9e80c872020-05-26 10:50:29 -0500219 /** @brief Get subtree from the mapper. */
Patrick Williamscb356d42022-07-22 19:26:53 -0500220 static auto getSubTree(sdbusplus::bus_t& bus, const std::string& path,
Matthew Barth9e80c872020-05-26 10:50:29 -0500221 const std::string& interface, int32_t depth)
222 {
223 auto mapperResp = getSubTreeRaw(bus, path, interface, depth);
224 if (mapperResp.empty())
225 {
226 phosphor::logging::log<phosphor::logging::level::ERR>(
227 "Empty response from mapper GetSubTree",
228 phosphor::logging::entry("SUBTREE=%s", path.c_str()),
229 phosphor::logging::entry("INTERFACE=%s", interface.c_str()),
230 phosphor::logging::entry("DEPTH=%u", depth));
231 phosphor::logging::elog<detail::errors::InternalFailure>();
232 }
233 return mapperResp;
234 }
235
Matthew Barthfcbdc0e2020-10-28 14:11:07 -0500236 /** @brief Get subtree paths from the mapper without checking response. */
Patrick Williamscb356d42022-07-22 19:26:53 -0500237 static auto getSubTreePathsRaw(sdbusplus::bus_t& bus,
Matthew Barthfcbdc0e2020-10-28 14:11:07 -0500238 const std::string& path,
239 const std::string& interface, int32_t depth)
240 {
241 using namespace std::literals::string_literals;
242
243 using Path = std::string;
244 using Intf = std::string;
245 using Intfs = std::vector<Intf>;
246 using ObjectPaths = std::vector<Path>;
247 Intfs intfs = {interface};
248
249 return callMethodAndRead<ObjectPaths>(
250 bus, "xyz.openbmc_project.ObjectMapper"s,
251 "/xyz/openbmc_project/object_mapper"s,
252 "xyz.openbmc_project.ObjectMapper"s, "GetSubTreePaths"s, path,
253 depth, intfs);
254 }
255
256 /** @brief Get subtree paths from the mapper. */
Patrick Williamscb356d42022-07-22 19:26:53 -0500257 static auto getSubTreePaths(sdbusplus::bus_t& bus, const std::string& path,
Matthew Barthfcbdc0e2020-10-28 14:11:07 -0500258 const std::string& interface, int32_t depth)
259 {
260 auto mapperResp = getSubTreePathsRaw(bus, path, interface, depth);
261 if (mapperResp.empty())
262 {
263 phosphor::logging::log<phosphor::logging::level::ERR>(
264 "Empty response from mapper GetSubTreePaths",
265 phosphor::logging::entry("SUBTREE=%s", path.c_str()),
266 phosphor::logging::entry("INTERFACE=%s", interface.c_str()),
267 phosphor::logging::entry("DEPTH=%u", depth));
268 phosphor::logging::elog<detail::errors::InternalFailure>();
269 }
270 return mapperResp;
271 }
272
Mike Cappsce6820a2021-05-26 10:40:19 -0400273 /** @brief Get service from the mapper without checking response. */
Patrick Williamscb356d42022-07-22 19:26:53 -0500274 static auto getServiceRaw(sdbusplus::bus_t& bus, const std::string& path,
Mike Cappsce6820a2021-05-26 10:40:19 -0400275 const std::string& interface)
Matthew Barth9e80c872020-05-26 10:50:29 -0500276 {
277 using namespace std::literals::string_literals;
278 using GetObject = std::map<std::string, std::vector<std::string>>;
279
Mike Cappsce6820a2021-05-26 10:40:19 -0400280 return callMethodAndRead<GetObject>(
281 bus, "xyz.openbmc_project.ObjectMapper"s,
282 "/xyz/openbmc_project/object_mapper"s,
283 "xyz.openbmc_project.ObjectMapper"s, "GetObject"s, path,
284 GetObject::mapped_type{interface});
285 }
286
287 /** @brief Get service from the mapper. */
Patrick Williamscb356d42022-07-22 19:26:53 -0500288 static auto getService(sdbusplus::bus_t& bus, const std::string& path,
Mike Cappsce6820a2021-05-26 10:40:19 -0400289 const std::string& interface)
290 {
Matthew Barth9e80c872020-05-26 10:50:29 -0500291 try
292 {
Mike Cappsce6820a2021-05-26 10:40:19 -0400293 auto mapperResp = getServiceRaw(bus, path, interface);
Matthew Barth9e80c872020-05-26 10:50:29 -0500294
295 if (mapperResp.empty())
296 {
297 // Should never happen. A missing object would fail
298 // in callMethodAndRead()
299 phosphor::logging::log<phosphor::logging::level::ERR>(
300 "Empty mapper response on service lookup");
301 throw DBusServiceError{path, interface};
302 }
303 return mapperResp.begin()->first;
304 }
Patrick Williamsddb773b2021-10-06 11:24:49 -0500305 catch (const DBusMethodError& e)
Matthew Barth9e80c872020-05-26 10:50:29 -0500306 {
307 throw DBusServiceError{path, interface};
308 }
309 }
310
311 /** @brief Get service from the mapper. */
312 static auto getService(const std::string& path,
313 const std::string& interface)
314 {
315 return getService(getBus(), path, interface);
316 }
317
Matthew Bartha3553632021-05-03 14:40:59 -0500318 /** @brief Get managed objects. */
319 template <typename Variant>
Patrick Williamscb356d42022-07-22 19:26:53 -0500320 static auto getManagedObjects(sdbusplus::bus_t& bus,
Matthew Bartha3553632021-05-03 14:40:59 -0500321 const std::string& service,
322 const std::string& path)
323 {
324 using namespace std::literals::string_literals;
325
326 using Path = sdbusplus::message::object_path;
327 using Intf = std::string;
328 using Prop = std::string;
329 using GetManagedObjects =
330 std::map<Path, std::map<Intf, std::map<Prop, Variant>>>;
331
332 return callMethodAndRead<GetManagedObjects>(
333 bus, service, path, "org.freedesktop.DBus.ObjectManager"s,
334 "GetManagedObjects"s);
335 }
336
Matthew Barth9e80c872020-05-26 10:50:29 -0500337 /** @brief Get a property with mapper lookup. */
338 template <typename Property>
Patrick Williamscb356d42022-07-22 19:26:53 -0500339 static auto getProperty(sdbusplus::bus_t& bus, const std::string& path,
Matthew Barth9e80c872020-05-26 10:50:29 -0500340 const std::string& interface,
341 const std::string& property)
342 {
343 using namespace std::literals::string_literals;
344
345 auto service = getService(bus, path, interface);
Patrick Williamsdfddd642024-08-16 15:21:51 -0400346 auto msg =
347 callMethod(bus, service, path, "org.freedesktop.DBus.Properties"s,
348 "Get"s, interface, property);
Matthew Barth9e80c872020-05-26 10:50:29 -0500349 if (msg.is_method_error())
350 {
351 throw DBusPropertyError{"DBus get property failed", service, path,
352 interface, property};
353 }
354 std::variant<Property> value;
355 msg.read(value);
356 return std::get<Property>(value);
357 }
358
359 /** @brief Get a property with mapper lookup. */
360 template <typename Property>
361 static auto getProperty(const std::string& path,
362 const std::string& interface,
363 const std::string& property)
364 {
365 return getProperty<Property>(getBus(), path, interface, property);
366 }
367
368 /** @brief Get a property variant with mapper lookup. */
369 template <typename Variant>
Patrick Williamsdfddd642024-08-16 15:21:51 -0400370 static auto getPropertyVariant(
371 sdbusplus::bus_t& bus, const std::string& path,
372 const std::string& interface, const std::string& property)
Matthew Barth9e80c872020-05-26 10:50:29 -0500373 {
374 using namespace std::literals::string_literals;
375
376 auto service = getService(bus, path, interface);
Patrick Williamsdfddd642024-08-16 15:21:51 -0400377 auto msg =
378 callMethod(bus, service, path, "org.freedesktop.DBus.Properties"s,
379 "Get"s, interface, property);
Matthew Barth9e80c872020-05-26 10:50:29 -0500380 if (msg.is_method_error())
381 {
382 throw DBusPropertyError{"DBus get property variant failed", service,
383 path, interface, property};
384 }
385 Variant value;
386 msg.read(value);
387 return value;
388 }
389
390 /** @brief Get a property variant with mapper lookup. */
391 template <typename Variant>
392 static auto getPropertyVariant(const std::string& path,
393 const std::string& interface,
394 const std::string& property)
395 {
396 return getPropertyVariant<Variant>(getBus(), path, interface, property);
397 }
398
Mike Capps808d7fe2022-06-13 10:12:16 -0400399 /** @brief Invoke a method and return without checking for error. */
400 template <typename... Args>
Patrick Williamsdfddd642024-08-16 15:21:51 -0400401 static auto callMethodAndReturn(
402 sdbusplus::bus_t& bus, const std::string& busName,
403 const std::string& path, const std::string& interface,
404 const std::string& method, Args&&... args)
Mike Capps808d7fe2022-06-13 10:12:16 -0400405 {
406 auto reqMsg = bus.new_method_call(busName.c_str(), path.c_str(),
407 interface.c_str(), method.c_str());
408 reqMsg.append(std::forward<Args>(args)...);
409 auto respMsg = bus.call(reqMsg);
410
411 return respMsg;
412 }
413
Matthew Barth9e80c872020-05-26 10:50:29 -0500414 /** @brief Get a property without mapper lookup. */
415 template <typename Property>
Patrick Williamscb356d42022-07-22 19:26:53 -0500416 static auto getProperty(sdbusplus::bus_t& bus, const std::string& service,
417 const std::string& path,
Matthew Barth9e80c872020-05-26 10:50:29 -0500418 const std::string& interface,
419 const std::string& property)
420 {
421 using namespace std::literals::string_literals;
422
423 auto msg = callMethodAndReturn(bus, service, path,
424 "org.freedesktop.DBus.Properties"s,
425 "Get"s, interface, property);
426 if (msg.is_method_error())
427 {
428 throw DBusPropertyError{"DBus get property failed", service, path,
429 interface, property};
430 }
431 std::variant<Property> value;
432 msg.read(value);
433 return std::get<Property>(value);
434 }
435
436 /** @brief Get a property without mapper lookup. */
437 template <typename Property>
438 static auto getProperty(const std::string& service, const std::string& path,
439 const std::string& interface,
440 const std::string& property)
441 {
442 return getProperty<Property>(getBus(), service, path, interface,
443 property);
444 }
445
446 /** @brief Get a property variant without mapper lookup. */
447 template <typename Variant>
Patrick Williamsdfddd642024-08-16 15:21:51 -0400448 static auto getPropertyVariant(
449 sdbusplus::bus_t& bus, const std::string& service,
450 const std::string& path, const std::string& interface,
451 const std::string& property)
Matthew Barth9e80c872020-05-26 10:50:29 -0500452 {
453 using namespace std::literals::string_literals;
454
455 auto msg = callMethodAndReturn(bus, service, path,
456 "org.freedesktop.DBus.Properties"s,
457 "Get"s, interface, property);
458 if (msg.is_method_error())
459 {
460 throw DBusPropertyError{"DBus get property variant failed", service,
461 path, interface, property};
462 }
463 Variant value;
464 msg.read(value);
465 return value;
466 }
467
468 /** @brief Get a property variant without mapper lookup. */
469 template <typename Variant>
Patrick Williamsdfddd642024-08-16 15:21:51 -0400470 static auto getPropertyVariant(
471 const std::string& service, const std::string& path,
472 const std::string& interface, const std::string& property)
Matthew Barth9e80c872020-05-26 10:50:29 -0500473 {
474 return getPropertyVariant<Variant>(getBus(), service, path, interface,
475 property);
476 }
477
478 /** @brief Set a property with mapper lookup. */
479 template <typename Property>
Patrick Williamscb356d42022-07-22 19:26:53 -0500480 static void setProperty(sdbusplus::bus_t& bus, const std::string& path,
Matthew Barth9e80c872020-05-26 10:50:29 -0500481 const std::string& interface,
482 const std::string& property, Property&& value)
483 {
484 using namespace std::literals::string_literals;
485
486 std::variant<Property> varValue(std::forward<Property>(value));
487
488 auto service = getService(bus, path, interface);
489 auto msg = callMethodAndReturn(bus, service, path,
490 "org.freedesktop.DBus.Properties"s,
491 "Set"s, interface, property, varValue);
492 if (msg.is_method_error())
493 {
494 throw DBusPropertyError{"DBus set property failed", service, path,
495 interface, property};
496 }
497 }
498
499 /** @brief Set a property with mapper lookup. */
500 template <typename Property>
501 static void setProperty(const std::string& path,
502 const std::string& interface,
503 const std::string& property, Property&& value)
504 {
505 return setProperty(getBus(), path, interface, property,
506 std::forward<Property>(value));
507 }
508
509 /** @brief Set a property without mapper lookup. */
510 template <typename Property>
Patrick Williamscb356d42022-07-22 19:26:53 -0500511 static void setProperty(sdbusplus::bus_t& bus, const std::string& service,
512 const std::string& path,
Matthew Barth9e80c872020-05-26 10:50:29 -0500513 const std::string& interface,
514 const std::string& property, Property&& value)
515 {
516 using namespace std::literals::string_literals;
517
518 std::variant<Property> varValue(std::forward<Property>(value));
519
520 auto msg = callMethodAndReturn(bus, service, path,
521 "org.freedesktop.DBus.Properties"s,
522 "Set"s, interface, property, varValue);
523 if (msg.is_method_error())
524 {
525 throw DBusPropertyError{"DBus set property failed", service, path,
526 interface, property};
527 }
528 }
529
530 /** @brief Set a property without mapper lookup. */
531 template <typename Property>
532 static void setProperty(const std::string& service, const std::string& path,
533 const std::string& interface,
534 const std::string& property, Property&& value)
535 {
536 return setProperty(getBus(), service, path, interface, property,
537 std::forward<Property>(value));
538 }
539
540 /** @brief Invoke method with mapper lookup. */
541 template <typename... Args>
Patrick Williamsdfddd642024-08-16 15:21:51 -0400542 static auto lookupAndCallMethod(
543 sdbusplus::bus_t& bus, const std::string& path,
544 const std::string& interface, const std::string& method, Args&&... args)
Matthew Barth9e80c872020-05-26 10:50:29 -0500545 {
546 return callMethod(bus, getService(bus, path, interface), path,
547 interface, method, std::forward<Args>(args)...);
548 }
549
550 /** @brief Invoke method with mapper lookup. */
551 template <typename... Args>
552 static auto lookupAndCallMethod(const std::string& path,
553 const std::string& interface,
554 const std::string& method, Args&&... args)
555 {
556 return lookupAndCallMethod(getBus(), path, interface, method,
557 std::forward<Args>(args)...);
558 }
559
560 /** @brief Invoke method and read with mapper lookup. */
561 template <typename Ret, typename... Args>
Patrick Williamsdfddd642024-08-16 15:21:51 -0400562 static auto lookupCallMethodAndRead(
563 sdbusplus::bus_t& bus, const std::string& path,
564 const std::string& interface, const std::string& method, Args&&... args)
Matthew Barth9e80c872020-05-26 10:50:29 -0500565 {
566 return callMethodAndRead(bus, getService(bus, path, interface), path,
567 interface, method,
568 std::forward<Args>(args)...);
569 }
570
571 /** @brief Invoke method and read with mapper lookup. */
572 template <typename Ret, typename... Args>
Patrick Williamsdfddd642024-08-16 15:21:51 -0400573 static auto lookupCallMethodAndRead(
574 const std::string& path, const std::string& interface,
575 const std::string& method, Args&&... args)
Matthew Barth9e80c872020-05-26 10:50:29 -0500576 {
577 return lookupCallMethodAndRead<Ret>(getBus(), path, interface, method,
578 std::forward<Args>(args)...);
579 }
Brad Bishop6e9cfdb2017-06-08 11:59:58 -0400580};
581
582} // namespace util
583} // namespace fan
584} // namespace phosphor