WorkQueue.cpp 1.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657
  1. /*
  2. * Copyright (c) 2021, the SerenityOS developers.
  3. *
  4. * SPDX-License-Identifier: BSD-2-Clause
  5. */
  6. #include <Kernel/Locking/Spinlock.h>
  7. #include <Kernel/Process.h>
  8. #include <Kernel/Sections.h>
  9. #include <Kernel/WaitQueue.h>
  10. #include <Kernel/WorkQueue.h>
  11. namespace Kernel {
  12. WorkQueue* g_io_work;
  13. UNMAP_AFTER_INIT void WorkQueue::initialize()
  14. {
  15. g_io_work = new WorkQueue("IO WorkQueue");
  16. }
  17. UNMAP_AFTER_INIT WorkQueue::WorkQueue(const char* name)
  18. {
  19. RefPtr<Thread> thread;
  20. Process::create_kernel_process(thread, name, [this] {
  21. for (;;) {
  22. WorkItem* item;
  23. bool have_more;
  24. {
  25. SpinlockLocker lock(m_lock);
  26. item = m_items.take_first();
  27. have_more = !m_items.is_empty();
  28. }
  29. if (item) {
  30. item->function();
  31. delete item;
  32. if (have_more)
  33. continue;
  34. }
  35. [[maybe_unused]] auto result = m_wait_queue.wait_on({});
  36. }
  37. });
  38. // If we can't create the thread we're in trouble...
  39. m_thread = thread.release_nonnull();
  40. }
  41. void WorkQueue::do_queue(WorkItem* item)
  42. {
  43. {
  44. SpinlockLocker lock(m_lock);
  45. m_items.append(*item);
  46. }
  47. m_wait_queue.wake_one();
  48. }
  49. }