perf tools: Add FIFO file names as alternative options to --control
[linux-block.git] / tools / perf / builtin-stat.c
index 483a28ef4ec4feefacb087c761ba11373e0a055b..14688710195cb8e77cd98086032f02b48c3188da 100644 (file)
@@ -404,7 +404,7 @@ static void read_counters(struct timespec *rs)
 {
        struct evsel *counter;
 
-       if (!stat_config.summary && (read_affinity_counters(rs) < 0))
+       if (!stat_config.stop_read_counter && (read_affinity_counters(rs) < 0))
                return;
 
        evlist__for_each_entry(evsel_list, counter) {
@@ -897,9 +897,9 @@ try_again_reset:
        if (stat_config.walltime_run_table)
                stat_config.walltime_run[run_idx] = t1 - t0;
 
-       if (interval) {
+       if (interval && stat_config.summary) {
                stat_config.interval = 0;
-               stat_config.summary = true;
+               stat_config.stop_read_counter = true;
                init_stats(&walltime_nsecs_stats);
                update_stats(&walltime_nsecs_stats, t1 - t0);
 
@@ -1045,27 +1045,19 @@ static int parse_control_option(const struct option *opt,
                                const char *str,
                                int unset __maybe_unused)
 {
-       char *comma = NULL, *endptr = NULL;
-       struct perf_stat_config *config = (struct perf_stat_config *)opt->value;
-
-       if (strncmp(str, "fd:", 3))
-               return -EINVAL;
-
-       config->ctl_fd = strtoul(&str[3], &endptr, 0);
-       if (endptr == &str[3])
-               return -EINVAL;
+       struct perf_stat_config *config = opt->value;
 
-       comma = strchr(str, ',');
-       if (comma) {
-               if (endptr != comma)
-                       return -EINVAL;
+       return evlist__parse_control(str, &config->ctl_fd, &config->ctl_fd_ack, &config->ctl_fd_close);
+}
 
-               config->ctl_fd_ack = strtoul(comma + 1, &endptr, 0);
-               if (endptr == comma + 1 || *endptr != '\0')
-                       return -EINVAL;
+static void close_control_option(struct perf_stat_config *config)
+{
+       if (config->ctl_fd_close) {
+               config->ctl_fd_close = false;
+               close(config->ctl_fd);
+               if (config->ctl_fd_ack >= 0)
+                       close(config->ctl_fd_ack);
        }
-
-       return 0;
 }
 
 static struct option stat_options[] = {
@@ -1164,14 +1156,17 @@ static struct option stat_options[] = {
                    "Use with 'percore' event qualifier to show the event "
                    "counts of one hardware thread by sum up total hardware "
                    "threads of same physical core"),
+       OPT_BOOLEAN(0, "summary", &stat_config.summary,
+                      "print summary for interval mode"),
 #ifdef HAVE_LIBPFM
        OPT_CALLBACK(0, "pfm-events", &evsel_list, "event",
                "libpfm4 event selector. use 'perf list' to list available events",
                parse_libpfm_events_option),
 #endif
-       OPT_CALLBACK(0, "control", &stat_config, "fd:ctl-fd[,ack-fd]",
+       OPT_CALLBACK(0, "control", &stat_config, "fd:ctl-fd[,ack-fd] or fifo:ctl-fifo[,ack-fifo]",
                     "Listen on ctl-fd descriptor for command to control measurement ('enable': enable events, 'disable': disable events).\n"
-                    "\t\t\t  Optionally send control command completion ('ack\\n') to ack-fd descriptor.",
+                    "\t\t\t  Optionally send control command completion ('ack\\n') to ack-fd descriptor.\n"
+                    "\t\t\t  Alternatively, ctl-fifo / ack-fifo will be opened and used as ctl-fd / ack-fd.",
                      parse_control_option),
        OPT_END()
 };
@@ -2414,6 +2409,7 @@ out:
 
        metricgroup__rblist_exit(&stat_config.metric_events);
        runtime_stat_delete(&stat_config);
+       close_control_option(&stat_config);
 
        return status;
 }