blob: 71bc260c087aeee3543c3c4213b42e846c0807ee [file] [log] [blame]
Mohammad Azim Khan95402612017-07-19 10:15:54 +01001#line 2 "suites/target_test.function"
Mohammad Azim Khanfff49042017-03-28 01:48:31 +01002
Azim Khan3e5d0002017-06-05 13:16:10 +01003#include "greentea-client/test_env.h"
Mohammad Azim Khanfff49042017-03-28 01:48:31 +01004
5/**
6 * \brief Increments pointer and asserts that it does not overflow.
7 *
8 * \param p Pointer to byte array
9 * \param start Pointer to start of byte array
10 * \param len Length of byte array
11 * \param step Increment size
12 *
13 */
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +020014#define INCR_ASSERT(p, start, len, step) \
15 do { \
16 TEST_HELPER_ASSERT((p) >= (start)); \
17 TEST_HELPER_ASSERT(sizeof(*(p)) == sizeof(*(start))); \
18 /* <= is checked to support use inside a loop where \
19 pointer is incremented after reading data. */ \
20 TEST_HELPER_ASSERT((uint32_t)(((p) - (start)) + (step)) <= (len)); \
21 (p) += (step); \
22 } while (0)
Mohammad Azim Khanfff49042017-03-28 01:48:31 +010023
24/**
25 * \brief 4 byte align unsigned char pointer
26 *
27 * \param p Pointer to byte array
28 * \param start Pointer to start of byte array
29 * \param len Length of byte array
30 *
31 */
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +020032#define ALIGN_32BIT(p, start, len) \
33 do { \
34 uint32_t align = (-(uintptr_t)(p)) % 4; \
35 INCR_ASSERT((p), (start), (len), align); \
36 } while (0)
Mohammad Azim Khanfff49042017-03-28 01:48:31 +010037
38/**
39 * \brief Verify dependencies. Dependency identifiers are
40 * encoded in the buffer as 8 bit unsigned integers.
41 *
42 * \param count Number of dependencies.
43 * \param dep_p Pointer to buffer.
44 *
45 * \return DEPENDENCY_SUPPORTED if success else DEPENDENCY_NOT_SUPPORTED.
46 */
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +020047int verify_dependencies(uint8_t count, uint8_t *dep_p)
Mohammad Azim Khanfff49042017-03-28 01:48:31 +010048{
49 uint8_t i;
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +020050 for (i = 0; i < count; i++) {
51 if (dep_check((int)(dep_p[i])) != DEPENDENCY_SUPPORTED)
52 return DEPENDENCY_NOT_SUPPORTED;
Mohammad Azim Khanfff49042017-03-28 01:48:31 +010053 }
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +020054 return DEPENDENCY_SUPPORTED;
Mohammad Azim Khanfff49042017-03-28 01:48:31 +010055}
56
Ron Eldor5075f4d2019-06-03 11:38:42 +030057/**
58 * \brief Receives hex string on serial interface, and converts to a byte.
59 *
60 * \param none
61 *
62 * \return unsigned int8
63 */
64uint8_t receive_byte()
65{
66 uint8_t byte;
Ron Eldorb2204892019-06-03 16:39:59 +030067 uint8_t c[3];
Ronald Crona0c25392020-06-18 10:10:46 +020068 size_t len;
69
Ron Eldorb2204892019-06-03 16:39:59 +030070 c[0] = greentea_getc();
71 c[1] = greentea_getc();
72 c[2] = '\0';
Ron Eldor5075f4d2019-06-03 11:38:42 +030073
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +020074 TEST_HELPER_ASSERT(mbedtls_test_unhexify(&byte, sizeof(byte), c, &len) ==
75 0);
76 TEST_HELPER_ASSERT(len != 2);
Ronald Crona0c25392020-06-18 10:10:46 +020077
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +020078 return byte;
Ron Eldor5075f4d2019-06-03 11:38:42 +030079}
Mohammad Azim Khanfff49042017-03-28 01:48:31 +010080
81/**
82 * \brief Receives unsigned integer on serial interface.
Ron Eldor5075f4d2019-06-03 11:38:42 +030083 * Integers are encoded in network order, and sent as hex ascii string.
Mohammad Azim Khanfff49042017-03-28 01:48:31 +010084 *
85 * \param none
86 *
87 * \return unsigned int
88 */
89uint32_t receive_uint32()
90{
91 uint32_t value;
Ronald Crona0c25392020-06-18 10:10:46 +020092 size_t len;
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +020093 const uint8_t c_be[8] = { greentea_getc(), greentea_getc(), greentea_getc(),
94 greentea_getc(), greentea_getc(), greentea_getc(),
95 greentea_getc(), greentea_getc() };
Ron Eldoraf7724e2019-09-09 14:52:50 +030096 const uint8_t c[9] = { c_be[6], c_be[7], c_be[4], c_be[5], c_be[2],
97 c_be[3], c_be[0], c_be[1], '\0' };
Ronald Crona0c25392020-06-18 10:10:46 +020098
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +020099 TEST_HELPER_ASSERT(
100 mbedtls_test_unhexify((uint8_t *)&value, sizeof(value), c, &len) == 0);
101 TEST_HELPER_ASSERT(len != 8);
Ronald Crona0c25392020-06-18 10:10:46 +0200102
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200103 return value;
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100104}
105
106/**
107 * \brief Parses out an unsigned 32 int value from the byte array.
108 * Integers are encoded in network order.
109 *
110 * \param p Pointer to byte array
111 *
112 * \return unsigned int
113 */
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200114uint32_t parse_uint32(uint8_t *p)
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100115{
116 uint32_t value;
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200117 value = *p++ << 24;
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100118 value |= *p++ << 16;
119 value |= *p++ << 8;
120 value |= *p;
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200121 return value;
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100122}
123
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100124/**
125 * \brief Receives test data on serial as greentea key,value pair:
126 * {{<length>;<byte array>}}
127 *
128 * \param data_len Out pointer to hold received data length.
129 *
130 * \return Byte array.
131 */
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200132uint8_t *receive_data(uint32_t *data_len)
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100133{
134 uint32_t i = 0, errors = 0;
135 char c;
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200136 uint8_t *data = NULL;
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100137
138 /* Read opening braces */
139 i = 0;
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200140 while (i < 2) {
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100141 c = greentea_getc();
142 /* Ignore any prevous CR LF characters */
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200143 if (c == '\n' || c == '\r')
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100144 continue;
145 i++;
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200146 if (c != '{')
147 return NULL;
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100148 }
149
150 /* Read data length */
151 *data_len = receive_uint32();
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200152 data = (uint8_t *)malloc(*data_len);
153 TEST_HELPER_ASSERT(data != NULL);
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100154
155 greentea_getc(); // read ';' received after key i.e. *data_len
156
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200157 for (i = 0; i < *data_len; i++)
Ron Eldor5075f4d2019-06-03 11:38:42 +0300158 data[i] = receive_byte();
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100159
160 /* Read closing braces */
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200161 for (i = 0; i < 2; i++) {
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100162 c = greentea_getc();
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200163 if (c != '}') {
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100164 errors++;
165 break;
166 }
167 }
168
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200169 if (errors) {
170 free(data);
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100171 data = NULL;
172 *data_len = 0;
173 }
174
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200175 return data;
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100176}
177
178/**
Azim Khan05d83fa2017-09-10 22:57:19 +0100179 * \brief Parse the received byte array and count the number of arguments
180 * to the test function passed as type hex.
Azim Khand59391a2017-06-01 14:04:17 +0100181 *
182 * \param count Parameter count
183 * \param data Received Byte array
184 * \param data_len Byte array length
185 *
186 * \return count of hex params
187 */
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200188uint32_t find_hex_count(uint8_t count, uint8_t *data, uint32_t data_len)
Azim Khand59391a2017-06-01 14:04:17 +0100189{
190 uint32_t i = 0, sz = 0;
191 char c;
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200192 uint8_t *p = NULL;
Azim Khand59391a2017-06-01 14:04:17 +0100193 uint32_t hex_count = 0;
194
195 p = data;
196
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200197 for (i = 0; i < count; i++) {
Azim Khand59391a2017-06-01 14:04:17 +0100198 c = (char)*p;
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200199 INCR_ASSERT(p, data, data_len, 1);
Azim Khand59391a2017-06-01 14:04:17 +0100200
201 /* Align p to 4 bytes for int, expression, string len or hex length */
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200202 ALIGN_32BIT(p, data, data_len);
Azim Khand59391a2017-06-01 14:04:17 +0100203
204 /* Network to host conversion */
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200205 sz = (int32_t)parse_uint32(p);
Azim Khand59391a2017-06-01 14:04:17 +0100206
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200207 INCR_ASSERT(p, data, data_len, sizeof(int32_t));
Azim Khand59391a2017-06-01 14:04:17 +0100208
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200209 if (c == 'H' || c == 'S') {
210 INCR_ASSERT(p, data, data_len, sz);
211 hex_count += (c == 'H') ? 1 : 0;
Azim Khand59391a2017-06-01 14:04:17 +0100212 }
213 }
214
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200215 return hex_count;
Azim Khand59391a2017-06-01 14:04:17 +0100216}
217
218/**
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100219 * \brief Parses received byte array for test parameters.
220 *
221 * \param count Parameter count
222 * \param data Received Byte array
223 * \param data_len Byte array length
224 * \param error Parsing error out variable.
225 *
226 * \return Array of parsed parameters allocated on heap.
227 * Note: Caller has the responsibility to delete
228 * the memory after use.
229 */
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200230void **
231parse_parameters(uint8_t count, uint8_t *data, uint32_t data_len, int *error)
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100232{
Azim Khand59391a2017-06-01 14:04:17 +0100233 uint32_t i = 0, hex_count = 0;
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100234 char c;
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200235 void **params = NULL;
236 void **cur = NULL;
237 uint8_t *p = NULL;
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100238
Azim Khand59391a2017-06-01 14:04:17 +0100239 hex_count = find_hex_count(count, data, data_len);
240
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200241 params = (void **)malloc(sizeof(void *) * (count + hex_count));
242 TEST_HELPER_ASSERT(params != NULL);
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100243 cur = params;
244
245 p = data;
246
247 /* Parameters */
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200248 for (i = 0; i < count; i++) {
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100249 c = (char)*p;
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200250 INCR_ASSERT(p, data, data_len, 1);
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100251
252 /* Align p to 4 bytes for int, expression, string len or hex length */
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200253 ALIGN_32BIT(p, data, data_len);
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100254
255 /* Network to host conversion */
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200256 *((int32_t *)p) = (int32_t)parse_uint32(p);
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100257
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200258 switch (c) {
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100259 case 'E':
260 {
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200261 if (get_expression(*((int32_t *)p), (int32_t *)p)) {
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100262 *error = KEY_VALUE_MAPPING_NOT_FOUND;
263 goto exit;
264 }
265 } /* Intentional fall through */
266 case 'I':
267 {
268 *cur++ = (void *)p;
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200269 INCR_ASSERT(p, data, data_len, sizeof(int32_t));
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100270 }
271 break;
Azim Khand59391a2017-06-01 14:04:17 +0100272 case 'H': /* Intentional fall through */
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100273 case 'S':
274 {
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200275 uint32_t *sz = (uint32_t *)p;
276 INCR_ASSERT(p, data, data_len, sizeof(int32_t));
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100277 *cur++ = (void *)p;
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200278 if (c == 'H')
Azim Khand59391a2017-06-01 14:04:17 +0100279 *cur++ = (void *)sz;
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200280 INCR_ASSERT(p, data, data_len, (*sz));
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100281 }
282 break;
283 default:
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200284 {
285 *error = DISPATCH_INVALID_TEST_DATA;
286 goto exit;
287 }
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100288 break;
289 }
290 }
291
292exit:
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200293 if (*error) {
294 free(params);
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100295 params = NULL;
296 }
297
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200298 return params;
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100299}
300
301/**
302 * \brief Sends greentea key and int value pair to host.
303 *
304 * \param key key string
305 * \param value integer value
306 *
307 * \return void
308 */
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200309void send_key_integer(char *key, int value)
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100310{
311 char str[50];
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200312 snprintf(str, sizeof(str), "%d", value);
313 greentea_send_kv(key, str);
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100314}
315
316/**
317 * \brief Sends test setup failure to the host.
318 *
319 * \param failure Test set failure
320 *
321 * \return void
322 */
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200323void send_failure(int failure)
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100324{
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200325 send_key_integer("F", failure);
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100326}
327
328/**
329 * \brief Sends test status to the host.
330 *
331 * \param status Test status (PASS=0/FAIL=!0)
332 *
333 * \return void
334 */
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200335void send_status(int status)
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100336{
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200337 send_key_integer("R", status);
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100338}
339
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100340/**
341 * \brief Embedded implementation of execute_tests().
342 * Ignores command line and received test data
343 * on serial.
344 *
345 * \param argc not used
346 * \param argv not used
347 *
348 * \return Program exit status.
349 */
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200350int execute_tests(int args, const char **argv)
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100351{
352 int ret = 0;
353 uint32_t data_len = 0;
354 uint8_t count = 0, function_id;
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200355 void **params = NULL;
356 uint8_t *data = NULL, *p = NULL;
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100357
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200358 GREENTEA_SETUP(800, "mbedtls_test");
359 greentea_send_kv("GO", " ");
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100360
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200361 while (1) {
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100362 ret = 0;
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200363 mbedtls_test_info_reset();
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100364 data_len = 0;
365
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200366 data = receive_data(&data_len);
367 if (data == NULL)
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100368 continue;
369 p = data;
370
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200371 do {
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100372 /* Read dependency count */
373 count = *p;
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200374 TEST_HELPER_ASSERT(count < data_len);
375 INCR_ASSERT(p, data, data_len, sizeof(uint8_t));
376 ret = verify_dependencies(count, p);
377 if (ret != DEPENDENCY_SUPPORTED)
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100378 break;
379
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200380 if (count)
381 INCR_ASSERT(p, data, data_len, count);
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100382
383 /* Read function id */
384 function_id = *p;
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200385 INCR_ASSERT(p, data, data_len, sizeof(uint8_t));
386 if ((ret = check_test(function_id)) != DISPATCH_TEST_SUCCESS)
Azim Khan13c6bfb2017-06-15 14:45:56 +0100387 break;
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100388
389 /* Read number of parameters */
390 count = *p;
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200391 INCR_ASSERT(p, data, data_len, sizeof(uint8_t));
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100392
Azim Khand59391a2017-06-01 14:04:17 +0100393 /* Parse parameters if present */
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200394 if (count) {
395 params =
396 parse_parameters(count, p, data_len - (p - data), &ret);
397 if (ret)
Azim Khand59391a2017-06-01 14:04:17 +0100398 break;
399 }
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100400
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200401 ret = dispatch_test(function_id, params);
402 } while (0);
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100403
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200404 if (data) {
405 free(data);
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100406 data = NULL;
407 }
408
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200409 if (params) {
410 free(params);
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100411 params = NULL;
412 }
413
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200414 if (ret)
415 send_failure(ret);
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100416 else
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200417 send_status(mbedtls_test_info.result);
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100418 }
Mateusz Starzykc0eabdc2021-08-03 14:09:02 +0200419 return 0;
Mohammad Azim Khanfff49042017-03-28 01:48:31 +0100420}