/
msgq.c
194 lines (158 loc) · 5.85 KB
/
msgq.c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
/*
* Copyright (c) 2018 Intel Corporation
*
* SPDX-License-Identifier: Apache-2.0
*/
#include <ztest.h>
#include <kernel.h>
#include <cmsis_os2.h>
struct sample_data {
int data1;
unsigned char data2;
unsigned int data3;
};
#define MESSAGE1 512
#define MESSAGE2 123456
#define TIMEOUT_TICKS 50
#define Q_LEN 5
#define STACKSZ CONFIG_CMSIS_V2_THREAD_MAX_STACK_SIZE
osMessageQueueId_t message_id;
void send_msg_thread(void *argument)
{
int i;
osStatus_t status;
u32_t sample = MESSAGE1;
struct sample_data data[Q_LEN] = { 0 };
/* Wait for message_recv to complete initial checks */
osDelay(TIMEOUT_TICKS);
/* Prepare and send the 1st message (a simple integer data) */
status = osMessageQueuePut(message_id, &sample, 0, osWaitForever);
zassert_true(status == osOK, "osMessageQueuePut failure for Message1");
/* The Queue should be empty at this point */
zassert_equal(osMessageQueueGetCount(message_id), 0,
"Something's wrong with osMessageQueueGetCount!");
zassert_equal(osMessageQueueGetSpace(message_id), Q_LEN,
"Something's wrong with osMessageQueueGetSpace!");
/* Fill the queue with blocks of messages */
for (i = 0; i < Q_LEN; i++) {
data[i].data1 = i * 3;
data[i].data2 = i * 3 + 1;
data[i].data3 = i * 3 + 2;
status = osMessageQueuePut(message_id, data + i,
0, osWaitForever);
zassert_true(status == osOK,
"osMessageQueuePut failure for message!");
}
/* The Queue should be full at this point */
zassert_equal(osMessageQueueGetCount(message_id), Q_LEN,
"Something's wrong with osMessageQueueGetCount!");
zassert_equal(osMessageQueueGetSpace(message_id), 0,
"Something's wrong with osMessageQueueGetSpace!");
/* Try putting message to a full queue immediately
* before it is emptied out and assert failure
*/
sample = MESSAGE2;
status = osMessageQueuePut(message_id, &sample, 0, 0);
zassert_true(status == osErrorResource,
"Something's wrong with osMessageQueuePut!");
/* Try putting message to a full queue within a duration
* less than TIMEOUT_TICKS, before the queue is emptied out
*/
sample = MESSAGE2;
status = osMessageQueuePut(message_id, &sample, 0, TIMEOUT_TICKS / 2);
zassert_true(status == osErrorTimeout,
"Something's wrong with osMessageQueuePut!");
/* Send another message after the queue is emptied */
sample = MESSAGE2;
status = osMessageQueuePut(message_id, &sample, 0, TIMEOUT_TICKS * 2);
zassert_true(status == osOK,
"osMessageQueuePut failure for message!");
}
void message_recv(void)
{
int i;
osStatus_t status;
u32_t sample;
struct sample_data recv_data;
/* Try getting message immediately before the queue is populated */
status = osMessageQueueGet(message_id, (void *)&sample, NULL, 0);
zassert_true(status == osErrorResource,
"Something's wrong with osMessageQueueGet!");
/* Try receiving message within a duration of TIMEOUT */
status = osMessageQueueGet(message_id, (void *)&sample,
NULL, TIMEOUT_TICKS);
zassert_true(status == osErrorTimeout,
"Something's wrong with osMessageQueueGet!");
zassert_equal(osMessageQueueGetCapacity(message_id), Q_LEN,
"Something's wrong with osMessageQueueGetCapacity!");
zassert_equal(osMessageQueueGetMsgSize(message_id),
sizeof(struct sample_data),
"Something's wrong with osMessageQueueGetMsgSize!");
/* Receive 1st message */
status = osMessageQueueGet(message_id, (void *)&sample,
NULL, osWaitForever);
zassert_true(status == osOK, "osMessageQueueGet failure");
zassert_equal(sample, MESSAGE1, NULL);
/* Wait for queue to get filled */
osDelay(TIMEOUT_TICKS);
/* Empty the queue */
for (i = 0; i < Q_LEN; i++) {
status = osMessageQueueGet(message_id, (void *)&recv_data, NULL,
osWaitForever);
zassert_true(status == osOK, "osMessageQueueGet failure");
zassert_equal(recv_data.data1, i * 3, NULL);
zassert_equal(recv_data.data2, i * 3 + 1, NULL);
zassert_equal(recv_data.data3, i * 3 + 2, NULL);
}
/* Receive the next message */
status = osMessageQueueGet(message_id, (void *)&sample,
NULL, osWaitForever);
zassert_true(status == osOK, "osMessageQueueGet failure");
zassert_equal(sample, MESSAGE2, NULL);
}
static K_THREAD_STACK_DEFINE(test_stack, STACKSZ);
osThreadAttr_t thread_attr = {
.name = "send_thread",
.stack_mem = &test_stack,
.stack_size = STACKSZ,
.priority = osPriorityNormal,
};
static char __aligned(4) sample_mem[sizeof(struct sample_data) * Q_LEN];
static const osMessageQueueAttr_t init_mem_attrs = {
.name = "TestMsgQ",
.attr_bits = 0,
.cb_mem = NULL,
.cb_size = 0,
.mq_mem = sample_mem,
.mq_size = sizeof(struct sample_data) * Q_LEN,
};
void test_messageq(void)
{
osStatus_t status;
u32_t sample = MESSAGE1;
osThreadId_t tid;
message_id = osMessageQueueNew(Q_LEN, sizeof(struct sample_data),
&init_mem_attrs);
zassert_true(message_id != NULL, "Message creation failed");
tid = osThreadNew(send_msg_thread, NULL, &thread_attr);
zassert_true(tid != NULL, "Thread creation failed");
message_recv();
/* Wait for the send_msg_thread to terminate before this thread
* terminates.
*/
osDelay(TIMEOUT_TICKS / 10);
/* Make sure msgq is empty */
zassert_equal(osMessageQueueGetCount(message_id), 0,
"Something's wrong with osMessageQueueGetCount!");
status = osMessageQueuePut(message_id, &sample, 0, osWaitForever);
zassert_true(status == osOK, "osMessageQueuePut failure for Message1");
zassert_equal(osMessageQueueGetCount(message_id), 1,
"Something's wrong with osMessageQueueGetCount!");
status = osMessageQueueReset(message_id);
zassert_true(status == osOK, "osMessageQueueReset failure");
/* After reset msgq must be empty */
zassert_equal(osMessageQueueGetCount(message_id), 0,
"Something's wrong with osMessageQueueGetCount!");
status = osMessageQueueDelete(message_id);
zassert_true(status == osOK, "osMessageQueueDelete failure");
}