xref: /linux/tools/tracing/rtla/tests/unit/timerlat_top_cli.c (revision 09005a63988521f74111fae344aecb3f63306168)
1 // SPDX-License-Identifier: GPL-2.0
2 
3 #define _GNU_SOURCE
4 #include <check.h>
5 #include <stdio.h>
6 #include <stdlib.h>
7 #include <sched.h>
8 #include <limits.h>
9 #include <unistd.h>
10 #include <sys/sysinfo.h>
11 
12 #include <linux/container_of.h>
13 
14 #include "cli_params_assert.h"
15 #include "../../src/cli.h"
16 
17 #define PARSE_ARGS(...) char *argv[] = { __VA_ARGS__, NULL  };\
18 			int argc = sizeof(argv) / sizeof(char *) - 1;\
19 			struct common_params *params =\
20 				timerlat_top_parse_args(argc, argv);\
21 			struct timerlat_params *tlat_params __maybe_unused =\
22 				to_timerlat_params(params)
23 
24 /* Tracing Options */
25 
26 START_TEST(test_irq_short)
27 {
28 	PARSE_ARGS("timerlat", "top", "-i", "20");
29 
30 	ck_assert_int_eq(params->stop_us, 20);
31 }
32 END_TEST
33 
34 START_TEST(test_irq_long)
35 {
36 	PARSE_ARGS("timerlat", "top", "--irq", "20");
37 
38 	ck_assert_int_eq(params->stop_us, 20);
39 }
40 END_TEST
41 
42 START_TEST(test_period_short)
43 {
44 	PARSE_ARGS("timerlat", "top", "-p", "200");
45 
46 	ck_assert_int_eq(tlat_params->timerlat_period_us, 200);
47 }
48 END_TEST
49 
50 START_TEST(test_period_long)
51 {
52 	PARSE_ARGS("timerlat", "top", "--period", "200");
53 
54 	ck_assert_int_eq(tlat_params->timerlat_period_us, 200);
55 }
56 END_TEST
57 
58 START_TEST(test_period_unset_short)
59 {
60 	PARSE_ARGS("timerlat", "top", "-p", "200", "--no-period");
61 
62 	ck_assert_int_eq(tlat_params->timerlat_period_us, 0);
63 }
64 END_TEST
65 
66 START_TEST(test_period_unset_long)
67 {
68 	PARSE_ARGS("timerlat", "top", "--period", "200", "--no-period");
69 
70 	ck_assert_int_eq(tlat_params->timerlat_period_us, 0);
71 }
72 END_TEST
73 
74 START_TEST(test_stack_short)
75 {
76 	PARSE_ARGS("timerlat", "top", "-s", "20");
77 
78 	ck_assert_int_eq(tlat_params->print_stack, 20);
79 }
80 END_TEST
81 
82 START_TEST(test_stack_long)
83 {
84 	PARSE_ARGS("timerlat", "top", "--stack", "20");
85 
86 	ck_assert_int_eq(tlat_params->print_stack, 20);
87 }
88 END_TEST
89 
90 START_TEST(test_thread_short)
91 {
92 	PARSE_ARGS("timerlat", "top", "-T", "20");
93 
94 	ck_assert_int_eq(params->stop_total_us, 20);
95 }
96 END_TEST
97 
98 START_TEST(test_thread_long)
99 {
100 	PARSE_ARGS("timerlat", "top", "--thread", "20");
101 
102 	ck_assert_int_eq(params->stop_total_us, 20);
103 }
104 END_TEST
105 
106 /* Event Configuration */
107 
108 START_TEST(test_event_short)
109 {
110 	PARSE_ARGS("timerlat", "top", "-e", "system:event");
111 
112 	CLI_ASSERT_SINGLE_EVENT("system", "event");
113 }
114 END_TEST
115 
116 START_TEST(test_event_long)
117 {
118 	PARSE_ARGS("timerlat", "top", "--event", "system:event");
119 
120 	CLI_ASSERT_SINGLE_EVENT("system", "event");
121 }
122 END_TEST
123 
124 START_TEST(test_filter)
125 {
126 	PARSE_ARGS("timerlat", "top", "-e", "system:event", "--filter", "filter");
127 
128 	CLI_ASSERT_SINGLE_FILTER("filter");
129 }
130 END_TEST
131 
132 START_TEST(test_trigger)
133 {
134 	PARSE_ARGS("timerlat", "top", "-e", "system:event", "--trigger", "trigger");
135 
136 	CLI_ASSERT_SINGLE_TRIGGER("trigger");
137 }
138 END_TEST
139 
140 START_TEST(test_trace_short_noarg)
141 {
142 	PARSE_ARGS("timerlat", "top", "-t");
143 
144 	CLI_ASSERT_SINGLE_ACTION(threshold_actions, ACTION_TRACE_OUTPUT, trace_output, str,
145 				 "timerlat_trace.txt");
146 }
147 END_TEST
148 
149 START_TEST(test_trace_short_followarg)
150 {
151 	PARSE_ARGS("timerlat", "top", "-t", "-d", "20");
152 
153 	CLI_ASSERT_SINGLE_ACTION(threshold_actions, ACTION_TRACE_OUTPUT, trace_output, str,
154 				 "timerlat_trace.txt");
155 	ck_assert_int_eq(params->duration, 20); /* check if next argument is read correctly */
156 }
157 END_TEST
158 
159 START_TEST(test_trace_short_space)
160 {
161 	PARSE_ARGS("timerlat", "top", "-t", "tracefile");
162 
163 	CLI_ASSERT_SINGLE_ACTION(threshold_actions, ACTION_TRACE_OUTPUT, trace_output, str,
164 				 "tracefile");
165 }
166 END_TEST
167 
168 START_TEST(test_trace_short_equals)
169 {
170 	PARSE_ARGS("timerlat", "top", "-t=tracefile");
171 
172 	CLI_ASSERT_SINGLE_ACTION(threshold_actions, ACTION_TRACE_OUTPUT, trace_output, str,
173 				 "tracefile");
174 }
175 END_TEST
176 
177 START_TEST(test_trace_long_noarg)
178 {
179 	PARSE_ARGS("timerlat", "top", "--trace");
180 
181 	CLI_ASSERT_SINGLE_ACTION(threshold_actions, ACTION_TRACE_OUTPUT, trace_output, str,
182 				 "timerlat_trace.txt");
183 }
184 END_TEST
185 
186 START_TEST(test_trace_long_followarg)
187 {
188 	PARSE_ARGS("timerlat", "top", "--trace", "-d", "20");
189 
190 	CLI_ASSERT_SINGLE_ACTION(threshold_actions, ACTION_TRACE_OUTPUT, trace_output, str,
191 				 "timerlat_trace.txt");
192 	ck_assert_int_eq(params->duration, 20); /* check if next argument is read correctly */
193 }
194 END_TEST
195 
196 START_TEST(test_trace_long_space)
197 {
198 	PARSE_ARGS("timerlat", "top", "--trace", "tracefile");
199 
200 	CLI_ASSERT_SINGLE_ACTION(threshold_actions, ACTION_TRACE_OUTPUT, trace_output, str,
201 				 "tracefile");
202 }
203 END_TEST
204 
205 START_TEST(test_trace_long_equals)
206 {
207 	PARSE_ARGS("timerlat", "top", "--trace=tracefile");
208 
209 	CLI_ASSERT_SINGLE_ACTION(threshold_actions, ACTION_TRACE_OUTPUT, trace_output, str,
210 				 "tracefile");
211 }
212 END_TEST
213 
214 /* CPU Configuration */
215 
216 START_TEST(test_cpus_short)
217 {
218 	nr_cpus = 4;
219 
220 	PARSE_ARGS("timerlat", "top", "-c", "0-1,3");
221 
222 	ck_assert_str_eq(params->cpus, "0-1,3");
223 	CLI_ASSERT_CPUSET(monitored_cpus, 0, 1, 3);
224 }
225 END_TEST
226 
227 START_TEST(test_cpus_long)
228 {
229 	nr_cpus = 4;
230 
231 	PARSE_ARGS("timerlat", "top", "--cpus", "0-1,3");
232 
233 	ck_assert_str_eq(params->cpus, "0-1,3");
234 	CLI_ASSERT_CPUSET(monitored_cpus, 0, 1, 3);
235 }
236 END_TEST
237 
238 START_TEST(test_housekeeping_short)
239 {
240 	nr_cpus = 4;
241 
242 	PARSE_ARGS("timerlat", "top", "-H", "0-1,3");
243 
244 	CLI_ASSERT_CPUSET(hk_cpu_set, 0, 1, 3);
245 }
246 END_TEST
247 
248 START_TEST(test_housekeeping_long)
249 {
250 	nr_cpus = 4;
251 
252 	PARSE_ARGS("timerlat", "top", "--house-keeping", "0-1,3");
253 
254 	CLI_ASSERT_CPUSET(hk_cpu_set, 0, 1, 3);
255 }
256 END_TEST
257 
258 /* Thread Configuration */
259 
260 START_TEST(test_cgroup_short_noarg)
261 {
262 	PARSE_ARGS("timerlat", "top", "-C");
263 
264 	ck_assert(params->cgroup);
265 	ck_assert_ptr_null(params->cgroup_name);
266 }
267 END_TEST
268 
269 START_TEST(test_cgroup_short_space)
270 {
271 	PARSE_ARGS("timerlat", "top", "-C", "cgroup");
272 
273 	ck_assert(params->cgroup);
274 	ck_assert_str_eq(params->cgroup_name, "cgroup");
275 }
276 END_TEST
277 
278 START_TEST(test_cgroup_short_equals)
279 {
280 	PARSE_ARGS("timerlat", "top", "-C=cgroup");
281 
282 	ck_assert(params->cgroup);
283 	ck_assert_str_eq(params->cgroup_name, "cgroup");
284 }
285 END_TEST
286 
287 START_TEST(test_cgroup_long_noarg)
288 {
289 	PARSE_ARGS("timerlat", "top", "--cgroup");
290 
291 	ck_assert(params->cgroup);
292 	ck_assert_ptr_null(params->cgroup_name);
293 }
294 END_TEST
295 
296 START_TEST(test_cgroup_long_space)
297 {
298 	PARSE_ARGS("timerlat", "top", "--cgroup", "cgroup");
299 
300 	ck_assert(params->cgroup);
301 	ck_assert_str_eq(params->cgroup_name, "cgroup");
302 }
303 END_TEST
304 
305 START_TEST(test_cgroup_long_equals)
306 {
307 	PARSE_ARGS("timerlat", "top", "--cgroup=cgroup");
308 
309 	ck_assert(params->cgroup);
310 	ck_assert_str_eq(params->cgroup_name, "cgroup");
311 }
312 END_TEST
313 
314 START_TEST(test_kernel_threads_short)
315 {
316 	PARSE_ARGS("timerlat", "top", "-k");
317 
318 	ck_assert(params->kernel_workload);
319 	ck_assert(!params->user_workload);
320 	ck_assert(!params->user_data);
321 }
322 END_TEST
323 
324 START_TEST(test_kernel_threads_long)
325 {
326 	PARSE_ARGS("timerlat", "top", "--kernel-threads");
327 
328 	ck_assert(params->kernel_workload);
329 	ck_assert(!params->user_workload);
330 	ck_assert(!params->user_data);
331 }
332 END_TEST
333 
334 START_TEST(test_priority_short)
335 {
336 	PARSE_ARGS("timerlat", "top", "-P", "f:95");
337 
338 	ck_assert_int_eq(params->sched_param.sched_policy, SCHED_FIFO);
339 	ck_assert_int_eq(params->sched_param.sched_priority, 95);
340 }
341 END_TEST
342 
343 START_TEST(test_priority_long)
344 {
345 	PARSE_ARGS("timerlat", "top", "--priority", "f:95");
346 
347 	ck_assert_int_eq(params->sched_param.sched_policy, SCHED_FIFO);
348 	ck_assert_int_eq(params->sched_param.sched_priority, 95);
349 }
350 END_TEST
351 
352 START_TEST(test_user_load_short)
353 {
354 	PARSE_ARGS("timerlat", "top", "-U");
355 
356 	ck_assert(!params->kernel_workload);
357 	ck_assert(!params->user_workload);
358 	ck_assert(params->user_data);
359 }
360 END_TEST
361 
362 START_TEST(test_user_load_long)
363 {
364 	PARSE_ARGS("timerlat", "top", "--user-load");
365 
366 	ck_assert(!params->kernel_workload);
367 	ck_assert(!params->user_workload);
368 	ck_assert(params->user_data);
369 }
370 END_TEST
371 
372 START_TEST(test_user_threads_short)
373 {
374 	PARSE_ARGS("timerlat", "top", "-u");
375 
376 	ck_assert(!params->kernel_workload);
377 	ck_assert(params->user_workload);
378 	ck_assert(params->user_data);
379 }
380 END_TEST
381 
382 START_TEST(test_user_threads_long)
383 {
384 	PARSE_ARGS("timerlat", "top", "--user-threads");
385 
386 	ck_assert(!params->kernel_workload);
387 	ck_assert(params->user_workload);
388 	ck_assert(params->user_data);
389 }
390 END_TEST
391 
392 START_TEST(test_aligned_short)
393 {
394 	PARSE_ARGS("timerlat", "top", "-A", "500");
395 
396 	ck_assert(tlat_params->timerlat_align);
397 	ck_assert_int_eq(tlat_params->timerlat_align_us, 500);
398 }
399 END_TEST
400 
401 START_TEST(test_aligned_long)
402 {
403 	PARSE_ARGS("timerlat", "top", "--aligned", "500");
404 
405 	ck_assert(tlat_params->timerlat_align);
406 	ck_assert_int_eq(tlat_params->timerlat_align_us, 500);
407 }
408 END_TEST
409 
410 /* Output */
411 
412 START_TEST(test_nano_short)
413 {
414 	PARSE_ARGS("timerlat", "top", "-n");
415 
416 	ck_assert_int_eq(params->output_divisor, 1);
417 }
418 END_TEST
419 
420 START_TEST(test_nano_long)
421 {
422 	PARSE_ARGS("timerlat", "top", "--nano");
423 
424 	ck_assert_int_eq(params->output_divisor, 1);
425 }
426 END_TEST
427 
428 START_TEST(test_quiet_short)
429 {
430 	PARSE_ARGS("timerlat", "top", "-q");
431 
432 	ck_assert(params->quiet);
433 }
434 END_TEST
435 
436 START_TEST(test_quiet_long)
437 {
438 	PARSE_ARGS("timerlat", "top", "--quiet");
439 
440 	ck_assert(params->quiet);
441 }
442 END_TEST
443 
444 /* System Tuning */
445 
446 START_TEST(test_deepest_idle_state)
447 {
448 	PARSE_ARGS("timerlat", "top", "--deepest-idle-state", "1");
449 
450 	ck_assert_int_eq(tlat_params->deepest_idle_state, 1);
451 }
452 END_TEST
453 
454 START_TEST(test_dma_latency)
455 {
456 	PARSE_ARGS("timerlat", "top", "--dma-latency", "10");
457 
458 	ck_assert_int_eq(tlat_params->dma_latency, 10);
459 }
460 END_TEST
461 
462 START_TEST(test_trace_buffer_size)
463 {
464 	PARSE_ARGS("timerlat", "top", "--trace-buffer-size", "200");
465 
466 	ck_assert_int_eq(params->buffer_size, 200);
467 }
468 END_TEST
469 
470 START_TEST(test_warm_up)
471 {
472 	PARSE_ARGS("timerlat", "top", "--warm-up", "5");
473 
474 	ck_assert_int_eq(params->warmup, 5);
475 }
476 END_TEST
477 
478 /* Auto Analysis and Actions */
479 
480 START_TEST(test_auto)
481 {
482 	PARSE_ARGS("timerlat", "top", "-a", "20");
483 
484 	CLI_TIMERLAT_ASSERT_AUTO(20);
485 }
486 END_TEST
487 
488 START_TEST(test_aa_only)
489 {
490 	PARSE_ARGS("timerlat", "top", "--aa-only", "20");
491 
492 	CLI_TIMERLAT_ASSERT_AA_ONLY(20);
493 }
494 END_TEST
495 
496 START_TEST(test_bpf_action)
497 {
498 	PARSE_ARGS("timerlat", "top", "--bpf-action", "program");
499 
500 	ck_assert_str_eq(tlat_params->bpf_action_program, "program");
501 }
502 END_TEST
503 
504 START_TEST(test_dump_tasks)
505 {
506 	PARSE_ARGS("timerlat", "top", "--dump-tasks");
507 
508 	ck_assert(tlat_params->dump_tasks);
509 }
510 END_TEST
511 
512 START_TEST(test_no_aa)
513 {
514 	PARSE_ARGS("timerlat", "top", "--no-aa");
515 
516 	ck_assert(tlat_params->no_aa);
517 }
518 END_TEST
519 
520 START_TEST(test_on_end)
521 {
522 	PARSE_ARGS("timerlat", "top", "--on-end", "trace");
523 
524 	CLI_ASSERT_SINGLE_ACTION(end_actions, ACTION_TRACE_OUTPUT, trace_output, str,
525 				 "timerlat_trace.txt");
526 }
527 END_TEST
528 
529 START_TEST(test_on_threshold)
530 {
531 	PARSE_ARGS("timerlat", "top", "--on-threshold", "trace");
532 
533 	CLI_ASSERT_SINGLE_ACTION(threshold_actions, ACTION_TRACE_OUTPUT, trace_output, str,
534 				 "timerlat_trace.txt");
535 }
536 END_TEST
537 
538 START_TEST(test_stack_format)
539 {
540 	PARSE_ARGS("timerlat", "top", "--stack-format", "truncate");
541 
542 	ck_assert_int_eq(tlat_params->stack_format, STACK_FORMAT_TRUNCATE);
543 }
544 END_TEST
545 
546 /* General */
547 
548 START_TEST(test_debug_short)
549 {
550 	PARSE_ARGS("timerlat", "top", "-D");
551 
552 	ck_assert(config_debug);
553 }
554 END_TEST
555 
556 START_TEST(test_debug_long)
557 {
558 	PARSE_ARGS("timerlat", "top", "--debug");
559 
560 	ck_assert(config_debug);
561 }
562 END_TEST
563 
564 START_TEST(test_duration_short)
565 {
566 	PARSE_ARGS("timerlat", "top", "-d", "1m");
567 
568 	ck_assert_int_eq(params->duration, 60);
569 }
570 END_TEST
571 
572 START_TEST(test_duration_long)
573 {
574 	PARSE_ARGS("timerlat", "top", "--duration", "1m");
575 
576 	ck_assert_int_eq(params->duration, 60);
577 }
578 END_TEST
579 
580 Suite *timerlat_top_cli_suite(void)
581 {
582 	Suite *s = suite_create("timerlat_top_cli");
583 	TCase *tc;
584 
585 	tc = tcase_create("tracing_options");
586 	tcase_add_test(tc, test_irq_short);
587 	tcase_add_test(tc, test_irq_long);
588 	tcase_add_test(tc, test_period_short);
589 	tcase_add_test(tc, test_period_long);
590 	tcase_add_test(tc, test_period_unset_short);
591 	tcase_add_test(tc, test_period_unset_long);
592 	tcase_add_test(tc, test_stack_short);
593 	tcase_add_test(tc, test_stack_long);
594 	tcase_add_test(tc, test_thread_short);
595 	tcase_add_test(tc, test_thread_long);
596 	tcase_add_test(tc, test_trace_short_noarg);
597 	tcase_add_test(tc, test_trace_short_followarg);
598 	tcase_add_test(tc, test_trace_short_space);
599 	tcase_add_test(tc, test_trace_short_equals);
600 	tcase_add_test(tc, test_trace_long_noarg);
601 	tcase_add_test(tc, test_trace_long_followarg);
602 	tcase_add_test(tc, test_trace_long_space);
603 	tcase_add_test(tc, test_trace_long_equals);
604 	suite_add_tcase(s, tc);
605 
606 	tc = tcase_create("event_configuration");
607 	tcase_add_test(tc, test_event_short);
608 	tcase_add_test(tc, test_event_long);
609 	tcase_add_test(tc, test_filter);
610 	tcase_add_test(tc, test_trigger);
611 	suite_add_tcase(s, tc);
612 
613 	tc = tcase_create("cpu_configuration");
614 	tcase_add_test(tc, test_cpus_short);
615 	tcase_add_test(tc, test_cpus_long);
616 	tcase_add_test(tc, test_housekeeping_short);
617 	tcase_add_test(tc, test_housekeeping_long);
618 	suite_add_tcase(s, tc);
619 
620 	tc = tcase_create("thread_configuration");
621 	tcase_add_test(tc, test_cgroup_short_noarg);
622 	tcase_add_test(tc, test_cgroup_short_space);
623 	tcase_add_test(tc, test_cgroup_short_equals);
624 	tcase_add_test(tc, test_cgroup_long_noarg);
625 	tcase_add_test(tc, test_cgroup_long_space);
626 	tcase_add_test(tc, test_cgroup_long_equals);
627 	tcase_add_test(tc, test_kernel_threads_short);
628 	tcase_add_test(tc, test_kernel_threads_long);
629 	tcase_add_test(tc, test_priority_short);
630 	tcase_add_test(tc, test_priority_long);
631 	tcase_add_test(tc, test_user_load_short);
632 	tcase_add_test(tc, test_user_load_long);
633 	tcase_add_test(tc, test_user_threads_short);
634 	tcase_add_test(tc, test_user_threads_long);
635 	tcase_add_test(tc, test_aligned_short);
636 	tcase_add_test(tc, test_aligned_long);
637 	suite_add_tcase(s, tc);
638 
639 	tc = tcase_create("output");
640 	tcase_add_test(tc, test_nano_short);
641 	tcase_add_test(tc, test_nano_long);
642 	tcase_add_test(tc, test_quiet_short);
643 	tcase_add_test(tc, test_quiet_long);
644 	suite_add_tcase(s, tc);
645 
646 	tc = tcase_create("system_tuning");
647 	tcase_add_test(tc, test_deepest_idle_state);
648 	tcase_add_test(tc, test_dma_latency);
649 	tcase_add_test(tc, test_trace_buffer_size);
650 	tcase_add_test(tc, test_warm_up);
651 	suite_add_tcase(s, tc);
652 
653 	tc = tcase_create("aa_actions");
654 	tcase_add_test(tc, test_auto);
655 	tcase_add_test(tc, test_aa_only);
656 	tcase_add_test(tc, test_bpf_action);
657 	tcase_add_test(tc, test_dump_tasks);
658 	tcase_add_test(tc, test_no_aa);
659 	tcase_add_test(tc, test_on_end);
660 	tcase_add_test(tc, test_on_threshold);
661 	tcase_add_test(tc, test_stack_format);
662 	suite_add_tcase(s, tc);
663 
664 	tc = tcase_create("general");
665 	tcase_add_test(tc, test_debug_short);
666 	tcase_add_test(tc, test_debug_long);
667 	tcase_add_test(tc, test_duration_short);
668 	tcase_add_test(tc, test_duration_long);
669 	suite_add_tcase(s, tc);
670 
671 	return s;
672 }
673