#pragma once #include #include #include namespace zstd { template struct static_buffer { char data[T]; }; template class channel_static { static_assert(T_capacity != 0); protected: int m_tail; int m_head; static_buffer m_buf[T_capacity]; std::mutex m_mtx; std::condition_variable m_cv; public: ~channel_static() { reset(); } channel_static() : m_tail(0), m_head(0), m_buf() {} int head() { return m_head; } int tail() { return m_tail; } int count() { return m_head - m_tail; } void reset() { for (int i = m_tail; i < m_head; i++) { std::destroy_at((T*)(m_buf + m_tail % T_capacity)); } m_tail = 0; m_head = 0; } template void release(Args... args) { std::unique_lock lck(m_mtx); while (m_head >= m_tail + T_capacity) { m_cv.wait(lck); } std::construct_at((T*)(m_buf + m_head % T_capacity), std::forward(args)...); if (m_head++ == m_tail) m_cv.notify_one(); }; T acquire() { std::unique_lock lck(m_mtx); while (m_tail >= m_head) { m_cv.wait(lck); } int tail = m_tail % T_capacity; if (m_tail++ == m_head - T_capacity) m_cv.notify_one(); return std::move(*(T*)(m_buf + tail)); }; }; }