File indexing completed on 2025-05-11 08:24:18
0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025
0026
0027
0028
0029
0030
0031
0032
0033
0034
0035
0036
0037
0038
0039
0040
0041 #ifdef HAVE_CONFIG_H
0042 #include "config.h"
0043 #endif
0044
0045 #include <ctype.h>
0046 #include <stdlib.h>
0047 #include <stdio.h>
0048 #include <string.h>
0049 #include <inttypes.h>
0050
0051 #include <rtems.h>
0052 #include <rtems/capture-cli.h>
0053 #include <rtems/captureimpl.h>
0054 #include <rtems/monitor.h>
0055 #include <rtems/cpuuse.h>
0056 #
0057 #define RC_UNUSED RTEMS_UNUSED
0058
0059 #define RTEMS_CAPTURE_CLI_MAX_LOAD_TASKS (20)
0060
0061
0062
0063
0064 static rtems_capture_timestamp capture_timestamp;
0065
0066
0067
0068
0069
0070
0071
0072
0073 static const char* open_usage = "usage: copen [-i] size\n";
0074
0075 static void
0076 rtems_capture_cli_open (int argc,
0077 char** argv,
0078 const rtems_monitor_command_arg_t* command_arg RC_UNUSED,
0079 bool verbose RC_UNUSED)
0080 {
0081 uint32_t size = 0;
0082 bool enable = false;
0083 rtems_status_code sc;
0084 int arg;
0085
0086 if (argc <= 1)
0087 {
0088 fprintf (stdout, open_usage);
0089 return;
0090 }
0091
0092 for (arg = 1; arg < argc; arg++)
0093 {
0094 if (argv[arg][0] == '-')
0095 {
0096 if (argv[arg][1] == 'i')
0097 enable = true;
0098 else
0099 fprintf (stdout, "warning: option -%c ignored\n", argv[arg][1]);
0100 }
0101 else
0102 {
0103 size = strtoul (argv[arg], 0, 0);
0104
0105 if (size < 100)
0106 {
0107 fprintf (stdout, "error: size must be greater than or equal to 100\n");
0108 return;
0109 }
0110 }
0111 }
0112
0113 sc = rtems_capture_open (size, capture_timestamp);
0114
0115 if (sc != RTEMS_SUCCESSFUL)
0116 {
0117 fprintf (stdout, "error: open failed: %s\n", rtems_status_text (sc));
0118 return;
0119 }
0120
0121 fprintf (stdout, "capture engine opened.\n");
0122
0123 if (!enable)
0124 return;
0125
0126 sc = rtems_capture_set_control (enable);
0127
0128 if (sc != RTEMS_SUCCESSFUL)
0129 {
0130 fprintf (stdout, "error: open enable failed: %s\n", rtems_status_text (sc));
0131 return;
0132 }
0133
0134 fprintf (stdout, "capture engine enabled.\n");
0135 }
0136
0137
0138
0139
0140
0141
0142
0143 static void
0144 rtems_capture_cli_close (int argc RC_UNUSED,
0145 char** argv RC_UNUSED,
0146 const rtems_monitor_command_arg_t* command_arg RC_UNUSED,
0147 bool verbose RC_UNUSED)
0148 {
0149 rtems_status_code sc;
0150
0151 sc = rtems_capture_close ();
0152
0153 if (sc != RTEMS_SUCCESSFUL)
0154 {
0155 fprintf (stdout, "error: close failed: %s\n", rtems_status_text (sc));
0156 return;
0157 }
0158
0159 fprintf (stdout, "capture engine closed.\n");
0160 }
0161
0162
0163
0164
0165
0166
0167
0168 static void
0169 rtems_capture_cli_enable (int argc RC_UNUSED,
0170 char** argv RC_UNUSED,
0171 const rtems_monitor_command_arg_t* command_arg RC_UNUSED,
0172 bool verbose RC_UNUSED)
0173 {
0174 rtems_status_code sc;
0175
0176 sc = rtems_capture_set_control (true);
0177
0178 if (sc != RTEMS_SUCCESSFUL)
0179 {
0180 fprintf (stdout, "error: enable failed: %s\n", rtems_status_text (sc));
0181 return;
0182 }
0183
0184 fprintf (stdout, "capture engine enabled.\n");
0185 }
0186
0187
0188
0189
0190
0191
0192
0193 static void
0194 rtems_capture_cli_disable (int argc RC_UNUSED,
0195 char** argv RC_UNUSED,
0196 const rtems_monitor_command_arg_t* command_arg RC_UNUSED,
0197 bool verbose RC_UNUSED)
0198 {
0199 rtems_status_code sc;
0200
0201 sc = rtems_capture_set_control (false);
0202
0203 if (sc != RTEMS_SUCCESSFUL)
0204 {
0205 fprintf (stdout, "error: disable failed: %s\n", rtems_status_text (sc));
0206 return;
0207 }
0208
0209 fprintf (stdout, "capture engine disabled.\n");
0210 }
0211
0212 static bool
0213 rtems_capture_cli_print_task (rtems_tcb *tcb, void *arg)
0214 {
0215 rtems_task_priority ceiling = rtems_capture_watch_get_ceiling ();
0216 rtems_task_priority floor = rtems_capture_watch_get_floor ();
0217 rtems_task_priority priority;
0218 int length;
0219 uint32_t flags = rtems_capture_task_control_flags (tcb);
0220
0221 priority = rtems_capture_task_real_priority (tcb);
0222
0223 fprintf (stdout, " ");
0224 rtems_monitor_dump_id (rtems_capture_task_id (tcb));
0225 fprintf (stdout, " ");
0226 if (rtems_capture_task_api (rtems_capture_task_id (tcb)) != OBJECTS_POSIX_API)
0227 {
0228 rtems_monitor_dump_name (rtems_capture_task_id (tcb));
0229 fprintf (stdout, " ");
0230 }
0231 else
0232 {
0233 fprintf (stdout, " ");
0234 }
0235 rtems_monitor_dump_priority (rtems_capture_task_start_priority (tcb));
0236 fprintf (stdout, " ");
0237 rtems_monitor_dump_priority (rtems_capture_task_real_priority (tcb));
0238 fprintf (stdout, " ");
0239 rtems_monitor_dump_priority (rtems_capture_task_curr_priority (tcb));
0240 fprintf (stdout, " ");
0241 length = rtems_monitor_dump_state (rtems_capture_task_state (tcb));
0242 fprintf (stdout, "%*c", 14 - length, ' ');
0243 fprintf (stdout, " %c%c",
0244 'a',
0245 flags & RTEMS_CAPTURE_TRACED ? 't' : '-');
0246
0247 if ((floor > ceiling) && (ceiling > priority))
0248 fprintf (stdout, "--");
0249 else
0250 {
0251 fprintf (stdout, "%c%c",
0252 rtems_capture_task_control (tcb) ?
0253 (flags & RTEMS_CAPTURE_WATCH ? 'w' : '+') : '-',
0254 rtems_capture_watch_global_on () ? 'g' : '-');
0255 }
0256 fprintf (stdout, "\n");
0257 return false;
0258 }
0259
0260
0261
0262
0263
0264
0265
0266
0267 static bool
0268 rtems_capture_cli_count_tasks (rtems_tcb *tcb, void *arg)
0269 {
0270 uint32_t *task_count = arg;
0271 ++(*task_count);
0272 return false;
0273 }
0274
0275
0276
0277
0278
0279
0280
0281
0282 static void
0283 rtems_capture_cli_task_list (int argc RC_UNUSED,
0284 char** argv RC_UNUSED,
0285 const rtems_monitor_command_arg_t* command_arg RC_UNUSED,
0286 bool verbose RC_UNUSED)
0287 {
0288 rtems_capture_time uptime;
0289 uint32_t task_count;
0290
0291 rtems_capture_get_time (&uptime);
0292
0293 task_count = 0;
0294 rtems_task_iterate (rtems_capture_cli_count_tasks, &task_count);
0295
0296 fprintf (stdout, "uptime: ");
0297 rtems_capture_print_timestamp (uptime);
0298 fprintf (stdout, "\ntotal %" PRIu32 "\n", task_count);
0299 rtems_task_iterate (rtems_capture_cli_print_task, NULL);
0300 }
0301
0302
0303
0304
0305
0306
0307
0308 static void
0309 rtems_capture_cli_watch_list (int argc RC_UNUSED,
0310 char** argv RC_UNUSED,
0311 const rtems_monitor_command_arg_t* command_arg RC_UNUSED,
0312 bool verbose RC_UNUSED)
0313 {
0314 rtems_capture_print_watch_list();
0315 }
0316
0317
0318
0319
0320
0321
0322
0323 static bool
0324 rtems_capture_cli_get_name_id (char* arg,
0325 bool* valid_name,
0326 bool* valid_id,
0327 rtems_name* name,
0328 rtems_id* id)
0329 {
0330 size_t l;
0331 size_t i;
0332
0333 if (*valid_name && *valid_id)
0334 {
0335 fprintf (stdout, "error: too many arguments\n");
0336 return 0;
0337 }
0338
0339
0340
0341
0342
0343 l = strlen (arg);
0344
0345 for (i = 0; i < l; i++)
0346 if (!isxdigit ((unsigned char)arg[i]))
0347 break;
0348
0349 if (i == l)
0350 {
0351 *id = strtoul (arg, 0, 16);
0352 *valid_id = true;
0353 }
0354 else
0355 {
0356
0357
0358
0359
0360
0361
0362
0363 rtems_name rname;
0364
0365 rname = rtems_build_name(arg[0], arg[1], arg[2], arg[3]);
0366 *name = rname;
0367 *valid_name = true;
0368 }
0369
0370 return 1;
0371 }
0372
0373
0374
0375
0376
0377
0378
0379
0380 static char const * watch_add_usage = "usage: cwadd [task name] [id]\n";
0381
0382 static void
0383 rtems_capture_cli_watch_add (int argc,
0384 char** argv,
0385 const rtems_monitor_command_arg_t* command_arg RC_UNUSED,
0386 bool verbose RC_UNUSED)
0387 {
0388 rtems_status_code sc;
0389 int arg;
0390 rtems_name name = 0;
0391 rtems_id id = 0;
0392 bool valid_name = false;
0393 bool valid_id = false;
0394
0395 if (argc <= 1)
0396 {
0397 fprintf (stdout, watch_add_usage);
0398 return;
0399 }
0400
0401 for (arg = 1; arg < argc; arg++)
0402 {
0403 if (argv[arg][0] == '-')
0404 {
0405 fprintf (stdout, "warning: option -%c ignored\n", argv[arg][1]);
0406 }
0407 else
0408 {
0409 if (!rtems_capture_cli_get_name_id (argv[arg], &valid_name, &valid_id,
0410 &name, &id))
0411 return;
0412 }
0413 }
0414
0415 if (!valid_name && !valid_id)
0416 {
0417 fprintf (stdout, "error: no valid name or task id located\n");
0418 return;
0419 }
0420
0421 sc = rtems_capture_watch_add (name, id);
0422
0423 if (sc != RTEMS_SUCCESSFUL)
0424 {
0425 fprintf (stdout,
0426 "error: watch add failed: %s\n", rtems_status_text (sc));
0427 return;
0428 }
0429
0430 fprintf (stdout, "watch added.\n");
0431 }
0432
0433
0434
0435
0436
0437
0438
0439
0440 static char const * watch_del_usage = "usage: cwdel [task name] [id]\n";
0441
0442 static void
0443 rtems_capture_cli_watch_del (int argc,
0444 char** argv,
0445 const rtems_monitor_command_arg_t* command_arg RC_UNUSED,
0446 bool verbose RC_UNUSED)
0447 {
0448 rtems_status_code sc;
0449 int arg;
0450 rtems_name name = 0;
0451 rtems_id id = 0;
0452 bool valid_name = false;
0453 bool valid_id = false;
0454
0455 if (argc <= 1)
0456 {
0457 fprintf (stdout, watch_del_usage);
0458 return;
0459 }
0460
0461 for (arg = 1; arg < argc; arg++)
0462 {
0463 if (argv[arg][0] == '-')
0464 {
0465 fprintf (stdout, "warning: option -%c ignored\n", argv[arg][1]);
0466 }
0467 else
0468 {
0469 if (!rtems_capture_cli_get_name_id (argv[arg], &valid_name, &valid_id,
0470 &name, &id))
0471 return;
0472 }
0473 }
0474
0475 if (!valid_name && !valid_id)
0476 {
0477 fprintf (stdout, "error: no valid name or task id located\n");
0478 return;
0479 }
0480
0481 sc = rtems_capture_watch_del (name, id);
0482
0483 if (sc != RTEMS_SUCCESSFUL)
0484 {
0485 fprintf (stdout, "error: watch delete failed: %s\n",
0486 rtems_status_text (sc));
0487 return;
0488 }
0489
0490 fprintf (stdout, "watch delete.\n");
0491 }
0492
0493
0494
0495
0496
0497
0498
0499 static char const * watch_control_usage = "usage: cwctl [task name] [id] on/off\n";
0500
0501 static void
0502 rtems_capture_cli_watch_control (int argc,
0503 char** argv,
0504 const rtems_monitor_command_arg_t* command_arg RC_UNUSED,
0505 bool verbose RC_UNUSED)
0506 {
0507 rtems_status_code sc;
0508 int arg;
0509 rtems_name name = 0;
0510 rtems_id id = 0;
0511 bool valid_name = false;
0512 bool valid_id = false;
0513 bool enable = false;
0514
0515 if (argc <= 2)
0516 {
0517 fprintf (stdout, watch_control_usage);
0518 return;
0519 }
0520
0521 for (arg = 1; arg < argc; arg++)
0522 {
0523 if (argv[arg][0] == '-')
0524 {
0525 fprintf (stdout, "warning: option -%c ignored\n", argv[arg][1]);
0526 }
0527 else
0528 {
0529 if (strcmp (argv[arg], "on") == 0)
0530 enable = true;
0531 else if (strcmp (argv[arg], "off") == 0)
0532 enable = false;
0533 else if (!rtems_capture_cli_get_name_id (argv[arg], &valid_name,
0534 &valid_id, &name, &id))
0535 return;
0536 }
0537 }
0538
0539 if (!valid_name && !valid_id)
0540 {
0541 fprintf (stdout, "error: no valid name or task id located\n");
0542 return;
0543 }
0544
0545 sc = rtems_capture_watch_ctrl (name, id, enable);
0546
0547 if (sc != RTEMS_SUCCESSFUL)
0548 {
0549 fprintf (stdout, "error: watch control failed: %s\n",
0550 rtems_status_text (sc));
0551 return;
0552 }
0553
0554 fprintf (stdout, "watch %s.\n", enable ? "enabled" : "disabled");
0555 }
0556
0557
0558
0559
0560
0561
0562
0563 static char const * watch_global_usage = "usage: cwglob on/off\n";
0564
0565 static void
0566 rtems_capture_cli_watch_global (int argc,
0567 char** argv,
0568 const rtems_monitor_command_arg_t* command_arg RC_UNUSED,
0569 bool verbose RC_UNUSED)
0570 {
0571 rtems_status_code sc;
0572 int arg;
0573 bool enable = false;
0574
0575 if (argc <= 1)
0576 {
0577 fprintf (stdout, watch_global_usage);
0578 return;
0579 }
0580
0581 for (arg = 1; arg < argc; arg++)
0582 {
0583 if (argv[arg][0] == '-')
0584 {
0585 fprintf (stdout, "warning: option -%c ignored\n", argv[arg][1]);
0586 }
0587 else
0588 {
0589 if (strcmp (argv[arg], "on") == 0)
0590 enable = true;
0591 else if (strcmp (argv[arg], "off") == 0)
0592 enable = false;
0593 }
0594 }
0595
0596 sc = rtems_capture_watch_global (enable);
0597
0598 if (sc != RTEMS_SUCCESSFUL)
0599 {
0600 fprintf (stdout, "error: global watch failed: %s\n",
0601 rtems_status_text (sc));
0602 return;
0603 }
0604
0605 fprintf (stdout, "global watch %s.\n", enable ? "enabled" : "disabled");
0606 }
0607
0608
0609
0610
0611
0612
0613
0614 static char const * watch_ceiling_usage = "usage: cwceil priority\n";
0615
0616 static void
0617 rtems_capture_cli_watch_ceiling (int argc,
0618 char** argv,
0619 const rtems_monitor_command_arg_t* command_arg RC_UNUSED,
0620 bool verbose RC_UNUSED)
0621 {
0622 rtems_status_code sc;
0623 int arg;
0624 rtems_task_priority priority = 0;
0625
0626 if (argc <= 1)
0627 {
0628 fprintf (stdout, watch_ceiling_usage);
0629 return;
0630 }
0631
0632 for (arg = 1; arg < argc; arg++)
0633 {
0634 if (argv[arg][0] == '-')
0635 {
0636 fprintf (stdout, "warning: option -%c ignored\n", argv[arg][1]);
0637 }
0638 else
0639 {
0640 priority = strtoul (argv[arg], 0, 0);
0641 }
0642 }
0643
0644 sc = rtems_capture_watch_ceiling (priority);
0645
0646 if (sc != RTEMS_SUCCESSFUL)
0647 {
0648 fprintf (stdout, "error: watch ceiling failed: %s\n",
0649 rtems_status_text (sc));
0650 return;
0651 }
0652
0653 fprintf (stdout, "watch ceiling is %" PRId32 ".\n", priority);
0654 }
0655
0656
0657
0658
0659
0660
0661
0662 static char const * watch_floor_usage = "usage: cwfloor priority\n";
0663
0664 static void
0665 rtems_capture_cli_watch_floor (int argc,
0666 char** argv,
0667 const rtems_monitor_command_arg_t* command_arg RC_UNUSED,
0668 bool verbose RC_UNUSED)
0669 {
0670 rtems_status_code sc;
0671 int arg;
0672 rtems_task_priority priority = 0;
0673
0674 if (argc <= 1)
0675 {
0676 fprintf (stdout, watch_floor_usage);
0677 return;
0678 }
0679
0680 for (arg = 1; arg < argc; arg++)
0681 {
0682 if (argv[arg][0] == '-')
0683 {
0684 fprintf (stdout, "warning: option -%c ignored\n", argv[arg][1]);
0685 }
0686 else
0687 {
0688 priority = strtoul (argv[arg], 0, 0);
0689 }
0690 }
0691
0692 sc = rtems_capture_watch_floor (priority);
0693
0694 if (sc != RTEMS_SUCCESSFUL)
0695 {
0696 fprintf (stdout, "error: watch floor failed: %s\n",
0697 rtems_status_text (sc));
0698 return;
0699 }
0700
0701 fprintf (stdout, "watch floor is %" PRId32 ".\n", priority);
0702 }
0703
0704
0705
0706
0707
0708
0709
0710 static char const *trigger_set_usage =
0711 "usage: %s [-?] type [to name/id] [from] [from name/id]\n";
0712
0713 static char const *trigger_set_types =
0714 " You can say 'type TASK' or 'type TO from FROM'\n" \
0715 " where TASK is the task the event is happening to\n" \
0716 " or you can say the event TO this task FROM this task.\n" \
0717 " No type defaults to 'switch'.\n" \
0718 " switch : context switch TASK or FROM or FROM->TO\n" \
0719 " create : create TASK, or create TO from FROM\n" \
0720 " start : start TASK, or start TO from FROM\n" \
0721 " restart : restart TASK, or restart TO from FROM\n" \
0722 " delete : delete TASK or delete TO from FROM\n" \
0723 " begin : begin TASK\n" \
0724 " exitted : exitted TASK\n";
0725
0726
0727
0728
0729 typedef struct rtems_capture_cli_triggers
0730 {
0731 char const * name;
0732 rtems_capture_trigger type;
0733 int to_only;
0734 } rtems_capture_cli_triggers;
0735
0736 static const rtems_capture_cli_triggers rtems_capture_cli_trigger[] =
0737 {
0738 { "switch", rtems_capture_switch, 0 },
0739 { "create", rtems_capture_create, 0 },
0740 { "start", rtems_capture_start, 0 },
0741 { "restart", rtems_capture_restart, 0 },
0742 { "delete", rtems_capture_delete, 0 },
0743 { "begin", rtems_capture_begin, 1 },
0744 { "exitted", rtems_capture_exitted, 1 }
0745 };
0746
0747 typedef enum rtems_capture_cli_trig_state
0748 {
0749 trig_type,
0750 trig_to,
0751 trig_from_from,
0752 trig_from
0753 } rtems_capture_cli_trig_state;
0754
0755 #define RTEMS_CAPTURE_CLI_TRIGGERS_NUM \
0756 (sizeof (rtems_capture_cli_trigger) / sizeof (rtems_capture_cli_triggers))
0757
0758 static void
0759 rtems_capture_cli_trigger_worker (int set, int argc, char** argv)
0760 {
0761 rtems_status_code sc;
0762 int arg;
0763 int trigger = 0;
0764 rtems_capture_trigger_mode trigger_mode = rtems_capture_from_any;
0765 bool trigger_set = false;
0766 bool is_from = false;
0767 bool is_to = false;
0768 rtems_name name = 0;
0769 rtems_id id = 0;
0770 bool valid_name = false;
0771 bool valid_id = false;
0772 rtems_name from_name = 0;
0773 rtems_id from_id = 0;
0774 bool from_valid_name = false;
0775 bool from_valid_id = false;
0776 rtems_name to_name = 0;
0777 rtems_id to_id = 0;
0778 bool to_valid_name = false;
0779 bool to_valid_id = false;
0780
0781 for (arg = 1; arg < argc; arg++)
0782 {
0783 if (argv[arg][0] == '-')
0784 {
0785 switch (argv[arg][1])
0786 {
0787 case '?':
0788 fprintf (stdout, trigger_set_usage, set ? "ctset" : "ctclear");
0789 fprintf (stdout, trigger_set_types);
0790 return;
0791 default:
0792 fprintf (stdout, "warning: option -%c ignored\n", argv[arg][1]);
0793 break;
0794 }
0795 }
0796 else
0797 {
0798 if (!trigger_set)
0799 {
0800 bool found = false;
0801 int t;
0802
0803 for (t = 0; t < RTEMS_CAPTURE_CLI_TRIGGERS_NUM; t++)
0804 if (strcmp (argv[arg], rtems_capture_cli_trigger[t].name) == 0)
0805 {
0806 trigger = t;
0807 found = true;
0808 break;
0809 }
0810
0811 trigger_set = true;
0812
0813
0814
0815
0816
0817 if (found)
0818 continue;
0819 }
0820
0821 if (strcmp (argv[arg], "from") == 0)
0822 {
0823 if (from_valid_name || from_valid_id)
0824 fprintf (stdout, "warning: extra 'from' ignored\n");
0825
0826 is_from = true;
0827 continue;
0828 }
0829
0830 if (strcmp (argv[arg], "to") == 0)
0831 {
0832 if (to_valid_name || from_valid_id)
0833 fprintf (stdout, "warning: extra 'to' ignored\n");
0834
0835 is_to = true;
0836 continue;
0837 }
0838
0839 if (!rtems_capture_cli_get_name_id (argv[arg], &valid_name, &valid_id,
0840 &name, &id))
0841 return;
0842
0843 if (valid_name)
0844 {
0845 if (!is_from && !is_to)
0846 is_to = true;
0847
0848 if (is_from)
0849 {
0850 if (!from_valid_name && !from_valid_id)
0851 {
0852 from_valid_name = true;
0853 from_name = name;
0854 }
0855 else
0856 fprintf (stdout, "warning: extra name arguments ignored\n");
0857 }
0858 else if (!to_valid_name && !to_valid_id)
0859 {
0860 to_valid_name = true;
0861 to_name = name;
0862 }
0863 else
0864 fprintf (stdout, "warning: extra name arguments ignored\n");
0865 }
0866
0867 if (valid_id)
0868 {
0869 if (!is_from && !is_to)
0870 is_to = true;
0871
0872 if (is_from)
0873 {
0874 if (!from_valid_name && !from_valid_id)
0875 {
0876 from_valid_id = true;
0877 from_id = id;
0878 }
0879 else
0880 fprintf (stdout, "warning: extra id arguments ignored\n");
0881 }
0882 else if (!to_valid_name && !to_valid_id)
0883 {
0884 to_valid_id = true;
0885 to_id = id;
0886 }
0887 else
0888 fprintf (stdout, "warning: extra id arguments ignored\n");
0889 }
0890 }
0891 }
0892
0893 if (is_from && rtems_capture_cli_trigger[trigger].to_only)
0894 {
0895 fprintf (stdout, "error: a %s trigger can be a TO trigger\n",
0896 rtems_capture_cli_trigger[trigger].name);
0897 return;
0898 }
0899
0900 if (!to_valid_name && !to_valid_id && !from_valid_name && !from_valid_id)
0901 {
0902 fprintf (stdout, trigger_set_usage, set ? "ctset" : "ctclear");
0903 return;
0904 }
0905
0906 if (!is_from && !to_valid_name && !to_valid_id)
0907 {
0908 fprintf (stdout, "error: a %s trigger needs a TO name or id\n",
0909 rtems_capture_cli_trigger[trigger].name);
0910 return;
0911 }
0912
0913 if (is_from && !from_valid_name && !from_valid_id)
0914 {
0915 fprintf (stdout, "error: a %s trigger needs a FROM name or id\n",
0916 rtems_capture_cli_trigger[trigger].name);
0917 return;
0918 }
0919
0920 if ((from_valid_name || from_valid_id) && (to_valid_name || to_valid_id))
0921 trigger_mode = rtems_capture_from_to;
0922 else if (from_valid_name || from_valid_id)
0923 trigger_mode = rtems_capture_to_any;
0924 else if (to_valid_name || to_valid_id)
0925 trigger_mode = rtems_capture_from_any;
0926
0927 if (set)
0928 sc = rtems_capture_set_trigger (from_name, from_id, to_name, to_id,
0929 trigger_mode,
0930 rtems_capture_cli_trigger[trigger].type);
0931 else
0932 sc = rtems_capture_clear_trigger (from_name, from_id, to_name, to_id,
0933 trigger_mode,
0934 rtems_capture_cli_trigger[trigger].type);
0935
0936 if (sc != RTEMS_SUCCESSFUL)
0937 {
0938 fprintf (stdout, "error: %sing the trigger failed: %s\n",
0939 set ? "sett" : "clear", rtems_status_text (sc));
0940 return;
0941 }
0942
0943 fprintf (stdout, "trigger %s.\n", set ? "set" : "cleared");
0944 }
0945
0946
0947
0948
0949
0950
0951
0952 static void
0953 rtems_capture_cli_trigger_set (int argc,
0954 char** argv,
0955 const rtems_monitor_command_arg_t* command_arg RC_UNUSED,
0956 bool verbose RC_UNUSED)
0957 {
0958 rtems_capture_cli_trigger_worker (1, argc, argv);
0959 }
0960
0961
0962
0963
0964
0965
0966
0967 static void
0968 rtems_capture_cli_trigger_clear (int argc,
0969 char** argv,
0970 const rtems_monitor_command_arg_t* command_arg RC_UNUSED,
0971 bool verbose RC_UNUSED)
0972 {
0973 rtems_capture_cli_trigger_worker (0, argc, argv);
0974 }
0975
0976
0977
0978
0979
0980
0981
0982 static void
0983 rtems_capture_cli_trace_records (int argc,
0984 char** argv,
0985 const rtems_monitor_command_arg_t* command_arg RC_UNUSED,
0986 bool verbose RC_UNUSED)
0987 {
0988 bool csv = false;
0989 static int dump_total = 22;
0990 int arg;
0991
0992 for (arg = 1; arg < argc; arg++)
0993 {
0994 if (argv[arg][0] == '-')
0995 {
0996 if (argv[arg][1] == 'c')
0997 csv = true;
0998 else
0999 fprintf (stdout, "warning: option -%c ignored\n", argv[arg][1]);
1000 }
1001 else
1002 {
1003 size_t i;
1004 size_t l;
1005
1006 l = strlen (argv[arg]);
1007
1008 for (i = 0; i < l; i++)
1009 if (!isdigit ((unsigned char)argv[arg][i]))
1010 {
1011 fprintf (stdout, "error: not a number\n");
1012 return;
1013 }
1014
1015 dump_total = strtoul (argv[arg], 0, 0);
1016 }
1017 }
1018
1019 rtems_capture_print_trace_records( dump_total, csv );
1020 }
1021
1022
1023
1024
1025
1026
1027
1028
1029 static void
1030 rtems_capture_cli_flush (int argc,
1031 char** argv,
1032 const rtems_monitor_command_arg_t* command_arg RC_UNUSED,
1033 bool verbose RC_UNUSED)
1034 {
1035 rtems_status_code sc;
1036 bool prime = true;
1037 int arg;
1038
1039 for (arg = 1; arg < argc; arg++)
1040 {
1041 if (argv[arg][0] == '-')
1042 {
1043 if (argv[arg][1] == 'n')
1044 prime = false;
1045 else
1046 fprintf (stdout, "warning: option -%c ignored\n", argv[arg][1]);
1047 }
1048 }
1049
1050 sc = rtems_capture_flush (prime);
1051
1052 if (sc != RTEMS_SUCCESSFUL)
1053 {
1054 fprintf (stdout, "error: flush failed: %s\n", rtems_status_text (sc));
1055 return;
1056 }
1057
1058 fprintf (stdout, "trace buffer flushed and %s.\n",
1059 prime ? "primed" : "not primed");
1060 }
1061
1062 static rtems_monitor_command_entry_t rtems_capture_cli_cmds[] =
1063 {
1064 {
1065 "copen",
1066 "usage: copen [-i] size",
1067 0,
1068 rtems_capture_cli_open,
1069 { 0 },
1070 0
1071 },
1072 {
1073 "cclose",
1074 "usage: cclose",
1075 0,
1076 rtems_capture_cli_close,
1077 { 0 },
1078 0
1079 },
1080 {
1081 "cenable",
1082 "usage: cenable",
1083 0,
1084 rtems_capture_cli_enable,
1085 { 0 },
1086 0
1087 },
1088 {
1089 "cdisable",
1090 "usage: cdisable",
1091 0,
1092 rtems_capture_cli_disable,
1093 { 0 },
1094 0
1095 },
1096 {
1097 "ctlist",
1098 "usage: ctlist",
1099 0,
1100 rtems_capture_cli_task_list,
1101 { 0 },
1102 0
1103 },
1104 {
1105 "cwlist",
1106 "usage: cwlist",
1107 0,
1108 rtems_capture_cli_watch_list,
1109 { 0 },
1110 0
1111 },
1112 {
1113 "cwadd",
1114 "usage: cwadd [task name] [id]",
1115 0,
1116 rtems_capture_cli_watch_add,
1117 { 0 },
1118 0
1119 },
1120 {
1121 "cwdel",
1122 "usage: cwdel [task name] [id]",
1123 0,
1124 rtems_capture_cli_watch_del,
1125 { 0 },
1126 0
1127 },
1128 {
1129 "cwctl",
1130 "usage: cwctl [task name] [id] on/off",
1131 0,
1132 rtems_capture_cli_watch_control,
1133 { 0 },
1134 0
1135 },
1136 {
1137 "cwglob",
1138 "usage: cwglob on/off",
1139 0,
1140 rtems_capture_cli_watch_global,
1141 { 0 },
1142 0
1143 },
1144 {
1145 "cwceil",
1146 "usage: cwceil priority",
1147 0,
1148 rtems_capture_cli_watch_ceiling,
1149 { 0 },
1150 0
1151 },
1152 {
1153 "cwfloor",
1154 "usage: cwfloor priority",
1155 0,
1156 rtems_capture_cli_watch_floor,
1157 { 0 },
1158 0
1159 },
1160 {
1161 "ctrace",
1162 "usage: ctrace [-c] [-r records]",
1163 0,
1164 rtems_capture_cli_trace_records,
1165 { 0 },
1166 0
1167 },
1168 {
1169 "ctset",
1170 "usage: ctset -h",
1171 0,
1172 rtems_capture_cli_trigger_set,
1173 { 0 },
1174 0
1175 },
1176 {
1177 "ctclear",
1178 "usage: ctclear -?",
1179 0,
1180 rtems_capture_cli_trigger_clear,
1181 { 0 },
1182 0
1183 },
1184 {
1185 "cflush",
1186 "usage: cflush [-n]",
1187 0,
1188 rtems_capture_cli_flush,
1189 { 0 },
1190 0
1191 }
1192 };
1193
1194
1195
1196
1197
1198
1199
1200
1201 rtems_status_code
1202 rtems_capture_cli_init (rtems_capture_timestamp timestamp)
1203 {
1204 size_t cmd;
1205
1206 capture_timestamp = timestamp;
1207
1208 for (cmd = 0;
1209 cmd < sizeof (rtems_capture_cli_cmds) / sizeof (rtems_monitor_command_entry_t);
1210 cmd++)
1211 rtems_monitor_insert_cmd (&rtems_capture_cli_cmds[cmd]);
1212
1213 return RTEMS_SUCCESSFUL;
1214 }