mempool: introduce helpers for populate and required size
[dpdk.git] / app / test-bbdev / test_bbdev_vector.c
1 /* SPDX-License-Identifier: BSD-3-Clause
2  * Copyright(c) 2017 Intel Corporation
3  */
4
5 #ifdef RTE_EXEC_ENV_FREEBSD
6         #define _WITH_GETLINE
7 #endif
8 #include <stdio.h>
9 #include <stdbool.h>
10 #include <rte_malloc.h>
11
12 #include "test_bbdev_vector.h"
13
14 #define VALUE_DELIMITER ","
15 #define ENTRY_DELIMITER "="
16
17 const char *op_data_prefixes[] = {
18         "input",
19         "soft_output",
20         "hard_output",
21         "harq_input",
22         "harq_output",
23 };
24
25 /* trim leading and trailing spaces */
26 static void
27 trim_space(char *str)
28 {
29         char *start, *end;
30
31         for (start = str; *start; start++) {
32                 if (!isspace((unsigned char) start[0]))
33                         break;
34         }
35
36         for (end = start + strlen(start); end > start + 1; end--) {
37                 if (!isspace((unsigned char) end[-1]))
38                         break;
39         }
40
41         *end = 0;
42
43         /* Shift from "start" to the beginning of the string */
44         if (start > str)
45                 memmove(str, start, (end - start) + 1);
46 }
47
48 static bool
49 starts_with(const char *str, const char *pre)
50 {
51         return strncmp(pre, str, strlen(pre)) == 0;
52 }
53
54 /* tokenization test values separated by a comma */
55 static int
56 parse_values(char *tokens, uint32_t **data, uint32_t *data_length)
57 {
58         uint32_t n_tokens = 0;
59         uint32_t data_size = 32;
60
61         uint32_t *values, *values_resized;
62         char *tok, *error = NULL;
63
64         tok = strtok(tokens, VALUE_DELIMITER);
65         if (tok == NULL)
66                 return -1;
67
68         values = (uint32_t *)
69                         rte_zmalloc(NULL, sizeof(uint32_t) * data_size, 0);
70         if (values == NULL)
71                 return -1;
72
73         while (tok != NULL) {
74                 values_resized = NULL;
75
76                 if (n_tokens >= data_size) {
77                         data_size *= 2;
78
79                         values_resized = (uint32_t *) rte_realloc(values,
80                                 sizeof(uint32_t) * data_size, 0);
81                         if (values_resized == NULL) {
82                                 rte_free(values);
83                                 return -1;
84                         }
85                         values = values_resized;
86                 }
87
88                 values[n_tokens] = (uint32_t) strtoul(tok, &error, 0);
89
90                 if ((error == NULL) || (*error != '\0')) {
91                         printf("Failed with convert '%s'\n", tok);
92                         rte_free(values);
93                         return -1;
94                 }
95
96                 *data_length = *data_length + (strlen(tok) - strlen("0x"))/2;
97
98                 tok = strtok(NULL, VALUE_DELIMITER);
99                 if (tok == NULL)
100                         break;
101
102                 n_tokens++;
103         }
104
105         values_resized = (uint32_t *) rte_realloc(values,
106                 sizeof(uint32_t) * (n_tokens + 1), 0);
107
108         if (values_resized == NULL) {
109                 rte_free(values);
110                 return -1;
111         }
112
113         *data = values_resized;
114
115         return 0;
116 }
117
118 /* convert turbo decoder flag from string to unsigned long int*/
119 static int
120 op_decoder_flag_strtoul(char *token, uint32_t *op_flag_value)
121 {
122         if (!strcmp(token, "RTE_BBDEV_TURBO_SUBBLOCK_DEINTERLEAVE"))
123                 *op_flag_value = RTE_BBDEV_TURBO_SUBBLOCK_DEINTERLEAVE;
124         else if (!strcmp(token, "RTE_BBDEV_TURBO_CRC_TYPE_24B"))
125                 *op_flag_value = RTE_BBDEV_TURBO_CRC_TYPE_24B;
126         else if (!strcmp(token, "RTE_BBDEV_TURBO_EQUALIZER"))
127                 *op_flag_value = RTE_BBDEV_TURBO_EQUALIZER;
128         else if (!strcmp(token, "RTE_BBDEV_TURBO_SOFT_OUT_SATURATE"))
129                 *op_flag_value = RTE_BBDEV_TURBO_SOFT_OUT_SATURATE;
130         else if (!strcmp(token, "RTE_BBDEV_TURBO_HALF_ITERATION_EVEN"))
131                 *op_flag_value = RTE_BBDEV_TURBO_HALF_ITERATION_EVEN;
132         else if (!strcmp(token, "RTE_BBDEV_TURBO_CONTINUE_CRC_MATCH"))
133                 *op_flag_value = RTE_BBDEV_TURBO_CONTINUE_CRC_MATCH;
134         else if (!strcmp(token, "RTE_BBDEV_TURBO_SOFT_OUTPUT"))
135                 *op_flag_value = RTE_BBDEV_TURBO_SOFT_OUTPUT;
136         else if (!strcmp(token, "RTE_BBDEV_TURBO_EARLY_TERMINATION"))
137                 *op_flag_value = RTE_BBDEV_TURBO_EARLY_TERMINATION;
138         else if (!strcmp(token, "RTE_BBDEV_TURBO_POS_LLR_1_BIT_IN"))
139                 *op_flag_value = RTE_BBDEV_TURBO_POS_LLR_1_BIT_IN;
140         else if (!strcmp(token, "RTE_BBDEV_TURBO_NEG_LLR_1_BIT_IN"))
141                 *op_flag_value = RTE_BBDEV_TURBO_NEG_LLR_1_BIT_IN;
142         else if (!strcmp(token, "RTE_BBDEV_TURBO_POS_LLR_1_BIT_SOFT_OUT"))
143                 *op_flag_value = RTE_BBDEV_TURBO_POS_LLR_1_BIT_SOFT_OUT;
144         else if (!strcmp(token, "RTE_BBDEV_TURBO_NEG_LLR_1_BIT_SOFT_OUT"))
145                 *op_flag_value = RTE_BBDEV_TURBO_NEG_LLR_1_BIT_SOFT_OUT;
146         else if (!strcmp(token, "RTE_BBDEV_TURBO_MAP_DEC"))
147                 *op_flag_value = RTE_BBDEV_TURBO_MAP_DEC;
148         else if (!strcmp(token, "RTE_BBDEV_TURBO_DEC_SCATTER_GATHER"))
149                 *op_flag_value = RTE_BBDEV_TURBO_DEC_SCATTER_GATHER;
150         else if (!strcmp(token, "RTE_BBDEV_TURBO_DEC_TB_CRC_24B_KEEP"))
151                 *op_flag_value = RTE_BBDEV_TURBO_DEC_TB_CRC_24B_KEEP;
152         else {
153                 printf("The given value is not a turbo decoder flag\n");
154                 return -1;
155         }
156
157         return 0;
158 }
159
160 /* convert LDPC flag from string to unsigned long int*/
161 static int
162 op_ldpc_decoder_flag_strtoul(char *token, uint32_t *op_flag_value)
163 {
164         if (!strcmp(token, "RTE_BBDEV_LDPC_CRC_TYPE_24A_CHECK"))
165                 *op_flag_value = RTE_BBDEV_LDPC_CRC_TYPE_24A_CHECK;
166         else if (!strcmp(token, "RTE_BBDEV_LDPC_CRC_TYPE_24B_CHECK"))
167                 *op_flag_value = RTE_BBDEV_LDPC_CRC_TYPE_24B_CHECK;
168         else if (!strcmp(token, "RTE_BBDEV_LDPC_CRC_TYPE_24B_DROP"))
169                 *op_flag_value = RTE_BBDEV_LDPC_CRC_TYPE_24B_DROP;
170         else if (!strcmp(token, "RTE_BBDEV_LDPC_DEINTERLEAVER_BYPASS"))
171                 *op_flag_value = RTE_BBDEV_LDPC_DEINTERLEAVER_BYPASS;
172         else if (!strcmp(token, "RTE_BBDEV_LDPC_HQ_COMBINE_IN_ENABLE"))
173                 *op_flag_value = RTE_BBDEV_LDPC_HQ_COMBINE_IN_ENABLE;
174         else if (!strcmp(token, "RTE_BBDEV_LDPC_HQ_COMBINE_OUT_ENABLE"))
175                 *op_flag_value = RTE_BBDEV_LDPC_HQ_COMBINE_OUT_ENABLE;
176         else if (!strcmp(token, "RTE_BBDEV_LDPC_DECODE_BYPASS"))
177                 *op_flag_value = RTE_BBDEV_LDPC_DECODE_BYPASS;
178         else if (!strcmp(token, "RTE_BBDEV_LDPC_SOFT_OUT_ENABLE"))
179                 *op_flag_value = RTE_BBDEV_LDPC_SOFT_OUT_ENABLE;
180         else if (!strcmp(token, "RTE_BBDEV_LDPC_SOFT_OUT_RM_BYPASS"))
181                 *op_flag_value = RTE_BBDEV_LDPC_SOFT_OUT_RM_BYPASS;
182         else if (!strcmp(token, "RTE_BBDEV_LDPC_SOFT_OUT_DEINTERLEAVER_BYPASS"))
183                 *op_flag_value = RTE_BBDEV_LDPC_SOFT_OUT_DEINTERLEAVER_BYPASS;
184         else if (!strcmp(token, "RTE_BBDEV_LDPC_ITERATION_STOP_ENABLE"))
185                 *op_flag_value = RTE_BBDEV_LDPC_ITERATION_STOP_ENABLE;
186         else if (!strcmp(token, "RTE_BBDEV_LDPC_DEC_INTERRUPTS"))
187                 *op_flag_value = RTE_BBDEV_LDPC_DEC_INTERRUPTS;
188         else if (!strcmp(token, "RTE_BBDEV_LDPC_DEC_SCATTER_GATHER"))
189                 *op_flag_value = RTE_BBDEV_LDPC_DEC_SCATTER_GATHER;
190         else if (!strcmp(token, "RTE_BBDEV_LDPC_HARQ_6BIT_COMPRESSION"))
191                 *op_flag_value = RTE_BBDEV_LDPC_HARQ_6BIT_COMPRESSION;
192         else if (!strcmp(token, "RTE_BBDEV_LDPC_LLR_COMPRESSION"))
193                 *op_flag_value = RTE_BBDEV_LDPC_LLR_COMPRESSION;
194         else if (!strcmp(token,
195                         "RTE_BBDEV_LDPC_INTERNAL_HARQ_MEMORY_IN_ENABLE"))
196                 *op_flag_value = RTE_BBDEV_LDPC_INTERNAL_HARQ_MEMORY_IN_ENABLE;
197         else if (!strcmp(token,
198                         "RTE_BBDEV_LDPC_INTERNAL_HARQ_MEMORY_OUT_ENABLE"))
199                 *op_flag_value = RTE_BBDEV_LDPC_INTERNAL_HARQ_MEMORY_OUT_ENABLE;
200         else {
201                 printf("The given value is not a LDPC decoder flag\n");
202                 return -1;
203         }
204
205         return 0;
206 }
207
208 /* convert turbo encoder flag from string to unsigned long int*/
209 static int
210 op_encoder_flag_strtoul(char *token, uint32_t *op_flag_value)
211 {
212         if (!strcmp(token, "RTE_BBDEV_TURBO_RV_INDEX_BYPASS"))
213                 *op_flag_value = RTE_BBDEV_TURBO_RV_INDEX_BYPASS;
214         else if (!strcmp(token, "RTE_BBDEV_TURBO_RATE_MATCH"))
215                 *op_flag_value = RTE_BBDEV_TURBO_RATE_MATCH;
216         else if (!strcmp(token, "RTE_BBDEV_TURBO_CRC_24B_ATTACH"))
217                 *op_flag_value = RTE_BBDEV_TURBO_CRC_24B_ATTACH;
218         else if (!strcmp(token, "RTE_BBDEV_TURBO_CRC_24A_ATTACH"))
219                 *op_flag_value = RTE_BBDEV_TURBO_CRC_24A_ATTACH;
220         else if (!strcmp(token, "RTE_BBDEV_TURBO_ENC_SCATTER_GATHER"))
221                 *op_flag_value = RTE_BBDEV_TURBO_ENC_SCATTER_GATHER;
222         else {
223                 printf("The given value is not a turbo encoder flag\n");
224                 return -1;
225         }
226
227         return 0;
228 }
229
230 /* convert LDPC encoder flag from string to unsigned long int*/
231 static int
232 op_ldpc_encoder_flag_strtoul(char *token, uint32_t *op_flag_value)
233 {
234         if (!strcmp(token, "RTE_BBDEV_LDPC_INTERLEAVER_BYPASS"))
235                 *op_flag_value = RTE_BBDEV_LDPC_INTERLEAVER_BYPASS;
236         else if (!strcmp(token, "RTE_BBDEV_LDPC_RATE_MATCH"))
237                 *op_flag_value = RTE_BBDEV_LDPC_RATE_MATCH;
238         else if (!strcmp(token, "RTE_BBDEV_LDPC_CRC_24A_ATTACH"))
239                 *op_flag_value = RTE_BBDEV_LDPC_CRC_24A_ATTACH;
240         else if (!strcmp(token, "RTE_BBDEV_LDPC_CRC_24B_ATTACH"))
241                 *op_flag_value = RTE_BBDEV_LDPC_CRC_24B_ATTACH;
242         else if (!strcmp(token, "RTE_BBDEV_LDPC_CRC_16_ATTACH"))
243                 *op_flag_value = RTE_BBDEV_LDPC_CRC_16_ATTACH;
244         else if (!strcmp(token, "RTE_BBDEV_LDPC_ENC_INTERRUPTS"))
245                 *op_flag_value = RTE_BBDEV_LDPC_ENC_INTERRUPTS;
246         else if (!strcmp(token, "RTE_BBDEV_LDPC_ENC_SCATTER_GATHER"))
247                 *op_flag_value = RTE_BBDEV_LDPC_ENC_SCATTER_GATHER;
248         else {
249                 printf("The given value is not a turbo encoder flag\n");
250                 return -1;
251         }
252
253         return 0;
254 }
255
256 /* tokenization turbo decoder/encoder flags values separated by a comma */
257 static int
258 parse_turbo_flags(char *tokens, uint32_t *op_flags,
259                 enum rte_bbdev_op_type op_type)
260 {
261         char *tok = NULL;
262         uint32_t op_flag_value = 0;
263
264         tok = strtok(tokens, VALUE_DELIMITER);
265         if (tok == NULL)
266                 return -1;
267
268         while (tok != NULL) {
269                 trim_space(tok);
270                 if (op_type == RTE_BBDEV_OP_TURBO_DEC) {
271                         if (op_decoder_flag_strtoul(tok, &op_flag_value) == -1)
272                                 return -1;
273                 } else if (op_type == RTE_BBDEV_OP_TURBO_ENC) {
274                         if (op_encoder_flag_strtoul(tok, &op_flag_value) == -1)
275                                 return -1;
276                 } else if (op_type == RTE_BBDEV_OP_LDPC_ENC) {
277                         if (op_ldpc_encoder_flag_strtoul(tok, &op_flag_value)
278                                         == -1)
279                                 return -1;
280                 } else if (op_type == RTE_BBDEV_OP_LDPC_DEC) {
281                         if (op_ldpc_decoder_flag_strtoul(tok, &op_flag_value)
282                                         == -1)
283                                 return -1;
284                 } else {
285                         return -1;
286                 }
287
288                 *op_flags = *op_flags | op_flag_value;
289
290                 tok = strtok(NULL, VALUE_DELIMITER);
291                 if (tok == NULL)
292                         break;
293         }
294
295         return 0;
296 }
297
298 /* convert turbo encoder/decoder op_type from string to enum*/
299 static int
300 op_turbo_type_strtol(char *token, enum rte_bbdev_op_type *op_type)
301 {
302         trim_space(token);
303         if (!strcmp(token, "RTE_BBDEV_OP_TURBO_DEC"))
304                 *op_type = RTE_BBDEV_OP_TURBO_DEC;
305         else if (!strcmp(token, "RTE_BBDEV_OP_TURBO_ENC"))
306                 *op_type = RTE_BBDEV_OP_TURBO_ENC;
307         else if (!strcmp(token, "RTE_BBDEV_OP_LDPC_ENC"))
308                 *op_type = RTE_BBDEV_OP_LDPC_ENC;
309         else if (!strcmp(token, "RTE_BBDEV_OP_LDPC_DEC"))
310                 *op_type = RTE_BBDEV_OP_LDPC_DEC;
311         else if (!strcmp(token, "RTE_BBDEV_OP_NONE"))
312                 *op_type = RTE_BBDEV_OP_NONE;
313         else {
314                 printf("Not valid turbo op_type: '%s'\n", token);
315                 return -1;
316         }
317
318         return 0;
319 }
320
321 /* tokenization expected status values separated by a comma */
322 static int
323 parse_expected_status(char *tokens, int *status, enum rte_bbdev_op_type op_type)
324 {
325         char *tok = NULL;
326         bool status_ok = false;
327
328         tok = strtok(tokens, VALUE_DELIMITER);
329         if (tok == NULL)
330                 return -1;
331
332         while (tok != NULL) {
333                 trim_space(tok);
334                 if (!strcmp(tok, "OK"))
335                         status_ok = true;
336                 else if (!strcmp(tok, "DMA"))
337                         *status = *status | (1 << RTE_BBDEV_DRV_ERROR);
338                 else if (!strcmp(tok, "FCW"))
339                         *status = *status | (1 << RTE_BBDEV_DATA_ERROR);
340                 else if (!strcmp(tok, "SYNCRC")) {
341                         *status = *status | (1 << RTE_BBDEV_SYNDROME_ERROR);
342                         *status = *status | (1 << RTE_BBDEV_CRC_ERROR);
343                 } else if (!strcmp(tok, "SYN"))
344                         *status = *status | (1 << RTE_BBDEV_SYNDROME_ERROR);
345                 else if (!strcmp(tok, "CRC")) {
346                         if ((op_type == RTE_BBDEV_OP_TURBO_DEC) ||
347                                         (op_type == RTE_BBDEV_OP_LDPC_DEC))
348                                 *status = *status | (1 << RTE_BBDEV_CRC_ERROR);
349                         else {
350                                 printf(
351                                                 "CRC is only a valid value for decoder\n");
352                                 return -1;
353                         }
354                 } else {
355                         printf("Not valid status: '%s'\n", tok);
356                         return -1;
357                 }
358
359                 tok = strtok(NULL, VALUE_DELIMITER);
360                 if (tok == NULL)
361                         break;
362         }
363
364         if (status_ok && *status != 0) {
365                 printf(
366                                 "Not valid status values. Cannot be OK and ERROR at the same time.\n");
367                 return -1;
368         }
369
370         return 0;
371 }
372
373 /* parse ops data entry (there can be more than 1 input entry, each will be
374  * contained in a separate op_data_buf struct)
375  */
376 static int
377 parse_data_entry(const char *key_token, char *token,
378                 struct test_bbdev_vector *vector, enum op_data_type type,
379                 const char *prefix)
380 {
381         int ret;
382         uint32_t data_length = 0;
383         uint32_t *data = NULL;
384         unsigned int id;
385         struct op_data_buf *op_data;
386         unsigned int *nb_ops;
387
388         if (type >= DATA_NUM_TYPES) {
389                 printf("Unknown op type: %d!\n", type);
390                 return -1;
391         }
392
393         op_data = vector->entries[type].segments;
394         nb_ops = &vector->entries[type].nb_segments;
395
396         if (*nb_ops >= RTE_BBDEV_TURBO_MAX_CODE_BLOCKS) {
397                 printf("Too many segments (code blocks defined): %u, max %d!\n",
398                                 *nb_ops, RTE_BBDEV_TURBO_MAX_CODE_BLOCKS);
399                 return -1;
400         }
401
402         if (sscanf(key_token + strlen(prefix), "%u", &id) != 1) {
403                 printf("Missing ID of %s\n", prefix);
404                 return -1;
405         }
406         if (id != *nb_ops) {
407                 printf(
408                         "Please order data entries sequentially, i.e. %s0, %s1, ...\n",
409                                 prefix, prefix);
410                 return -1;
411         }
412
413         /* Clear new op data struct */
414         memset(op_data + *nb_ops, 0, sizeof(struct op_data_buf));
415
416         ret = parse_values(token, &data, &data_length);
417         if (!ret) {
418                 op_data[*nb_ops].addr = data;
419                 op_data[*nb_ops].length = data_length;
420                 ++(*nb_ops);
421         }
422
423         return ret;
424 }
425
426 /* parses turbo decoder parameters and assigns to global variable */
427 static int
428 parse_decoder_params(const char *key_token, char *token,
429                 struct test_bbdev_vector *vector)
430 {
431         int ret = 0, status = 0;
432         uint32_t op_flags = 0;
433         char *err = NULL;
434
435         struct rte_bbdev_op_turbo_dec *turbo_dec = &vector->turbo_dec;
436
437         /* compare keys */
438         if (starts_with(key_token, op_data_prefixes[DATA_INPUT]))
439                 ret = parse_data_entry(key_token, token, vector,
440                                 DATA_INPUT, op_data_prefixes[DATA_INPUT]);
441
442         else if (starts_with(key_token, op_data_prefixes[DATA_SOFT_OUTPUT]))
443                 ret = parse_data_entry(key_token, token, vector,
444                                 DATA_SOFT_OUTPUT,
445                                 op_data_prefixes[DATA_SOFT_OUTPUT]);
446
447         else if (starts_with(key_token, op_data_prefixes[DATA_HARD_OUTPUT]))
448                 ret = parse_data_entry(key_token, token, vector,
449                                 DATA_HARD_OUTPUT,
450                                 op_data_prefixes[DATA_HARD_OUTPUT]);
451         else if (!strcmp(key_token, "e")) {
452                 vector->mask |= TEST_BBDEV_VF_E;
453                 turbo_dec->cb_params.e = (uint32_t) strtoul(token, &err, 0);
454         } else if (!strcmp(key_token, "ea")) {
455                 vector->mask |= TEST_BBDEV_VF_EA;
456                 turbo_dec->tb_params.ea = (uint32_t) strtoul(token, &err, 0);
457                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
458         } else if (!strcmp(key_token, "eb")) {
459                 vector->mask |= TEST_BBDEV_VF_EB;
460                 turbo_dec->tb_params.eb = (uint32_t) strtoul(token, &err, 0);
461                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
462         } else if (!strcmp(key_token, "k")) {
463                 vector->mask |= TEST_BBDEV_VF_K;
464                 turbo_dec->cb_params.k = (uint16_t) strtoul(token, &err, 0);
465                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
466         } else if (!strcmp(key_token, "k_pos")) {
467                 vector->mask |= TEST_BBDEV_VF_K_POS;
468                 turbo_dec->tb_params.k_pos = (uint16_t) strtoul(token, &err, 0);
469                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
470         } else if (!strcmp(key_token, "k_neg")) {
471                 vector->mask |= TEST_BBDEV_VF_K_NEG;
472                 turbo_dec->tb_params.k_neg = (uint16_t) strtoul(token, &err, 0);
473                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
474         } else if (!strcmp(key_token, "c")) {
475                 vector->mask |= TEST_BBDEV_VF_C;
476                 turbo_dec->tb_params.c = (uint16_t) strtoul(token, &err, 0);
477                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
478         } else if (!strcmp(key_token, "c_neg")) {
479                 vector->mask |= TEST_BBDEV_VF_C_NEG;
480                 turbo_dec->tb_params.c_neg = (uint16_t) strtoul(token, &err, 0);
481                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
482         } else if (!strcmp(key_token, "cab")) {
483                 vector->mask |= TEST_BBDEV_VF_CAB;
484                 turbo_dec->tb_params.cab = (uint8_t) strtoul(token, &err, 0);
485                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
486         } else if (!strcmp(key_token, "rv_index")) {
487                 vector->mask |= TEST_BBDEV_VF_RV_INDEX;
488                 turbo_dec->rv_index = (uint8_t) strtoul(token, &err, 0);
489                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
490         } else if (!strcmp(key_token, "iter_max")) {
491                 vector->mask |= TEST_BBDEV_VF_ITER_MAX;
492                 turbo_dec->iter_max = (uint8_t) strtoul(token, &err, 0);
493                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
494         } else if (!strcmp(key_token, "iter_min")) {
495                 vector->mask |= TEST_BBDEV_VF_ITER_MIN;
496                 turbo_dec->iter_min = (uint8_t) strtoul(token, &err, 0);
497                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
498         } else if (!strcmp(key_token, "expected_iter_count")) {
499                 vector->mask |= TEST_BBDEV_VF_EXPECTED_ITER_COUNT;
500                 turbo_dec->iter_count = (uint8_t) strtoul(token, &err, 0);
501                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
502         } else if (!strcmp(key_token, "ext_scale")) {
503                 vector->mask |= TEST_BBDEV_VF_EXT_SCALE;
504                 turbo_dec->ext_scale = (uint8_t) strtoul(token, &err, 0);
505                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
506         } else if (!strcmp(key_token, "num_maps")) {
507                 vector->mask |= TEST_BBDEV_VF_NUM_MAPS;
508                 turbo_dec->num_maps = (uint8_t) strtoul(token, &err, 0);
509                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
510         } else if (!strcmp(key_token, "r")) {
511                 vector->mask |= TEST_BBDEV_VF_R;
512                 turbo_dec->tb_params.r = (uint8_t)strtoul(token, &err, 0);
513                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
514         } else if (!strcmp(key_token, "code_block_mode")) {
515                 vector->mask |= TEST_BBDEV_VF_CODE_BLOCK_MODE;
516                 turbo_dec->code_block_mode = (uint8_t) strtoul(token, &err, 0);
517                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
518         } else if (!strcmp(key_token, "op_flags")) {
519                 vector->mask |= TEST_BBDEV_VF_OP_FLAGS;
520                 ret = parse_turbo_flags(token, &op_flags,
521                         vector->op_type);
522                 if (!ret)
523                         turbo_dec->op_flags = op_flags;
524         } else if (!strcmp(key_token, "expected_status")) {
525                 vector->mask |= TEST_BBDEV_VF_EXPECTED_STATUS;
526                 ret = parse_expected_status(token, &status, vector->op_type);
527                 if (!ret)
528                         vector->expected_status = status;
529         } else {
530                 printf("Not valid dec key: '%s'\n", key_token);
531                 return -1;
532         }
533
534         if (ret != 0) {
535                 printf("Failed with convert '%s\t%s'\n", key_token, token);
536                 return -1;
537         }
538
539         return 0;
540 }
541
542 /* parses turbo encoder parameters and assigns to global variable */
543 static int
544 parse_encoder_params(const char *key_token, char *token,
545                 struct test_bbdev_vector *vector)
546 {
547         int ret = 0, status = 0;
548         uint32_t op_flags = 0;
549         char *err = NULL;
550
551
552         struct rte_bbdev_op_turbo_enc *turbo_enc = &vector->turbo_enc;
553
554         if (starts_with(key_token, op_data_prefixes[DATA_INPUT]))
555                 ret = parse_data_entry(key_token, token, vector,
556                                 DATA_INPUT, op_data_prefixes[DATA_INPUT]);
557         else if (starts_with(key_token, "output"))
558                 ret = parse_data_entry(key_token, token, vector,
559                                 DATA_HARD_OUTPUT, "output");
560         else if (!strcmp(key_token, "e")) {
561                 vector->mask |= TEST_BBDEV_VF_E;
562                 turbo_enc->cb_params.e = (uint32_t) strtoul(token, &err, 0);
563                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
564         } else if (!strcmp(key_token, "ea")) {
565                 vector->mask |= TEST_BBDEV_VF_EA;
566                 turbo_enc->tb_params.ea = (uint32_t) strtoul(token, &err, 0);
567                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
568         } else if (!strcmp(key_token, "eb")) {
569                 vector->mask |= TEST_BBDEV_VF_EB;
570                 turbo_enc->tb_params.eb = (uint32_t) strtoul(token, &err, 0);
571                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
572         } else if (!strcmp(key_token, "k")) {
573                 vector->mask |= TEST_BBDEV_VF_K;
574                 turbo_enc->cb_params.k = (uint16_t) strtoul(token, &err, 0);
575                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
576         } else if (!strcmp(key_token, "k_neg")) {
577                 vector->mask |= TEST_BBDEV_VF_K_NEG;
578                 turbo_enc->tb_params.k_neg = (uint16_t) strtoul(token, &err, 0);
579                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
580         } else if (!strcmp(key_token, "k_pos")) {
581                 vector->mask |= TEST_BBDEV_VF_K_POS;
582                 turbo_enc->tb_params.k_pos = (uint16_t) strtoul(token, &err, 0);
583                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
584         } else if (!strcmp(key_token, "c_neg")) {
585                 vector->mask |= TEST_BBDEV_VF_C_NEG;
586                 turbo_enc->tb_params.c_neg = (uint8_t) strtoul(token, &err, 0);
587                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
588         } else if (!strcmp(key_token, "c")) {
589                 vector->mask |= TEST_BBDEV_VF_C;
590                 turbo_enc->tb_params.c = (uint8_t) strtoul(token, &err, 0);
591                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
592         } else if (!strcmp(key_token, "cab")) {
593                 vector->mask |= TEST_BBDEV_VF_CAB;
594                 turbo_enc->tb_params.cab = (uint8_t) strtoul(token, &err, 0);
595                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
596         } else if (!strcmp(key_token, "rv_index")) {
597                 vector->mask |= TEST_BBDEV_VF_RV_INDEX;
598                 turbo_enc->rv_index = (uint8_t) strtoul(token, &err, 0);
599                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
600         } else if (!strcmp(key_token, "ncb")) {
601                 vector->mask |= TEST_BBDEV_VF_NCB;
602                 turbo_enc->cb_params.ncb = (uint16_t) strtoul(token, &err, 0);
603                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
604         } else if (!strcmp(key_token, "ncb_neg")) {
605                 vector->mask |= TEST_BBDEV_VF_NCB_NEG;
606                 turbo_enc->tb_params.ncb_neg =
607                                 (uint16_t) strtoul(token, &err, 0);
608                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
609         } else if (!strcmp(key_token, "ncb_pos")) {
610                 vector->mask |= TEST_BBDEV_VF_NCB_POS;
611                 turbo_enc->tb_params.ncb_pos =
612                                 (uint16_t) strtoul(token, &err, 0);
613                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
614         } else if (!strcmp(key_token, "r")) {
615                 vector->mask |= TEST_BBDEV_VF_R;
616                 turbo_enc->tb_params.r = (uint8_t) strtoul(token, &err, 0);
617                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
618         } else if (!strcmp(key_token, "code_block_mode")) {
619                 vector->mask |= TEST_BBDEV_VF_CODE_BLOCK_MODE;
620                 turbo_enc->code_block_mode = (uint8_t) strtoul(token, &err, 0);
621                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
622         } else if (!strcmp(key_token, "op_flags")) {
623                 vector->mask |= TEST_BBDEV_VF_OP_FLAGS;
624                 ret = parse_turbo_flags(token, &op_flags,
625                                 vector->op_type);
626                 if (!ret)
627                         turbo_enc->op_flags = op_flags;
628         } else if (!strcmp(key_token, "expected_status")) {
629                 vector->mask |= TEST_BBDEV_VF_EXPECTED_STATUS;
630                 ret = parse_expected_status(token, &status, vector->op_type);
631                 if (!ret)
632                         vector->expected_status = status;
633         } else {
634                 printf("Not valid enc key: '%s'\n", key_token);
635                 return -1;
636         }
637
638         if (ret != 0) {
639                 printf("Failed with convert '%s\t%s'\n", key_token, token);
640                 return -1;
641         }
642
643         return 0;
644 }
645
646
647 /* parses LDPC encoder parameters and assigns to global variable */
648 static int
649 parse_ldpc_encoder_params(const char *key_token, char *token,
650                 struct test_bbdev_vector *vector)
651 {
652         int ret = 0, status = 0;
653         uint32_t op_flags = 0;
654         char *err = NULL;
655
656         struct rte_bbdev_op_ldpc_enc *ldpc_enc = &vector->ldpc_enc;
657
658         if (starts_with(key_token, op_data_prefixes[DATA_INPUT]))
659                 ret = parse_data_entry(key_token, token, vector,
660                                 DATA_INPUT,
661                                 op_data_prefixes[DATA_INPUT]);
662         else if (starts_with(key_token, "output"))
663                 ret = parse_data_entry(key_token, token, vector,
664                                 DATA_HARD_OUTPUT,
665                                 "output");
666         else if (!strcmp(key_token, "e")) {
667                 vector->mask |= TEST_BBDEV_VF_E;
668                 ldpc_enc->cb_params.e = (uint32_t) strtoul(token, &err, 0);
669                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
670         } else if (!strcmp(key_token, "ea")) {
671                 vector->mask |= TEST_BBDEV_VF_EA;
672                 ldpc_enc->tb_params.ea = (uint32_t) strtoul(token, &err, 0);
673                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
674         } else if (!strcmp(key_token, "eb")) {
675                 vector->mask |= TEST_BBDEV_VF_EB;
676                 ldpc_enc->tb_params.eb = (uint32_t) strtoul(token, &err, 0);
677                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
678         } else if (!strcmp(key_token, "c")) {
679                 vector->mask |= TEST_BBDEV_VF_C;
680                 ldpc_enc->tb_params.c = (uint8_t) strtoul(token, &err, 0);
681                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
682         } else if (!strcmp(key_token, "cab")) {
683                 vector->mask |= TEST_BBDEV_VF_CAB;
684                 ldpc_enc->tb_params.cab = (uint8_t) strtoul(token, &err, 0);
685                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
686         } else if (!strcmp(key_token, "rv_index")) {
687                 vector->mask |= TEST_BBDEV_VF_RV_INDEX;
688                 ldpc_enc->rv_index = (uint8_t) strtoul(token, &err, 0);
689                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
690         } else if (!strcmp(key_token, "n_cb")) {
691                 vector->mask |= TEST_BBDEV_VF_NCB;
692                 ldpc_enc->n_cb = (uint16_t) strtoul(token, &err, 0);
693                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
694         } else if (!strcmp(key_token, "r")) {
695                 vector->mask |= TEST_BBDEV_VF_R;
696                 ldpc_enc->tb_params.r = (uint8_t) strtoul(token, &err, 0);
697                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
698         } else if (!strcmp(key_token, "q_m")) {
699                 vector->mask |= TEST_BBDEV_VF_QM;
700                 ldpc_enc->q_m = (uint8_t) strtoul(token, &err, 0);
701                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
702         } else if (!strcmp(key_token, "basegraph")) {
703                 vector->mask |= TEST_BBDEV_VF_BG;
704                 ldpc_enc->basegraph = (uint8_t) strtoul(token, &err, 0);
705                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
706         } else if (!strcmp(key_token, "z_c")) {
707                 vector->mask |= TEST_BBDEV_VF_ZC;
708                 ldpc_enc->z_c = (uint16_t) strtoul(token, &err, 0);
709                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
710         } else if (!strcmp(key_token, "n_filler")) {
711                 vector->mask |= TEST_BBDEV_VF_F;
712                 ldpc_enc->n_filler = (uint16_t) strtoul(token, &err, 0);
713                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
714         } else if (!strcmp(key_token, "code_block_mode")) {
715                 vector->mask |= TEST_BBDEV_VF_CODE_BLOCK_MODE;
716                 ldpc_enc->code_block_mode = (uint8_t) strtoul(token, &err, 0);
717                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
718         } else if (!strcmp(key_token, "op_flags")) {
719                 vector->mask |= TEST_BBDEV_VF_OP_FLAGS;
720                 ret = parse_turbo_flags(token, &op_flags, vector->op_type);
721                 if (!ret)
722                         ldpc_enc->op_flags = op_flags;
723         } else if (!strcmp(key_token, "expected_status")) {
724                 vector->mask |= TEST_BBDEV_VF_EXPECTED_STATUS;
725                 ret = parse_expected_status(token, &status, vector->op_type);
726                 if (!ret)
727                         vector->expected_status = status;
728         } else {
729                 printf("Not valid ldpc enc key: '%s'\n", key_token);
730                 return -1;
731         }
732
733         if (ret != 0) {
734                 printf("Failed with convert '%s\t%s'\n", key_token, token);
735                 return -1;
736         }
737
738         return 0;
739 }
740
741 /* parses LDPC decoder parameters and assigns to global variable */
742 static int
743 parse_ldpc_decoder_params(const char *key_token, char *token,
744                 struct test_bbdev_vector *vector)
745 {
746         int ret = 0, status = 0;
747         uint32_t op_flags = 0;
748         char *err = NULL;
749
750         struct rte_bbdev_op_ldpc_dec *ldpc_dec = &vector->ldpc_dec;
751
752         if (starts_with(key_token, op_data_prefixes[DATA_INPUT]))
753                 ret = parse_data_entry(key_token, token, vector,
754                                 DATA_INPUT,
755                                 op_data_prefixes[DATA_INPUT]);
756         else if (starts_with(key_token, "output"))
757                 ret = parse_data_entry(key_token, token, vector,
758                                 DATA_HARD_OUTPUT,
759                                 "output");
760         else if (starts_with(key_token, op_data_prefixes[DATA_HARQ_INPUT]))
761                 ret = parse_data_entry(key_token, token, vector,
762                                 DATA_HARQ_INPUT,
763                                 op_data_prefixes[DATA_HARQ_INPUT]);
764         else if (starts_with(key_token, op_data_prefixes[DATA_HARQ_OUTPUT]))
765                 ret = parse_data_entry(key_token, token, vector,
766                                 DATA_HARQ_OUTPUT,
767                                 op_data_prefixes[DATA_HARQ_OUTPUT]);
768         else if (!strcmp(key_token, "e")) {
769                 vector->mask |= TEST_BBDEV_VF_E;
770                 ldpc_dec->cb_params.e = (uint32_t) strtoul(token, &err, 0);
771                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
772         } else if (!strcmp(key_token, "ea")) {
773                 vector->mask |= TEST_BBDEV_VF_EA;
774                 ldpc_dec->tb_params.ea = (uint32_t) strtoul(token, &err, 0);
775                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
776         } else if (!strcmp(key_token, "eb")) {
777                 vector->mask |= TEST_BBDEV_VF_EB;
778                 ldpc_dec->tb_params.eb = (uint32_t) strtoul(token, &err, 0);
779                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
780         } else if (!strcmp(key_token, "c")) {
781                 vector->mask |= TEST_BBDEV_VF_C;
782                 ldpc_dec->tb_params.c = (uint8_t) strtoul(token, &err, 0);
783                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
784         } else if (!strcmp(key_token, "cab")) {
785                 vector->mask |= TEST_BBDEV_VF_CAB;
786                 ldpc_dec->tb_params.cab = (uint8_t) strtoul(token, &err, 0);
787                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
788         } else if (!strcmp(key_token, "rv_index")) {
789                 vector->mask |= TEST_BBDEV_VF_RV_INDEX;
790                 ldpc_dec->rv_index = (uint8_t) strtoul(token, &err, 0);
791                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
792         } else if (!strcmp(key_token, "n_cb")) {
793                 vector->mask |= TEST_BBDEV_VF_NCB;
794                 ldpc_dec->n_cb = (uint16_t) strtoul(token, &err, 0);
795                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
796         } else if (!strcmp(key_token, "r")) {
797                 vector->mask |= TEST_BBDEV_VF_R;
798                 ldpc_dec->tb_params.r = (uint8_t) strtoul(token, &err, 0);
799                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
800         } else if (!strcmp(key_token, "q_m")) {
801                 vector->mask |= TEST_BBDEV_VF_QM;
802                 ldpc_dec->q_m = (uint8_t) strtoul(token, &err, 0);
803                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
804         } else if (!strcmp(key_token, "basegraph")) {
805                 vector->mask |= TEST_BBDEV_VF_BG;
806                 ldpc_dec->basegraph = (uint8_t) strtoul(token, &err, 0);
807                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
808         } else if (!strcmp(key_token, "z_c")) {
809                 vector->mask |= TEST_BBDEV_VF_ZC;
810                 ldpc_dec->z_c = (uint16_t) strtoul(token, &err, 0);
811                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
812         } else if (!strcmp(key_token, "n_filler")) {
813                 vector->mask |= TEST_BBDEV_VF_F;
814                 ldpc_dec->n_filler = (uint16_t) strtoul(token, &err, 0);
815                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
816         } else if (!strcmp(key_token, "expected_iter_count")) {
817                 vector->mask |= TEST_BBDEV_VF_EXPECTED_ITER_COUNT;
818                 ldpc_dec->iter_count = (uint8_t) strtoul(token, &err, 0);
819                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
820         } else if (!strcmp(key_token, "iter_max")) {
821                 vector->mask |= TEST_BBDEV_VF_ITER_MAX;
822                 ldpc_dec->iter_max = (uint8_t) strtoul(token, &err, 0);
823                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
824         } else if (!strcmp(key_token, "code_block_mode")) {
825                 vector->mask |= TEST_BBDEV_VF_CODE_BLOCK_MODE;
826                 ldpc_dec->code_block_mode = (uint8_t) strtoul(token, &err, 0);
827                 ret = ((err == NULL) || (*err != '\0')) ? -1 : 0;
828         } else if (!strcmp(key_token, "op_flags")) {
829                 vector->mask |= TEST_BBDEV_VF_OP_FLAGS;
830                 ret = parse_turbo_flags(token, &op_flags, vector->op_type);
831                 if (!ret)
832                         ldpc_dec->op_flags = op_flags;
833         } else if (!strcmp(key_token, "expected_status")) {
834                 vector->mask |= TEST_BBDEV_VF_EXPECTED_STATUS;
835                 ret = parse_expected_status(token, &status, vector->op_type);
836                 if (!ret)
837                         vector->expected_status = status;
838         } else {
839                 printf("Not valid ldpc dec key: '%s'\n", key_token);
840                 return -1;
841         }
842
843         if (ret != 0) {
844                 printf("Failed with convert '%s\t%s'\n", key_token, token);
845                 return -1;
846         }
847
848         return 0;
849 }
850
851 /* checks the type of key and assigns data */
852 static int
853 parse_entry(char *entry, struct test_bbdev_vector *vector)
854 {
855         int ret = 0;
856         char *token, *key_token;
857         enum rte_bbdev_op_type op_type = RTE_BBDEV_OP_NONE;
858
859         if (entry == NULL) {
860                 printf("Expected entry value\n");
861                 return -1;
862         }
863
864         /* get key */
865         token = strtok(entry, ENTRY_DELIMITER);
866         key_token = token;
867         /* get values for key */
868         token = strtok(NULL, ENTRY_DELIMITER);
869
870         if (key_token == NULL || token == NULL) {
871                 printf("Expected 'key = values' but was '%.40s'..\n", entry);
872                 return -1;
873         }
874         trim_space(key_token);
875
876         /* first key_token has to specify type of operation */
877         if (vector->op_type == RTE_BBDEV_OP_NONE) {
878                 if (!strcmp(key_token, "op_type")) {
879                         ret = op_turbo_type_strtol(token, &op_type);
880                         if (!ret)
881                                 vector->op_type = op_type;
882                         return (!ret) ? 0 : -1;
883                 }
884                 printf("First key_token (%s) does not specify op_type\n",
885                                 key_token);
886                 return -1;
887         }
888
889         /* compare keys */
890         if (vector->op_type == RTE_BBDEV_OP_TURBO_DEC) {
891                 if (parse_decoder_params(key_token, token, vector) == -1)
892                         return -1;
893         } else if (vector->op_type == RTE_BBDEV_OP_TURBO_ENC) {
894                 if (parse_encoder_params(key_token, token, vector) == -1)
895                         return -1;
896         } else if (vector->op_type == RTE_BBDEV_OP_LDPC_ENC) {
897                 if (parse_ldpc_encoder_params(key_token, token, vector) == -1)
898                         return -1;
899         } else if (vector->op_type == RTE_BBDEV_OP_LDPC_DEC) {
900                 if (parse_ldpc_decoder_params(key_token, token, vector) == -1)
901                         return -1;
902         }
903
904         return 0;
905 }
906
907 static int
908 check_decoder_segments(struct test_bbdev_vector *vector)
909 {
910         unsigned char i;
911         struct rte_bbdev_op_turbo_dec *turbo_dec = &vector->turbo_dec;
912
913         if (vector->entries[DATA_INPUT].nb_segments == 0)
914                 return -1;
915
916         for (i = 0; i < vector->entries[DATA_INPUT].nb_segments; i++)
917                 if (vector->entries[DATA_INPUT].segments[i].addr == NULL)
918                         return -1;
919
920         if (vector->entries[DATA_HARD_OUTPUT].nb_segments == 0)
921                 return -1;
922
923         for (i = 0; i < vector->entries[DATA_HARD_OUTPUT].nb_segments;
924                         i++)
925                 if (vector->entries[DATA_HARD_OUTPUT].segments[i].addr == NULL)
926                         return -1;
927
928         if ((turbo_dec->op_flags & RTE_BBDEV_TURBO_SOFT_OUTPUT) &&
929                         (vector->entries[DATA_SOFT_OUTPUT].nb_segments == 0))
930                 return -1;
931
932         for (i = 0; i < vector->entries[DATA_SOFT_OUTPUT].nb_segments;
933                         i++)
934                 if (vector->entries[DATA_SOFT_OUTPUT].segments[i].addr == NULL)
935                         return -1;
936
937         return 0;
938 }
939
940 static int
941 check_ldpc_decoder_segments(struct test_bbdev_vector *vector)
942 {
943         unsigned char i;
944         struct rte_bbdev_op_ldpc_dec *ldpc_dec = &vector->ldpc_dec;
945
946         if (vector->entries[DATA_INPUT].nb_segments == 0)
947                 return -1;
948
949         for (i = 0; i < vector->entries[DATA_INPUT].nb_segments; i++)
950                 if (vector->entries[DATA_INPUT].segments[i].addr == NULL)
951                         return -1;
952
953         if (vector->entries[DATA_HARD_OUTPUT].nb_segments == 0)
954                 return -1;
955
956         for (i = 0; i < vector->entries[DATA_HARD_OUTPUT].nb_segments; i++)
957                 if (vector->entries[DATA_HARD_OUTPUT].segments[i].addr == NULL)
958                         return -1;
959
960         if ((ldpc_dec->op_flags & RTE_BBDEV_LDPC_SOFT_OUT_ENABLE) &&
961                         (vector->entries[DATA_SOFT_OUTPUT].nb_segments == 0))
962                 return -1;
963
964         for (i = 0; i < vector->entries[DATA_SOFT_OUTPUT].nb_segments; i++)
965                 if (vector->entries[DATA_SOFT_OUTPUT].segments[i].addr == NULL)
966                         return -1;
967
968         if ((ldpc_dec->op_flags & RTE_BBDEV_LDPC_HQ_COMBINE_OUT_ENABLE) &&
969                         (vector->entries[DATA_HARQ_OUTPUT].nb_segments == 0))
970                 return -1;
971
972         for (i = 0; i < vector->entries[DATA_HARQ_OUTPUT].nb_segments; i++)
973                 if (vector->entries[DATA_HARQ_OUTPUT].segments[i].addr == NULL)
974                         return -1;
975
976         return 0;
977 }
978
979 static int
980 check_decoder_llr_spec(struct test_bbdev_vector *vector)
981 {
982         struct rte_bbdev_op_turbo_dec *turbo_dec = &vector->turbo_dec;
983
984         /* Check input LLR sign formalism specification */
985         if ((turbo_dec->op_flags & RTE_BBDEV_TURBO_POS_LLR_1_BIT_IN) &&
986                         (turbo_dec->op_flags &
987                         RTE_BBDEV_TURBO_NEG_LLR_1_BIT_IN)) {
988                 printf(
989                         "Both positive and negative LLR input flags were set!\n");
990                 return -1;
991         }
992         if (!(turbo_dec->op_flags & RTE_BBDEV_TURBO_POS_LLR_1_BIT_IN) &&
993                         !(turbo_dec->op_flags &
994                         RTE_BBDEV_TURBO_NEG_LLR_1_BIT_IN)) {
995                 printf(
996                         "INFO: input LLR sign formalism was not specified and will be set to negative LLR for '1' bit\n");
997                 turbo_dec->op_flags |= RTE_BBDEV_TURBO_NEG_LLR_1_BIT_IN;
998         }
999
1000         if (!(turbo_dec->op_flags & RTE_BBDEV_TURBO_SOFT_OUTPUT))
1001                 return 0;
1002
1003         /* Check output LLR sign formalism specification */
1004         if ((turbo_dec->op_flags & RTE_BBDEV_TURBO_POS_LLR_1_BIT_SOFT_OUT) &&
1005                         (turbo_dec->op_flags &
1006                         RTE_BBDEV_TURBO_NEG_LLR_1_BIT_SOFT_OUT)) {
1007                 printf(
1008                         "Both positive and negative LLR output flags were set!\n");
1009                 return -1;
1010         }
1011         if (!(turbo_dec->op_flags & RTE_BBDEV_TURBO_POS_LLR_1_BIT_SOFT_OUT) &&
1012                         !(turbo_dec->op_flags &
1013                         RTE_BBDEV_TURBO_NEG_LLR_1_BIT_SOFT_OUT)) {
1014                 printf(
1015                         "INFO: soft output LLR sign formalism was not specified and will be set to negative LLR for '1' bit\n");
1016                 turbo_dec->op_flags |=
1017                                 RTE_BBDEV_TURBO_NEG_LLR_1_BIT_SOFT_OUT;
1018         }
1019
1020         return 0;
1021 }
1022
1023 static int
1024 check_decoder_op_flags(struct test_bbdev_vector *vector)
1025 {
1026         struct rte_bbdev_op_turbo_dec *turbo_dec = &vector->turbo_dec;
1027
1028         if ((turbo_dec->op_flags & RTE_BBDEV_TURBO_DEC_TB_CRC_24B_KEEP) &&
1029                 !(turbo_dec->op_flags & RTE_BBDEV_TURBO_CRC_TYPE_24B)) {
1030                 printf(
1031                         "WARNING: RTE_BBDEV_TURBO_DEC_TB_CRC_24B_KEEP flag is missing RTE_BBDEV_TURBO_CRC_TYPE_24B\n");
1032                 return -1;
1033         }
1034
1035         return 0;
1036 }
1037
1038 /* checks decoder parameters */
1039 static int
1040 check_decoder(struct test_bbdev_vector *vector)
1041 {
1042         struct rte_bbdev_op_turbo_dec *turbo_dec = &vector->turbo_dec;
1043         const int mask = vector->mask;
1044
1045         if (check_decoder_segments(vector) < 0)
1046                 return -1;
1047
1048         if (check_decoder_llr_spec(vector) < 0)
1049                 return -1;
1050
1051         if (check_decoder_op_flags(vector) < 0)
1052                 return -1;
1053
1054         /* Check which params were set */
1055         if (!(mask & TEST_BBDEV_VF_CODE_BLOCK_MODE)) {
1056                 printf(
1057                         "WARNING: code_block_mode was not specified in vector file and will be set to 1 (0 - TB Mode, 1 - CB mode)\n");
1058                 turbo_dec->code_block_mode = 1;
1059         }
1060         if (turbo_dec->code_block_mode == 0) {
1061                 if (!(mask & TEST_BBDEV_VF_EA))
1062                         printf(
1063                                 "WARNING: ea was not specified in vector file and will be set to 0\n");
1064                 if (!(mask & TEST_BBDEV_VF_EB))
1065                         printf(
1066                                 "WARNING: eb was not specified in vector file and will be set to 0\n");
1067                 if (!(mask & TEST_BBDEV_VF_K_NEG))
1068                         printf(
1069                                 "WARNING: k_neg was not specified in vector file and will be set to 0\n");
1070                 if (!(mask & TEST_BBDEV_VF_K_POS))
1071                         printf(
1072                                 "WARNING: k_pos was not specified in vector file and will be set to 0\n");
1073                 if (!(mask & TEST_BBDEV_VF_C_NEG))
1074                         printf(
1075                                 "WARNING: c_neg was not specified in vector file and will be set to 0\n");
1076                 if (!(mask & TEST_BBDEV_VF_C)) {
1077                         printf(
1078                                 "WARNING: c was not specified in vector file and will be set to 1\n");
1079                         turbo_dec->tb_params.c = 1;
1080                 }
1081                 if (!(mask & TEST_BBDEV_VF_CAB))
1082                         printf(
1083                                 "WARNING: cab was not specified in vector file and will be set to 0\n");
1084                 if (!(mask & TEST_BBDEV_VF_R))
1085                         printf(
1086                                 "WARNING: r was not specified in vector file and will be set to 0\n");
1087         } else {
1088                 if (!(mask & TEST_BBDEV_VF_E))
1089                         printf(
1090                                 "WARNING: e was not specified in vector file and will be set to 0\n");
1091                 if (!(mask & TEST_BBDEV_VF_K))
1092                         printf(
1093                                 "WARNING: k was not specified in vector file and will be set to 0\n");
1094         }
1095         if (!(mask & TEST_BBDEV_VF_RV_INDEX))
1096                 printf(
1097                         "INFO: rv_index was not specified in vector file and will be set to 0\n");
1098         if (!(mask & TEST_BBDEV_VF_ITER_MIN))
1099                 printf(
1100                         "WARNING: iter_min was not specified in vector file and will be set to 0\n");
1101         if (!(mask & TEST_BBDEV_VF_ITER_MAX))
1102                 printf(
1103                         "WARNING: iter_max was not specified in vector file and will be set to 0\n");
1104         if (!(mask & TEST_BBDEV_VF_EXPECTED_ITER_COUNT))
1105                 printf(
1106                         "WARNING: expected_iter_count was not specified in vector file and iter_count will not be validated\n");
1107         if (!(mask & TEST_BBDEV_VF_EXT_SCALE))
1108                 printf(
1109                         "WARNING: ext_scale was not specified in vector file and will be set to 0\n");
1110         if (!(mask & TEST_BBDEV_VF_OP_FLAGS)) {
1111                 printf(
1112                         "WARNING: op_flags was not specified in vector file and capabilities will not be validated\n");
1113                 turbo_dec->num_maps = 0;
1114         } else if (!(turbo_dec->op_flags & RTE_BBDEV_TURBO_MAP_DEC) &&
1115                         mask & TEST_BBDEV_VF_NUM_MAPS) {
1116                 printf(
1117                         "INFO: RTE_BBDEV_TURBO_MAP_DEC was not set in vector file and num_maps will be set to 0\n");
1118                 turbo_dec->num_maps = 0;
1119         }
1120         if (!(mask & TEST_BBDEV_VF_EXPECTED_STATUS))
1121                 printf(
1122                         "WARNING: expected_status was not specified in vector file and will be set to 0\n");
1123         return 0;
1124 }
1125
1126 /* checks LDPC decoder parameters */
1127 static int
1128 check_ldpc_decoder(struct test_bbdev_vector *vector)
1129 {
1130         struct rte_bbdev_op_ldpc_dec *ldpc_dec = &vector->ldpc_dec;
1131         const int mask = vector->mask;
1132
1133         if (check_ldpc_decoder_segments(vector) < 0)
1134                 return -1;
1135
1136         /*
1137          * if (check_ldpc_decoder_llr_spec(vector) < 0)
1138          *      return -1;
1139          *
1140          * if (check_ldpc_decoder_op_flags(vector) < 0)
1141          *      return -1;
1142          */
1143
1144         /* Check which params were set */
1145         if (!(mask & TEST_BBDEV_VF_CODE_BLOCK_MODE)) {
1146                 printf(
1147                         "WARNING: code_block_mode was not specified in vector file and will be set to 1 (0 - TB Mode, 1 - CB mode)\n");
1148                 ldpc_dec->code_block_mode = 1;
1149         }
1150         if (ldpc_dec->code_block_mode == 0) {
1151                 if (!(mask & TEST_BBDEV_VF_EA))
1152                         printf(
1153                                 "WARNING: ea was not specified in vector file and will be set to 0\n");
1154                 if (!(mask & TEST_BBDEV_VF_EB))
1155                         printf(
1156                                 "WARNING: eb was not specified in vector file and will be set to 0\n");
1157                 if (!(mask & TEST_BBDEV_VF_C)) {
1158                         printf(
1159                                 "WARNING: c was not specified in vector file and will be set to 1\n");
1160                         ldpc_dec->tb_params.c = 1;
1161                 }
1162                 if (!(mask & TEST_BBDEV_VF_CAB))
1163                         printf(
1164                                 "WARNING: cab was not specified in vector file and will be set to 0\n");
1165                 if (!(mask & TEST_BBDEV_VF_R))
1166                         printf(
1167                                 "WARNING: r was not specified in vector file and will be set to 0\n");
1168         } else {
1169                 if (!(mask & TEST_BBDEV_VF_E))
1170                         printf(
1171                                 "WARNING: e was not specified in vector file and will be set to 0\n");
1172         }
1173         if (!(mask & TEST_BBDEV_VF_RV_INDEX))
1174                 printf(
1175                         "INFO: rv_index was not specified in vector file and will be set to 0\n");
1176         if (!(mask & TEST_BBDEV_VF_ITER_MAX))
1177                 printf(
1178                         "WARNING: iter_max was not specified in vector file and will be set to 0\n");
1179         if (!(mask & TEST_BBDEV_VF_EXPECTED_ITER_COUNT))
1180                 printf(
1181                         "WARNING: expected_iter_count was not specified in vector file and iter_count will not be validated\n");
1182         if (!(mask & TEST_BBDEV_VF_OP_FLAGS)) {
1183                 printf(
1184                         "WARNING: op_flags was not specified in vector file and capabilities will not be validated\n");
1185         }
1186         if (!(mask & TEST_BBDEV_VF_EXPECTED_STATUS))
1187                 printf(
1188                         "WARNING: expected_status was not specified in vector file and will be set to 0\n");
1189         return 0;
1190 }
1191
1192 /* checks encoder parameters */
1193 static int
1194 check_encoder(struct test_bbdev_vector *vector)
1195 {
1196         unsigned char i;
1197         const int mask = vector->mask;
1198
1199         if (vector->entries[DATA_INPUT].nb_segments == 0)
1200                 return -1;
1201
1202         for (i = 0; i < vector->entries[DATA_INPUT].nb_segments; i++)
1203                 if (vector->entries[DATA_INPUT].segments[i].addr == NULL)
1204                         return -1;
1205
1206         if (vector->entries[DATA_HARD_OUTPUT].nb_segments == 0)
1207                 return -1;
1208
1209         for (i = 0; i < vector->entries[DATA_HARD_OUTPUT].nb_segments; i++)
1210                 if (vector->entries[DATA_HARD_OUTPUT].segments[i].addr == NULL)
1211                         return -1;
1212
1213         if (!(mask & TEST_BBDEV_VF_CODE_BLOCK_MODE)) {
1214                 printf(
1215                         "WARNING: code_block_mode was not specified in vector file and will be set to 1\n");
1216                 vector->turbo_enc.code_block_mode = 1;
1217         }
1218         if (vector->turbo_enc.code_block_mode == 0) {
1219                 if (!(mask & TEST_BBDEV_VF_EA) && (vector->turbo_enc.op_flags &
1220                                 RTE_BBDEV_TURBO_RATE_MATCH))
1221                         printf(
1222                                 "WARNING: ea was not specified in vector file and will be set to 0\n");
1223                 if (!(mask & TEST_BBDEV_VF_EB) && (vector->turbo_enc.op_flags &
1224                                 RTE_BBDEV_TURBO_RATE_MATCH))
1225                         printf(
1226                                 "WARNING: eb was not specified in vector file and will be set to 0\n");
1227                 if (!(mask & TEST_BBDEV_VF_K_NEG))
1228                         printf(
1229                                 "WARNING: k_neg was not specified in vector file and will be set to 0\n");
1230                 if (!(mask & TEST_BBDEV_VF_K_POS))
1231                         printf(
1232                                 "WARNING: k_pos was not specified in vector file and will be set to 0\n");
1233                 if (!(mask & TEST_BBDEV_VF_C_NEG))
1234                         printf(
1235                                 "WARNING: c_neg was not specified in vector file and will be set to 0\n");
1236                 if (!(mask & TEST_BBDEV_VF_C)) {
1237                         printf(
1238                                 "WARNING: c was not specified in vector file and will be set to 1\n");
1239                         vector->turbo_enc.tb_params.c = 1;
1240                 }
1241                 if (!(mask & TEST_BBDEV_VF_CAB) && (vector->turbo_enc.op_flags &
1242                                 RTE_BBDEV_TURBO_RATE_MATCH))
1243                         printf(
1244                                 "WARNING: cab was not specified in vector file and will be set to 0\n");
1245                 if (!(mask & TEST_BBDEV_VF_NCB_NEG))
1246                         printf(
1247                                 "WARNING: ncb_neg was not specified in vector file and will be set to 0\n");
1248                 if (!(mask & TEST_BBDEV_VF_NCB_POS))
1249                         printf(
1250                                 "WARNING: ncb_pos was not specified in vector file and will be set to 0\n");
1251                 if (!(mask & TEST_BBDEV_VF_R))
1252                         printf(
1253                                 "WARNING: r was not specified in vector file and will be set to 0\n");
1254         } else {
1255                 if (!(mask & TEST_BBDEV_VF_E) && (vector->turbo_enc.op_flags &
1256                                 RTE_BBDEV_TURBO_RATE_MATCH))
1257                         printf(
1258                                 "WARNING: e was not specified in vector file and will be set to 0\n");
1259                 if (!(mask & TEST_BBDEV_VF_K))
1260                         printf(
1261                                 "WARNING: k was not specified in vector file and will be set to 0\n");
1262                 if (!(mask & TEST_BBDEV_VF_NCB))
1263                         printf(
1264                                 "WARNING: ncb was not specified in vector file and will be set to 0\n");
1265         }
1266         if (!(mask & TEST_BBDEV_VF_RV_INDEX))
1267                 printf(
1268                         "INFO: rv_index was not specified in vector file and will be set to 0\n");
1269         if (!(mask & TEST_BBDEV_VF_OP_FLAGS))
1270                 printf(
1271                         "INFO: op_flags was not specified in vector file and capabilities will not be validated\n");
1272         if (!(mask & TEST_BBDEV_VF_EXPECTED_STATUS))
1273                 printf(
1274                         "WARNING: expected_status was not specified in vector file and will be set to 0\n");
1275
1276         return 0;
1277 }
1278
1279
1280 /* checks encoder parameters */
1281 static int
1282 check_ldpc_encoder(struct test_bbdev_vector *vector)
1283 {
1284         unsigned char i;
1285         const int mask = vector->mask;
1286
1287         if (vector->entries[DATA_INPUT].nb_segments == 0)
1288                 return -1;
1289
1290         for (i = 0; i < vector->entries[DATA_INPUT].nb_segments; i++)
1291                 if (vector->entries[DATA_INPUT].segments[i].addr == NULL)
1292                         return -1;
1293
1294         if (vector->entries[DATA_HARD_OUTPUT].nb_segments == 0)
1295                 return -1;
1296
1297         for (i = 0; i < vector->entries[DATA_HARD_OUTPUT].nb_segments; i++)
1298                 if (vector->entries[DATA_HARD_OUTPUT].segments[i].addr == NULL)
1299                         return -1;
1300
1301         if (!(mask & TEST_BBDEV_VF_CODE_BLOCK_MODE)) {
1302                 printf(
1303                         "WARNING: code_block_mode was not specified in vector file and will be set to 1\n");
1304                 vector->turbo_enc.code_block_mode = 1;
1305         }
1306         if (vector->turbo_enc.code_block_mode == 0) {
1307         } else {
1308                 if (!(mask & TEST_BBDEV_VF_E) && (vector->turbo_enc.op_flags &
1309                                 RTE_BBDEV_TURBO_RATE_MATCH))
1310                         printf(
1311                                 "WARNING: e was not specified in vector file and will be set to 0\n");
1312                 if (!(mask & TEST_BBDEV_VF_NCB))
1313                         printf(
1314                                 "WARNING: ncb was not specified in vector file and will be set to 0\n");
1315         }
1316         if (!(mask & TEST_BBDEV_VF_BG))
1317                 printf(
1318                         "WARNING: BG was not specified in vector file and will be set to 0\n");
1319         if (!(mask & TEST_BBDEV_VF_ZC))
1320                 printf(
1321                         "WARNING: Zc was not specified in vector file and will be set to 0\n");
1322         if (!(mask & TEST_BBDEV_VF_RV_INDEX))
1323                 printf(
1324                         "INFO: rv_index was not specified in vector file and will be set to 0\n");
1325         if (!(mask & TEST_BBDEV_VF_OP_FLAGS))
1326                 printf(
1327                         "INFO: op_flags was not specified in vector file and capabilities will not be validated\n");
1328         if (!(mask & TEST_BBDEV_VF_EXPECTED_STATUS))
1329                 printf(
1330                         "WARNING: expected_status was not specified in vector file and will be set to 0\n");
1331
1332         return 0;
1333 }
1334
1335 static int
1336 bbdev_check_vector(struct test_bbdev_vector *vector)
1337 {
1338         if (vector->op_type == RTE_BBDEV_OP_TURBO_DEC) {
1339                 if (check_decoder(vector) == -1)
1340                         return -1;
1341         } else if (vector->op_type == RTE_BBDEV_OP_TURBO_ENC) {
1342                 if (check_encoder(vector) == -1)
1343                         return -1;
1344         } else if (vector->op_type == RTE_BBDEV_OP_LDPC_ENC) {
1345                 if (check_ldpc_encoder(vector) == -1)
1346                         return -1;
1347         } else if (vector->op_type == RTE_BBDEV_OP_LDPC_DEC) {
1348                 if (check_ldpc_decoder(vector) == -1)
1349                         return -1;
1350         } else if (vector->op_type != RTE_BBDEV_OP_NONE) {
1351                 printf("Vector was not filled\n");
1352                 return -1;
1353         }
1354
1355         return 0;
1356 }
1357
1358 int
1359 test_bbdev_vector_read(const char *filename,
1360                 struct test_bbdev_vector *vector)
1361 {
1362         int ret = 0;
1363         size_t len = 0;
1364
1365         FILE *fp = NULL;
1366         char *line = NULL;
1367         char *entry = NULL;
1368
1369         fp = fopen(filename, "r");
1370         if (fp == NULL) {
1371                 printf("File %s does not exist\n", filename);
1372                 return -1;
1373         }
1374
1375         while (getline(&line, &len, fp) != -1) {
1376
1377                 /* ignore comments and new lines */
1378                 if (line[0] == '#' || line[0] == '/' || line[0] == '\n'
1379                         || line[0] == '\r')
1380                         continue;
1381
1382                 trim_space(line);
1383
1384                 /* buffer for multiline */
1385                 entry = realloc(entry, strlen(line) + 1);
1386                 if (entry == NULL) {
1387                         printf("Fail to realloc %zu bytes\n", strlen(line) + 1);
1388                         ret = -ENOMEM;
1389                         goto exit;
1390                 }
1391
1392                 strcpy(entry, line);
1393
1394                 /* check if entry ends with , or = */
1395                 if (entry[strlen(entry) - 1] == ','
1396                         || entry[strlen(entry) - 1] == '=') {
1397                         while (getline(&line, &len, fp) != -1) {
1398                                 trim_space(line);
1399
1400                                 /* extend entry about length of new line */
1401                                 char *entry_extended = realloc(entry,
1402                                                 strlen(line) +
1403                                                 strlen(entry) + 1);
1404
1405                                 if (entry_extended == NULL) {
1406                                         printf("Fail to allocate %zu bytes\n",
1407                                                         strlen(line) +
1408                                                         strlen(entry) + 1);
1409                                         ret = -ENOMEM;
1410                                         goto exit;
1411                                 }
1412
1413                                 entry = entry_extended;
1414                                 /* entry has been allocated accordingly */
1415                                 strcpy(&entry[strlen(entry)], line);
1416
1417                                 if (entry[strlen(entry) - 1] != ',')
1418                                         break;
1419                         }
1420                 }
1421                 ret = parse_entry(entry, vector);
1422                 if (ret != 0) {
1423                         printf("An error occurred while parsing!\n");
1424                         goto exit;
1425                 }
1426         }
1427         ret = bbdev_check_vector(vector);
1428         if (ret != 0)
1429                 printf("An error occurred while checking!\n");
1430
1431 exit:
1432         fclose(fp);
1433         free(line);
1434         free(entry);
1435
1436         return ret;
1437 }