1//
2// Semaphore.h
3//
4// Library: Foundation
5// Package: Threading
6// Module: Semaphore
7//
8// Definition of the Semaphore class.
9//
10// Copyright (c) 2004-2006, Applied Informatics Software Engineering GmbH.
11// and Contributors.
12//
13// SPDX-License-Identifier: BSL-1.0
14//
15
16
17#ifndef Foundation_Semaphore_INCLUDED
18#define Foundation_Semaphore_INCLUDED
19
20
21#include "Poco/Foundation.h"
22#include "Poco/Exception.h"
23#include <mutex>
24#include <condition_variable>
25
26
27namespace Poco {
28
29
30class Foundation_API Semaphore
31 /// A Semaphore is a synchronization object with the following
32 /// characteristics:
33 /// A semaphore has a value that is constrained to be a non-negative
34 /// integer and two atomic operations. The allowable operations are V
35 /// (here called set()) and P (here called wait()). A V (set()) operation
36 /// increases the value of the semaphore by one.
37 /// A P (wait()) operation decreases the value of the semaphore by one,
38 /// provided that can be done without violating the constraint that the
39 /// value be non-negative. A P (wait()) operation that is initiated when
40 /// the value of the semaphore is 0 suspends the calling thread.
41 /// The calling thread may continue when the value becomes positive again.
42{
43public:
44 Semaphore(int n);
45 Semaphore(int n, int max);
46 /// Creates the semaphore. The current value
47 /// of the semaphore is given in n. The
48 /// maximum value of the semaphore is given
49 /// in max.
50 /// If only n is given, it must be greater than
51 /// zero.
52 /// If both n and max are given, max must be
53 /// greater than zero, n must be greater than
54 /// or equal to zero and less than or equal
55 /// to max.
56
57 ~Semaphore();
58 /// Destroys the semaphore.
59
60 void set();
61 /// Increments the semaphore's value by one and
62 /// thus signals the semaphore. Another thread
63 /// waiting for the semaphore will be able
64 /// to continue.
65
66 void wait();
67 /// Waits for the semaphore to become signalled.
68 /// To become signalled, a semaphore's value must
69 /// be greater than zero.
70 /// Decrements the semaphore's value by one.
71
72 void wait(long milliseconds);
73 /// Waits for the semaphore to become signalled.
74 /// To become signalled, a semaphore's value must
75 /// be greater than zero.
76 /// Throws a TimeoutException if the semaphore
77 /// does not become signalled within the specified
78 /// time interval.
79 /// Decrements the semaphore's value by one
80 /// if successful.
81
82 bool tryWait(long milliseconds);
83 /// Waits for the semaphore to become signalled.
84 /// To become signalled, a semaphore's value must
85 /// be greater than zero.
86 /// Returns true if the semaphore
87 /// became signalled within the specified
88 /// time interval, false otherwise.
89 /// Decrements the semaphore's value by one
90 /// if successful.
91
92private:
93 Semaphore();
94 Semaphore(const Semaphore&);
95 Semaphore& operator = (const Semaphore&);
96
97 bool waitImpl(long milliseconds);
98
99 int _count;
100 int _max;
101 std::mutex _mutex;
102 std::condition_variable _cv;
103};
104
105
106//
107// inlines
108//
109
110inline void Semaphore::wait(long milliseconds)
111{
112 if (!waitImpl(milliseconds)) throw TimeoutException();
113}
114
115
116inline bool Semaphore::tryWait(long milliseconds)
117{
118 return waitImpl(milliseconds);
119}
120
121
122} // namespace Poco
123
124
125#endif // Foundation_Semaphore_INCLUDED
126