Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
Kitware
GitHub Repository: Kitware/CMake
Path: blob/master/Utilities/cmcppdap/src/chan.h
3153 views
1
// Copyright 2019 Google LLC
2
//
3
// Licensed under the Apache License, Version 2.0 (the "License");
4
// you may not use this file except in compliance with the License.
5
// You may obtain a copy of the License at
6
//
7
// https://www.apache.org/licenses/LICENSE-2.0
8
//
9
// Unless required by applicable law or agreed to in writing, software
10
// distributed under the License is distributed on an "AS IS" BASIS,
11
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
// See the License for the specific language governing permissions and
13
// limitations under the License.
14
15
#ifndef dap_chan_h
16
#define dap_chan_h
17
18
#include "dap/optional.h"
19
20
#include <condition_variable>
21
#include <mutex>
22
#include <queue>
23
24
namespace dap {
25
26
template <typename T>
27
struct Chan {
28
public:
29
void reset();
30
void close();
31
optional<T> take();
32
void put(T&& in);
33
void put(const T& in);
34
35
private:
36
bool closed = false;
37
std::queue<T> queue;
38
std::condition_variable cv;
39
std::mutex mutex;
40
};
41
42
template <typename T>
43
void Chan<T>::reset() {
44
std::unique_lock<std::mutex> lock(mutex);
45
queue = {};
46
closed = false;
47
}
48
49
template <typename T>
50
void Chan<T>::close() {
51
std::unique_lock<std::mutex> lock(mutex);
52
closed = true;
53
cv.notify_all();
54
}
55
56
template <typename T>
57
optional<T> Chan<T>::take() {
58
std::unique_lock<std::mutex> lock(mutex);
59
cv.wait(lock, [&] { return queue.size() > 0 || closed; });
60
if (queue.size() == 0) {
61
return optional<T>();
62
}
63
auto out = std::move(queue.front());
64
queue.pop();
65
return optional<T>(std::move(out));
66
}
67
68
template <typename T>
69
void Chan<T>::put(T&& in) {
70
std::unique_lock<std::mutex> lock(mutex);
71
auto notify = queue.size() == 0 && !closed;
72
queue.push(std::move(in));
73
if (notify) {
74
cv.notify_all();
75
}
76
}
77
78
template <typename T>
79
void Chan<T>::put(const T& in) {
80
std::unique_lock<std::mutex> lock(mutex);
81
auto notify = queue.size() == 0 && !closed;
82
queue.push(in);
83
if (notify) {
84
cv.notify_all();
85
}
86
}
87
88
} // namespace dap
89
90
#endif // dap_chan_h
91
92