Advertisement
Guest User

Untitled

a guest
Jul 23rd, 2019
90
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 2.26 KB | None | 0 0
  1. const int kDispatcherTaskExpiration = 2000;
  2. const auto kSystemTimeZero = std::chrono::system_clock::time_point(std::chrono::milliseconds(0));
  3.  
  4. class Task
  5. {
  6. public:
  7. explicit Task(std::function<void(void)>&& f) :
  8. func_(std::move(f)) {}
  9.  
  10. Task(uint32_t ms, std::function<void(void)>&& f) :
  11. expiration(std::chrono::system_clock::now() + std::chrono::milliseconds(ms)), func_(std::move(f)) {}
  12.  
  13. virtual ~Task() = default;
  14.  
  15. void operator()()
  16. {
  17. func_();
  18. }
  19.  
  20. void SetDontExpire()
  21. {
  22. expiration = kSystemTimeZero;
  23. }
  24.  
  25. bool HasExpired() const
  26. {
  27. if (expiration == kSystemTimeZero)
  28. {
  29. return false;
  30. }
  31.  
  32. return expiration < std::chrono::system_clock::now();
  33. }
  34.  
  35. protected:
  36. std::chrono::system_clock::time_point expiration = kSystemTimeZero;
  37.  
  38. private:
  39. std::function<void(void)> func_;
  40. };
  41.  
  42. Task* CreateTask(std::function<void(void)> f);
  43. Task* CreateTask(uint32_t expiration, std::function<void(void)> f);
  44.  
  45. class Dispatcher
  46. {
  47. public:
  48. void AddTask(Task* task, bool push_front = false);
  49. Task* GetTask();
  50.  
  51. bool HasTaskToExecute() const
  52. {
  53. return !taskList_.empty();
  54. }
  55.  
  56. uint64_t GetDispatcherCycle() const
  57. {
  58. return dispatcherCycle_;
  59. }
  60.  
  61. private:
  62. std::mutex taskLock_;
  63.  
  64. std::list<Task*> taskList_;
  65. uint64_t dispatcherCycle_ = 0;
  66. };
  67.  
  68.  
  69. Task* CreateTask(std::function<void(void)> f)
  70. {
  71. return new Task(std::move(f));
  72. }
  73.  
  74. Task* CreateTask(uint32_t expiration, std::function<void(void)> f)
  75. {
  76. return new Task(expiration, std::move(f));
  77. }
  78.  
  79. void Dispatcher::AddTask(Task* task, bool push_front)
  80. {
  81. bool doSignal = false;
  82.  
  83. taskLock_.lock();
  84.  
  85. doSignal = taskList_.empty();
  86.  
  87. if (push_front)
  88. {
  89. taskList_.push_front(task);
  90. }
  91. else
  92. {
  93. taskList_.push_back(task);
  94. }
  95.  
  96. taskLock_.unlock();
  97. }
  98.  
  99. Task* Dispatcher::GetTask()
  100. {
  101. // NOTE: second argument defer_lock is to prevent from immediate locking
  102. std::unique_lock<std::mutex> taskLockUnique(taskLock_, std::defer_lock);
  103.  
  104. taskLockUnique.lock();
  105.  
  106. if (!taskList_.empty)
  107. {
  108. Task* task = taskList_.front();
  109. taskList_.pop_front();
  110.  
  111. taskLockUnique.unlock();
  112.  
  113. if (!task->HasExpired())
  114. {
  115. ++dispatcherCycle_;
  116.  
  117. return task;
  118. }
  119.  
  120. delete task;
  121. }
  122. else
  123. {
  124. taskLockUnique.unlock();
  125. }
  126.  
  127. return nullptr;
  128. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement