1 /*
2  * Copyright (c) 2021-2022 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #ifndef BASE_EVENTHANDLER_INTERFACES_INNER_API_EVENT_RUNNER_H
17 #define BASE_EVENTHANDLER_INTERFACES_INNER_API_EVENT_RUNNER_H
18 
19 #include <atomic>
20 
21 #include "event_queue.h"
22 #include "dumper.h"
23 #include "event_inner_logger.h"
24 #include "inner_event.h"
25 
26 namespace OHOS {
27 namespace AppExecFwk {
28 class EventInnerRunner;
29 
30 // Running mode of eventrunner
31 enum class Mode: uint32_t {
32     DEFAULT = 0,  // Default polling mode
33     NO_WAIT,      // One poll mode
34 };
35 
36 enum class ThreadMode: uint32_t {
37     NEW_THREAD = 0,    // for new thread mode, event handler create thread
38     FFRT,           // for new thread mode, use ffrt
39 };
40 
41 class EventRunner final {
42 public:
43     EventRunner() = delete;
44     ~EventRunner();
45     DISALLOW_COPY_AND_MOVE(EventRunner);
46 
47     using DistributeBeginTime = std::function<InnerEvent::TimePoint(const std::string&)>;
48     using DistributeEndTime = std::function<void(const std::string&, const InnerEvent::TimePoint&)>;
49     using CallbackTime = std::function<void(int64_t)>;
50     static DistributeBeginTime distributeBegin_;
51     static DistributeEndTime distributeEnd_;
52     static CallbackTime distributeCallback_;
53 
54     /**
55      * Create new 'EventRunner'.
56      *
57      * @deprecated This function is deprecated, use 'Create(const std::string &threadName, ThreadMode threadMode)'.
58      * @param inNewThread True if create new thread to start the 'EventRunner' automatically.
59      * @return Returns shared pointer of the new 'EventRunner'.
60      */
61     static std::shared_ptr<EventRunner> Create(bool inNewThread = true);
62 
63     /**
64      * Create new 'EventRunner'.
65      *
66      * @param inNewThread True if create new thread to start the 'EventRunner' automatically.
67      * @param threadMode thread mode, use ffrt or new thread, for inNewThread = true.
68      * @return Returns shared pointer of the new 'EventRunner'.
69      */
70     static std::shared_ptr<EventRunner> Create(bool inNewThread, ThreadMode threadMode);
71 
72     /**
73      * Create new 'EventRunner' and start to run in a new thread.
74      *
75      * @deprecated This function is deprecated, use 'Create(const std::string &threadName, ThreadMode threadMode)'.
76      * @param threadName Thread name of the new created thread.
77      * @return Returns shared pointer of the new 'EventRunner'.
78      */
Create(const std::string &threadName)79     static std::shared_ptr<EventRunner> Create(const std::string &threadName)
80     {
81         return Create(threadName, Mode::DEFAULT, ThreadMode::NEW_THREAD);
82     }
83 
84     /**
85      * Create new 'EventRunner' and start to run in a new thread.
86      *
87      * @param threadName Thread name of the new created thread.
88      * @param threadMode thread mode, use ffrt or new thread.
89      * @return Returns shared pointer of the new 'EventRunner'.
90      */
Create(const std::string &threadName, ThreadMode threadMode)91     static std::shared_ptr<EventRunner> Create(const std::string &threadName, ThreadMode threadMode)
92     {
93         return Create(threadName, Mode::DEFAULT, threadMode);
94     }
95 
96     /**
97      * Create new 'EventRunner' and start to run in a new thread.
98      * Eliminate ambiguity, while calling like 'EventRunner::Create("threadName")'.
99      *
100      * @deprecated This function is deprecated, use 'Create(const char *threadName, ThreadMode threadMode)'.
101      * @param threadName Thread name of the new created thread.
102      * @return Returns shared pointer of the new 'EventRunner'.
103      */
Create(const char *threadName)104     static inline std::shared_ptr<EventRunner> Create(const char *threadName)
105     {
106         return Create((threadName != nullptr) ? std::string(threadName) : std::string(), Mode::DEFAULT,
107             ThreadMode::NEW_THREAD);
108     }
109 
110     /**
111      * Create new 'EventRunner' and start to run in a new thread.
112      * Eliminate ambiguity, while calling like 'EventRunner::Create("threadName")'.
113      *
114      * @param threadName Thread name of the new created thread.
115      * @param threadMode thread mode, use ffrt or new thread.
116      * @return Returns shared pointer of the new 'EventRunner'.
117      */
Create(const char *threadName, ThreadMode threadMode)118     static inline std::shared_ptr<EventRunner> Create(const char *threadName, ThreadMode threadMode)
119     {
120         return Create((threadName != nullptr) ? std::string(threadName) : std::string(), Mode::DEFAULT, threadMode);
121     }
122 
123     /**
124      * Create new 'EventRunner' for nowait mode.
125      *
126      * @param threadName Thread name of the new created thread.
127      * @return Returns shared pointer of the new 'EventRunner'.
128      */
CreateNoWait(const std::string &threadName)129     static std::shared_ptr<EventRunner> CreateNoWait(const std::string &threadName)
130     {
131         return Create(threadName, Mode::NO_WAIT, ThreadMode::NEW_THREAD);
132     }
133 
134     /**
135      * Get event runner on current thread.
136      *
137      * @return Returns shared pointer of the current 'EventRunner'.
138      */
139     static std::shared_ptr<EventRunner> Current();
140 
141     /**
142      * Start to run the 'EventRunner'. Only used for the 'EventRunner' which is not running in new thread.
143      * Only running on single thread.
144      *
145      * @return Returns 'ERR_OK' on success.
146      */
147     ErrCode Run();
148 
149     /**
150      * Stop to run the 'EventRunner'. Only used for the 'EventRunner' which is not running in new thread.
151      * It is a good practice to call {@link #Stop} on the same thread that called {@link #Run}.
152      *
153      * @return Returns 'ERR_OK' on success.
154      */
155     ErrCode Stop();
156 
157     /**
158      * Get thread name
159      *
160      * @return Returns thread name.
161      */
162     std::string GetRunnerThreadName() const;
163 
164     /**
165      * Get event queue from event runner.
166      * This method only called by 'EventHandler'.
167      *
168      * @return Returns event queue.
169      */
GetEventQueue() const170     inline const std::shared_ptr<EventQueue> &GetEventQueue() const
171     {
172         return queue_;
173     }
174 
175     /**
176      * Obtain the event queue of the EventRunner associated with the current thread.
177      *
178      * @return Return current event queue.
179      */
180     static std::shared_ptr<EventQueue> GetCurrentEventQueue();
181 
182     /**
183      * Print out the internal information about an object in the specified format,
184      * helping you diagnose internal errors of the object.
185      *
186      * @param dumpr The Dumper object you have implemented to process the output internal information.
187      */
188     void Dump(Dumper &dumper);
189 
190     /**
191      * Print out the internal information about an object in the specified format,
192      * helping you diagnose internal errors of the object.
193      *
194      * @param runnerInfo runner Info.
195      */
196     void DumpRunnerInfo(std::string& runnerInfo);
197 
198     /**
199      * Set the Logger object for logging messages that are processed by this event runner.
200      *
201      * @param logger The Logger object you have implemented for logging messages.
202      */
203     void SetLogger(const std::shared_ptr<Logger> &logger);
204 
205     /**
206      * Obtain the ID of the worker thread associated with this EventRunner.
207      *
208      * @return thread id.
209      */
210     uint64_t GetThreadId();
211 
212     /**
213      * Obtain the kernel thread ID of the worker thread associated with this EventRunner.
214      *
215      * @return kernel thread id.
216      */
217     uint64_t GetKernelThreadId();
218 
219     /**
220      * Check whether the current thread is the worker thread of this EventRunner.
221      *
222      * @return Returns true if the current thread is the worker thread of this EventRunner; returns false otherwise.
223      */
224     bool IsCurrentRunnerThread();
225 
226     /**
227      * Set the distribution standard expiration time.
228      *
229      * @param deliveryTimeout the distribution standard expiration time.
230      */
SetDeliveryTimeout(int64_t deliveryTimeout)231     void SetDeliveryTimeout(int64_t deliveryTimeout)
232     {
233         deliveryTimeout_ = deliveryTimeout;
234     }
235 
236     /**
237      * Get the distribution standard expiration time.
238      *
239      * @return the distribution standard expiration time.
240      */
GetDeliveryTimeout() const241     int64_t GetDeliveryTimeout() const
242     {
243         return deliveryTimeout_;
244     }
245 
246     /**
247      * Set the execution standard timeout period.
248      *
249      * @param distributeTimeout the distribution standard expiration time.
250      */
SetDistributeTimeout(int64_t distributeTimeout)251     void SetDistributeTimeout(int64_t distributeTimeout)
252     {
253         distributeTimeout_ = distributeTimeout;
254     }
255 
256     /**
257      * Get the execution standard timeout period.
258      *
259      * @return the distribution standard expiration time.
260      */
GetDistributeTimeout() const261     int64_t GetDistributeTimeout() const
262     {
263         return distributeTimeout_;
264     }
265 
266     /**
267      * Set the main thread timeout period.
268      *
269      * @param distributeTimeout the distribution standard expiration time.
270      */
SetTimeout(int64_t distributeTimeout)271     void SetTimeout(int64_t distributeTimeout)
272     {
273         timeout_ = distributeTimeout;
274     }
275 
276     /**
277      * Set distribute time out callback.
278      *
279      * @param callback Distribute Time out callback.
280      */
SetTimeoutCallback(CallbackTime callback)281     void SetTimeoutCallback(CallbackTime callback)
282     {
283         distributeCallback_ = callback;
284     }
285 
286     /**
287      * Get the execution standard timeout period.
288      *
289      * @return the distribution standard expiration time.
290      */
GetTimeout() const291     int64_t GetTimeout() const
292     {
293         return timeout_;
294     }
295 
296     /**
297      * Check if the current application is the main thread.
298      */
299     static bool IsAppMainThread();
300 
301     /**
302      * Set app main thread watcher.
303      *
304      * @param callback Distribute Start Time callback.
305      * @param callback Distribute End Time callback.
306      */
307     void SetMainLooperWatcher(const DistributeBeginTime begin, const DistributeEndTime end);
308 
309     /**
310      * Obtains the EventRunner for the main thread of the application.
311      *
312      * @return Returns the EventRunner for the main thread of the application.
313      */
314     static std::shared_ptr<EventRunner> GetMainEventRunner();
315 
316 private:
317     explicit EventRunner(bool deposit, Mode runningMode = Mode::DEFAULT);
318 
319     friend class EventHandler;
320 
321     static std::shared_ptr<EventRunner> Create(const std::string &threadName, Mode mode, ThreadMode threadMode);
322 
323     /**
324      * Check whether this event runner is running.
325      *
326      * @return if this event runner is running return true otherwise return false
327      */
IsRunning() const328     inline bool IsRunning() const
329     {
330         // If this runner is deposited, it it always running
331         return (deposit_ && runningMode_ == Mode::DEFAULT) || (running_.load());
332     }
333 
334     /**
335      * Start event running for no_wait mode in new thread.
336      */
337     void StartRunningForNoWait();
338 
339     int64_t deliveryTimeout_ = 0;
340     int64_t distributeTimeout_ = 0;
341     int64_t timeout_ = 0;
342     bool deposit_{true};
343     std::atomic<bool> running_{false};
344     std::shared_ptr<EventQueue> queue_;
345     std::shared_ptr<EventInnerRunner> innerRunner_;
346     static std::shared_ptr<EventRunner> mainRunner_;
347     std::string currentEventInfo_;
348     Mode runningMode_ = Mode::DEFAULT;
349     ThreadMode threadMode_ = ThreadMode::NEW_THREAD;
350     std::string runnerId_;
351 };
352 }  // namespace AppExecFwk
353 namespace EventHandling = AppExecFwk;
354 }  // namespace OHOS
355 
356 #endif  // #ifndef BASE_EVENTHANDLER_INTERFACES_INNER_API_EVENT_RUNNER_H
357