tasks.h 1.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748
  1. #pragma once
  2. #include <library/cpp/deprecated/atomic/atomic.h>
  3. #include <util/system/yassert.h>
  4. namespace NActor {
  5. class TTasks {
  6. enum {
  7. // order of values is important
  8. E_WAITING,
  9. E_RUNNING_NO_TASKS,
  10. E_RUNNING_GOT_TASKS,
  11. };
  12. private:
  13. TAtomic State;
  14. public:
  15. TTasks()
  16. : State(E_WAITING)
  17. {
  18. }
  19. // @return true iff caller have to either schedule task or execute it
  20. bool AddTask() {
  21. // High contention case optimization: AtomicGet is cheaper than AtomicSwap.
  22. if (E_RUNNING_GOT_TASKS == AtomicGet(State)) {
  23. return false;
  24. }
  25. TAtomicBase oldState = AtomicSwap(&State, E_RUNNING_GOT_TASKS);
  26. return oldState == E_WAITING;
  27. }
  28. // called by executor
  29. // @return true iff we have to recheck queues
  30. bool FetchTask() {
  31. TAtomicBase newState = AtomicDecrement(State);
  32. if (newState == E_RUNNING_NO_TASKS) {
  33. return true;
  34. } else if (newState == E_WAITING) {
  35. return false;
  36. }
  37. Y_ABORT("unknown");
  38. }
  39. };
  40. }