GCC Code Coverage Report


Directory: src/
File: src/support/types.c
Date: 2026-02-23 15:13:19
Exec Total Coverage
Lines: 358 386 92.7%
Functions: 52 54 96.3%
Branches: 210 246 85.4%

Line Branch Exec Source
1 /*********************************************************************************/
2 /* Copyright 2009-2024 Barcelona Supercomputing Center */
3 /* */
4 /* This file is part of the DLB library. */
5 /* */
6 /* DLB is free software: you can redistribute it and/or modify */
7 /* it under the terms of the GNU Lesser General Public License as published by */
8 /* the Free Software Foundation, either version 3 of the License, or */
9 /* (at your option) any later version. */
10 /* */
11 /* DLB is distributed in the hope that it will be useful, */
12 /* but WITHOUT ANY WARRANTY; without even the implied warranty of */
13 /* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the */
14 /* GNU Lesser General Public License for more details. */
15 /* */
16 /* You should have received a copy of the GNU Lesser General Public License */
17 /* along with DLB. If not, see <https://www.gnu.org/licenses/>. */
18 /*********************************************************************************/
19
20 #include "support/types.h"
21 #include "support/debug.h"
22 #include "apis/dlb_errors.h"
23
24 #include <limits.h>
25 #include <stdlib.h>
26 #include <string.h>
27 #include <stdio.h>
28 #include <errno.h>
29
30 #define LINE_BREAK "\n "
31
32 // option delimiter: flag options accept either : or , as delimiters
33 static const char *delim = ":,";
34
35 3004 int parse_bool(const char *str, bool *value) {
36
2/2
✓ Branch 0 taken 2999 times.
✓ Branch 1 taken 5 times.
3004 if (strcasecmp(str, "1")==0 ||
37
2/2
✓ Branch 0 taken 2367 times.
✓ Branch 1 taken 632 times.
2999 strcasecmp(str, "yes")==0 ||
38
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 2366 times.
2367 strcasecmp(str, "true")==0) {
39 638 *value = true;
40
2/2
✓ Branch 0 taken 2360 times.
✓ Branch 1 taken 6 times.
2366 } else if (strcasecmp(str, "0")==0 ||
41
2/2
✓ Branch 0 taken 5 times.
✓ Branch 1 taken 2355 times.
2360 strcasecmp(str, "no")==0 ||
42
2/2
✓ Branch 0 taken 3 times.
✓ Branch 1 taken 2 times.
5 strcasecmp(str, "false")==0) {
43 2364 *value = false;
44 } else {
45 2 return DLB_ERR_NOENT;
46 }
47 3002 return DLB_SUCCESS;
48 }
49
50 3 bool equivalent_bool(const char *str1, const char *str2) {
51 3 bool b1 = false;
52 3 bool b2 = true;
53 3 int err1 = parse_bool(str1, &b1);
54 3 int err2 = parse_bool(str2, &b2);
55
4/6
✓ Branch 0 taken 3 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 3 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 1 times.
✓ Branch 5 taken 2 times.
3 return err1 == DLB_SUCCESS && err2 == DLB_SUCCESS && b1 == b2;
56 }
57
58 16 int parse_negated_bool(const char *str, bool *value) {
59
2/2
✓ Branch 0 taken 14 times.
✓ Branch 1 taken 2 times.
16 if (strcasecmp(str, "1")==0 ||
60
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 4 times.
14 strcasecmp(str, "yes")==0 ||
61
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 9 times.
10 strcasecmp(str, "true")==0) {
62 7 *value = false;
63
2/2
✓ Branch 0 taken 7 times.
✓ Branch 1 taken 2 times.
9 } else if (strcasecmp(str, "0")==0 ||
64
2/2
✓ Branch 0 taken 5 times.
✓ Branch 1 taken 2 times.
7 strcasecmp(str, "no")==0 ||
65
2/2
✓ Branch 0 taken 3 times.
✓ Branch 1 taken 2 times.
5 strcasecmp(str, "false")==0) {
66 7 *value = true;
67 } else {
68 2 return DLB_ERR_NOENT;
69 }
70 14 return DLB_SUCCESS;
71 }
72
73 2 bool equivalent_negated_bool(const char *str1, const char *str2) {
74 2 bool b1 = false;
75 2 bool b2 = true;
76 2 int err1 = parse_negated_bool(str1, &b1);
77 2 int err2 = parse_negated_bool(str2, &b2);
78
4/6
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 1 times.
✓ Branch 5 taken 1 times.
2 return err1 == DLB_SUCCESS && err2 == DLB_SUCCESS && b1 == b2;
79 }
80
81 1107 int parse_int(const char *str, int *value) {
82 char *endptr;
83 1107 long val = strtol(str, &endptr, 0);
84
4/4
✓ Branch 0 taken 890 times.
✓ Branch 1 taken 217 times.
✓ Branch 2 taken 888 times.
✓ Branch 3 taken 2 times.
1107 if ((val == 0 && endptr == str)
85
2/6
✓ Branch 0 taken 1105 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 1105 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
1105 || ((val == LONG_MIN || val == LONG_MAX) && errno == ERANGE)) {
86 2 debug_warning("Error parsing integer. str: %s, strlen: %lu, val: %ld, "
87 "errno: %d, strptr: %p, endptr: %p", str, strlen(str), val,
88 errno, str, endptr);
89 2 return DLB_ERR_NOENT;
90 }
91 1105 *value = (int)val;
92 1105 return DLB_SUCCESS;
93 }
94
95 2 bool equivalent_int(const char *str1, const char *str2) {
96 2 int i1 = 0;
97 2 int i2 = 1;
98 2 int err1 = parse_int(str1, &i1);
99 2 int err2 = parse_int(str2, &i2);
100
4/6
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 1 times.
✓ Branch 5 taken 1 times.
2 return err1 == DLB_SUCCESS && err2 == DLB_SUCCESS && i1 == i2;
101 }
102
103
104 /* verbose_opts_t */
105 static const verbose_opts_t verbose_opts_values[] =
106 {VB_CLEAR, VB_ALL, VB_API, VB_MICROLB, VB_SHMEM, VB_MPI_API, VB_MPI_INT, VB_STATS,
107 VB_DROM, VB_ASYNC, VB_OMPT, VB_AFFINITY, VB_BARRIER, VB_TALP, VB_INSTR};
108 static const char* const verbose_opts_choices[] =
109 {"no", "all", "api", "microlb", "shmem", "mpi_api", "mpi_intercept", "stats", "drom",
110 "async", "ompt", "affinity", "barrier", "talp", "instrument"};
111 static const char verbose_opts_choices_str[] =
112 "no:all:api:microlb:shmem:mpi_api:mpi_intercept:stats:"LINE_BREAK
113 "drom:async:ompt:affinity:barrier:talp:instrument";
114 enum { verbose_opts_nelems = sizeof(verbose_opts_values) / sizeof(verbose_opts_values[0]) };
115
116 242 int parse_verbose_opts(const char *str, verbose_opts_t *value) {
117 /* particular case: '--verbose/--verbose=yes' enables all verbose options */
118
2/2
✓ Branch 0 taken 3 times.
✓ Branch 1 taken 239 times.
242 if (strcmp(str, "yes") == 0) {
119 3 *value = VB_ALL;
120 3 return DLB_SUCCESS;
121 }
122
123 239 *value = VB_CLEAR;
124
125 /* tokenize multiple options separated by ':' */
126 239 char *end_token = NULL;
127 239 size_t len = strlen(str) + 1;
128 239 char *str_copy = malloc(sizeof(char)*len);
129 239 strcpy(str_copy, str);
130 239 char *token = strtok_r(str_copy, delim, &end_token);
131
2/2
✓ Branch 0 taken 254 times.
✓ Branch 1 taken 239 times.
493 while (token) {
132 int i;
133
2/2
✓ Branch 0 taken 536 times.
✓ Branch 1 taken 2 times.
538 for (i=0; i<verbose_opts_nelems; ++i) {
134
2/2
✓ Branch 0 taken 252 times.
✓ Branch 1 taken 284 times.
536 if (strcmp(token, verbose_opts_choices[i]) == 0) {
135 252 *value |= verbose_opts_values[i];
136 252 break;
137 }
138 }
139
2/2
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 252 times.
254 if (i == verbose_opts_nelems) {
140 2 warning("Unknown --verbose option: %s", token);
141 }
142 254 token = strtok_r(NULL, delim, &end_token);
143 }
144 239 free(str_copy);
145
146 239 return DLB_SUCCESS;
147 }
148
149 7 const char* verbose_opts_tostr(verbose_opts_t value) {
150 /* particular cases */
151
2/2
✓ Branch 0 taken 5 times.
✓ Branch 1 taken 2 times.
7 if (value == VB_CLEAR) {
152 5 return "no";
153 }
154
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 1 times.
2 if (value == VB_ALL) {
155 1 return "all";
156 }
157
158 static char str[sizeof(verbose_opts_choices_str)] = "";
159 1 char *p = str;
160 int i;
161
2/2
✓ Branch 0 taken 13 times.
✓ Branch 1 taken 1 times.
14 for (i=2; i<verbose_opts_nelems; ++i) {
162
2/2
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 11 times.
13 if (value & verbose_opts_values[i]) {
163
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 1 times.
2 if (p!=str) {
164 1 *p = ':';
165 1 ++p;
166 1 *p = '\0';
167 }
168 2 p += sprintf(p, "%s", verbose_opts_choices[i]);
169 }
170 }
171 1 return str;
172 }
173
174 4 const char* get_verbose_opts_choices(void) {
175 4 return verbose_opts_choices_str;
176 }
177
178 3 bool equivalent_verbose_opts(const char *str1, const char *str2) {
179 verbose_opts_t value1, value2;
180 3 parse_verbose_opts(str1, &value1);
181 3 parse_verbose_opts(str2, &value2);
182 3 return value1 == value2;
183 }
184
185
186 /* verbose_fmt_t */
187 static const verbose_fmt_t verbose_fmt_values[] =
188 {VBF_NODE, VBF_MPINODE, VBF_MPIRANK, VBF_SPID, VBF_THREAD, VBF_TSTAMP};
189 static const char* const verbose_fmt_choices[] =
190 {"node", "mpinode", "mpirank", "spid", "thread", "timestamp"};
191 static const char verbose_fmt_choices_str[] =
192 "node:mpinode:mpirank:spid:thread:timestamp";
193 enum { verbose_fmt_nelems = sizeof(verbose_fmt_values) / sizeof(verbose_fmt_values[0]) };
194
195 187 int parse_verbose_fmt(const char *str, verbose_fmt_t *value) {
196 187 *value = VBF_CLEAR;
197
198 /* tokenize multiple options separated by ':' */
199 187 char *end_token = NULL;
200 187 size_t len = strlen(str) + 1;
201 187 char *str_copy = malloc(sizeof(char)*len);
202 187 strcpy(str_copy, str);
203 187 char *token = strtok_r(str_copy, delim, &end_token);
204
2/2
✓ Branch 0 taken 368 times.
✓ Branch 1 taken 187 times.
555 while (token) {
205 int i;
206
2/2
✓ Branch 0 taken 935 times.
✓ Branch 1 taken 2 times.
937 for (i=0; i<verbose_fmt_nelems; ++i) {
207
2/2
✓ Branch 0 taken 366 times.
✓ Branch 1 taken 569 times.
935 if (strcmp(token, verbose_fmt_choices[i]) == 0) {
208 366 *value |= verbose_fmt_values[i];
209 366 break;
210 }
211 }
212
2/2
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 366 times.
368 if (i == verbose_fmt_nelems) {
213 2 warning("Unknown --verbose-format option: %s", token);
214 }
215 368 token = strtok_r(NULL, delim, &end_token);
216 }
217 187 free(str_copy);
218
219 187 return DLB_SUCCESS;
220 }
221
222 8 const char* verbose_fmt_tostr(verbose_fmt_t value) {
223 static char str[sizeof(verbose_fmt_choices_str)] = "";
224 8 char *p = str;
225 int i;
226
2/2
✓ Branch 0 taken 48 times.
✓ Branch 1 taken 8 times.
56 for (i=0; i<verbose_fmt_nelems; ++i) {
227
2/2
✓ Branch 0 taken 12 times.
✓ Branch 1 taken 36 times.
48 if (value & verbose_fmt_values[i]) {
228
2/2
✓ Branch 0 taken 5 times.
✓ Branch 1 taken 7 times.
12 if (p!=str) {
229 5 *p = ':';
230 5 ++p;
231 5 *p = '\0';
232 }
233 12 p += sprintf(p, "%s", verbose_fmt_choices[i]);
234 }
235 }
236 8 return str;
237 }
238
239 4 const char* get_verbose_fmt_choices(void) {
240 4 return verbose_fmt_choices_str;
241 }
242
243 3 bool equivalent_verbose_fmt(const char *str1, const char *str2) {
244 verbose_fmt_t value1, value2;
245 3 parse_verbose_fmt(str1, &value1);
246 3 parse_verbose_fmt(str2, &value2);
247 3 return value1 == value2;
248 }
249
250
251 /* instrument_items_t */
252 static const instrument_items_t instrument_items_values[] =
253 {INST_NONE, INST_ALL, INST_MPI, INST_LEWI, INST_DROM, INST_TALP, INST_BARR, INST_OMPT, INST_CPUS, INST_CBCK};
254 static const char* const instrument_items_choices[] =
255 {"none", "all", "mpi", "lewi", "drom", "talp", "barrier", "ompt", "cpus", "callbacks"};
256 static const char instrument_items_choices_str[] =
257 "none:all:mpi:lewi:drom:talp:barrier:ompt:cpus:callbacks";
258 enum { instrument_items_nelems = sizeof(instrument_items_values) / sizeof(instrument_items_values[0]) };
259
260 188 int parse_instrument_items(const char *str, instrument_items_t *value) {
261 /* particular case: '--instrument/--instrument=yes' enables all instrument items */
262
2/2
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 186 times.
188 if (strcmp(str, "yes") == 0) {
263 2 *value = INST_ALL;
264 2 return DLB_SUCCESS;
265 }
266
267 /* particular case: '--no-instrument/--instrument=no' disables all instrument items */
268
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 186 times.
186 if (strcmp(str, "no") == 0) {
269 *value = INST_NONE;
270 return DLB_SUCCESS;
271 }
272
273 186 *value = INST_NONE;
274
275 /* tokenize multiple options separated by ':' */
276 186 char *end_token = NULL;
277 186 size_t len = strlen(str) + 1;
278 186 char *str_copy = malloc(sizeof(char)*len);
279 186 strcpy(str_copy, str);
280 186 char *token = strtok_r(str_copy, delim, &end_token);
281
2/2
✓ Branch 0 taken 196 times.
✓ Branch 1 taken 186 times.
382 while (token) {
282 int i;
283
2/2
✓ Branch 0 taken 469 times.
✓ Branch 1 taken 4 times.
473 for (i=0; i<instrument_items_nelems; ++i) {
284
2/2
✓ Branch 0 taken 192 times.
✓ Branch 1 taken 277 times.
469 if (strcmp(token, instrument_items_choices[i]) == 0) {
285 192 *value |= instrument_items_values[i];
286 192 break;
287 }
288 }
289
2/2
✓ Branch 0 taken 4 times.
✓ Branch 1 taken 192 times.
196 if (i == instrument_items_nelems) {
290 4 warning("Unknown --instrument option: %s", token);
291 }
292 196 token = strtok_r(NULL, delim, &end_token);
293 }
294 186 free(str_copy);
295
296 186 return DLB_SUCCESS;
297 }
298
299 7 const char* instrument_items_tostr(instrument_items_t value) {
300 // particular cases
301
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 6 times.
7 if (value == INST_NONE) {
302 1 return "none";
303 }
304
2/2
✓ Branch 0 taken 5 times.
✓ Branch 1 taken 1 times.
6 if (value == INST_ALL) {
305 5 return "all";
306 }
307
308 static char str[sizeof(instrument_items_choices_str)] = "";
309 1 char *p = str;
310 int i;
311
2/2
✓ Branch 0 taken 8 times.
✓ Branch 1 taken 1 times.
9 for (i=2; i<instrument_items_nelems; ++i) {
312
2/2
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 6 times.
8 if (value & instrument_items_values[i]) {
313
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 1 times.
2 if (p!=str) {
314 1 *p = ':';
315 1 ++p;
316 1 *p = '\0';
317 }
318 2 p += sprintf(p, "%s", instrument_items_choices[i]);
319 }
320 }
321 1 return str;
322 }
323
324 4 const char* get_instrument_items_choices(void) {
325 4 return instrument_items_choices_str;
326 }
327
328 3 bool equivalent_instrument_items(const char *str1, const char *str2) {
329 instrument_items_t value1, value2;
330 3 parse_instrument_items(str1, &value1);
331 3 parse_instrument_items(str2, &value2);
332 3 return value1 == value2;
333 }
334
335
336 /* debug_opts_t */
337 static const debug_opts_t debug_opts_values[] =
338 {DBG_RETURNSTOLEN, DBG_WERROR, DBG_LPOSTMORTEM, DBG_WARNMPI};
339 static const char* const debug_opts_choices[] =
340 {"return-stolen", "werror", "lend-post-mortem", "warn-mpi-version"};
341 static const char debug_opts_choices_str[] =
342 "return-stolen:werror:lend-post-mortem:warn-mpi-version";
343 enum { debug_opts_nelems = sizeof(debug_opts_values) / sizeof(debug_opts_values[0]) };
344
345 177 int parse_debug_opts(const char *str, debug_opts_t *value) {
346 177 *value = DBG_CLEAR;
347 int i;
348
2/2
✓ Branch 0 taken 708 times.
✓ Branch 1 taken 177 times.
885 for (i=0; i<debug_opts_nelems; ++i) {
349
2/2
✓ Branch 0 taken 3 times.
✓ Branch 1 taken 705 times.
708 if (strstr(str, debug_opts_choices[i]) != NULL) {
350 3 *value |= debug_opts_values[i];
351 }
352 }
353 177 return DLB_SUCCESS;
354 }
355
356 1 const char* debug_opts_tostr(debug_opts_t value) {
357 static char str[sizeof(debug_opts_choices_str)] = "";
358 1 char *p = str;
359 int i;
360
2/2
✓ Branch 0 taken 4 times.
✓ Branch 1 taken 1 times.
5 for (i=0; i<debug_opts_nelems; ++i) {
361
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 4 times.
4 if (value & debug_opts_values[i]) {
362 if (p!=str) {
363 *p = ':';
364 ++p;
365 *p = '\0';
366 }
367 p += sprintf(p, "%s", debug_opts_choices[i]);
368 }
369 }
370 1 return str;
371 }
372
373 1 const char* get_debug_opts_choices(void) {
374 1 return debug_opts_choices_str;
375 }
376
377 bool equivalent_debug_opts(const char *str1, const char *str2) {
378 debug_opts_t value1, value2;
379 parse_debug_opts(str1, &value1);
380 parse_debug_opts(str2, &value2);
381 return value1 == value2;
382 }
383
384
385 /* lewi_affinity_t */
386 static const lewi_affinity_t lewi_affinity_values[] =
387 {LEWI_AFFINITY_AUTO, LEWI_AFFINITY_NONE, LEWI_AFFINITY_MASK,
388 LEWI_AFFINITY_NEARBY_FIRST, LEWI_AFFINITY_NEARBY_ONLY, LEWI_AFFINITY_SPREAD_IFEMPTY};
389 static const char* const lewi_affinity_choices[] =
390 {"auto", "none", "mask", "nearby-first", "nearby-only", "spread-ifempty"};
391 static const char lewi_affinity_choices_str[] =
392 "auto, none, mask, nearby-first,"LINE_BREAK
393 "nearby-only, spread-ifempty";
394 enum { lewi_affinity_nelems = sizeof(lewi_affinity_values) / sizeof(lewi_affinity_values[0]) };
395
396 246 int parse_lewi_affinity(const char *str, lewi_affinity_t *value) {
397
398
2/2
✓ Branch 0 taken 294 times.
✓ Branch 1 taken 4 times.
298 for (int i = 0; i < lewi_affinity_nelems; ++i) {
399
2/2
✓ Branch 0 taken 242 times.
✓ Branch 1 taken 52 times.
294 if (strcasecmp(str, lewi_affinity_choices[i]) == 0) {
400 242 *value = lewi_affinity_values[i];
401 242 return DLB_SUCCESS;
402 }
403 }
404
405 /* Support deprecated values */
406
2/2
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 2 times.
4 if (strcasecmp(str, "any") == 0) {
407 2 *value = LEWI_AFFINITY_MASK;
408 2 return DLB_SUCCESS;
409 }
410
411 2 return DLB_ERR_NOENT;
412 }
413
414 4 const char* lewi_affinity_tostr(lewi_affinity_t value) {
415 int i;
416
1/2
✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
4 for (i=0; i<lewi_affinity_nelems; ++i) {
417
1/2
✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
4 if (lewi_affinity_values[i] == value) {
418 4 return lewi_affinity_choices[i];
419 }
420 }
421 return "unknown";
422 }
423
424 4 const char* get_lewi_affinity_choices(void) {
425 4 return lewi_affinity_choices_str;
426 }
427
428 2 bool equivalent_lewi_affinity(const char *str1, const char *str2) {
429 2 lewi_affinity_t value1 = LEWI_AFFINITY_NONE;
430 2 lewi_affinity_t value2 = LEWI_AFFINITY_MASK;
431 2 int err1 = parse_lewi_affinity(str1, &value1);
432 2 int err2 = parse_lewi_affinity(str2, &value2);
433
4/6
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 1 times.
✓ Branch 5 taken 1 times.
2 return err1 == DLB_SUCCESS && err2 == DLB_SUCCESS && value1 == value2;
434 }
435
436
437 /* talp_summary_t */
438 static const talp_summary_t talp_summary_values[] =
439 {SUMMARY_NONE, SUMMARY_ALL, SUMMARY_POP_METRICS, SUMMARY_POP_RAW, SUMMARY_NODE,
440 SUMMARY_PROCESS};
441 static const char* const talp_summary_choices[] =
442 {"none", "all", "pop-metrics", "pop-raw", "node", "process"};
443 static const char talp_summary_choices_str[] =
444 "none:all:pop-metrics:process";
445 enum { talp_summary_nelems = sizeof(talp_summary_values) / sizeof(talp_summary_values[0]) };
446
447 187 int parse_talp_summary(const char *str, talp_summary_t *value) {
448 /* particular case: '--talp-summary/--talp-summary=yes' enables only POP metrics */
449
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 186 times.
187 if (strcmp(str, "yes") == 0) {
450 1 *value = SUMMARY_POP_METRICS;
451 1 return DLB_SUCCESS;
452 }
453
454 /* particular case: '--no-talp-summary/--talp-summary=no' disables all summaries */
455
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 186 times.
186 if (strcmp(str, "no") == 0) {
456 *value = SUMMARY_NONE;
457 return DLB_SUCCESS;
458 }
459
460 186 *value = SUMMARY_NONE;
461
462 /* tokenize multiple options separated by ':' */
463 186 char *end_token = NULL;
464 186 size_t len = strlen(str) + 1;
465 186 char *str_copy = malloc(sizeof(char)*len);
466 186 strcpy(str_copy, str);
467 186 char *token = strtok_r(str_copy, delim, &end_token);
468
2/2
✓ Branch 0 taken 188 times.
✓ Branch 1 taken 186 times.
374 while (token) {
469 int i;
470
2/2
✓ Branch 0 taken 584 times.
✓ Branch 1 taken 4 times.
588 for (i=0; i<talp_summary_nelems; ++i) {
471
2/2
✓ Branch 0 taken 184 times.
✓ Branch 1 taken 400 times.
584 if (strcmp(token, talp_summary_choices[i]) == 0) {
472 184 *value |= talp_summary_values[i];
473 184 break;
474 }
475
476 /* Support deprecated values */
477
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 400 times.
400 if (strcmp(token, "app") == 0) {
478 *value |= SUMMARY_POP_METRICS;
479 break;
480 }
481 }
482
2/2
✓ Branch 0 taken 4 times.
✓ Branch 1 taken 184 times.
188 if (i == talp_summary_nelems) {
483 4 warning("Unknown --talp-summary option: %s", token);
484 }
485 188 token = strtok_r(NULL, delim, &end_token);
486 }
487 186 free(str_copy);
488
489 /* Deprecation warnings: */
490
491
2/2
✓ Branch 0 taken 3 times.
✓ Branch 1 taken 183 times.
186 if (*value & SUMMARY_POP_RAW) {
492 3 warning("Deprecated: --talp-summary=pop-raw is deprecated. Use pop-metrics instead.");
493 }
494
495
2/2
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 184 times.
186 if (*value & SUMMARY_NODE) {
496 2 warning("Deprecated: --talp-summary=node is deprecated. Use process instead.");
497 }
498
499 186 return DLB_SUCCESS;
500 }
501
502 7 const char* talp_summary_tostr(talp_summary_t value) {
503 // particular cases
504
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 6 times.
7 if (value == SUMMARY_NONE) {
505 1 return "none";
506 }
507
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 5 times.
6 if (value == SUMMARY_ALL) {
508 1 return "all";
509 }
510
511 static char str[sizeof(talp_summary_choices_str)] = "";
512 5 char *p = str;
513 int i;
514
2/2
✓ Branch 0 taken 20 times.
✓ Branch 1 taken 5 times.
25 for (i=2; i<talp_summary_nelems; ++i) {
515
2/2
✓ Branch 0 taken 5 times.
✓ Branch 1 taken 15 times.
20 if (value & talp_summary_values[i]) {
516
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 5 times.
5 if (p!=str) {
517 *p = ':';
518 ++p;
519 *p = '\0';
520 }
521 5 p += sprintf(p, "%s", talp_summary_choices[i]);
522 }
523 }
524 5 return str;
525 }
526
527 4 const char* get_talp_summary_choices(void) {
528 4 return talp_summary_choices_str;
529 }
530
531 3 bool equivalent_talp_summary(const char *str1, const char *str2) {
532 talp_summary_t value1, value2;
533 3 parse_talp_summary(str1, &value1);
534 3 parse_talp_summary(str2, &value2);
535 3 return value1 == value2;
536 }
537
538
539 /* talp_model_t */
540 static const talp_model_t talp_model_values[] = {TALP_MODEL_HYBRID_V1, TALP_MODEL_HYBRID_V2};
541 static const char* const talp_model_choices[] = {"hybrid-v1", "hybrid-v2"};
542 static const char talp_model_choices_str[] = "hybrid-v1, hybrid-v2";
543 enum { talp_model_nelems = sizeof(talp_model_values) / sizeof(talp_model_values[0]) };
544
545 183 int parse_talp_model(const char *str, talp_model_t *value) {
546 int i;
547
2/2
✓ Branch 0 taken 362 times.
✓ Branch 1 taken 1 times.
363 for (i=0; i<talp_model_nelems; ++i) {
548
2/2
✓ Branch 0 taken 182 times.
✓ Branch 1 taken 180 times.
362 if (strcasecmp(str, talp_model_choices[i]) == 0) {
549 182 *value = talp_model_values[i];
550 182 return DLB_SUCCESS;
551 }
552 }
553 1 return DLB_ERR_NOENT;
554 }
555
556 2 const char* talp_model_tostr(talp_model_t value) {
557 int i;
558
1/2
✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
4 for (i=0; i<talp_model_nelems; ++i) {
559
2/2
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 2 times.
4 if (talp_model_values[i] == value) {
560 2 return talp_model_choices[i];
561 }
562 }
563 return "unknown";
564 }
565
566 1 const char* get_talp_model_choices(void) {
567 1 return talp_model_choices_str;
568 }
569
570 2 bool equivalent_talp_model(const char *str1, const char *str2) {
571 2 talp_model_t value1 = TALP_MODEL_HYBRID_V1;
572 2 talp_model_t value2 = TALP_MODEL_HYBRID_V2;
573 2 int err1 = parse_talp_model(str1, &value1);
574 2 int err2 = parse_talp_model(str2, &value2);
575
4/6
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 1 times.
✓ Branch 5 taken 1 times.
2 return err1 == DLB_SUCCESS && err2 == DLB_SUCCESS && value1 == value2;
576 }
577
578
579 /* policy_t: most of this stuff is depcrecated, only policy_tostr is still used */
580 static const policy_t policy_values[] = {POLICY_NONE, POLICY_LEWI, POLICY_LEWI_ASYNC, POLICY_LEWI_MASK};
581 static const char* const policy_choices[] = {"no", "LeWI", "LeWI_async", "LeWI_mask"};
582 static const char policy_choices_str[] = "no, LeWI, LeWI_async, LeWI_mask";
583 enum { policy_nelems = sizeof(policy_values) / sizeof(policy_values[0]) };
584
585 9 int parse_policy(const char *str, policy_t *value) {
586 int i;
587
2/2
✓ Branch 0 taken 25 times.
✓ Branch 1 taken 2 times.
27 for (i=0; i<policy_nelems; ++i) {
588
2/2
✓ Branch 0 taken 7 times.
✓ Branch 1 taken 18 times.
25 if (strcasecmp(str, policy_choices[i]) == 0) {
589 7 *value = policy_values[i];
590 7 return DLB_SUCCESS;
591 }
592 }
593 2 return DLB_ERR_NOENT;
594 }
595
596 62 const char* policy_tostr(policy_t value) {
597 int i;
598
2/2
✓ Branch 0 taken 181 times.
✓ Branch 1 taken 1 times.
182 for (i=0; i<policy_nelems; ++i) {
599
2/2
✓ Branch 0 taken 61 times.
✓ Branch 1 taken 120 times.
181 if (policy_values[i] == value) {
600 61 return policy_choices[i];
601 }
602 }
603 1 return "error";
604 }
605
606 const char* get_policy_choices(void) {
607 return policy_choices_str;
608 }
609
610 2 bool equivalent_policy(const char *str1, const char *str2) {
611 2 policy_t value1 = POLICY_NONE;
612 2 policy_t value2 = POLICY_LEWI;
613 2 int err1 = parse_policy(str1, &value1);
614 2 int err2 = parse_policy(str2, &value2);
615
4/6
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 1 times.
✓ Branch 5 taken 1 times.
2 return err1 == DLB_SUCCESS && err2 == DLB_SUCCESS && value1 == value2;
616 }
617
618 /* interaction_mode_t */
619 static const interaction_mode_t mode_values[] = {MODE_POLLING, MODE_ASYNC};
620 static const char* const mode_choices[] = {"polling", "async"};
621 static const char mode_choices_str[] = "polling, async";
622 enum { mode_nelems = sizeof(mode_values) / sizeof(mode_values[0]) };
623
624 184 int parse_mode(const char *str, interaction_mode_t *value) {
625 int i;
626
2/2
✓ Branch 0 taken 212 times.
✓ Branch 1 taken 2 times.
214 for (i=0; i<mode_nelems; ++i) {
627
2/2
✓ Branch 0 taken 182 times.
✓ Branch 1 taken 30 times.
212 if (strcasecmp(str, mode_choices[i]) == 0) {
628 182 *value = mode_values[i];
629 182 return DLB_SUCCESS;
630 }
631 }
632 2 return DLB_ERR_NOENT;
633 }
634
635 8 const char* mode_tostr(interaction_mode_t value) {
636 int i;
637
1/2
✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
10 for (i=0; i<mode_nelems; ++i) {
638
2/2
✓ Branch 0 taken 8 times.
✓ Branch 1 taken 2 times.
10 if (mode_values[i] == value) {
639 8 return mode_choices[i];
640 }
641 }
642 return "unknown";
643 }
644
645 4 const char* get_mode_choices(void) {
646 4 return mode_choices_str;
647 }
648
649 2 bool equivalent_mode(const char *str1, const char *str2) {
650 2 interaction_mode_t value1 = MODE_POLLING;
651 2 interaction_mode_t value2 = MODE_ASYNC;
652 2 int err1 = parse_mode(str1, &value1);
653 2 int err2 = parse_mode(str2, &value2);
654
4/6
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 1 times.
✓ Branch 5 taken 1 times.
2 return err1 == DLB_SUCCESS && err2 == DLB_SUCCESS && value1 == value2;
655 }
656
657 /* mpi_set_t */
658 static const mpi_set_t mpiset_values[] = {MPISET_NONE, MPISET_ALL, MPISET_BARRIER, MPISET_COLLECTIVES};
659 static const char* const mpiset_choices[] = {"none", "all", "barrier", "collectives"};
660 static const char mpiset_choices_str[] = "none, all, barrier, collectives";
661 enum { mpiset_nelems = sizeof(mpiset_values) / sizeof(mpiset_values[0]) };
662
663 241 int parse_mpiset(const char *str, mpi_set_t *value) {
664 int i;
665
2/2
✓ Branch 0 taken 488 times.
✓ Branch 1 taken 1 times.
489 for (i=0; i<mpiset_nelems; ++i) {
666
2/2
✓ Branch 0 taken 240 times.
✓ Branch 1 taken 248 times.
488 if (strcasecmp(str, mpiset_choices[i]) == 0) {
667 240 *value = mpiset_values[i];
668 240 return DLB_SUCCESS;
669 }
670 }
671 1 return DLB_ERR_NOENT;
672 }
673
674 6 const char* mpiset_tostr(mpi_set_t value) {
675 int i;
676
1/2
✓ Branch 0 taken 13 times.
✗ Branch 1 not taken.
13 for (i=0; i<mpiset_nelems; ++i) {
677
2/2
✓ Branch 0 taken 6 times.
✓ Branch 1 taken 7 times.
13 if (mpiset_values[i] == value) {
678 6 return mpiset_choices[i];
679 }
680 }
681 return "unknown";
682 }
683
684 4 const char* get_mpiset_choices(void) {
685 4 return mpiset_choices_str;
686 }
687
688 2 bool equivalent_mpiset(const char *str1, const char *str2) {
689 2 mpi_set_t value1 = MPISET_NONE;
690 2 mpi_set_t value2 = MPISET_ALL;
691 2 int err1 = parse_mpiset(str1, &value1);
692 2 int err2 = parse_mpiset(str2, &value2);
693
4/6
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 1 times.
✓ Branch 5 taken 1 times.
2 return err1 == DLB_SUCCESS && err2 == DLB_SUCCESS && value1 == value2;
694 }
695
696 /* omptool_opts_t */
697 static const omptool_opts_t omptool_opts_values[] =
698 {OMPTOOL_OPTS_NONE, OMPTOOL_OPTS_BORROW, OMPTOOL_OPTS_LEND};
699 static const char* const omptool_opts_choices[] = {"none", "borrow", "lend"};
700 static const char omptool_opts_choices_str[] = "none, {borrow:lend}";
701 enum { omptool_opts_nelems = sizeof(omptool_opts_values) / sizeof(omptool_opts_values[0]) };
702
703 242 int parse_omptool_opts(const char *str, omptool_opts_t *value) {
704
705 242 *value = OMPTOOL_OPTS_NONE;
706
707 /* tokenize multiple options separated by ':' */
708 242 char *end_token = NULL;
709 242 size_t len = strlen(str) + 1;
710 242 char *str_copy = malloc(sizeof(char)*len);
711 242 strcpy(str_copy, str);
712 242 char *token = strtok_r(str_copy, delim, &end_token);
713
2/2
✓ Branch 0 taken 246 times.
✓ Branch 1 taken 242 times.
488 while (token) {
714 int i;
715
2/2
✓ Branch 0 taken 499 times.
✓ Branch 1 taken 1 times.
500 for (i=0; i<omptool_opts_nelems; ++i) {
716
2/2
✓ Branch 0 taken 245 times.
✓ Branch 1 taken 254 times.
499 if (strcmp(token, omptool_opts_choices[i]) == 0) {
717 245 *value |= omptool_opts_values[i];
718 245 break;
719 }
720 }
721
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 245 times.
246 if (i == omptool_opts_nelems) {
722 1 warning("Unknown --lewi-ompt option: %s", token);
723 }
724 246 token = strtok_r(NULL, delim, &end_token);
725 }
726 242 free(str_copy);
727
728 242 return DLB_SUCCESS;
729 }
730
731 5 const char* omptool_opts_tostr(omptool_opts_t value) {
732 static char str[sizeof(omptool_opts_choices_str)] = "";
733 5 char *p = str;
734 int i;
735
2/2
✓ Branch 0 taken 15 times.
✓ Branch 1 taken 5 times.
20 for (i=0; i<omptool_opts_nelems; ++i) {
736
2/2
✓ Branch 0 taken 5 times.
✓ Branch 1 taken 10 times.
15 if (value & omptool_opts_values[i]) {
737
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 5 times.
5 if (p!=str) {
738 *p = ':';
739 ++p;
740 *p = '\0';
741 }
742 5 p += sprintf(p, "%s", omptool_opts_choices[i]);
743 }
744 }
745 5 return str;
746 }
747
748 4 const char* get_omptool_opts_choices(void) {
749 4 return omptool_opts_choices_str;
750 }
751
752 3 bool equivalent_omptool_opts(const char *str1, const char *str2) {
753 omptool_opts_t value1, value2;
754 3 parse_omptool_opts(str1, &value1);
755 3 parse_omptool_opts(str2, &value2);
756 3 return value1 == value2;
757 }
758
759 /* omptm_version_t */
760 static const omptm_version_t omptm_version_values[] = {OMPTM_NONE, OMPTM_OMP5,
761 OMPTM_FREE_AGENTS, OMPTM_ROLE_SHIFT};
762 static const char* const omptm_version_choices[] = {"none", "omp5", "free-agents", "role-shift"};
763 static const char omptm_version_choices_str[] = "none, omp5, free-agents, role-shift";
764 enum { omptm_version_nelems = sizeof(omptm_version_values) / sizeof(omptm_version_values[0]) };
765
766 181 int parse_omptm_version(const char *str, omptm_version_t *value) {
767 int i;
768
2/2
✓ Branch 0 taken 365 times.
✓ Branch 1 taken 1 times.
366 for (i=0; i<omptm_version_nelems; ++i) {
769
2/2
✓ Branch 0 taken 180 times.
✓ Branch 1 taken 185 times.
365 if (strcasecmp(str, omptm_version_choices[i]) == 0) {
770 180 *value = omptm_version_values[i];
771 180 return DLB_SUCCESS;
772 }
773 }
774 1 return DLB_ERR_NOENT;
775 }
776
777 4 const char* omptm_version_tostr(omptm_version_t value) {
778 int i;
779
1/2
✓ Branch 0 taken 8 times.
✗ Branch 1 not taken.
8 for (i=0; i<omptm_version_nelems; ++i) {
780
2/2
✓ Branch 0 taken 4 times.
✓ Branch 1 taken 4 times.
8 if (omptm_version_values[i] == value) {
781 4 return omptm_version_choices[i];
782 }
783 }
784 return "unknown";
785 }
786
787 4 const char* get_omptm_version_choices(void) {
788 4 return omptm_version_choices_str;
789 }
790
791 2 bool equivalent_omptm_version_opts(const char *str1, const char *str2) {
792 2 omptm_version_t value1 = OMPTM_OMP5;
793 2 omptm_version_t value2 = OMPTM_FREE_AGENTS;
794 2 int err1 = parse_omptm_version(str1, &value1);
795 2 int err2 = parse_omptm_version(str2, &value2);
796
4/6
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 1 times.
✓ Branch 5 taken 1 times.
2 return err1 == DLB_SUCCESS && err2 == DLB_SUCCESS && value1 == value2;
797 }
798
799