Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
main.cpp
00001 /* mbed Microcontroller Library 00002 * Copyright (c) 2017 ARM Limited 00003 * 00004 * Licensed under the Apache License, Version 2.0 (the "License"); 00005 * you may not use this file except in compliance with the License. 00006 * You may obtain a copy of the License at 00007 * 00008 * http://www.apache.org/licenses/LICENSE-2.0 00009 * 00010 * Unless required by applicable law or agreed to in writing, software 00011 * distributed under the License is distributed on an "AS IS" BASIS, 00012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 00013 * See the License for the specific language governing permissions and 00014 * limitations under the License. 00015 */ 00016 00017 #include "utest/utest.h" 00018 #include "unity/unity.h" 00019 #include "greentea-client/test_env.h" 00020 00021 #include "mbed.h" 00022 00023 using namespace utest::v1; 00024 00025 /* Structure for complex type. */ 00026 typedef struct 00027 { 00028 int a; 00029 char b; 00030 int c; 00031 } COMPLEX_TYPE; 00032 00033 /* Function to check if complex type object holds specified values.*/ 00034 bool comp_is_equal(COMPLEX_TYPE *object, int a, char b, int c) 00035 { 00036 if (object->a == a && object->b == b && object->c == c) { 00037 return true; 00038 } 00039 00040 return false; 00041 } 00042 00043 /* Function to set complex type object fields.*/ 00044 void comp_set(COMPLEX_TYPE *object, int a, char b, int c) 00045 { 00046 object->a = a; 00047 object->b = b; 00048 object->c = c; 00049 } 00050 00051 /* Test circular buffer - input does not exceed capacity. 00052 * 00053 * Given is a circular buffer with the capacity equal to N (BufferSize). 00054 * When circular buffer is filled with N elements. 00055 * Then all elements are read from the circular buffer in the FIFO order. 00056 * 00057 */ 00058 template<typename T, uint32_t BufferSize, typename CounterType> 00059 void test_input_does_not_exceed_capacity_push_max_pop_max() 00060 { 00061 CircularBuffer<T, BufferSize, CounterType> cb; 00062 T data = 0; 00063 00064 for (uint32_t i = 0; i < BufferSize; i++) { 00065 data = (0xAA + i); 00066 cb.push(data); 00067 TEST_ASSERT_EQUAL(i + 1, cb.size()); 00068 } 00069 00070 for (uint32_t i = 0; i < BufferSize; i++) { 00071 TEST_ASSERT_TRUE(cb.pop(data)); 00072 TEST_ASSERT_EQUAL(0xAA + i, data); 00073 TEST_ASSERT_EQUAL(BufferSize - i - 1, cb.size()); 00074 } 00075 } 00076 00077 /* Test circular buffer - input does not exceed capacity. 00078 * 00079 * Given is a circular buffer with the capacity equal to N (BufferSize). 00080 * When circular buffer is filled as follows: (2 * N - 2) times 2 elements are pushed and 1 element is popped. 00081 * Then all elements are read from the circular buffer in the FIFO order. 00082 * 00083 */ 00084 template<typename T, uint32_t BufferSize, typename CounterType> 00085 void test_input_does_not_exceed_capacity_push_2_pop_1() 00086 { 00087 CircularBuffer<T, BufferSize, CounterType> cb; 00088 static const int num_of_elem_push = (2 * BufferSize - 2); 00089 T push_buffer = 0; 00090 T pop_buffer = 0; 00091 00092 /* Push 2 elements and pop one element in each cycle. */ 00093 for (uint32_t i = 0; i < num_of_elem_push; i += 2) { 00094 push_buffer = (0xAA + i); 00095 cb.push(push_buffer); 00096 push_buffer++; 00097 cb.push(push_buffer); 00098 TEST_ASSERT_EQUAL(i / 2 + 2, cb.size()); 00099 00100 TEST_ASSERT_TRUE(cb.pop(pop_buffer)); 00101 TEST_ASSERT_EQUAL(0xAA + i / 2, pop_buffer); 00102 TEST_ASSERT_EQUAL(i / 2 + 1, cb.size()); 00103 } 00104 00105 /* Pop the rest. */ 00106 for (uint32_t i = 0; i < (num_of_elem_push / 2); i++) { 00107 TEST_ASSERT_TRUE(cb.pop(pop_buffer)); 00108 TEST_ASSERT_EQUAL(0xAA + num_of_elem_push / 2 + i, pop_buffer); 00109 TEST_ASSERT_EQUAL(num_of_elem_push / 2 - 1 - i, cb.size()); 00110 00111 } 00112 } 00113 00114 /* Test circular buffer - input exceeds capacity. 00115 * 00116 * Given is a circular buffer with the capacity equal to N (BufferSize). 00117 * When circular buffer is filled with N + 1 elements. 00118 * Then first pushed element is lost (overwritten by the last element) and 00119 * elements are read from the circular buffer in the FIFO order. 00120 * 00121 */ 00122 template<typename T, uint32_t BufferSize, typename CounterType> 00123 void test_input_exceeds_capacity_push_max_plus_1_pop_max() 00124 { 00125 CircularBuffer<T, BufferSize, CounterType> cb; 00126 static const int num_of_elem_push = (BufferSize + 1); 00127 T data = 0; 00128 00129 for (uint32_t i = 0; i < num_of_elem_push; i++) { 00130 data = (0xAA + i); 00131 cb.push(data); 00132 if (i < BufferSize) { 00133 TEST_ASSERT_EQUAL(i + 1, cb.size()); 00134 } else { 00135 TEST_ASSERT_EQUAL(BufferSize, cb.size()); 00136 } 00137 00138 } 00139 00140 for (uint32_t i = 0; i < (BufferSize - 1); i++) { 00141 TEST_ASSERT_TRUE(cb.pop(data)); 00142 TEST_ASSERT_EQUAL(0xAA + i + 1, data); 00143 TEST_ASSERT_EQUAL(BufferSize - 1 - i, cb.size()); 00144 } 00145 00146 /* First element should be overwritten. */ 00147 TEST_ASSERT_TRUE(cb.pop(data)); 00148 TEST_ASSERT_EQUAL((0xAA + num_of_elem_push - 1), data); 00149 TEST_ASSERT_EQUAL(0, cb.size()); 00150 } 00151 00152 /* Test circular buffer - input exceeds capacity. 00153 * 00154 * Given is a circular buffer with the capacity equal to N (BufferSize). 00155 * When circular buffer is filled as follows: (2 * N) times 2 elements are pushed and 1 element is popped. 00156 * Then first pushed element is lost (overwritten by the last element) and 00157 * elements are read from the circular buffer in the FIFO order. 00158 * 00159 */ 00160 template<typename T, uint32_t BufferSize, typename CounterType> 00161 void test_input_exceeds_capacity_push_2_pop_1() 00162 { 00163 CircularBuffer<T, BufferSize, CounterType> cb; 00164 static const int num_of_elem_push = (2 * BufferSize); 00165 T push_buffer = 0; 00166 T pop_buffer = 0; 00167 00168 /* Push 2 elements and pop one element in each cycle. */ 00169 for (uint32_t i = 0; i < num_of_elem_push; i += 2) { 00170 push_buffer = (0xAA + i); 00171 cb.push(push_buffer); 00172 push_buffer++; 00173 cb.push(push_buffer); 00174 if ((i / 2 + 1) < BufferSize) { 00175 TEST_ASSERT_EQUAL(i / 2 + 2, cb.size()); 00176 } else { 00177 TEST_ASSERT_EQUAL(BufferSize, cb.size()); 00178 } 00179 00180 TEST_ASSERT_TRUE(cb.pop(pop_buffer)); 00181 if ((i / 2 + 1) < BufferSize) { 00182 TEST_ASSERT_EQUAL(i / 2 + 1, cb.size()); 00183 } else { 00184 TEST_ASSERT_EQUAL(BufferSize - 1, cb.size()); 00185 } 00186 00187 /* First element has been overwritten. */ 00188 if (i == (num_of_elem_push - 2)) { 00189 TEST_ASSERT_EQUAL(0xAA + i / 2 + 1, pop_buffer); 00190 } else { 00191 TEST_ASSERT_EQUAL(0xAA + i / 2, pop_buffer); 00192 } 00193 } 00194 00195 /* Pop the rest - one element has been overwritten. */ 00196 for (uint32_t i = 0; i < (num_of_elem_push / 2 - 1); i++) { 00197 TEST_ASSERT_TRUE(cb.pop(pop_buffer)); 00198 TEST_ASSERT_EQUAL(0xAA + num_of_elem_push / 2 + i + 1, pop_buffer); 00199 } 00200 } 00201 00202 /* Test circular buffer - input exceeds capacity (complex type). 00203 * 00204 * Given is a circular buffer with the capacity equal to N (BufferSize). 00205 * When circular buffer is filled as follows: (2 * N) times 2 elements are pushed and 1 element is popped. 00206 * Then first pushed element is lost (overwritten by the last element) and 00207 * elements are read from the circular buffer in the FIFO order. 00208 * 00209 */ 00210 template<uint32_t BufferSize, typename CounterType> 00211 void test_input_exceeds_capacity_push_2_pop_1_complex_type() 00212 { 00213 CircularBuffer<COMPLEX_TYPE, BufferSize, CounterType> cb; 00214 static const int num_of_elem_push = (2 * BufferSize); 00215 COMPLEX_TYPE push_buffer = {0}; 00216 COMPLEX_TYPE pop_buffer = {0}; 00217 00218 /* Push 2 elements and pop one element in each cycle. */ 00219 for (uint32_t i = 0; i < num_of_elem_push; i += 2) { 00220 comp_set(&push_buffer, 0xAA + i, 0xBB + i, 0xCC + i); 00221 cb.push(push_buffer); 00222 comp_set(&push_buffer, 0xAA + i + 1, 0xBB + i + 1, 0xCC + i + 1); 00223 cb.push(push_buffer); 00224 if ((i / 2 + 1) < BufferSize) { 00225 TEST_ASSERT_EQUAL(i / 2 + 2, cb.size()); 00226 } else { 00227 TEST_ASSERT_EQUAL(BufferSize, cb.size()); 00228 } 00229 00230 TEST_ASSERT_TRUE(cb.pop(pop_buffer)); 00231 if ((i / 2 + 1) < BufferSize) { 00232 TEST_ASSERT_EQUAL(i / 2 + 1, cb.size()); 00233 } else { 00234 TEST_ASSERT_EQUAL(BufferSize - 1, cb.size()); 00235 } 00236 00237 /* First element has been overwritten. */ 00238 if (i == (num_of_elem_push - 2)) { 00239 const bool result = comp_is_equal(&pop_buffer, 0xAA + 1 + i / 2, 0xBB + 1 + i / 2, 0xCC + 1 + i / 2); 00240 TEST_ASSERT_TRUE(result); 00241 } else { 00242 const bool result = comp_is_equal(&pop_buffer, 0xAA + i / 2, 0xBB + i / 2, 0xCC + i / 2); 00243 TEST_ASSERT_TRUE(result); 00244 } 00245 } 00246 00247 /* Pop the rest - one element has been overwritten. */ 00248 for (uint32_t i = 0; i < (num_of_elem_push / 2 - 1); i++) { 00249 TEST_ASSERT_TRUE(cb.pop(pop_buffer)); 00250 const bool result = comp_is_equal(&pop_buffer, 0xAA + num_of_elem_push / 2 + i + 1, 00251 0xBB + num_of_elem_push / 2 + i + 1, 0xCC + num_of_elem_push / 2 + i + 1); 00252 TEST_ASSERT_TRUE(result); 00253 } 00254 } 00255 00256 /* Test circular buffer - test pop(), peek(), empty(), full(), size() after CircularBuffer creation. 00257 * 00258 * Given is a circular buffer. 00259 * When circular buffer is created. 00260 * Then circular buffer is empty: 00261 * - empty() returns true, 00262 * - pop() function returns false, 00263 * - peek() function returns false, 00264 * - full() function returns false, 00265 * - size() function returns 0, 00266 * 00267 */ 00268 void test_pop_empty_full_size_after_creation() 00269 { 00270 CircularBuffer<int, 1> cb; 00271 int data = 0; 00272 00273 TEST_ASSERT_TRUE(cb.empty()); 00274 TEST_ASSERT_FALSE(cb.pop(data)); 00275 TEST_ASSERT_FALSE(cb.peek(data)); 00276 TEST_ASSERT_FALSE(cb.full()); 00277 TEST_ASSERT_EQUAL(0, cb.size()); 00278 } 00279 00280 /* Test circular buffer - test empty() function. 00281 * 00282 * Given is a circular buffer with the capacity equal to N (BufferSize). 00283 * When operations on circular buffer are performed (push, pop). 00284 * Then empty() function returns true if buffer is empty, false otherwise. 00285 * 00286 */ 00287 template<typename T, uint32_t BufferSize> 00288 void test_empty() 00289 { 00290 CircularBuffer<T, BufferSize> cb; 00291 T data = 0; 00292 00293 /* Push max elements. */ 00294 for (uint32_t i = 0; i < BufferSize; i++) { 00295 cb.push(data); 00296 TEST_ASSERT_FALSE(cb.empty()); 00297 } 00298 00299 /* Push next 2*BufferSize elements (overwrite entries). */ 00300 for (uint32_t i = 0; i < (2 * BufferSize); i++) { 00301 cb.push(data); 00302 TEST_ASSERT_FALSE(cb.empty()); 00303 } 00304 00305 /* Pop (BufferSize - 1) elements (leave one). */ 00306 for (uint32_t i = 0; i < (BufferSize - 1); i++) { 00307 TEST_ASSERT_TRUE(cb.pop(data)); 00308 TEST_ASSERT_FALSE(cb.empty()); 00309 } 00310 00311 /* Take one which is left. */ 00312 TEST_ASSERT_TRUE(cb.pop(data)); 00313 TEST_ASSERT_TRUE(cb.empty()); 00314 00315 /* Add one element to the empty buffer. */ 00316 cb.push(data); 00317 TEST_ASSERT_FALSE(cb.empty()); 00318 } 00319 00320 /* Test circular buffer - test full() function. 00321 * 00322 * Given is a circular buffer with the capacity equal to N (BufferSize). 00323 * When operations on circular buffer are performed (push, pop). 00324 * Then full() function returns true if buffer is full, false otherwise. 00325 * 00326 */ 00327 template<typename T, uint32_t BufferSize> 00328 void test_full() 00329 { 00330 CircularBuffer<T, BufferSize> cb; 00331 T data = 0; 00332 00333 /* Push max elements - 1. */ 00334 for (uint32_t i = 0; i < (BufferSize - 1); i++) { 00335 cb.push(data); 00336 TEST_ASSERT_FALSE(cb.full()); 00337 } 00338 00339 /* Push one element - buffer should be full now. */ 00340 cb.push(data); 00341 TEST_ASSERT_TRUE(cb.full()); 00342 00343 /* Push next 2*BufferSize elements (overwrite entries). */ 00344 for (uint32_t i = 0; i < (2 * BufferSize); i++) { 00345 cb.push(data); 00346 TEST_ASSERT_TRUE(cb.full()); 00347 } 00348 00349 /* Pop all elements. */ 00350 for (uint32_t i = 0; i < BufferSize; i++) { 00351 TEST_ASSERT_TRUE(cb.pop(data)); 00352 TEST_ASSERT_FALSE(cb.full()); 00353 } 00354 } 00355 00356 /* Test circular buffer - test reset() function. 00357 * 00358 * Given is a circular buffer with the capacity equal to N (BufferSize). 00359 * When reset operation is performed on circular buffer. 00360 * Then circular buffer is cleared. 00361 * 00362 */ 00363 template<typename T, uint32_t BufferSize> 00364 void test_reset() 00365 { 00366 CircularBuffer<T, BufferSize> cb; 00367 T data = 0xAA; 00368 00369 /* Push max elements. */ 00370 for (uint32_t i = 0; i < BufferSize; i++) { 00371 cb.push(data); 00372 } 00373 00374 TEST_ASSERT_TRUE(cb.full()); 00375 TEST_ASSERT_FALSE(cb.empty()); 00376 TEST_ASSERT_EQUAL(BufferSize, cb.size()); 00377 00378 cb.reset(); 00379 00380 TEST_ASSERT_FALSE(cb.full()); 00381 TEST_ASSERT_TRUE(cb.empty()); 00382 TEST_ASSERT_FALSE(cb.pop(data)); 00383 TEST_ASSERT_EQUAL(0, cb.size()); 00384 00385 /* Check if after reset push and pop operations work. */ 00386 for (uint32_t i = 0; i < BufferSize; i++) { 00387 cb.push(data); 00388 data++; 00389 } 00390 00391 for (uint32_t i = 0; i < BufferSize; i++) { 00392 cb.pop(data); 00393 TEST_ASSERT_EQUAL(0xAA + i, data); 00394 } 00395 } 00396 00397 /* Test circular buffer - creation of circular buffer with max buffer size consistent with counter type. 00398 * 00399 * Given is a circular buffer. 00400 * When circular buffer is created with buffer size equal to 255 and counter type equal to unsigned char. 00401 * Then circular buffer is successfully created. 00402 * 00403 */ 00404 void test_counter_type_buffer_size() 00405 { 00406 CircularBuffer<int, 255, unsigned char> cb; 00407 int data = 100; 00408 00409 /* Perform some operations. */ 00410 cb.push(data); 00411 data = 0; 00412 cb.pop(data); 00413 TEST_ASSERT_EQUAL(100, data); 00414 } 00415 00416 /* Test circular buffer - peek should not update buffer data. 00417 * 00418 * When circular buffer peek operation is performed along with 00419 * push and pop, it should not update the buffer data elements. 00420 * Elements read using pop/peek operation should match. 00421 * 00422 */ 00423 void test_peek_no_pop() 00424 { 00425 CircularBuffer<int, 3, unsigned char> cb; 00426 int data = 0; 00427 int peek_data = 0; 00428 00429 for (uint32_t i = 0; i < 3; i++) { 00430 data = (0xAA + i); 00431 cb.push(data); 00432 cb.peek(peek_data); 00433 TEST_ASSERT_EQUAL(i + 1, cb.size()); 00434 } 00435 00436 for (uint32_t i = 0; i < 3; i++) { 00437 TEST_ASSERT_TRUE(cb.peek(peek_data)); 00438 TEST_ASSERT_EQUAL(0xAA + i, peek_data); 00439 TEST_ASSERT_TRUE(cb.pop(data)); 00440 TEST_ASSERT_EQUAL(0xAA + i, data); 00441 TEST_ASSERT_EQUAL(3 - i - 1, cb.size()); 00442 } 00443 } 00444 00445 utest::v1::status_t greentea_failure_handler(const Case *const source, const failure_t reason) 00446 { 00447 greentea_case_failure_abort_handler(source, reason); 00448 return STATUS_CONTINUE; 00449 } 00450 00451 Case cases[] = { 00452 Case("Input does not exceed capacity(1) push max, pop max.", 00453 test_input_does_not_exceed_capacity_push_max_pop_max<uint32_t, 1, unsigned int>, greentea_failure_handler), 00454 Case("Input does not exceed capacity(3) push max, pop max.", 00455 test_input_does_not_exceed_capacity_push_max_pop_max<char, 3, unsigned int>, greentea_failure_handler), 00456 00457 Case("Input does not exceed capacity(5) push 2, pop 1.", 00458 test_input_does_not_exceed_capacity_push_2_pop_1<uint32_t, 5, unsigned char>, greentea_failure_handler), 00459 Case("Input does not exceed capacity(10) push 2, pop 1.", 00460 test_input_does_not_exceed_capacity_push_2_pop_1<char, 10, unsigned char>, greentea_failure_handler), 00461 00462 Case("Input exceeds capacity(1) push max+1, pop max.", 00463 test_input_exceeds_capacity_push_max_plus_1_pop_max<uint32_t, 1, unsigned int>, greentea_failure_handler), 00464 Case("Input exceeds capacity(3) push max+1, pop max.", 00465 test_input_exceeds_capacity_push_max_plus_1_pop_max<char, 3, unsigned int>, greentea_failure_handler), 00466 00467 Case("Input exceeds capacity(5) push 2, pop 1.", 00468 test_input_exceeds_capacity_push_2_pop_1<uint32_t, 5, unsigned short>, greentea_failure_handler), 00469 Case("Input exceeds capacity(10) push 2, pop 1.", 00470 test_input_exceeds_capacity_push_2_pop_1<char, 10, unsigned short>, greentea_failure_handler), 00471 00472 Case("empty() returns true when buffer(3 elements) is empty.", test_empty<uint32_t, 3>, greentea_failure_handler), 00473 Case("empty() returns true when buffer(5 elements) is empty.", test_empty<uint32_t, 5>, greentea_failure_handler), 00474 00475 Case("full() returns true when buffer(3 elements) is full.", test_full<uint32_t, 3>, greentea_failure_handler), 00476 Case("full() returns true when buffer(5 elements) is full.", test_full<uint32_t, 5>, greentea_failure_handler), 00477 00478 Case("reset() clears the buffer.", test_reset<uint32_t, 5>, greentea_failure_handler), 00479 00480 Case("Test pop(), peek(), empty(), full(), size() after CircularBuffer creation.", 00481 test_pop_empty_full_size_after_creation, greentea_failure_handler), 00482 00483 Case("Test CounterType/BufferSize boarder case.", test_counter_type_buffer_size, greentea_failure_handler), 00484 00485 Case("Input exceeds capacity(5) push 2, pop 1 - complex type.", 00486 test_input_exceeds_capacity_push_2_pop_1_complex_type<5, unsigned short>, greentea_failure_handler), 00487 00488 Case("peek() return data without popping the element.", test_peek_no_pop, greentea_failure_handler), 00489 }; 00490 00491 utest::v1::status_t greentea_test_setup(const size_t number_of_cases) 00492 { 00493 GREENTEA_SETUP(15, "default_auto"); 00494 return greentea_test_setup_handler(number_of_cases); 00495 } 00496 00497 Specification specification(greentea_test_setup, cases, greentea_test_teardown_handler); 00498 00499 int main() 00500 { 00501 return Harness::run(specification); 00502 }
Generated on Tue Jul 12 2022 14:24:25 by
