blob: f631311520cb4e0559953fec3da8e716a541d6cb [file] [log] [blame]
Matthew Barth38a93a82017-05-11 14:12:27 -05001#pragma once
2
Matthew Barth336f18a2017-09-26 09:15:56 -05003#include "sdbusplus.hpp"
Matthew Barth3e1bb272020-05-26 11:09:21 -05004#include "types.hpp"
5
Matthew Barth38a93a82017-05-11 14:12:27 -05006#include <phosphor-logging/log.hpp>
7
8namespace phosphor
9{
10namespace fan
11{
12namespace control
13{
14class Zone;
15
Matthew Barth336f18a2017-09-26 09:15:56 -050016using namespace phosphor::fan;
Matthew Barth5a302572017-10-03 11:27:06 -050017using namespace sdbusplus::bus::match;
Matthew Barth38a93a82017-05-11 14:12:27 -050018using namespace phosphor::logging;
19
20/**
Matthew Barth1b3e9602019-02-13 11:37:03 -060021 * @brief Create a zone handler function object
22 *
23 * @param[in] handler - The handler being created
24 *
25 * @return - The created zone handler function object
26 */
27template <typename T>
28auto make_zoneHandler(T&& handler)
29{
30 return ZoneHandler(std::forward<T>(handler));
31}
32
33/**
Matthew Barth1b4de262018-03-06 13:03:16 -060034 * @brief Create a trigger function object
35 *
36 * @param[in] trigger - The trigger being created
37 *
38 * @return - The created trigger function object
39 */
40template <typename T>
41auto make_trigger(T&& trigger)
42{
Matthew Barth3e1bb272020-05-26 11:09:21 -050043 return Trigger(std::forward<T>(trigger));
Matthew Barth1b4de262018-03-06 13:03:16 -060044}
45
46/**
Matthew Barth38a93a82017-05-11 14:12:27 -050047 * @brief Create a handler function object
48 *
49 * @param[in] handler - The handler being created
50 *
51 * @return - The created handler function object
52 */
Matthew Barth926df662018-10-09 09:51:12 -050053template <typename T, typename U>
54auto make_handler(U&& handler)
Matthew Barth38a93a82017-05-11 14:12:27 -050055{
Matthew Barth926df662018-10-09 09:51:12 -050056 return T(std::forward<U>(handler));
Matthew Barth38a93a82017-05-11 14:12:27 -050057}
58
59/**
Matthew Barth17d1fe22017-05-11 15:00:36 -050060 * @brief Create an action function object
61 *
62 * @param[in] action - The action being created
63 *
64 * @return - The created action function object
65 */
66template <typename T>
67auto make_action(T&& action)
68{
69 return Action(std::forward<T>(action));
70}
71
72/**
Matthew Barth926df662018-10-09 09:51:12 -050073 * @struct Properties
74 * @brief A set of match filter functors for Dbus property values. Each
75 * functor provides an associated process for retrieving the value
76 * for a given property and providing it to the given handler function.
Matthew Barth38a93a82017-05-11 14:12:27 -050077 *
78 * @tparam T - The type of the property value
79 * @tparam U - The type of the handler
80 */
81template <typename T, typename U>
Matthew Barth926df662018-10-09 09:51:12 -050082struct Properties
Matthew Barth38a93a82017-05-11 14:12:27 -050083{
Matthew Barth926df662018-10-09 09:51:12 -050084 Properties() = delete;
85 ~Properties() = default;
86 Properties(const Properties&) = default;
87 Properties& operator=(const Properties&) = default;
88 Properties(Properties&&) = default;
89 Properties& operator=(Properties&&) = default;
Matthew Barth3e1bb272020-05-26 11:09:21 -050090 explicit Properties(U&& handler) : _handler(std::forward<U>(handler))
91 {}
92 Properties(const char* path, const char* intf, const char* prop,
Matthew Barth926df662018-10-09 09:51:12 -050093 U&& handler) :
Matthew Barth336f18a2017-09-26 09:15:56 -050094 _path(path),
Matthew Barth3e1bb272020-05-26 11:09:21 -050095 _intf(intf), _prop(prop), _handler(std::forward<U>(handler))
96 {}
Matthew Barth38a93a82017-05-11 14:12:27 -050097
98 /** @brief Run signal handler function
99 *
100 * Extract the property from the PropertiesChanged
Matthew Barth926df662018-10-09 09:51:12 -0500101 * message and run the handler function.
Matthew Barth38a93a82017-05-11 14:12:27 -0500102 */
Matthew Barth3e1bb272020-05-26 11:09:21 -0500103 void operator()(sdbusplus::bus::bus& bus, sdbusplus::message::message& msg,
Matthew Barth38a93a82017-05-11 14:12:27 -0500104 Zone& zone) const
105 {
Matthew Barth336f18a2017-09-26 09:15:56 -0500106 if (msg)
Matthew Barth38a93a82017-05-11 14:12:27 -0500107 {
Matthew Barth469d1362018-10-11 14:10:47 -0500108 std::string intf;
Matthew Barth469d1362018-10-11 14:10:47 -0500109 msg.read(intf);
110 if (intf != _intf)
Matthew Barth336f18a2017-09-26 09:15:56 -0500111 {
Matthew Barth469d1362018-10-11 14:10:47 -0500112 // Interface name does not match on object
Matthew Barth336f18a2017-09-26 09:15:56 -0500113 return;
114 }
115
Matthew Barth7f4c5482020-02-07 16:14:46 -0600116 std::map<std::string, PropertyVariantType> props;
Matthew Barth469d1362018-10-11 14:10:47 -0500117 msg.read(props);
118 auto it = props.find(_prop);
119 if (it == props.cend())
Matthew Barth336f18a2017-09-26 09:15:56 -0500120 {
Matthew Barth469d1362018-10-11 14:10:47 -0500121 // Property not included in dictionary of properties changed
Matthew Barth336f18a2017-09-26 09:15:56 -0500122 return;
123 }
124
Matthew Barth7f4c5482020-02-07 16:14:46 -0600125 // Retrieve the property's value applying any visitors necessary
126 auto value =
127 zone.getPropertyValueVisitor<T>(_intf, _prop, it->second);
128
129 _handler(zone, _path, _intf, _prop, std::forward<T>(value));
Matthew Barth336f18a2017-09-26 09:15:56 -0500130 }
131 else
Matthew Barth38a93a82017-05-11 14:12:27 -0500132 {
Matthew Barth336f18a2017-09-26 09:15:56 -0500133 try
134 {
Matthew Barth469d1362018-10-11 14:10:47 -0500135 auto val = zone.getPropertyByName<T>(_path, _intf, _prop);
136 _handler(zone, _path, _intf, _prop, std::forward<T>(val));
Matthew Barth336f18a2017-09-26 09:15:56 -0500137 }
Matthew Barth86be4762018-07-17 10:51:36 -0500138 catch (const sdbusplus::exception::SdBusError&)
139 {
140 // Property will not be used unless a property changed
141 // signal message is received for this property.
142 }
143 catch (const util::DBusError&)
Matthew Barth336f18a2017-09-26 09:15:56 -0500144 {
145 // Property will not be used unless a property changed
146 // signal message is received for this property.
Matthew Barth336f18a2017-09-26 09:15:56 -0500147 }
Matthew Barth38a93a82017-05-11 14:12:27 -0500148 }
Matthew Barth38a93a82017-05-11 14:12:27 -0500149 }
150
Matthew Barth926df662018-10-09 09:51:12 -0500151 /** @brief Run init handler function
152 *
153 * Get the property from each member object of the group
154 * and run the handler function.
155 */
156 void operator()(Zone& zone, const Group& group) const
157 {
158 std::for_each(
Matthew Barth3e1bb272020-05-26 11:09:21 -0500159 group.begin(), group.end(),
160 [&zone, handler = std::move(_handler)](auto const& member) {
Matthew Barth926df662018-10-09 09:51:12 -0500161 auto path = std::get<pathPos>(member);
162 auto intf = std::get<intfPos>(member);
163 auto prop = std::get<propPos>(member);
164 try
165 {
166 auto val = zone.getPropertyByName<T>(path, intf, prop);
Matthew Barth469d1362018-10-11 14:10:47 -0500167 handler(zone, path, intf, prop, std::forward<T>(val));
Matthew Barth926df662018-10-09 09:51:12 -0500168 }
169 catch (const sdbusplus::exception::SdBusError&)
170 {
171 // Property value not sent to handler
172 }
173 catch (const util::DBusError&)
174 {
175 // Property value not sent to handler
176 }
Matthew Barth3e1bb272020-05-26 11:09:21 -0500177 });
Matthew Barth926df662018-10-09 09:51:12 -0500178 }
179
Matthew Barth3e1bb272020-05-26 11:09:21 -0500180 private:
Matthew Barth336f18a2017-09-26 09:15:56 -0500181 const char* _path;
Matthew Barth469d1362018-10-11 14:10:47 -0500182 const char* _intf;
183 const char* _prop;
Matthew Barth38a93a82017-05-11 14:12:27 -0500184 U _handler;
185};
186
187/**
Matthew Barth469d1362018-10-11 14:10:47 -0500188 * @brief Used to process a Dbus properties changed signal event
Matthew Barth38a93a82017-05-11 14:12:27 -0500189 *
Matthew Barth336f18a2017-09-26 09:15:56 -0500190 * @param[in] path - Object path
Matthew Barth469d1362018-10-11 14:10:47 -0500191 * @param[in] intf - Object interface
192 * @param[in] prop - Object property
Matthew Barth38a93a82017-05-11 14:12:27 -0500193 * @param[in] handler - Handler function to perform
194 *
195 * @tparam T - The type of the property
196 * @tparam U - The type of the handler
197 */
198template <typename T, typename U>
Matthew Barth3e1bb272020-05-26 11:09:21 -0500199auto propertiesChanged(const char* path, const char* intf, const char* prop,
Matthew Barth926df662018-10-09 09:51:12 -0500200 U&& handler)
Matthew Barth38a93a82017-05-11 14:12:27 -0500201{
Matthew Barth3e1bb272020-05-26 11:09:21 -0500202 return Properties<T, U>(path, intf, prop, std::forward<U>(handler));
Matthew Barth926df662018-10-09 09:51:12 -0500203}
204
205/**
Matthew Barth469d1362018-10-11 14:10:47 -0500206 * @brief Used to get the properties of an event's group
Matthew Barth926df662018-10-09 09:51:12 -0500207 *
208 * @param[in] handler - Handler function to perform
209 *
Matthew Barth469d1362018-10-11 14:10:47 -0500210 * @tparam T - The type of all the properties
Matthew Barth926df662018-10-09 09:51:12 -0500211 * @tparam U - The type of the handler
212 */
213template <typename T, typename U>
Matthew Barth469d1362018-10-11 14:10:47 -0500214auto getProperties(U&& handler)
Matthew Barth926df662018-10-09 09:51:12 -0500215{
216 return Properties<T, U>(std::forward<U>(handler));
Matthew Barth38a93a82017-05-11 14:12:27 -0500217}
218
Matthew Bartheb639c52017-08-04 09:43:11 -0500219/**
Matthew Barth469d1362018-10-11 14:10:47 -0500220 * @struct Interfaces Added
221 * @brief A match filter functor for Dbus interfaces added signals
Matthew Bartheb639c52017-08-04 09:43:11 -0500222 *
223 * @tparam T - The type of the property value
224 * @tparam U - The type of the handler
225 */
226template <typename T, typename U>
Matthew Barth469d1362018-10-11 14:10:47 -0500227struct InterfacesAdded
Matthew Bartheb639c52017-08-04 09:43:11 -0500228{
Matthew Barth469d1362018-10-11 14:10:47 -0500229 InterfacesAdded() = delete;
230 ~InterfacesAdded() = default;
231 InterfacesAdded(const InterfacesAdded&) = default;
232 InterfacesAdded& operator=(const InterfacesAdded&) = default;
233 InterfacesAdded(InterfacesAdded&&) = default;
234 InterfacesAdded& operator=(InterfacesAdded&&) = default;
Matthew Barth3e1bb272020-05-26 11:09:21 -0500235 InterfacesAdded(const char* path, const char* intf, const char* prop,
Matthew Barth469d1362018-10-11 14:10:47 -0500236 U&& handler) :
Matthew Bartheb639c52017-08-04 09:43:11 -0500237 _path(path),
Matthew Barth3e1bb272020-05-26 11:09:21 -0500238 _intf(intf), _prop(prop), _handler(std::forward<U>(handler))
239 {}
Matthew Bartheb639c52017-08-04 09:43:11 -0500240
241 /** @brief Run signal handler function
242 *
243 * Extract the property from the InterfacesAdded
244 * message and run the handler function.
245 */
Matthew Barth3e1bb272020-05-26 11:09:21 -0500246 void operator()(sdbusplus::bus::bus&, sdbusplus::message::message& msg,
Matthew Bartheb639c52017-08-04 09:43:11 -0500247 Zone& zone) const
248 {
Matthew Barth336f18a2017-09-26 09:15:56 -0500249 if (msg)
Matthew Bartheb639c52017-08-04 09:43:11 -0500250 {
Matthew Barth336f18a2017-09-26 09:15:56 -0500251 sdbusplus::message::object_path op;
Matthew Bartheb639c52017-08-04 09:43:11 -0500252
Matthew Barth336f18a2017-09-26 09:15:56 -0500253 msg.read(op);
Matthew Barthd5cfdbe2017-11-14 15:29:50 -0600254 if (static_cast<const std::string&>(op) != _path)
Matthew Barth336f18a2017-09-26 09:15:56 -0500255 {
256 // Object path does not match this handler's path
257 return;
258 }
Matthew Bartheb639c52017-08-04 09:43:11 -0500259
Matthew Barth3e1bb272020-05-26 11:09:21 -0500260 std::map<std::string, std::map<std::string, PropertyVariantType>>
261 intfProp;
Matthew Barth336f18a2017-09-26 09:15:56 -0500262 msg.read(intfProp);
Matthew Barth469d1362018-10-11 14:10:47 -0500263 auto itIntf = intfProp.find(_intf);
Matthew Barth336f18a2017-09-26 09:15:56 -0500264 if (itIntf == intfProp.cend())
265 {
266 // Interface not found on this handler's path
267 return;
268 }
Matthew Barth469d1362018-10-11 14:10:47 -0500269 auto itProp = itIntf->second.find(_prop);
Matthew Barth336f18a2017-09-26 09:15:56 -0500270 if (itProp == itIntf->second.cend())
271 {
272 // Property not found on this handler's path
273 return;
274 }
275
Matthew Barth7f4c5482020-02-07 16:14:46 -0600276 // Retrieve the property's value applying any visitors necessary
277 auto value =
278 zone.getPropertyValueVisitor<T>(_intf, _prop, itProp->second);
279
280 _handler(zone, _path, _intf, _prop, std::forward<T>(value));
Matthew Barth336f18a2017-09-26 09:15:56 -0500281 }
Matthew Bartheb639c52017-08-04 09:43:11 -0500282 }
283
Matthew Barth3e1bb272020-05-26 11:09:21 -0500284 private:
Matthew Bartheb639c52017-08-04 09:43:11 -0500285 const char* _path;
Matthew Barth469d1362018-10-11 14:10:47 -0500286 const char* _intf;
287 const char* _prop;
Matthew Bartheb639c52017-08-04 09:43:11 -0500288 U _handler;
289};
290
291/**
Matthew Barth926df662018-10-09 09:51:12 -0500292 * @brief Used to process a Dbus interfaces added signal event
Matthew Bartheb639c52017-08-04 09:43:11 -0500293 *
294 * @param[in] path - Object path
Matthew Barth469d1362018-10-11 14:10:47 -0500295 * @param[in] intf - Object interface
296 * @param[in] prop - Object property
Matthew Bartheb639c52017-08-04 09:43:11 -0500297 * @param[in] handler - Handler function to perform
298 *
299 * @tparam T - The type of the property
300 * @tparam U - The type of the handler
301 */
302template <typename T, typename U>
Matthew Barth3e1bb272020-05-26 11:09:21 -0500303auto interfacesAdded(const char* path, const char* intf, const char* prop,
Matthew Barth926df662018-10-09 09:51:12 -0500304 U&& handler)
Matthew Bartheb639c52017-08-04 09:43:11 -0500305{
Matthew Barth3e1bb272020-05-26 11:09:21 -0500306 return InterfacesAdded<T, U>(path, intf, prop, std::forward<U>(handler));
Matthew Bartheb639c52017-08-04 09:43:11 -0500307}
308
Matthew Barth8fa02da2017-09-28 12:18:20 -0500309/**
Matthew Barth469d1362018-10-11 14:10:47 -0500310 * @struct Interfaces Removed
311 * @brief A match filter functor for Dbus interfaces removed signals
Matthew Barth1499a5c2018-03-20 15:52:33 -0500312 *
313 * @tparam U - The type of the handler
314 */
315template <typename U>
Matthew Barth469d1362018-10-11 14:10:47 -0500316struct InterfacesRemoved
Matthew Barth1499a5c2018-03-20 15:52:33 -0500317{
Matthew Barth469d1362018-10-11 14:10:47 -0500318 InterfacesRemoved() = delete;
319 ~InterfacesRemoved() = default;
320 InterfacesRemoved(const InterfacesRemoved&) = default;
321 InterfacesRemoved& operator=(const InterfacesRemoved&) = default;
322 InterfacesRemoved(InterfacesRemoved&&) = default;
323 InterfacesRemoved& operator=(InterfacesRemoved&&) = default;
Matthew Barth3e1bb272020-05-26 11:09:21 -0500324 InterfacesRemoved(const char* path, const char* intf, U&& handler) :
325 _path(path), _intf(intf), _handler(std::forward<U>(handler))
326 {}
Matthew Barth1499a5c2018-03-20 15:52:33 -0500327
328 /** @brief Run signal handler function
329 *
Matthew Barth469d1362018-10-11 14:10:47 -0500330 * Extract the interfaces from the InterfacesRemoved
Matthew Barth1499a5c2018-03-20 15:52:33 -0500331 * message and run the handler function.
332 */
Matthew Barth3e1bb272020-05-26 11:09:21 -0500333 void operator()(sdbusplus::bus::bus&, sdbusplus::message::message& msg,
Matthew Barth1499a5c2018-03-20 15:52:33 -0500334 Zone& zone) const
335 {
336 if (msg)
337 {
338 std::vector<std::string> intfs;
339 sdbusplus::message::object_path op;
340
341 msg.read(op);
342 if (static_cast<const std::string&>(op) != _path)
343 {
344 // Object path does not match this handler's path
345 return;
346 }
347
348 msg.read(intfs);
Matthew Barth469d1362018-10-11 14:10:47 -0500349 auto itIntf = std::find(intfs.begin(), intfs.end(), _intf);
Matthew Barth1499a5c2018-03-20 15:52:33 -0500350 if (itIntf == intfs.cend())
351 {
352 // Interface not found on this handler's path
353 return;
354 }
355
356 _handler(zone);
357 }
358 }
359
Matthew Barth3e1bb272020-05-26 11:09:21 -0500360 private:
Matthew Barth1499a5c2018-03-20 15:52:33 -0500361 const char* _path;
Matthew Barth469d1362018-10-11 14:10:47 -0500362 const char* _intf;
Matthew Barth1499a5c2018-03-20 15:52:33 -0500363 U _handler;
364};
365
366/**
Matthew Barth926df662018-10-09 09:51:12 -0500367 * @brief Used to process a Dbus interfaces removed signal event
Matthew Barth1499a5c2018-03-20 15:52:33 -0500368 *
369 * @param[in] path - Object path
Matthew Barth469d1362018-10-11 14:10:47 -0500370 * @param[in] intf - Object interface
Matthew Barth1499a5c2018-03-20 15:52:33 -0500371 * @param[in] handler - Handler function to perform
372 *
373 * @tparam U - The type of the handler
374 */
375template <typename U>
Matthew Barth3e1bb272020-05-26 11:09:21 -0500376auto interfacesRemoved(const char* path, const char* intf, U&& handler)
Matthew Barth1499a5c2018-03-20 15:52:33 -0500377{
Matthew Barth3e1bb272020-05-26 11:09:21 -0500378 return InterfacesRemoved<U>(path, intf, std::forward<U>(handler));
Matthew Barth1499a5c2018-03-20 15:52:33 -0500379}
380
381/**
Matthew Barth926df662018-10-09 09:51:12 -0500382 * @struct Name Owner
383 * @brief A functor for Dbus name owner signals and methods
Matthew Barth8fa02da2017-09-28 12:18:20 -0500384 *
385 * @tparam U - The type of the handler
386 */
387template <typename U>
Matthew Barth926df662018-10-09 09:51:12 -0500388struct NameOwner
Matthew Barth8fa02da2017-09-28 12:18:20 -0500389{
Matthew Barth926df662018-10-09 09:51:12 -0500390 NameOwner() = delete;
391 ~NameOwner() = default;
392 NameOwner(const NameOwner&) = default;
393 NameOwner& operator=(const NameOwner&) = default;
394 NameOwner(NameOwner&&) = default;
395 NameOwner& operator=(NameOwner&&) = default;
Matthew Barth3e1bb272020-05-26 11:09:21 -0500396 explicit NameOwner(U&& handler) : _handler(std::forward<U>(handler))
397 {}
Matthew Barth8fa02da2017-09-28 12:18:20 -0500398
399 /** @brief Run signal handler function
400 *
401 * Extract the name owner from the NameOwnerChanged
Matthew Barth926df662018-10-09 09:51:12 -0500402 * message and run the handler function.
Matthew Barth8fa02da2017-09-28 12:18:20 -0500403 */
Matthew Barth3e1bb272020-05-26 11:09:21 -0500404 void operator()(sdbusplus::bus::bus& bus, sdbusplus::message::message& msg,
Matthew Barth8fa02da2017-09-28 12:18:20 -0500405 Zone& zone) const
406 {
Matthew Barth5a302572017-10-03 11:27:06 -0500407 std::string name;
408 bool hasOwner = false;
Matthew Barth8fa02da2017-09-28 12:18:20 -0500409 if (msg)
410 {
Matthew Barth5a302572017-10-03 11:27:06 -0500411 // Handle NameOwnerChanged signals
412 msg.read(name);
413
414 std::string oldOwn;
415 msg.read(oldOwn);
416
417 std::string newOwn;
418 msg.read(newOwn);
419 if (!newOwn.empty())
420 {
421 hasOwner = true;
422 }
Matthew Barth926df662018-10-09 09:51:12 -0500423 _handler(zone, name, hasOwner);
Matthew Barth8fa02da2017-09-28 12:18:20 -0500424 }
Matthew Barth926df662018-10-09 09:51:12 -0500425 }
Matthew Barth5a302572017-10-03 11:27:06 -0500426
Matthew Barth3e1bb272020-05-26 11:09:21 -0500427 void operator()(Zone& zone, const Group& group) const
Matthew Barth926df662018-10-09 09:51:12 -0500428 {
429 std::string name = "";
430 bool hasOwner = false;
431 std::for_each(
Matthew Barth3e1bb272020-05-26 11:09:21 -0500432 group.begin(), group.end(),
433 [&zone, &group, &name, &hasOwner,
434 handler = std::move(_handler)](auto const& member) {
Matthew Barth926df662018-10-09 09:51:12 -0500435 auto path = std::get<pathPos>(member);
436 auto intf = std::get<intfPos>(member);
437 try
438 {
439 auto servName = zone.getService(path, intf);
440 if (name != servName)
441 {
442 name = servName;
443 hasOwner = util::SDBusPlus::callMethodAndRead<bool>(
Matthew Barth3e1bb272020-05-26 11:09:21 -0500444 zone.getBus(), "org.freedesktop.DBus",
445 "/org/freedesktop/DBus", "org.freedesktop.DBus",
446 "NameHasOwner", name);
Matthew Barth926df662018-10-09 09:51:12 -0500447 // Update service name owner state list of a group
448 handler(zone, name, hasOwner);
449 }
450 }
451 catch (const util::DBusMethodError& e)
452 {
453 // Failed to get service name owner state
454 name = "";
455 hasOwner = false;
456 }
Matthew Barth3e1bb272020-05-26 11:09:21 -0500457 });
Matthew Barth8fa02da2017-09-28 12:18:20 -0500458 }
459
Matthew Barth3e1bb272020-05-26 11:09:21 -0500460 private:
Matthew Barth8fa02da2017-09-28 12:18:20 -0500461 U _handler;
462};
463
464/**
465 * @brief Used to process a Dbus name owner changed signal event
466 *
Matthew Barth8fa02da2017-09-28 12:18:20 -0500467 * @param[in] handler - Handler function to perform
468 *
469 * @tparam U - The type of the handler
470 *
471 * @return - The NameOwnerChanged signal struct
472 */
473template <typename U>
Matthew Barth926df662018-10-09 09:51:12 -0500474auto nameOwnerChanged(U&& handler)
Matthew Barth8fa02da2017-09-28 12:18:20 -0500475{
Matthew Barth926df662018-10-09 09:51:12 -0500476 return NameOwner<U>(std::forward<U>(handler));
477}
478
479/**
480 * @brief Used to process the init of a name owner event
481 *
482 * @param[in] handler - Handler function to perform
483 *
484 * @tparam U - The type of the handler
485 *
486 * @return - The NameOwnerChanged signal struct
487 */
488template <typename U>
489auto nameHasOwner(U&& handler)
490{
491 return NameOwner<U>(std::forward<U>(handler));
Matthew Barth8fa02da2017-09-28 12:18:20 -0500492}
493
Matthew Barth38a93a82017-05-11 14:12:27 -0500494} // namespace control
495} // namespace fan
496} // namespace phosphor