LocalSignal.h
Go to the documentation of this file.
1 #ifndef art_Framework_Services_Registry_LocalSignal_h
2 #define art_Framework_Services_Registry_LocalSignal_h
3 
4 ////////////////////////////////////////////////////////////////////////
5 // LocalSignal.h
6 //
7 // Define a wrapper for local signals. The watch(...) functions are for
8 // users wishing to register for callbacks; the invoke() and clear()
9 // functions are intended to be called only by art code.
10 //
11 // Multi-threaded behavior:
12 //
13 // watch...() access should be sequential only by construction since
14 // watch() calls are made from service constructors. Other calling
15 // origins are not supported.
16 //
17 // invoke...() access should be only from within the correct schedule's
18 // context so lock-free access to the correct signal is automatic and
19 // safe.
20 ////////////////////////////////////////////////////////////////////////
24 
25 #include <deque>
26 #include <functional>
27 
28 namespace art {
29  template <detail::SignalResponseType, typename ResultType, typename... Args>
30  class LocalSignal;
31 
32  template <detail::SignalResponseType STYPE,
33  typename ResultType,
34  typename... Args>
35  class LocalSignal<STYPE, ResultType(Args...)> {
36  public:
37  // Typedefs
38  using slot_type = std::function<ResultType(Args...)>;
39  using result_type = ResultType;
40 
41  private:
42  // Required for derivative alias below.
43  using ContainerType_ = std::vector<std::deque<slot_type>>;
44 
45  public:
46  using size_type = typename ContainerType_::size_type;
47 
48  // Constructor.
49  LocalSignal(size_t nSchedules);
50 
51  // 1. Free function or functor (or pre-bound member function).
52  void watch(ScheduleID const, std::function<ResultType(Args...)> slot);
53  // 2. Non-const member function.
54  template <typename T>
55  void watch(ScheduleID const, ResultType (T::*slot)(Args...), T& t);
56  // 3. Const member function.
57  template <typename T>
58  void watch(ScheduleID const,
59  ResultType (T::*slot)(Args...) const,
60  T const& t);
61 
62  // 1. Free function or functor (or pre-bound member function).
63  void watchAll(std::function<ResultType(Args...)> slot);
64  // 2. Non-const member function.
65  template <typename T>
66  void watchAll(ResultType (T::*slot)(Args...), T& t);
67  // 3. Const member function.
68  template <typename T>
69  void watchAll(ResultType (T::*slot)(Args...) const, T const& t);
70 
71  void invoke(ScheduleID const, Args&&... args) const; // Discard ResultType.
72 
73  private:
75  };
76 
77  template <detail::SignalResponseType STYPE,
78  typename ResultType,
79  typename... Args>
80  LocalSignal<STYPE, ResultType(Args...)>::LocalSignal(size_t nSchedules)
81  : signals_(nSchedules)
82  {}
83 
84  // 1.
85  template <detail::SignalResponseType STYPE,
86  typename ResultType,
87  typename... Args>
88  void
89  LocalSignal<STYPE, ResultType(Args...)>::watch(
90  ScheduleID const sID,
91  std::function<ResultType(Args...)> slot)
92  {
93  detail::connect_to_signal<STYPE>(signals_.at(sID.id()), slot);
94  }
95 
96  // 2.
97  template <detail::SignalResponseType STYPE,
98  typename ResultType,
99  typename... Args>
100  template <typename T>
101  void
102  LocalSignal<STYPE, ResultType(Args...)>::watch(ScheduleID const sID,
103  ResultType (T::*slot)(Args...),
104  T& t)
105  {
106  watch(sID, detail::makeWatchFunc(slot, t));
107  }
108 
109  // 3.
110  template <detail::SignalResponseType STYPE,
111  typename ResultType,
112  typename... Args>
113  template <typename T>
114  void
115  LocalSignal<STYPE, ResultType(Args...)>::watch(ScheduleID const sID,
116  ResultType (T::*slot)(Args...)
117  const,
118  T const& t)
119  {
120  watch(sID, detail::makeWatchFunc(slot, t));
121  }
122 
123  // 1.
124  template <detail::SignalResponseType STYPE,
125  typename ResultType,
126  typename... Args>
127  void
128  LocalSignal<STYPE, ResultType(Args...)>::watchAll(
129  std::function<ResultType(Args...)> slot)
130  {
131  for (auto& signal : signals_) {
132  detail::connect_to_signal<STYPE>(signal, slot);
133  }
134  }
135 
136  // 2.
137  template <detail::SignalResponseType STYPE,
138  typename ResultType,
139  typename... Args>
140  template <typename T>
141  void
142  LocalSignal<STYPE, ResultType(Args...)>::watchAll(
143  ResultType (T::*slot)(Args...),
144  T& t)
145  {
146  watchAll(detail::makeWatchFunc(slot, t));
147  }
148 
149  // 3.
150  template <detail::SignalResponseType STYPE,
151  typename ResultType,
152  typename... Args>
153  template <typename T>
154  void
155  LocalSignal<STYPE, ResultType(Args...)>::watchAll(
156  ResultType (T::*slot)(Args...) const,
157  T const& t)
158  {
159  watchAll(detail::makeWatchFunc(slot, t));
160  }
161 
162  template <detail::SignalResponseType STYPE,
163  typename ResultType,
164  typename... Args>
165  void
166  LocalSignal<STYPE, ResultType(Args...)>::invoke(ScheduleID const sID,
167  Args&&... args) const
168  {
169  for (auto f : signals_.at(sID.id())) {
170  f(std::forward<Args>(args)...);
171  }
172  }
173 
174 } // namespace art
175 #endif /* art_Framework_Services_Registry_LocalSignal_h */
176 
177 // Local Variables:
178 // mode: c++
179 // End:
std::vector< std::deque< slot_type >> ContainerType_
Definition: LocalSignal.h:43
std::function< ResultType(Args...)> makeWatchFunc(ResultType(T::*slot)(Args...), T &t)
Definition: makeWatchFunc.h:16
typename ContainerType_::size_type size_type
Definition: LocalSignal.h:46
static QCString args
Definition: declinfo.cpp:674
std::function< ResultType(Args...)> slot_type
Definition: LocalSignal.h:38
constexpr id_type id() const noexcept
Definition: ScheduleID.h:77
void function(int client, int *resource, int parblock, int *test, int p)