Bitcoin ABC  0.26.3
P2P Digital Currency
scheduler.h
Go to the documentation of this file.
1 // Copyright (c) 2015 The Bitcoin Core developers
2 // Distributed under the MIT software license, see the accompanying
3 // file COPYING or http://www.opensource.org/licenses/mit-license.php.
4 
5 #ifndef BITCOIN_SCHEDULER_H
6 #define BITCOIN_SCHEDULER_H
7 
8 #include <sync.h>
9 
10 #include <condition_variable>
11 #include <functional>
12 #include <list>
13 #include <map>
14 #include <thread>
15 
36 class CScheduler {
37 public:
38  CScheduler();
39  ~CScheduler();
40 
41  std::thread m_service_thread;
42 
43  typedef std::function<void()> Function;
44  typedef std::function<bool()> Predicate;
45 
47  void schedule(Function f, std::chrono::steady_clock::time_point t);
48 
50  void scheduleFromNow(Function f, std::chrono::milliseconds delta) {
51  schedule(std::move(f), std::chrono::steady_clock::now() + delta);
52  }
53 
61  void scheduleEvery(Predicate p, std::chrono::milliseconds delta);
62 
68  void MockForward(std::chrono::seconds delta_seconds);
69 
73  void serviceQueue();
74 
79  void stop() {
80  WITH_LOCK(newTaskMutex, stopRequested = true);
81  newTaskScheduled.notify_all();
82  if (m_service_thread.joinable()) {
83  m_service_thread.join();
84  }
85  }
86 
91  void StopWhenDrained() {
92  WITH_LOCK(newTaskMutex, stopWhenEmpty = true);
93  newTaskScheduled.notify_all();
94  if (m_service_thread.joinable()) {
95  m_service_thread.join();
96  }
97  }
98 
103  size_t getQueueInfo(std::chrono::steady_clock::time_point &first,
104  std::chrono::steady_clock::time_point &last) const;
105 
107  bool AreThreadsServicingQueue() const;
108 
109 private:
111  std::condition_variable newTaskScheduled;
112  std::multimap<std::chrono::steady_clock::time_point, Function>
114  int nThreadsServicingQueue GUARDED_BY(newTaskMutex){0};
115  bool stopRequested GUARDED_BY(newTaskMutex){false};
116  bool stopWhenEmpty GUARDED_BY(newTaskMutex){false};
118  return stopRequested || (stopWhenEmpty && taskQueue.empty());
119  }
120 };
121 
133 private:
135 
137  std::list<std::function<void()>>
138  m_callbacks_pending GUARDED_BY(m_cs_callbacks_pending);
139  bool m_are_callbacks_running GUARDED_BY(m_cs_callbacks_pending) = false;
140 
142  void ProcessQueue();
143 
144 public:
146  : m_pscheduler(pschedulerIn) {}
147 
154  void AddToProcessQueue(std::function<void()> func);
155 
161  void EmptyQueue();
162 
163  size_t CallbacksPending();
164 };
165 
166 #endif // BITCOIN_SCHEDULER_H
Simple class for background tasks that should be run periodically or once "after a while".
Definition: scheduler.h:36
bool stopWhenEmpty GUARDED_BY(newTaskMutex)
Definition: scheduler.h:116
void serviceQueue()
Services the queue 'forever'.
Definition: scheduler.cpp:23
std::function< bool()> Predicate
Definition: scheduler.h:44
bool stopRequested GUARDED_BY(newTaskMutex)
Definition: scheduler.h:115
size_t getQueueInfo(std::chrono::steady_clock::time_point &first, std::chrono::steady_clock::time_point &last) const
Returns number of tasks waiting to be serviced, and first and last task times.
Definition: scheduler.cpp:120
void scheduleFromNow(Function f, std::chrono::milliseconds delta)
Call f once after the delta has passed.
Definition: scheduler.h:50
void schedule(Function f, std::chrono::steady_clock::time_point t)
Call func at/after time t.
Definition: scheduler.cpp:74
std::multimap< std::chrono::steady_clock::time_point, Function > taskQueue GUARDED_BY(newTaskMutex)
int nThreadsServicingQueue GUARDED_BY(newTaskMutex)
Definition: scheduler.h:114
void StopWhenDrained()
Tell any threads running serviceQueue to stop when there is no work left to be done.
Definition: scheduler.h:91
std::function< void()> Function
Definition: scheduler.h:43
void MockForward(std::chrono::seconds delta_seconds)
Mock the scheduler to fast forward in time.
Definition: scheduler.cpp:83
std::thread m_service_thread
Definition: scheduler.h:41
bool shouldStop() const EXCLUSIVE_LOCKS_REQUIRED(newTaskMutex)
Definition: scheduler.h:117
void stop()
Tell any threads running serviceQueue to stop as soon as the current task is done.
Definition: scheduler.h:79
void scheduleEvery(Predicate p, std::chrono::milliseconds delta)
Repeat p until it return false.
Definition: scheduler.cpp:114
bool AreThreadsServicingQueue() const
Returns true if there are threads actively running in serviceQueue()
Definition: scheduler.cpp:131
std::condition_variable newTaskScheduled
Definition: scheduler.h:111
Mutex newTaskMutex
Definition: scheduler.h:110
Class used by CScheduler clients which may schedule multiple jobs which are required to be run serial...
Definition: scheduler.h:132
void EmptyQueue()
Processes all remaining queue members on the calling thread, blocking until queue is empty.
Definition: scheduler.cpp:200
std::list< std::function< void()> > m_callbacks_pending GUARDED_BY(m_cs_callbacks_pending)
void AddToProcessQueue(std::function< void()> func)
Add a callback to be executed.
Definition: scheduler.cpp:189
bool m_are_callbacks_running GUARDED_BY(m_cs_callbacks_pending)
RecursiveMutex m_cs_callbacks_pending
Definition: scheduler.h:136
SingleThreadedSchedulerClient(CScheduler *pschedulerIn)
Definition: scheduler.h:145
#define WITH_LOCK(cs, code)
Run code while locking a mutex.
Definition: sync.h:276
#define EXCLUSIVE_LOCKS_REQUIRED(...)
Definition: threadsafety.h:56