Skip to content

Commit a65ab3c

Browse files
authored
Merge pull request #13 from n7space/n7s-aur#274-fix-queue-issue
fixed queue issues and did small refactor
2 parents 28cc822 + 97dbb3a commit a65ab3c

3 files changed

Lines changed: 97 additions & 46 deletions

File tree

src/Queue.h

Lines changed: 38 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -29,13 +29,10 @@
2929
*/
3030

3131
#include <condition_variable>
32-
#include <cstddef>
3332
#include <iostream>
3433
#include <mutex>
3534
#include <queue>
3635

37-
#include <sched.h>
38-
3936
#include "Request.h"
4037

4138
namespace taste {
@@ -109,11 +106,14 @@ class Queue final
109106
*/
110107
bool is_empty() const;
111108

109+
private:
110+
bool check_for_message_loss() const;
111+
112112
private:
113113
const size_t m_max_elements;
114114
const char* m_queue_name;
115115
mutable std::mutex m_mutex;
116-
mutable std::condition_variable m_cv;
116+
mutable std::condition_variable m_condition_variable;
117117
std::queue<Request<PARAMETER_SIZE>> m_queue;
118118
};
119119

@@ -128,58 +128,48 @@ template<size_t PARAMETER_SIZE>
128128
void
129129
Queue<PARAMETER_SIZE>::put(const Request<PARAMETER_SIZE>& request)
130130
{
131-
m_mutex.lock();
132-
if(m_queue.size() >= m_max_elements) {
133-
std::cerr << "Message loss in " << m_queue_name << " - queue is full, " << m_max_elements << " allowed"
134-
<< std::endl;
135-
m_mutex.unlock();
136-
} else {
131+
{
132+
std::lock_guard<std::mutex> lock(m_mutex);
133+
134+
if(check_for_message_loss()) {
135+
return;
136+
}
137+
137138
m_queue.push(request);
138-
m_mutex.unlock();
139-
m_cv.notify_one();
140139
}
140+
141+
m_condition_variable.notify_one();
141142
}
142143

143144
template<size_t PARAMETER_SIZE>
144145
void
145146
Queue<PARAMETER_SIZE>::put(const asn1SccPID sender_pid, const uint8_t* data, size_t length)
146147
{
147-
m_mutex.lock();
148-
static Request<PARAMETER_SIZE> request;
149-
150-
if(length > PARAMETER_SIZE) {
151-
std::cerr << "Internal error in " << m_queue_name << " - queue accepts messages with size " << PARAMETER_SIZE
152-
<< std::endl;
153-
m_mutex.unlock();
154-
}
148+
{
149+
std::lock_guard<std::mutex> lock(m_mutex);
155150

156-
memcpy(request.data(), data, length);
157-
request.set_length(length);
158-
request.set_sender_pid(sender_pid);
151+
if(check_for_message_loss()) {
152+
return;
153+
}
159154

160-
if(m_queue.size() >= m_max_elements) {
161-
std::cerr << "Message loss in " << m_queue_name << " - queue is full, " << m_max_elements << " allowed"
162-
<< std::endl;
163-
m_mutex.unlock();
164-
} else {
165-
m_queue.push(request);
166-
m_mutex.unlock();
167-
m_cv.notify_one();
155+
m_queue.emplace(sender_pid, data, length);
168156
}
157+
158+
m_condition_variable.notify_one();
169159
}
170160

171161
template<size_t PARAMETER_SIZE>
172162
void
173163
Queue<PARAMETER_SIZE>::get(Request<PARAMETER_SIZE>& request)
174164
{
175165
std::unique_lock<std::mutex> lock(m_mutex);
166+
176167
while(true) {
177168
if(m_queue.empty()) {
178-
m_cv.wait(lock);
169+
m_condition_variable.wait(lock);
179170
} else {
180171
request = m_queue.front();
181172
m_queue.pop();
182-
lock.unlock();
183173
return;
184174
}
185175
}
@@ -192,6 +182,21 @@ Queue<PARAMETER_SIZE>::is_empty() const
192182
std::unique_lock<std::mutex> lock(m_mutex);
193183
return m_queue.empty();
194184
}
185+
186+
template<size_t PARAMETER_SIZE>
187+
bool
188+
Queue<PARAMETER_SIZE>::check_for_message_loss() const
189+
{
190+
if(m_queue.size() >= m_max_elements) {
191+
std::cerr << "Message loss in '" << m_queue_name << "' - queue is full, " << m_max_elements
192+
<< " elements are allowed" << std::endl;
193+
194+
return true;
195+
}
196+
197+
return false;
198+
}
199+
195200
} // namespace taste
196201

197202
#endif

src/Request.h

Lines changed: 46 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@
3131
#include <cstdint>
3232
#include <cstring>
3333
#include <array>
34+
#include <iostream>
3435
#include "dataview-uniq.h"
3536

3637
namespace taste {
@@ -49,6 +50,13 @@ struct Request final
4950
*/
5051
Request();
5152

53+
/**
54+
* @brief Constructor
55+
*
56+
* Constructs Request with provided arguments
57+
*/
58+
Request(const asn1SccPID sender_pid, const uint8_t* const data, const size_t length);
59+
5260
/// @brief default copy constructor
5361
Request(const Request& other) = default;
5462

@@ -65,16 +73,16 @@ struct Request final
6573
*
6674
* @return the actual length of data
6775
*/
68-
uint32_t length() const;
76+
size_t length() const;
6977

7078
/**
7179
* @brief set the request length
7280
*
73-
* The value shall be between 0 and PARAMETER_SIZE
81+
* The length shall be between 0 and PARAMETER_SIZE
7482
*
75-
* @param value new length value
83+
* @param length new length value
7684
*/
77-
void set_length(uint32_t value);
85+
void set_length(size_t length);
7886

7987
/**
8088
* @brief get the request data
@@ -105,31 +113,45 @@ struct Request final
105113
void set_sender_pid(asn1SccPID sender_pid);
106114

107115
private:
108-
uint32_t m_length;
109-
std::array<uint8_t, PARAMETER_SIZE> m_data;
116+
void check_length(size_t length) const;
117+
118+
private:
119+
size_t m_length;
110120
asn1SccPID m_sender_pid;
121+
std::array<uint8_t, PARAMETER_SIZE> m_data;
111122
};
112123

113124
template<size_t PARAMETER_SIZE>
114125
Request<PARAMETER_SIZE>::Request()
115126
: m_length(0)
127+
, m_sender_pid(PID_env)
116128
{
117129
}
118130

119131
template<size_t PARAMETER_SIZE>
120-
uint32_t
132+
Request<PARAMETER_SIZE>::Request(const asn1SccPID sender_pid, const uint8_t* const data, const size_t length)
133+
: m_length(length)
134+
, m_sender_pid(sender_pid)
135+
{
136+
check_length(length);
137+
138+
memcpy(m_data.data(), data, length);
139+
}
140+
141+
template<size_t PARAMETER_SIZE>
142+
size_t
121143
Request<PARAMETER_SIZE>::length() const
122144
{
123145
return m_length;
124146
}
125147

126148
template<size_t PARAMETER_SIZE>
127149
void
128-
Request<PARAMETER_SIZE>::set_length(uint32_t value)
150+
Request<PARAMETER_SIZE>::set_length(size_t length)
129151
{
130-
if(value <= PARAMETER_SIZE && value >= 0) {
131-
m_length = value;
132-
}
152+
check_length(length);
153+
154+
m_length = length;
133155
}
134156

135157
template<size_t PARAMETER_SIZE>
@@ -159,6 +181,19 @@ Request<PARAMETER_SIZE>::set_sender_pid(asn1SccPID sender_pid)
159181
{
160182
m_sender_pid = sender_pid;
161183
}
184+
185+
template<size_t PARAMETER_SIZE>
186+
void
187+
Request<PARAMETER_SIZE>::check_length(size_t length) const
188+
{
189+
if(length > PARAMETER_SIZE) {
190+
std::cerr << "Request data size shall be <= " << PARAMETER_SIZE << " - new length value ("
191+
<< length << ") is greater than " << PARAMETER_SIZE << std::endl;
192+
193+
exit(EXIT_FAILURE);
194+
}
195+
}
196+
162197
} // namespace taste
163198

164199
#endif

src/StartBarrier.cc

Lines changed: 13 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -21,19 +21,30 @@
2121
*/
2222

2323
#include "StartBarrier.h"
24+
#include <iostream>
2425

2526
namespace taste {
2627
void
2728
StartBarrier::initialize(size_t number, InitCallback init_callback)
2829
{
2930
m_init_callback = init_callback;
30-
pthread_barrier_init(&m_init_barrier, nullptr, number);
31+
32+
const int error_code = pthread_barrier_init(&m_init_barrier, nullptr, number);
33+
if(error_code != 0) {
34+
std::cerr << "Barrier has not been created properly. Error code : " << error_code << std::endl;
35+
exit(EXIT_FAILURE);
36+
}
3137
}
3238

3339
void
3440
StartBarrier::wait()
3541
{
36-
pthread_barrier_wait(&m_init_barrier);
42+
const int error_code = pthread_barrier_wait(&m_init_barrier);
43+
if(error_code != PTHREAD_BARRIER_SERIAL_THREAD && error_code != 0) {
44+
std::cerr << "Barrier Wait has been failed. Error code : " << error_code << std::endl;
45+
exit(EXIT_FAILURE);
46+
}
47+
3748
std::call_once(m_init_callback_flag, m_init_callback);
3849
}
3950

0 commit comments

Comments
 (0)