From 2d59006262d6e45f41ee325af78433475884dca4 Mon Sep 17 00:00:00 2001 From: Emma Miler Date: Fri, 2 Dec 2022 23:00:33 +0100 Subject: Move include directory (#337) * Move include directory to shared folder This commit moves the `include` directory from the NorthstarDLL project folder to the solution folder. This allows both the DLL and Launcher project to target it properly. * Fix filters * Update memalloc.h * Fix filters * Update NorthstarLauncher.vcxproj * Remove stuff from other PR * Update NorthstarLauncher.vcxproj * Update NorthstarLauncher.vcxproj * Update NorthstarDLL.vcxproj --- include/spdlog/details/mpmc_blocking_q.h | 126 +++++++++++++++++++++++++++++++ 1 file changed, 126 insertions(+) create mode 100644 include/spdlog/details/mpmc_blocking_q.h (limited to 'include/spdlog/details/mpmc_blocking_q.h') diff --git a/include/spdlog/details/mpmc_blocking_q.h b/include/spdlog/details/mpmc_blocking_q.h new file mode 100644 index 00000000..5c3cca76 --- /dev/null +++ b/include/spdlog/details/mpmc_blocking_q.h @@ -0,0 +1,126 @@ +// Copyright(c) 2015-present, Gabi Melman & spdlog contributors. +// Distributed under the MIT License (http://opensource.org/licenses/MIT) + +#pragma once + +// multi producer-multi consumer blocking queue. +// enqueue(..) - will block until room found to put the new message. +// enqueue_nowait(..) - will return immediately with false if no room left in +// the queue. +// dequeue_for(..) - will block until the queue is not empty or timeout have +// passed. + +#include + +#include +#include + +namespace spdlog { +namespace details { + +template +class mpmc_blocking_queue +{ +public: + using item_type = T; + explicit mpmc_blocking_queue(size_t max_items) + : q_(max_items) + {} + +#ifndef __MINGW32__ + // try to enqueue and block if no room left + void enqueue(T &&item) + { + { + std::unique_lock lock(queue_mutex_); + pop_cv_.wait(lock, [this] { return !this->q_.full(); }); + q_.push_back(std::move(item)); + } + push_cv_.notify_one(); + } + + // enqueue immediately. overrun oldest message in the queue if no room left. + void enqueue_nowait(T &&item) + { + { + std::unique_lock lock(queue_mutex_); + q_.push_back(std::move(item)); + } + push_cv_.notify_one(); + } + + // try to dequeue item. if no item found. wait upto timeout and try again + // Return true, if succeeded dequeue item, false otherwise + bool dequeue_for(T &popped_item, std::chrono::milliseconds wait_duration) + { + { + std::unique_lock lock(queue_mutex_); + if (!push_cv_.wait_for(lock, wait_duration, [this] { return !this->q_.empty(); })) + { + return false; + } + popped_item = std::move(q_.front()); + q_.pop_front(); + } + pop_cv_.notify_one(); + return true; + } + +#else + // apparently mingw deadlocks if the mutex is released before cv.notify_one(), + // so release the mutex at the very end each function. + + // try to enqueue and block if no room left + void enqueue(T &&item) + { + std::unique_lock lock(queue_mutex_); + pop_cv_.wait(lock, [this] { return !this->q_.full(); }); + q_.push_back(std::move(item)); + push_cv_.notify_one(); + } + + // enqueue immediately. overrun oldest message in the queue if no room left. + void enqueue_nowait(T &&item) + { + std::unique_lock lock(queue_mutex_); + q_.push_back(std::move(item)); + push_cv_.notify_one(); + } + + // try to dequeue item. if no item found. wait upto timeout and try again + // Return true, if succeeded dequeue item, false otherwise + bool dequeue_for(T &popped_item, std::chrono::milliseconds wait_duration) + { + std::unique_lock lock(queue_mutex_); + if (!push_cv_.wait_for(lock, wait_duration, [this] { return !this->q_.empty(); })) + { + return false; + } + popped_item = std::move(q_.front()); + q_.pop_front(); + pop_cv_.notify_one(); + return true; + } + +#endif + + size_t overrun_counter() + { + std::unique_lock lock(queue_mutex_); + return q_.overrun_counter(); + } + + size_t size() + { + std::unique_lock lock(queue_mutex_); + return q_.size(); + } + +private: + std::mutex queue_mutex_; + std::condition_variable push_cv_; + std::condition_variable pop_cv_; + spdlog::details::circular_q q_; +}; +} // namespace details +} // namespace spdlog -- cgit v1.2.3