]> Git Repo - linux.git/blob - tools/perf/builtin-script.c
perf sched map: Always show task comm with -v
[linux.git] / tools / perf / builtin-script.c
1 #include "builtin.h"
2
3 #include "perf.h"
4 #include "util/cache.h"
5 #include "util/debug.h"
6 #include <subcmd/exec-cmd.h>
7 #include "util/header.h"
8 #include <subcmd/parse-options.h>
9 #include "util/perf_regs.h"
10 #include "util/session.h"
11 #include "util/tool.h"
12 #include "util/symbol.h"
13 #include "util/thread.h"
14 #include "util/trace-event.h"
15 #include "util/util.h"
16 #include "util/evlist.h"
17 #include "util/evsel.h"
18 #include "util/sort.h"
19 #include "util/data.h"
20 #include "util/auxtrace.h"
21 #include "util/cpumap.h"
22 #include "util/thread_map.h"
23 #include "util/stat.h"
24 #include "util/thread-stack.h"
25 #include <linux/bitmap.h>
26 #include <linux/stringify.h>
27 #include <linux/time64.h>
28 #include "asm/bug.h"
29 #include "util/mem-events.h"
30
31 static char const               *script_name;
32 static char const               *generate_script_lang;
33 static bool                     debug_mode;
34 static u64                      last_timestamp;
35 static u64                      nr_unordered;
36 static bool                     no_callchain;
37 static bool                     latency_format;
38 static bool                     system_wide;
39 static bool                     print_flags;
40 static bool                     nanosecs;
41 static const char               *cpu_list;
42 static DECLARE_BITMAP(cpu_bitmap, MAX_NR_CPUS);
43 static struct perf_stat_config  stat_config;
44
45 unsigned int scripting_max_stack = PERF_MAX_STACK_DEPTH;
46
47 enum perf_output_field {
48         PERF_OUTPUT_COMM            = 1U << 0,
49         PERF_OUTPUT_TID             = 1U << 1,
50         PERF_OUTPUT_PID             = 1U << 2,
51         PERF_OUTPUT_TIME            = 1U << 3,
52         PERF_OUTPUT_CPU             = 1U << 4,
53         PERF_OUTPUT_EVNAME          = 1U << 5,
54         PERF_OUTPUT_TRACE           = 1U << 6,
55         PERF_OUTPUT_IP              = 1U << 7,
56         PERF_OUTPUT_SYM             = 1U << 8,
57         PERF_OUTPUT_DSO             = 1U << 9,
58         PERF_OUTPUT_ADDR            = 1U << 10,
59         PERF_OUTPUT_SYMOFFSET       = 1U << 11,
60         PERF_OUTPUT_SRCLINE         = 1U << 12,
61         PERF_OUTPUT_PERIOD          = 1U << 13,
62         PERF_OUTPUT_IREGS           = 1U << 14,
63         PERF_OUTPUT_BRSTACK         = 1U << 15,
64         PERF_OUTPUT_BRSTACKSYM      = 1U << 16,
65         PERF_OUTPUT_DATA_SRC        = 1U << 17,
66         PERF_OUTPUT_WEIGHT          = 1U << 18,
67         PERF_OUTPUT_BPF_OUTPUT      = 1U << 19,
68         PERF_OUTPUT_CALLINDENT      = 1U << 20,
69         PERF_OUTPUT_INSN            = 1U << 21,
70         PERF_OUTPUT_INSNLEN         = 1U << 22,
71 };
72
73 struct output_option {
74         const char *str;
75         enum perf_output_field field;
76 } all_output_options[] = {
77         {.str = "comm",  .field = PERF_OUTPUT_COMM},
78         {.str = "tid",   .field = PERF_OUTPUT_TID},
79         {.str = "pid",   .field = PERF_OUTPUT_PID},
80         {.str = "time",  .field = PERF_OUTPUT_TIME},
81         {.str = "cpu",   .field = PERF_OUTPUT_CPU},
82         {.str = "event", .field = PERF_OUTPUT_EVNAME},
83         {.str = "trace", .field = PERF_OUTPUT_TRACE},
84         {.str = "ip",    .field = PERF_OUTPUT_IP},
85         {.str = "sym",   .field = PERF_OUTPUT_SYM},
86         {.str = "dso",   .field = PERF_OUTPUT_DSO},
87         {.str = "addr",  .field = PERF_OUTPUT_ADDR},
88         {.str = "symoff", .field = PERF_OUTPUT_SYMOFFSET},
89         {.str = "srcline", .field = PERF_OUTPUT_SRCLINE},
90         {.str = "period", .field = PERF_OUTPUT_PERIOD},
91         {.str = "iregs", .field = PERF_OUTPUT_IREGS},
92         {.str = "brstack", .field = PERF_OUTPUT_BRSTACK},
93         {.str = "brstacksym", .field = PERF_OUTPUT_BRSTACKSYM},
94         {.str = "data_src", .field = PERF_OUTPUT_DATA_SRC},
95         {.str = "weight",   .field = PERF_OUTPUT_WEIGHT},
96         {.str = "bpf-output",   .field = PERF_OUTPUT_BPF_OUTPUT},
97         {.str = "callindent", .field = PERF_OUTPUT_CALLINDENT},
98         {.str = "insn", .field = PERF_OUTPUT_INSN},
99         {.str = "insnlen", .field = PERF_OUTPUT_INSNLEN},
100 };
101
102 /* default set to maintain compatibility with current format */
103 static struct {
104         bool user_set;
105         bool wildcard_set;
106         unsigned int print_ip_opts;
107         u64 fields;
108         u64 invalid_fields;
109 } output[PERF_TYPE_MAX] = {
110
111         [PERF_TYPE_HARDWARE] = {
112                 .user_set = false,
113
114                 .fields = PERF_OUTPUT_COMM | PERF_OUTPUT_TID |
115                               PERF_OUTPUT_CPU | PERF_OUTPUT_TIME |
116                               PERF_OUTPUT_EVNAME | PERF_OUTPUT_IP |
117                               PERF_OUTPUT_SYM | PERF_OUTPUT_DSO |
118                               PERF_OUTPUT_PERIOD,
119
120                 .invalid_fields = PERF_OUTPUT_TRACE | PERF_OUTPUT_BPF_OUTPUT,
121         },
122
123         [PERF_TYPE_SOFTWARE] = {
124                 .user_set = false,
125
126                 .fields = PERF_OUTPUT_COMM | PERF_OUTPUT_TID |
127                               PERF_OUTPUT_CPU | PERF_OUTPUT_TIME |
128                               PERF_OUTPUT_EVNAME | PERF_OUTPUT_IP |
129                               PERF_OUTPUT_SYM | PERF_OUTPUT_DSO |
130                               PERF_OUTPUT_PERIOD | PERF_OUTPUT_BPF_OUTPUT,
131
132                 .invalid_fields = PERF_OUTPUT_TRACE,
133         },
134
135         [PERF_TYPE_TRACEPOINT] = {
136                 .user_set = false,
137
138                 .fields = PERF_OUTPUT_COMM | PERF_OUTPUT_TID |
139                                   PERF_OUTPUT_CPU | PERF_OUTPUT_TIME |
140                                   PERF_OUTPUT_EVNAME | PERF_OUTPUT_TRACE
141         },
142
143         [PERF_TYPE_RAW] = {
144                 .user_set = false,
145
146                 .fields = PERF_OUTPUT_COMM | PERF_OUTPUT_TID |
147                               PERF_OUTPUT_CPU | PERF_OUTPUT_TIME |
148                               PERF_OUTPUT_EVNAME | PERF_OUTPUT_IP |
149                               PERF_OUTPUT_SYM | PERF_OUTPUT_DSO |
150                               PERF_OUTPUT_PERIOD |  PERF_OUTPUT_ADDR |
151                               PERF_OUTPUT_DATA_SRC | PERF_OUTPUT_WEIGHT,
152
153                 .invalid_fields = PERF_OUTPUT_TRACE | PERF_OUTPUT_BPF_OUTPUT,
154         },
155
156         [PERF_TYPE_BREAKPOINT] = {
157                 .user_set = false,
158
159                 .fields = PERF_OUTPUT_COMM | PERF_OUTPUT_TID |
160                               PERF_OUTPUT_CPU | PERF_OUTPUT_TIME |
161                               PERF_OUTPUT_EVNAME | PERF_OUTPUT_IP |
162                               PERF_OUTPUT_SYM | PERF_OUTPUT_DSO |
163                               PERF_OUTPUT_PERIOD,
164
165                 .invalid_fields = PERF_OUTPUT_TRACE | PERF_OUTPUT_BPF_OUTPUT,
166         },
167 };
168
169 static bool output_set_by_user(void)
170 {
171         int j;
172         for (j = 0; j < PERF_TYPE_MAX; ++j) {
173                 if (output[j].user_set)
174                         return true;
175         }
176         return false;
177 }
178
179 static const char *output_field2str(enum perf_output_field field)
180 {
181         int i, imax = ARRAY_SIZE(all_output_options);
182         const char *str = "";
183
184         for (i = 0; i < imax; ++i) {
185                 if (all_output_options[i].field == field) {
186                         str = all_output_options[i].str;
187                         break;
188                 }
189         }
190         return str;
191 }
192
193 #define PRINT_FIELD(x)  (output[attr->type].fields & PERF_OUTPUT_##x)
194
195 static int perf_evsel__do_check_stype(struct perf_evsel *evsel,
196                                       u64 sample_type, const char *sample_msg,
197                                       enum perf_output_field field,
198                                       bool allow_user_set)
199 {
200         struct perf_event_attr *attr = &evsel->attr;
201         int type = attr->type;
202         const char *evname;
203
204         if (attr->sample_type & sample_type)
205                 return 0;
206
207         if (output[type].user_set) {
208                 if (allow_user_set)
209                         return 0;
210                 evname = perf_evsel__name(evsel);
211                 pr_err("Samples for '%s' event do not have %s attribute set. "
212                        "Cannot print '%s' field.\n",
213                        evname, sample_msg, output_field2str(field));
214                 return -1;
215         }
216
217         /* user did not ask for it explicitly so remove from the default list */
218         output[type].fields &= ~field;
219         evname = perf_evsel__name(evsel);
220         pr_debug("Samples for '%s' event do not have %s attribute set. "
221                  "Skipping '%s' field.\n",
222                  evname, sample_msg, output_field2str(field));
223
224         return 0;
225 }
226
227 static int perf_evsel__check_stype(struct perf_evsel *evsel,
228                                    u64 sample_type, const char *sample_msg,
229                                    enum perf_output_field field)
230 {
231         return perf_evsel__do_check_stype(evsel, sample_type, sample_msg, field,
232                                           false);
233 }
234
235 static int perf_evsel__check_attr(struct perf_evsel *evsel,
236                                   struct perf_session *session)
237 {
238         struct perf_event_attr *attr = &evsel->attr;
239         bool allow_user_set;
240
241         if (perf_header__has_feat(&session->header, HEADER_STAT))
242                 return 0;
243
244         allow_user_set = perf_header__has_feat(&session->header,
245                                                HEADER_AUXTRACE);
246
247         if (PRINT_FIELD(TRACE) &&
248                 !perf_session__has_traces(session, "record -R"))
249                 return -EINVAL;
250
251         if (PRINT_FIELD(IP)) {
252                 if (perf_evsel__check_stype(evsel, PERF_SAMPLE_IP, "IP",
253                                             PERF_OUTPUT_IP))
254                         return -EINVAL;
255         }
256
257         if (PRINT_FIELD(ADDR) &&
258                 perf_evsel__do_check_stype(evsel, PERF_SAMPLE_ADDR, "ADDR",
259                                            PERF_OUTPUT_ADDR, allow_user_set))
260                 return -EINVAL;
261
262         if (PRINT_FIELD(DATA_SRC) &&
263                 perf_evsel__check_stype(evsel, PERF_SAMPLE_DATA_SRC, "DATA_SRC",
264                                         PERF_OUTPUT_DATA_SRC))
265                 return -EINVAL;
266
267         if (PRINT_FIELD(WEIGHT) &&
268                 perf_evsel__check_stype(evsel, PERF_SAMPLE_WEIGHT, "WEIGHT",
269                                         PERF_OUTPUT_WEIGHT))
270                 return -EINVAL;
271
272         if (PRINT_FIELD(SYM) && !PRINT_FIELD(IP) && !PRINT_FIELD(ADDR)) {
273                 pr_err("Display of symbols requested but neither sample IP nor "
274                            "sample address\nis selected. Hence, no addresses to convert "
275                        "to symbols.\n");
276                 return -EINVAL;
277         }
278         if (PRINT_FIELD(SYMOFFSET) && !PRINT_FIELD(SYM)) {
279                 pr_err("Display of offsets requested but symbol is not"
280                        "selected.\n");
281                 return -EINVAL;
282         }
283         if (PRINT_FIELD(DSO) && !PRINT_FIELD(IP) && !PRINT_FIELD(ADDR)) {
284                 pr_err("Display of DSO requested but neither sample IP nor "
285                            "sample address\nis selected. Hence, no addresses to convert "
286                        "to DSO.\n");
287                 return -EINVAL;
288         }
289         if (PRINT_FIELD(SRCLINE) && !PRINT_FIELD(IP)) {
290                 pr_err("Display of source line number requested but sample IP is not\n"
291                        "selected. Hence, no address to lookup the source line number.\n");
292                 return -EINVAL;
293         }
294
295         if ((PRINT_FIELD(PID) || PRINT_FIELD(TID)) &&
296                 perf_evsel__check_stype(evsel, PERF_SAMPLE_TID, "TID",
297                                         PERF_OUTPUT_TID|PERF_OUTPUT_PID))
298                 return -EINVAL;
299
300         if (PRINT_FIELD(TIME) &&
301                 perf_evsel__check_stype(evsel, PERF_SAMPLE_TIME, "TIME",
302                                         PERF_OUTPUT_TIME))
303                 return -EINVAL;
304
305         if (PRINT_FIELD(CPU) &&
306                 perf_evsel__do_check_stype(evsel, PERF_SAMPLE_CPU, "CPU",
307                                            PERF_OUTPUT_CPU, allow_user_set))
308                 return -EINVAL;
309
310         if (PRINT_FIELD(PERIOD) &&
311                 perf_evsel__check_stype(evsel, PERF_SAMPLE_PERIOD, "PERIOD",
312                                         PERF_OUTPUT_PERIOD))
313                 return -EINVAL;
314
315         if (PRINT_FIELD(IREGS) &&
316                 perf_evsel__check_stype(evsel, PERF_SAMPLE_REGS_INTR, "IREGS",
317                                         PERF_OUTPUT_IREGS))
318                 return -EINVAL;
319
320         return 0;
321 }
322
323 static void set_print_ip_opts(struct perf_event_attr *attr)
324 {
325         unsigned int type = attr->type;
326
327         output[type].print_ip_opts = 0;
328         if (PRINT_FIELD(IP))
329                 output[type].print_ip_opts |= EVSEL__PRINT_IP;
330
331         if (PRINT_FIELD(SYM))
332                 output[type].print_ip_opts |= EVSEL__PRINT_SYM;
333
334         if (PRINT_FIELD(DSO))
335                 output[type].print_ip_opts |= EVSEL__PRINT_DSO;
336
337         if (PRINT_FIELD(SYMOFFSET))
338                 output[type].print_ip_opts |= EVSEL__PRINT_SYMOFFSET;
339
340         if (PRINT_FIELD(SRCLINE))
341                 output[type].print_ip_opts |= EVSEL__PRINT_SRCLINE;
342 }
343
344 /*
345  * verify all user requested events exist and the samples
346  * have the expected data
347  */
348 static int perf_session__check_output_opt(struct perf_session *session)
349 {
350         unsigned int j;
351         struct perf_evsel *evsel;
352
353         for (j = 0; j < PERF_TYPE_MAX; ++j) {
354                 evsel = perf_session__find_first_evtype(session, j);
355
356                 /*
357                  * even if fields is set to 0 (ie., show nothing) event must
358                  * exist if user explicitly includes it on the command line
359                  */
360                 if (!evsel && output[j].user_set && !output[j].wildcard_set) {
361                         pr_err("%s events do not exist. "
362                                "Remove corresponding -f option to proceed.\n",
363                                event_type(j));
364                         return -1;
365                 }
366
367                 if (evsel && output[j].fields &&
368                         perf_evsel__check_attr(evsel, session))
369                         return -1;
370
371                 if (evsel == NULL)
372                         continue;
373
374                 set_print_ip_opts(&evsel->attr);
375         }
376
377         if (!no_callchain) {
378                 bool use_callchain = false;
379                 bool not_pipe = false;
380
381                 evlist__for_each_entry(session->evlist, evsel) {
382                         not_pipe = true;
383                         if (evsel->attr.sample_type & PERF_SAMPLE_CALLCHAIN) {
384                                 use_callchain = true;
385                                 break;
386                         }
387                 }
388                 if (not_pipe && !use_callchain)
389                         symbol_conf.use_callchain = false;
390         }
391
392         /*
393          * set default for tracepoints to print symbols only
394          * if callchains are present
395          */
396         if (symbol_conf.use_callchain &&
397             !output[PERF_TYPE_TRACEPOINT].user_set) {
398                 struct perf_event_attr *attr;
399
400                 j = PERF_TYPE_TRACEPOINT;
401
402                 evlist__for_each_entry(session->evlist, evsel) {
403                         if (evsel->attr.type != j)
404                                 continue;
405
406                         attr = &evsel->attr;
407
408                         if (attr->sample_type & PERF_SAMPLE_CALLCHAIN) {
409                                 output[j].fields |= PERF_OUTPUT_IP;
410                                 output[j].fields |= PERF_OUTPUT_SYM;
411                                 output[j].fields |= PERF_OUTPUT_DSO;
412                                 set_print_ip_opts(attr);
413                                 goto out;
414                         }
415                 }
416         }
417
418 out:
419         return 0;
420 }
421
422 static void print_sample_iregs(struct perf_sample *sample,
423                           struct perf_event_attr *attr)
424 {
425         struct regs_dump *regs = &sample->intr_regs;
426         uint64_t mask = attr->sample_regs_intr;
427         unsigned i = 0, r;
428
429         if (!regs)
430                 return;
431
432         for_each_set_bit(r, (unsigned long *) &mask, sizeof(mask) * 8) {
433                 u64 val = regs->regs[i++];
434                 printf("%5s:0x%"PRIx64" ", perf_reg_name(r), val);
435         }
436 }
437
438 static void print_sample_start(struct perf_sample *sample,
439                                struct thread *thread,
440                                struct perf_evsel *evsel)
441 {
442         struct perf_event_attr *attr = &evsel->attr;
443         unsigned long secs;
444         unsigned long usecs;
445         unsigned long long nsecs;
446
447         if (PRINT_FIELD(COMM)) {
448                 if (latency_format)
449                         printf("%8.8s ", thread__comm_str(thread));
450                 else if (PRINT_FIELD(IP) && symbol_conf.use_callchain)
451                         printf("%s ", thread__comm_str(thread));
452                 else
453                         printf("%16s ", thread__comm_str(thread));
454         }
455
456         if (PRINT_FIELD(PID) && PRINT_FIELD(TID))
457                 printf("%5d/%-5d ", sample->pid, sample->tid);
458         else if (PRINT_FIELD(PID))
459                 printf("%5d ", sample->pid);
460         else if (PRINT_FIELD(TID))
461                 printf("%5d ", sample->tid);
462
463         if (PRINT_FIELD(CPU)) {
464                 if (latency_format)
465                         printf("%3d ", sample->cpu);
466                 else
467                         printf("[%03d] ", sample->cpu);
468         }
469
470         if (PRINT_FIELD(TIME)) {
471                 nsecs = sample->time;
472                 secs = nsecs / NSEC_PER_SEC;
473                 nsecs -= secs * NSEC_PER_SEC;
474                 usecs = nsecs / NSEC_PER_USEC;
475                 if (nanosecs)
476                         printf("%5lu.%09llu: ", secs, nsecs);
477                 else
478                         printf("%5lu.%06lu: ", secs, usecs);
479         }
480 }
481
482 static inline char
483 mispred_str(struct branch_entry *br)
484 {
485         if (!(br->flags.mispred  || br->flags.predicted))
486                 return '-';
487
488         return br->flags.predicted ? 'P' : 'M';
489 }
490
491 static void print_sample_brstack(struct perf_sample *sample)
492 {
493         struct branch_stack *br = sample->branch_stack;
494         u64 i;
495
496         if (!(br && br->nr))
497                 return;
498
499         for (i = 0; i < br->nr; i++) {
500                 printf(" 0x%"PRIx64"/0x%"PRIx64"/%c/%c/%c/%d ",
501                         br->entries[i].from,
502                         br->entries[i].to,
503                         mispred_str( br->entries + i),
504                         br->entries[i].flags.in_tx? 'X' : '-',
505                         br->entries[i].flags.abort? 'A' : '-',
506                         br->entries[i].flags.cycles);
507         }
508 }
509
510 static void print_sample_brstacksym(struct perf_sample *sample,
511                                     struct thread *thread)
512 {
513         struct branch_stack *br = sample->branch_stack;
514         struct addr_location alf, alt;
515         u64 i, from, to;
516
517         if (!(br && br->nr))
518                 return;
519
520         for (i = 0; i < br->nr; i++) {
521
522                 memset(&alf, 0, sizeof(alf));
523                 memset(&alt, 0, sizeof(alt));
524                 from = br->entries[i].from;
525                 to   = br->entries[i].to;
526
527                 thread__find_addr_map(thread, sample->cpumode, MAP__FUNCTION, from, &alf);
528                 if (alf.map)
529                         alf.sym = map__find_symbol(alf.map, alf.addr);
530
531                 thread__find_addr_map(thread, sample->cpumode, MAP__FUNCTION, to, &alt);
532                 if (alt.map)
533                         alt.sym = map__find_symbol(alt.map, alt.addr);
534
535                 symbol__fprintf_symname_offs(alf.sym, &alf, stdout);
536                 putchar('/');
537                 symbol__fprintf_symname_offs(alt.sym, &alt, stdout);
538                 printf("/%c/%c/%c/%d ",
539                         mispred_str( br->entries + i),
540                         br->entries[i].flags.in_tx? 'X' : '-',
541                         br->entries[i].flags.abort? 'A' : '-',
542                         br->entries[i].flags.cycles);
543         }
544 }
545
546
547 static void print_sample_addr(struct perf_sample *sample,
548                           struct thread *thread,
549                           struct perf_event_attr *attr)
550 {
551         struct addr_location al;
552
553         printf("%16" PRIx64, sample->addr);
554
555         if (!sample_addr_correlates_sym(attr))
556                 return;
557
558         thread__resolve(thread, &al, sample);
559
560         if (PRINT_FIELD(SYM)) {
561                 printf(" ");
562                 if (PRINT_FIELD(SYMOFFSET))
563                         symbol__fprintf_symname_offs(al.sym, &al, stdout);
564                 else
565                         symbol__fprintf_symname(al.sym, stdout);
566         }
567
568         if (PRINT_FIELD(DSO)) {
569                 printf(" (");
570                 map__fprintf_dsoname(al.map, stdout);
571                 printf(")");
572         }
573 }
574
575 static void print_sample_callindent(struct perf_sample *sample,
576                                     struct perf_evsel *evsel,
577                                     struct thread *thread,
578                                     struct addr_location *al)
579 {
580         struct perf_event_attr *attr = &evsel->attr;
581         size_t depth = thread_stack__depth(thread);
582         struct addr_location addr_al;
583         const char *name = NULL;
584         static int spacing;
585         int len = 0;
586         u64 ip = 0;
587
588         /*
589          * The 'return' has already been popped off the stack so the depth has
590          * to be adjusted to match the 'call'.
591          */
592         if (thread->ts && sample->flags & PERF_IP_FLAG_RETURN)
593                 depth += 1;
594
595         if (sample->flags & (PERF_IP_FLAG_CALL | PERF_IP_FLAG_TRACE_BEGIN)) {
596                 if (sample_addr_correlates_sym(attr)) {
597                         thread__resolve(thread, &addr_al, sample);
598                         if (addr_al.sym)
599                                 name = addr_al.sym->name;
600                         else
601                                 ip = sample->addr;
602                 } else {
603                         ip = sample->addr;
604                 }
605         } else if (sample->flags & (PERF_IP_FLAG_RETURN | PERF_IP_FLAG_TRACE_END)) {
606                 if (al->sym)
607                         name = al->sym->name;
608                 else
609                         ip = sample->ip;
610         }
611
612         if (name)
613                 len = printf("%*s%s", (int)depth * 4, "", name);
614         else if (ip)
615                 len = printf("%*s%16" PRIx64, (int)depth * 4, "", ip);
616
617         if (len < 0)
618                 return;
619
620         /*
621          * Try to keep the output length from changing frequently so that the
622          * output lines up more nicely.
623          */
624         if (len > spacing || (len && len < spacing - 52))
625                 spacing = round_up(len + 4, 32);
626
627         if (len < spacing)
628                 printf("%*s", spacing - len, "");
629 }
630
631 static void print_insn(struct perf_sample *sample,
632                        struct perf_event_attr *attr)
633 {
634         if (PRINT_FIELD(INSNLEN))
635                 printf(" ilen: %d", sample->insn_len);
636         if (PRINT_FIELD(INSN)) {
637                 int i;
638
639                 printf(" insn:");
640                 for (i = 0; i < sample->insn_len; i++)
641                         printf(" %02x", (unsigned char)sample->insn[i]);
642         }
643 }
644
645 static void print_sample_bts(struct perf_sample *sample,
646                              struct perf_evsel *evsel,
647                              struct thread *thread,
648                              struct addr_location *al)
649 {
650         struct perf_event_attr *attr = &evsel->attr;
651         bool print_srcline_last = false;
652
653         if (PRINT_FIELD(CALLINDENT))
654                 print_sample_callindent(sample, evsel, thread, al);
655
656         /* print branch_from information */
657         if (PRINT_FIELD(IP)) {
658                 unsigned int print_opts = output[attr->type].print_ip_opts;
659                 struct callchain_cursor *cursor = NULL;
660
661                 if (symbol_conf.use_callchain && sample->callchain &&
662                     thread__resolve_callchain(al->thread, &callchain_cursor, evsel,
663                                               sample, NULL, NULL, scripting_max_stack) == 0)
664                         cursor = &callchain_cursor;
665
666                 if (cursor == NULL) {
667                         putchar(' ');
668                         if (print_opts & EVSEL__PRINT_SRCLINE) {
669                                 print_srcline_last = true;
670                                 print_opts &= ~EVSEL__PRINT_SRCLINE;
671                         }
672                 } else
673                         putchar('\n');
674
675                 sample__fprintf_sym(sample, al, 0, print_opts, cursor, stdout);
676         }
677
678         /* print branch_to information */
679         if (PRINT_FIELD(ADDR) ||
680             ((evsel->attr.sample_type & PERF_SAMPLE_ADDR) &&
681              !output[attr->type].user_set)) {
682                 printf(" => ");
683                 print_sample_addr(sample, thread, attr);
684         }
685
686         if (print_srcline_last)
687                 map__fprintf_srcline(al->map, al->addr, "\n  ", stdout);
688
689         print_insn(sample, attr);
690
691         printf("\n");
692 }
693
694 static struct {
695         u32 flags;
696         const char *name;
697 } sample_flags[] = {
698         {PERF_IP_FLAG_BRANCH | PERF_IP_FLAG_CALL, "call"},
699         {PERF_IP_FLAG_BRANCH | PERF_IP_FLAG_RETURN, "return"},
700         {PERF_IP_FLAG_BRANCH | PERF_IP_FLAG_CONDITIONAL, "jcc"},
701         {PERF_IP_FLAG_BRANCH, "jmp"},
702         {PERF_IP_FLAG_BRANCH | PERF_IP_FLAG_CALL | PERF_IP_FLAG_INTERRUPT, "int"},
703         {PERF_IP_FLAG_BRANCH | PERF_IP_FLAG_RETURN | PERF_IP_FLAG_INTERRUPT, "iret"},
704         {PERF_IP_FLAG_BRANCH | PERF_IP_FLAG_CALL | PERF_IP_FLAG_SYSCALLRET, "syscall"},
705         {PERF_IP_FLAG_BRANCH | PERF_IP_FLAG_RETURN | PERF_IP_FLAG_SYSCALLRET, "sysret"},
706         {PERF_IP_FLAG_BRANCH | PERF_IP_FLAG_ASYNC, "async"},
707         {PERF_IP_FLAG_BRANCH | PERF_IP_FLAG_CALL | PERF_IP_FLAG_ASYNC | PERF_IP_FLAG_INTERRUPT, "hw int"},
708         {PERF_IP_FLAG_BRANCH | PERF_IP_FLAG_TX_ABORT, "tx abrt"},
709         {PERF_IP_FLAG_BRANCH | PERF_IP_FLAG_TRACE_BEGIN, "tr strt"},
710         {PERF_IP_FLAG_BRANCH | PERF_IP_FLAG_TRACE_END, "tr end"},
711         {0, NULL}
712 };
713
714 static void print_sample_flags(u32 flags)
715 {
716         const char *chars = PERF_IP_FLAG_CHARS;
717         const int n = strlen(PERF_IP_FLAG_CHARS);
718         bool in_tx = flags & PERF_IP_FLAG_IN_TX;
719         const char *name = NULL;
720         char str[33];
721         int i, pos = 0;
722
723         for (i = 0; sample_flags[i].name ; i++) {
724                 if (sample_flags[i].flags == (flags & ~PERF_IP_FLAG_IN_TX)) {
725                         name = sample_flags[i].name;
726                         break;
727                 }
728         }
729
730         for (i = 0; i < n; i++, flags >>= 1) {
731                 if (flags & 1)
732                         str[pos++] = chars[i];
733         }
734         for (; i < 32; i++, flags >>= 1) {
735                 if (flags & 1)
736                         str[pos++] = '?';
737         }
738         str[pos] = 0;
739
740         if (name)
741                 printf("  %-7s%4s ", name, in_tx ? "(x)" : "");
742         else
743                 printf("  %-11s ", str);
744 }
745
746 struct printer_data {
747         int line_no;
748         bool hit_nul;
749         bool is_printable;
750 };
751
752 static void
753 print_sample_bpf_output_printer(enum binary_printer_ops op,
754                                 unsigned int val,
755                                 void *extra)
756 {
757         unsigned char ch = (unsigned char)val;
758         struct printer_data *printer_data = extra;
759
760         switch (op) {
761         case BINARY_PRINT_DATA_BEGIN:
762                 printf("\n");
763                 break;
764         case BINARY_PRINT_LINE_BEGIN:
765                 printf("%17s", !printer_data->line_no ? "BPF output:" :
766                                                         "           ");
767                 break;
768         case BINARY_PRINT_ADDR:
769                 printf(" %04x:", val);
770                 break;
771         case BINARY_PRINT_NUM_DATA:
772                 printf(" %02x", val);
773                 break;
774         case BINARY_PRINT_NUM_PAD:
775                 printf("   ");
776                 break;
777         case BINARY_PRINT_SEP:
778                 printf("  ");
779                 break;
780         case BINARY_PRINT_CHAR_DATA:
781                 if (printer_data->hit_nul && ch)
782                         printer_data->is_printable = false;
783
784                 if (!isprint(ch)) {
785                         printf("%c", '.');
786
787                         if (!printer_data->is_printable)
788                                 break;
789
790                         if (ch == '\0')
791                                 printer_data->hit_nul = true;
792                         else
793                                 printer_data->is_printable = false;
794                 } else {
795                         printf("%c", ch);
796                 }
797                 break;
798         case BINARY_PRINT_CHAR_PAD:
799                 printf(" ");
800                 break;
801         case BINARY_PRINT_LINE_END:
802                 printf("\n");
803                 printer_data->line_no++;
804                 break;
805         case BINARY_PRINT_DATA_END:
806         default:
807                 break;
808         }
809 }
810
811 static void print_sample_bpf_output(struct perf_sample *sample)
812 {
813         unsigned int nr_bytes = sample->raw_size;
814         struct printer_data printer_data = {0, false, true};
815
816         print_binary(sample->raw_data, nr_bytes, 8,
817                      print_sample_bpf_output_printer, &printer_data);
818
819         if (printer_data.is_printable && printer_data.hit_nul)
820                 printf("%17s \"%s\"\n", "BPF string:",
821                        (char *)(sample->raw_data));
822 }
823
824 struct perf_script {
825         struct perf_tool        tool;
826         struct perf_session     *session;
827         bool                    show_task_events;
828         bool                    show_mmap_events;
829         bool                    show_switch_events;
830         bool                    allocated;
831         struct cpu_map          *cpus;
832         struct thread_map       *threads;
833         int                     name_width;
834 };
835
836 static int perf_evlist__max_name_len(struct perf_evlist *evlist)
837 {
838         struct perf_evsel *evsel;
839         int max = 0;
840
841         evlist__for_each_entry(evlist, evsel) {
842                 int len = strlen(perf_evsel__name(evsel));
843
844                 max = MAX(len, max);
845         }
846
847         return max;
848 }
849
850 static size_t data_src__printf(u64 data_src)
851 {
852         struct mem_info mi = { .data_src.val = data_src };
853         char decode[100];
854         char out[100];
855         static int maxlen;
856         int len;
857
858         perf_script__meminfo_scnprintf(decode, 100, &mi);
859
860         len = scnprintf(out, 100, "%16" PRIx64 " %s", data_src, decode);
861         if (maxlen < len)
862                 maxlen = len;
863
864         return printf("%-*s", maxlen, out);
865 }
866
867 static void process_event(struct perf_script *script,
868                           struct perf_sample *sample, struct perf_evsel *evsel,
869                           struct addr_location *al)
870 {
871         struct thread *thread = al->thread;
872         struct perf_event_attr *attr = &evsel->attr;
873
874         if (output[attr->type].fields == 0)
875                 return;
876
877         print_sample_start(sample, thread, evsel);
878
879         if (PRINT_FIELD(PERIOD))
880                 printf("%10" PRIu64 " ", sample->period);
881
882         if (PRINT_FIELD(EVNAME)) {
883                 const char *evname = perf_evsel__name(evsel);
884
885                 if (!script->name_width)
886                         script->name_width = perf_evlist__max_name_len(script->session->evlist);
887
888                 printf("%*s: ", script->name_width,
889                        evname ? evname : "[unknown]");
890         }
891
892         if (print_flags)
893                 print_sample_flags(sample->flags);
894
895         if (is_bts_event(attr)) {
896                 print_sample_bts(sample, evsel, thread, al);
897                 return;
898         }
899
900         if (PRINT_FIELD(TRACE))
901                 event_format__print(evsel->tp_format, sample->cpu,
902                                     sample->raw_data, sample->raw_size);
903         if (PRINT_FIELD(ADDR))
904                 print_sample_addr(sample, thread, attr);
905
906         if (PRINT_FIELD(DATA_SRC))
907                 data_src__printf(sample->data_src);
908
909         if (PRINT_FIELD(WEIGHT))
910                 printf("%16" PRIu64, sample->weight);
911
912         if (PRINT_FIELD(IP)) {
913                 struct callchain_cursor *cursor = NULL;
914
915                 if (symbol_conf.use_callchain && sample->callchain &&
916                     thread__resolve_callchain(al->thread, &callchain_cursor, evsel,
917                                               sample, NULL, NULL, scripting_max_stack) == 0)
918                         cursor = &callchain_cursor;
919
920                 putchar(cursor ? '\n' : ' ');
921                 sample__fprintf_sym(sample, al, 0, output[attr->type].print_ip_opts, cursor, stdout);
922         }
923
924         if (PRINT_FIELD(IREGS))
925                 print_sample_iregs(sample, attr);
926
927         if (PRINT_FIELD(BRSTACK))
928                 print_sample_brstack(sample);
929         else if (PRINT_FIELD(BRSTACKSYM))
930                 print_sample_brstacksym(sample, thread);
931
932         if (perf_evsel__is_bpf_output(evsel) && PRINT_FIELD(BPF_OUTPUT))
933                 print_sample_bpf_output(sample);
934         print_insn(sample, attr);
935         printf("\n");
936 }
937
938 static struct scripting_ops     *scripting_ops;
939
940 static void __process_stat(struct perf_evsel *counter, u64 tstamp)
941 {
942         int nthreads = thread_map__nr(counter->threads);
943         int ncpus = perf_evsel__nr_cpus(counter);
944         int cpu, thread;
945         static int header_printed;
946
947         if (counter->system_wide)
948                 nthreads = 1;
949
950         if (!header_printed) {
951                 printf("%3s %8s %15s %15s %15s %15s %s\n",
952                        "CPU", "THREAD", "VAL", "ENA", "RUN", "TIME", "EVENT");
953                 header_printed = 1;
954         }
955
956         for (thread = 0; thread < nthreads; thread++) {
957                 for (cpu = 0; cpu < ncpus; cpu++) {
958                         struct perf_counts_values *counts;
959
960                         counts = perf_counts(counter->counts, cpu, thread);
961
962                         printf("%3d %8d %15" PRIu64 " %15" PRIu64 " %15" PRIu64 " %15" PRIu64 " %s\n",
963                                 counter->cpus->map[cpu],
964                                 thread_map__pid(counter->threads, thread),
965                                 counts->val,
966                                 counts->ena,
967                                 counts->run,
968                                 tstamp,
969                                 perf_evsel__name(counter));
970                 }
971         }
972 }
973
974 static void process_stat(struct perf_evsel *counter, u64 tstamp)
975 {
976         if (scripting_ops && scripting_ops->process_stat)
977                 scripting_ops->process_stat(&stat_config, counter, tstamp);
978         else
979                 __process_stat(counter, tstamp);
980 }
981
982 static void process_stat_interval(u64 tstamp)
983 {
984         if (scripting_ops && scripting_ops->process_stat_interval)
985                 scripting_ops->process_stat_interval(tstamp);
986 }
987
988 static void setup_scripting(void)
989 {
990         setup_perl_scripting();
991         setup_python_scripting();
992 }
993
994 static int flush_scripting(void)
995 {
996         return scripting_ops ? scripting_ops->flush_script() : 0;
997 }
998
999 static int cleanup_scripting(void)
1000 {
1001         pr_debug("\nperf script stopped\n");
1002
1003         return scripting_ops ? scripting_ops->stop_script() : 0;
1004 }
1005
1006 static int process_sample_event(struct perf_tool *tool,
1007                                 union perf_event *event,
1008                                 struct perf_sample *sample,
1009                                 struct perf_evsel *evsel,
1010                                 struct machine *machine)
1011 {
1012         struct perf_script *scr = container_of(tool, struct perf_script, tool);
1013         struct addr_location al;
1014
1015         if (debug_mode) {
1016                 if (sample->time < last_timestamp) {
1017                         pr_err("Samples misordered, previous: %" PRIu64
1018                                 " this: %" PRIu64 "\n", last_timestamp,
1019                                 sample->time);
1020                         nr_unordered++;
1021                 }
1022                 last_timestamp = sample->time;
1023                 return 0;
1024         }
1025
1026         if (machine__resolve(machine, &al, sample) < 0) {
1027                 pr_err("problem processing %d event, skipping it.\n",
1028                        event->header.type);
1029                 return -1;
1030         }
1031
1032         if (al.filtered)
1033                 goto out_put;
1034
1035         if (cpu_list && !test_bit(sample->cpu, cpu_bitmap))
1036                 goto out_put;
1037
1038         if (scripting_ops)
1039                 scripting_ops->process_event(event, sample, evsel, &al);
1040         else
1041                 process_event(scr, sample, evsel, &al);
1042
1043 out_put:
1044         addr_location__put(&al);
1045         return 0;
1046 }
1047
1048 static int process_attr(struct perf_tool *tool, union perf_event *event,
1049                         struct perf_evlist **pevlist)
1050 {
1051         struct perf_script *scr = container_of(tool, struct perf_script, tool);
1052         struct perf_evlist *evlist;
1053         struct perf_evsel *evsel, *pos;
1054         int err;
1055
1056         err = perf_event__process_attr(tool, event, pevlist);
1057         if (err)
1058                 return err;
1059
1060         evlist = *pevlist;
1061         evsel = perf_evlist__last(*pevlist);
1062
1063         if (evsel->attr.type >= PERF_TYPE_MAX)
1064                 return 0;
1065
1066         evlist__for_each_entry(evlist, pos) {
1067                 if (pos->attr.type == evsel->attr.type && pos != evsel)
1068                         return 0;
1069         }
1070
1071         set_print_ip_opts(&evsel->attr);
1072
1073         if (evsel->attr.sample_type)
1074                 err = perf_evsel__check_attr(evsel, scr->session);
1075
1076         return err;
1077 }
1078
1079 static int process_comm_event(struct perf_tool *tool,
1080                               union perf_event *event,
1081                               struct perf_sample *sample,
1082                               struct machine *machine)
1083 {
1084         struct thread *thread;
1085         struct perf_script *script = container_of(tool, struct perf_script, tool);
1086         struct perf_session *session = script->session;
1087         struct perf_evsel *evsel = perf_evlist__id2evsel(session->evlist, sample->id);
1088         int ret = -1;
1089
1090         thread = machine__findnew_thread(machine, event->comm.pid, event->comm.tid);
1091         if (thread == NULL) {
1092                 pr_debug("problem processing COMM event, skipping it.\n");
1093                 return -1;
1094         }
1095
1096         if (perf_event__process_comm(tool, event, sample, machine) < 0)
1097                 goto out;
1098
1099         if (!evsel->attr.sample_id_all) {
1100                 sample->cpu = 0;
1101                 sample->time = 0;
1102                 sample->tid = event->comm.tid;
1103                 sample->pid = event->comm.pid;
1104         }
1105         print_sample_start(sample, thread, evsel);
1106         perf_event__fprintf(event, stdout);
1107         ret = 0;
1108 out:
1109         thread__put(thread);
1110         return ret;
1111 }
1112
1113 static int process_fork_event(struct perf_tool *tool,
1114                               union perf_event *event,
1115                               struct perf_sample *sample,
1116                               struct machine *machine)
1117 {
1118         struct thread *thread;
1119         struct perf_script *script = container_of(tool, struct perf_script, tool);
1120         struct perf_session *session = script->session;
1121         struct perf_evsel *evsel = perf_evlist__id2evsel(session->evlist, sample->id);
1122
1123         if (perf_event__process_fork(tool, event, sample, machine) < 0)
1124                 return -1;
1125
1126         thread = machine__findnew_thread(machine, event->fork.pid, event->fork.tid);
1127         if (thread == NULL) {
1128                 pr_debug("problem processing FORK event, skipping it.\n");
1129                 return -1;
1130         }
1131
1132         if (!evsel->attr.sample_id_all) {
1133                 sample->cpu = 0;
1134                 sample->time = event->fork.time;
1135                 sample->tid = event->fork.tid;
1136                 sample->pid = event->fork.pid;
1137         }
1138         print_sample_start(sample, thread, evsel);
1139         perf_event__fprintf(event, stdout);
1140         thread__put(thread);
1141
1142         return 0;
1143 }
1144 static int process_exit_event(struct perf_tool *tool,
1145                               union perf_event *event,
1146                               struct perf_sample *sample,
1147                               struct machine *machine)
1148 {
1149         int err = 0;
1150         struct thread *thread;
1151         struct perf_script *script = container_of(tool, struct perf_script, tool);
1152         struct perf_session *session = script->session;
1153         struct perf_evsel *evsel = perf_evlist__id2evsel(session->evlist, sample->id);
1154
1155         thread = machine__findnew_thread(machine, event->fork.pid, event->fork.tid);
1156         if (thread == NULL) {
1157                 pr_debug("problem processing EXIT event, skipping it.\n");
1158                 return -1;
1159         }
1160
1161         if (!evsel->attr.sample_id_all) {
1162                 sample->cpu = 0;
1163                 sample->time = 0;
1164                 sample->tid = event->fork.tid;
1165                 sample->pid = event->fork.pid;
1166         }
1167         print_sample_start(sample, thread, evsel);
1168         perf_event__fprintf(event, stdout);
1169
1170         if (perf_event__process_exit(tool, event, sample, machine) < 0)
1171                 err = -1;
1172
1173         thread__put(thread);
1174         return err;
1175 }
1176
1177 static int process_mmap_event(struct perf_tool *tool,
1178                               union perf_event *event,
1179                               struct perf_sample *sample,
1180                               struct machine *machine)
1181 {
1182         struct thread *thread;
1183         struct perf_script *script = container_of(tool, struct perf_script, tool);
1184         struct perf_session *session = script->session;
1185         struct perf_evsel *evsel = perf_evlist__id2evsel(session->evlist, sample->id);
1186
1187         if (perf_event__process_mmap(tool, event, sample, machine) < 0)
1188                 return -1;
1189
1190         thread = machine__findnew_thread(machine, event->mmap.pid, event->mmap.tid);
1191         if (thread == NULL) {
1192                 pr_debug("problem processing MMAP event, skipping it.\n");
1193                 return -1;
1194         }
1195
1196         if (!evsel->attr.sample_id_all) {
1197                 sample->cpu = 0;
1198                 sample->time = 0;
1199                 sample->tid = event->mmap.tid;
1200                 sample->pid = event->mmap.pid;
1201         }
1202         print_sample_start(sample, thread, evsel);
1203         perf_event__fprintf(event, stdout);
1204         thread__put(thread);
1205         return 0;
1206 }
1207
1208 static int process_mmap2_event(struct perf_tool *tool,
1209                               union perf_event *event,
1210                               struct perf_sample *sample,
1211                               struct machine *machine)
1212 {
1213         struct thread *thread;
1214         struct perf_script *script = container_of(tool, struct perf_script, tool);
1215         struct perf_session *session = script->session;
1216         struct perf_evsel *evsel = perf_evlist__id2evsel(session->evlist, sample->id);
1217
1218         if (perf_event__process_mmap2(tool, event, sample, machine) < 0)
1219                 return -1;
1220
1221         thread = machine__findnew_thread(machine, event->mmap2.pid, event->mmap2.tid);
1222         if (thread == NULL) {
1223                 pr_debug("problem processing MMAP2 event, skipping it.\n");
1224                 return -1;
1225         }
1226
1227         if (!evsel->attr.sample_id_all) {
1228                 sample->cpu = 0;
1229                 sample->time = 0;
1230                 sample->tid = event->mmap2.tid;
1231                 sample->pid = event->mmap2.pid;
1232         }
1233         print_sample_start(sample, thread, evsel);
1234         perf_event__fprintf(event, stdout);
1235         thread__put(thread);
1236         return 0;
1237 }
1238
1239 static int process_switch_event(struct perf_tool *tool,
1240                                 union perf_event *event,
1241                                 struct perf_sample *sample,
1242                                 struct machine *machine)
1243 {
1244         struct thread *thread;
1245         struct perf_script *script = container_of(tool, struct perf_script, tool);
1246         struct perf_session *session = script->session;
1247         struct perf_evsel *evsel = perf_evlist__id2evsel(session->evlist, sample->id);
1248
1249         if (perf_event__process_switch(tool, event, sample, machine) < 0)
1250                 return -1;
1251
1252         thread = machine__findnew_thread(machine, sample->pid,
1253                                          sample->tid);
1254         if (thread == NULL) {
1255                 pr_debug("problem processing SWITCH event, skipping it.\n");
1256                 return -1;
1257         }
1258
1259         print_sample_start(sample, thread, evsel);
1260         perf_event__fprintf(event, stdout);
1261         thread__put(thread);
1262         return 0;
1263 }
1264
1265 static void sig_handler(int sig __maybe_unused)
1266 {
1267         session_done = 1;
1268 }
1269
1270 static int __cmd_script(struct perf_script *script)
1271 {
1272         int ret;
1273
1274         signal(SIGINT, sig_handler);
1275
1276         /* override event processing functions */
1277         if (script->show_task_events) {
1278                 script->tool.comm = process_comm_event;
1279                 script->tool.fork = process_fork_event;
1280                 script->tool.exit = process_exit_event;
1281         }
1282         if (script->show_mmap_events) {
1283                 script->tool.mmap = process_mmap_event;
1284                 script->tool.mmap2 = process_mmap2_event;
1285         }
1286         if (script->show_switch_events)
1287                 script->tool.context_switch = process_switch_event;
1288
1289         ret = perf_session__process_events(script->session);
1290
1291         if (debug_mode)
1292                 pr_err("Misordered timestamps: %" PRIu64 "\n", nr_unordered);
1293
1294         return ret;
1295 }
1296
1297 struct script_spec {
1298         struct list_head        node;
1299         struct scripting_ops    *ops;
1300         char                    spec[0];
1301 };
1302
1303 static LIST_HEAD(script_specs);
1304
1305 static struct script_spec *script_spec__new(const char *spec,
1306                                             struct scripting_ops *ops)
1307 {
1308         struct script_spec *s = malloc(sizeof(*s) + strlen(spec) + 1);
1309
1310         if (s != NULL) {
1311                 strcpy(s->spec, spec);
1312                 s->ops = ops;
1313         }
1314
1315         return s;
1316 }
1317
1318 static void script_spec__add(struct script_spec *s)
1319 {
1320         list_add_tail(&s->node, &script_specs);
1321 }
1322
1323 static struct script_spec *script_spec__find(const char *spec)
1324 {
1325         struct script_spec *s;
1326
1327         list_for_each_entry(s, &script_specs, node)
1328                 if (strcasecmp(s->spec, spec) == 0)
1329                         return s;
1330         return NULL;
1331 }
1332
1333 int script_spec_register(const char *spec, struct scripting_ops *ops)
1334 {
1335         struct script_spec *s;
1336
1337         s = script_spec__find(spec);
1338         if (s)
1339                 return -1;
1340
1341         s = script_spec__new(spec, ops);
1342         if (!s)
1343                 return -1;
1344         else
1345                 script_spec__add(s);
1346
1347         return 0;
1348 }
1349
1350 static struct scripting_ops *script_spec__lookup(const char *spec)
1351 {
1352         struct script_spec *s = script_spec__find(spec);
1353         if (!s)
1354                 return NULL;
1355
1356         return s->ops;
1357 }
1358
1359 static void list_available_languages(void)
1360 {
1361         struct script_spec *s;
1362
1363         fprintf(stderr, "\n");
1364         fprintf(stderr, "Scripting language extensions (used in "
1365                 "perf script -s [spec:]script.[spec]):\n\n");
1366
1367         list_for_each_entry(s, &script_specs, node)
1368                 fprintf(stderr, "  %-42s [%s]\n", s->spec, s->ops->name);
1369
1370         fprintf(stderr, "\n");
1371 }
1372
1373 static int parse_scriptname(const struct option *opt __maybe_unused,
1374                             const char *str, int unset __maybe_unused)
1375 {
1376         char spec[PATH_MAX];
1377         const char *script, *ext;
1378         int len;
1379
1380         if (strcmp(str, "lang") == 0) {
1381                 list_available_languages();
1382                 exit(0);
1383         }
1384
1385         script = strchr(str, ':');
1386         if (script) {
1387                 len = script - str;
1388                 if (len >= PATH_MAX) {
1389                         fprintf(stderr, "invalid language specifier");
1390                         return -1;
1391                 }
1392                 strncpy(spec, str, len);
1393                 spec[len] = '\0';
1394                 scripting_ops = script_spec__lookup(spec);
1395                 if (!scripting_ops) {
1396                         fprintf(stderr, "invalid language specifier");
1397                         return -1;
1398                 }
1399                 script++;
1400         } else {
1401                 script = str;
1402                 ext = strrchr(script, '.');
1403                 if (!ext) {
1404                         fprintf(stderr, "invalid script extension");
1405                         return -1;
1406                 }
1407                 scripting_ops = script_spec__lookup(++ext);
1408                 if (!scripting_ops) {
1409                         fprintf(stderr, "invalid script extension");
1410                         return -1;
1411                 }
1412         }
1413
1414         script_name = strdup(script);
1415
1416         return 0;
1417 }
1418
1419 static int parse_output_fields(const struct option *opt __maybe_unused,
1420                             const char *arg, int unset __maybe_unused)
1421 {
1422         char *tok;
1423         int i, imax = ARRAY_SIZE(all_output_options);
1424         int j;
1425         int rc = 0;
1426         char *str = strdup(arg);
1427         int type = -1;
1428
1429         if (!str)
1430                 return -ENOMEM;
1431
1432         /* first word can state for which event type the user is specifying
1433          * the fields. If no type exists, the specified fields apply to all
1434          * event types found in the file minus the invalid fields for a type.
1435          */
1436         tok = strchr(str, ':');
1437         if (tok) {
1438                 *tok = '\0';
1439                 tok++;
1440                 if (!strcmp(str, "hw"))
1441                         type = PERF_TYPE_HARDWARE;
1442                 else if (!strcmp(str, "sw"))
1443                         type = PERF_TYPE_SOFTWARE;
1444                 else if (!strcmp(str, "trace"))
1445                         type = PERF_TYPE_TRACEPOINT;
1446                 else if (!strcmp(str, "raw"))
1447                         type = PERF_TYPE_RAW;
1448                 else if (!strcmp(str, "break"))
1449                         type = PERF_TYPE_BREAKPOINT;
1450                 else {
1451                         fprintf(stderr, "Invalid event type in field string.\n");
1452                         rc = -EINVAL;
1453                         goto out;
1454                 }
1455
1456                 if (output[type].user_set)
1457                         pr_warning("Overriding previous field request for %s events.\n",
1458                                    event_type(type));
1459
1460                 output[type].fields = 0;
1461                 output[type].user_set = true;
1462                 output[type].wildcard_set = false;
1463
1464         } else {
1465                 tok = str;
1466                 if (strlen(str) == 0) {
1467                         fprintf(stderr,
1468                                 "Cannot set fields to 'none' for all event types.\n");
1469                         rc = -EINVAL;
1470                         goto out;
1471                 }
1472
1473                 if (output_set_by_user())
1474                         pr_warning("Overriding previous field request for all events.\n");
1475
1476                 for (j = 0; j < PERF_TYPE_MAX; ++j) {
1477                         output[j].fields = 0;
1478                         output[j].user_set = true;
1479                         output[j].wildcard_set = true;
1480                 }
1481         }
1482
1483         for (tok = strtok(tok, ","); tok; tok = strtok(NULL, ",")) {
1484                 for (i = 0; i < imax; ++i) {
1485                         if (strcmp(tok, all_output_options[i].str) == 0)
1486                                 break;
1487                 }
1488                 if (i == imax && strcmp(tok, "flags") == 0) {
1489                         print_flags = true;
1490                         continue;
1491                 }
1492                 if (i == imax) {
1493                         fprintf(stderr, "Invalid field requested.\n");
1494                         rc = -EINVAL;
1495                         goto out;
1496                 }
1497
1498                 if (type == -1) {
1499                         /* add user option to all events types for
1500                          * which it is valid
1501                          */
1502                         for (j = 0; j < PERF_TYPE_MAX; ++j) {
1503                                 if (output[j].invalid_fields & all_output_options[i].field) {
1504                                         pr_warning("\'%s\' not valid for %s events. Ignoring.\n",
1505                                                    all_output_options[i].str, event_type(j));
1506                                 } else
1507                                         output[j].fields |= all_output_options[i].field;
1508                         }
1509                 } else {
1510                         if (output[type].invalid_fields & all_output_options[i].field) {
1511                                 fprintf(stderr, "\'%s\' not valid for %s events.\n",
1512                                          all_output_options[i].str, event_type(type));
1513
1514                                 rc = -EINVAL;
1515                                 goto out;
1516                         }
1517                         output[type].fields |= all_output_options[i].field;
1518                 }
1519         }
1520
1521         if (type >= 0) {
1522                 if (output[type].fields == 0) {
1523                         pr_debug("No fields requested for %s type. "
1524                                  "Events will not be displayed.\n", event_type(type));
1525                 }
1526         }
1527
1528 out:
1529         free(str);
1530         return rc;
1531 }
1532
1533 /* Helper function for filesystems that return a dent->d_type DT_UNKNOWN */
1534 static int is_directory(const char *base_path, const struct dirent *dent)
1535 {
1536         char path[PATH_MAX];
1537         struct stat st;
1538
1539         sprintf(path, "%s/%s", base_path, dent->d_name);
1540         if (stat(path, &st))
1541                 return 0;
1542
1543         return S_ISDIR(st.st_mode);
1544 }
1545
1546 #define for_each_lang(scripts_path, scripts_dir, lang_dirent)           \
1547         while ((lang_dirent = readdir(scripts_dir)) != NULL)            \
1548                 if ((lang_dirent->d_type == DT_DIR ||                   \
1549                      (lang_dirent->d_type == DT_UNKNOWN &&              \
1550                       is_directory(scripts_path, lang_dirent))) &&      \
1551                     (strcmp(lang_dirent->d_name, ".")) &&               \
1552                     (strcmp(lang_dirent->d_name, "..")))
1553
1554 #define for_each_script(lang_path, lang_dir, script_dirent)             \
1555         while ((script_dirent = readdir(lang_dir)) != NULL)             \
1556                 if (script_dirent->d_type != DT_DIR &&                  \
1557                     (script_dirent->d_type != DT_UNKNOWN ||             \
1558                      !is_directory(lang_path, script_dirent)))
1559
1560
1561 #define RECORD_SUFFIX                   "-record"
1562 #define REPORT_SUFFIX                   "-report"
1563
1564 struct script_desc {
1565         struct list_head        node;
1566         char                    *name;
1567         char                    *half_liner;
1568         char                    *args;
1569 };
1570
1571 static LIST_HEAD(script_descs);
1572
1573 static struct script_desc *script_desc__new(const char *name)
1574 {
1575         struct script_desc *s = zalloc(sizeof(*s));
1576
1577         if (s != NULL && name)
1578                 s->name = strdup(name);
1579
1580         return s;
1581 }
1582
1583 static void script_desc__delete(struct script_desc *s)
1584 {
1585         zfree(&s->name);
1586         zfree(&s->half_liner);
1587         zfree(&s->args);
1588         free(s);
1589 }
1590
1591 static void script_desc__add(struct script_desc *s)
1592 {
1593         list_add_tail(&s->node, &script_descs);
1594 }
1595
1596 static struct script_desc *script_desc__find(const char *name)
1597 {
1598         struct script_desc *s;
1599
1600         list_for_each_entry(s, &script_descs, node)
1601                 if (strcasecmp(s->name, name) == 0)
1602                         return s;
1603         return NULL;
1604 }
1605
1606 static struct script_desc *script_desc__findnew(const char *name)
1607 {
1608         struct script_desc *s = script_desc__find(name);
1609
1610         if (s)
1611                 return s;
1612
1613         s = script_desc__new(name);
1614         if (!s)
1615                 goto out_delete_desc;
1616
1617         script_desc__add(s);
1618
1619         return s;
1620
1621 out_delete_desc:
1622         script_desc__delete(s);
1623
1624         return NULL;
1625 }
1626
1627 static const char *ends_with(const char *str, const char *suffix)
1628 {
1629         size_t suffix_len = strlen(suffix);
1630         const char *p = str;
1631
1632         if (strlen(str) > suffix_len) {
1633                 p = str + strlen(str) - suffix_len;
1634                 if (!strncmp(p, suffix, suffix_len))
1635                         return p;
1636         }
1637
1638         return NULL;
1639 }
1640
1641 static int read_script_info(struct script_desc *desc, const char *filename)
1642 {
1643         char line[BUFSIZ], *p;
1644         FILE *fp;
1645
1646         fp = fopen(filename, "r");
1647         if (!fp)
1648                 return -1;
1649
1650         while (fgets(line, sizeof(line), fp)) {
1651                 p = ltrim(line);
1652                 if (strlen(p) == 0)
1653                         continue;
1654                 if (*p != '#')
1655                         continue;
1656                 p++;
1657                 if (strlen(p) && *p == '!')
1658                         continue;
1659
1660                 p = ltrim(p);
1661                 if (strlen(p) && p[strlen(p) - 1] == '\n')
1662                         p[strlen(p) - 1] = '\0';
1663
1664                 if (!strncmp(p, "description:", strlen("description:"))) {
1665                         p += strlen("description:");
1666                         desc->half_liner = strdup(ltrim(p));
1667                         continue;
1668                 }
1669
1670                 if (!strncmp(p, "args:", strlen("args:"))) {
1671                         p += strlen("args:");
1672                         desc->args = strdup(ltrim(p));
1673                         continue;
1674                 }
1675         }
1676
1677         fclose(fp);
1678
1679         return 0;
1680 }
1681
1682 static char *get_script_root(struct dirent *script_dirent, const char *suffix)
1683 {
1684         char *script_root, *str;
1685
1686         script_root = strdup(script_dirent->d_name);
1687         if (!script_root)
1688                 return NULL;
1689
1690         str = (char *)ends_with(script_root, suffix);
1691         if (!str) {
1692                 free(script_root);
1693                 return NULL;
1694         }
1695
1696         *str = '\0';
1697         return script_root;
1698 }
1699
1700 static int list_available_scripts(const struct option *opt __maybe_unused,
1701                                   const char *s __maybe_unused,
1702                                   int unset __maybe_unused)
1703 {
1704         struct dirent *script_dirent, *lang_dirent;
1705         char scripts_path[MAXPATHLEN];
1706         DIR *scripts_dir, *lang_dir;
1707         char script_path[MAXPATHLEN];
1708         char lang_path[MAXPATHLEN];
1709         struct script_desc *desc;
1710         char first_half[BUFSIZ];
1711         char *script_root;
1712
1713         snprintf(scripts_path, MAXPATHLEN, "%s/scripts", get_argv_exec_path());
1714
1715         scripts_dir = opendir(scripts_path);
1716         if (!scripts_dir) {
1717                 fprintf(stdout,
1718                         "open(%s) failed.\n"
1719                         "Check \"PERF_EXEC_PATH\" env to set scripts dir.\n",
1720                         scripts_path);
1721                 exit(-1);
1722         }
1723
1724         for_each_lang(scripts_path, scripts_dir, lang_dirent) {
1725                 snprintf(lang_path, MAXPATHLEN, "%s/%s/bin", scripts_path,
1726                          lang_dirent->d_name);
1727                 lang_dir = opendir(lang_path);
1728                 if (!lang_dir)
1729                         continue;
1730
1731                 for_each_script(lang_path, lang_dir, script_dirent) {
1732                         script_root = get_script_root(script_dirent, REPORT_SUFFIX);
1733                         if (script_root) {
1734                                 desc = script_desc__findnew(script_root);
1735                                 snprintf(script_path, MAXPATHLEN, "%s/%s",
1736                                          lang_path, script_dirent->d_name);
1737                                 read_script_info(desc, script_path);
1738                                 free(script_root);
1739                         }
1740                 }
1741         }
1742
1743         fprintf(stdout, "List of available trace scripts:\n");
1744         list_for_each_entry(desc, &script_descs, node) {
1745                 sprintf(first_half, "%s %s", desc->name,
1746                         desc->args ? desc->args : "");
1747                 fprintf(stdout, "  %-36s %s\n", first_half,
1748                         desc->half_liner ? desc->half_liner : "");
1749         }
1750
1751         exit(0);
1752 }
1753
1754 /*
1755  * Some scripts specify the required events in their "xxx-record" file,
1756  * this function will check if the events in perf.data match those
1757  * mentioned in the "xxx-record".
1758  *
1759  * Fixme: All existing "xxx-record" are all in good formats "-e event ",
1760  * which is covered well now. And new parsing code should be added to
1761  * cover the future complexing formats like event groups etc.
1762  */
1763 static int check_ev_match(char *dir_name, char *scriptname,
1764                         struct perf_session *session)
1765 {
1766         char filename[MAXPATHLEN], evname[128];
1767         char line[BUFSIZ], *p;
1768         struct perf_evsel *pos;
1769         int match, len;
1770         FILE *fp;
1771
1772         sprintf(filename, "%s/bin/%s-record", dir_name, scriptname);
1773
1774         fp = fopen(filename, "r");
1775         if (!fp)
1776                 return -1;
1777
1778         while (fgets(line, sizeof(line), fp)) {
1779                 p = ltrim(line);
1780                 if (*p == '#')
1781                         continue;
1782
1783                 while (strlen(p)) {
1784                         p = strstr(p, "-e");
1785                         if (!p)
1786                                 break;
1787
1788                         p += 2;
1789                         p = ltrim(p);
1790                         len = strcspn(p, " \t");
1791                         if (!len)
1792                                 break;
1793
1794                         snprintf(evname, len + 1, "%s", p);
1795
1796                         match = 0;
1797                         evlist__for_each_entry(session->evlist, pos) {
1798                                 if (!strcmp(perf_evsel__name(pos), evname)) {
1799                                         match = 1;
1800                                         break;
1801                                 }
1802                         }
1803
1804                         if (!match) {
1805                                 fclose(fp);
1806                                 return -1;
1807                         }
1808                 }
1809         }
1810
1811         fclose(fp);
1812         return 0;
1813 }
1814
1815 /*
1816  * Return -1 if none is found, otherwise the actual scripts number.
1817  *
1818  * Currently the only user of this function is the script browser, which
1819  * will list all statically runnable scripts, select one, execute it and
1820  * show the output in a perf browser.
1821  */
1822 int find_scripts(char **scripts_array, char **scripts_path_array)
1823 {
1824         struct dirent *script_dirent, *lang_dirent;
1825         char scripts_path[MAXPATHLEN], lang_path[MAXPATHLEN];
1826         DIR *scripts_dir, *lang_dir;
1827         struct perf_session *session;
1828         struct perf_data_file file = {
1829                 .path = input_name,
1830                 .mode = PERF_DATA_MODE_READ,
1831         };
1832         char *temp;
1833         int i = 0;
1834
1835         session = perf_session__new(&file, false, NULL);
1836         if (!session)
1837                 return -1;
1838
1839         snprintf(scripts_path, MAXPATHLEN, "%s/scripts", get_argv_exec_path());
1840
1841         scripts_dir = opendir(scripts_path);
1842         if (!scripts_dir) {
1843                 perf_session__delete(session);
1844                 return -1;
1845         }
1846
1847         for_each_lang(scripts_path, scripts_dir, lang_dirent) {
1848                 snprintf(lang_path, MAXPATHLEN, "%s/%s", scripts_path,
1849                          lang_dirent->d_name);
1850 #ifdef NO_LIBPERL
1851                 if (strstr(lang_path, "perl"))
1852                         continue;
1853 #endif
1854 #ifdef NO_LIBPYTHON
1855                 if (strstr(lang_path, "python"))
1856                         continue;
1857 #endif
1858
1859                 lang_dir = opendir(lang_path);
1860                 if (!lang_dir)
1861                         continue;
1862
1863                 for_each_script(lang_path, lang_dir, script_dirent) {
1864                         /* Skip those real time scripts: xxxtop.p[yl] */
1865                         if (strstr(script_dirent->d_name, "top."))
1866                                 continue;
1867                         sprintf(scripts_path_array[i], "%s/%s", lang_path,
1868                                 script_dirent->d_name);
1869                         temp = strchr(script_dirent->d_name, '.');
1870                         snprintf(scripts_array[i],
1871                                 (temp - script_dirent->d_name) + 1,
1872                                 "%s", script_dirent->d_name);
1873
1874                         if (check_ev_match(lang_path,
1875                                         scripts_array[i], session))
1876                                 continue;
1877
1878                         i++;
1879                 }
1880                 closedir(lang_dir);
1881         }
1882
1883         closedir(scripts_dir);
1884         perf_session__delete(session);
1885         return i;
1886 }
1887
1888 static char *get_script_path(const char *script_root, const char *suffix)
1889 {
1890         struct dirent *script_dirent, *lang_dirent;
1891         char scripts_path[MAXPATHLEN];
1892         char script_path[MAXPATHLEN];
1893         DIR *scripts_dir, *lang_dir;
1894         char lang_path[MAXPATHLEN];
1895         char *__script_root;
1896
1897         snprintf(scripts_path, MAXPATHLEN, "%s/scripts", get_argv_exec_path());
1898
1899         scripts_dir = opendir(scripts_path);
1900         if (!scripts_dir)
1901                 return NULL;
1902
1903         for_each_lang(scripts_path, scripts_dir, lang_dirent) {
1904                 snprintf(lang_path, MAXPATHLEN, "%s/%s/bin", scripts_path,
1905                          lang_dirent->d_name);
1906                 lang_dir = opendir(lang_path);
1907                 if (!lang_dir)
1908                         continue;
1909
1910                 for_each_script(lang_path, lang_dir, script_dirent) {
1911                         __script_root = get_script_root(script_dirent, suffix);
1912                         if (__script_root && !strcmp(script_root, __script_root)) {
1913                                 free(__script_root);
1914                                 closedir(lang_dir);
1915                                 closedir(scripts_dir);
1916                                 snprintf(script_path, MAXPATHLEN, "%s/%s",
1917                                          lang_path, script_dirent->d_name);
1918                                 return strdup(script_path);
1919                         }
1920                         free(__script_root);
1921                 }
1922                 closedir(lang_dir);
1923         }
1924         closedir(scripts_dir);
1925
1926         return NULL;
1927 }
1928
1929 static bool is_top_script(const char *script_path)
1930 {
1931         return ends_with(script_path, "top") == NULL ? false : true;
1932 }
1933
1934 static int has_required_arg(char *script_path)
1935 {
1936         struct script_desc *desc;
1937         int n_args = 0;
1938         char *p;
1939
1940         desc = script_desc__new(NULL);
1941
1942         if (read_script_info(desc, script_path))
1943                 goto out;
1944
1945         if (!desc->args)
1946                 goto out;
1947
1948         for (p = desc->args; *p; p++)
1949                 if (*p == '<')
1950                         n_args++;
1951 out:
1952         script_desc__delete(desc);
1953
1954         return n_args;
1955 }
1956
1957 static int have_cmd(int argc, const char **argv)
1958 {
1959         char **__argv = malloc(sizeof(const char *) * argc);
1960
1961         if (!__argv) {
1962                 pr_err("malloc failed\n");
1963                 return -1;
1964         }
1965
1966         memcpy(__argv, argv, sizeof(const char *) * argc);
1967         argc = parse_options(argc, (const char **)__argv, record_options,
1968                              NULL, PARSE_OPT_STOP_AT_NON_OPTION);
1969         free(__argv);
1970
1971         system_wide = (argc == 0);
1972
1973         return 0;
1974 }
1975
1976 static void script__setup_sample_type(struct perf_script *script)
1977 {
1978         struct perf_session *session = script->session;
1979         u64 sample_type = perf_evlist__combined_sample_type(session->evlist);
1980
1981         if (symbol_conf.use_callchain || symbol_conf.cumulate_callchain) {
1982                 if ((sample_type & PERF_SAMPLE_REGS_USER) &&
1983                     (sample_type & PERF_SAMPLE_STACK_USER))
1984                         callchain_param.record_mode = CALLCHAIN_DWARF;
1985                 else if (sample_type & PERF_SAMPLE_BRANCH_STACK)
1986                         callchain_param.record_mode = CALLCHAIN_LBR;
1987                 else
1988                         callchain_param.record_mode = CALLCHAIN_FP;
1989         }
1990 }
1991
1992 static int process_stat_round_event(struct perf_tool *tool __maybe_unused,
1993                                     union perf_event *event,
1994                                     struct perf_session *session)
1995 {
1996         struct stat_round_event *round = &event->stat_round;
1997         struct perf_evsel *counter;
1998
1999         evlist__for_each_entry(session->evlist, counter) {
2000                 perf_stat_process_counter(&stat_config, counter);
2001                 process_stat(counter, round->time);
2002         }
2003
2004         process_stat_interval(round->time);
2005         return 0;
2006 }
2007
2008 static int process_stat_config_event(struct perf_tool *tool __maybe_unused,
2009                                      union perf_event *event,
2010                                      struct perf_session *session __maybe_unused)
2011 {
2012         perf_event__read_stat_config(&stat_config, &event->stat_config);
2013         return 0;
2014 }
2015
2016 static int set_maps(struct perf_script *script)
2017 {
2018         struct perf_evlist *evlist = script->session->evlist;
2019
2020         if (!script->cpus || !script->threads)
2021                 return 0;
2022
2023         if (WARN_ONCE(script->allocated, "stats double allocation\n"))
2024                 return -EINVAL;
2025
2026         perf_evlist__set_maps(evlist, script->cpus, script->threads);
2027
2028         if (perf_evlist__alloc_stats(evlist, true))
2029                 return -ENOMEM;
2030
2031         script->allocated = true;
2032         return 0;
2033 }
2034
2035 static
2036 int process_thread_map_event(struct perf_tool *tool,
2037                              union perf_event *event,
2038                              struct perf_session *session __maybe_unused)
2039 {
2040         struct perf_script *script = container_of(tool, struct perf_script, tool);
2041
2042         if (script->threads) {
2043                 pr_warning("Extra thread map event, ignoring.\n");
2044                 return 0;
2045         }
2046
2047         script->threads = thread_map__new_event(&event->thread_map);
2048         if (!script->threads)
2049                 return -ENOMEM;
2050
2051         return set_maps(script);
2052 }
2053
2054 static
2055 int process_cpu_map_event(struct perf_tool *tool __maybe_unused,
2056                           union perf_event *event,
2057                           struct perf_session *session __maybe_unused)
2058 {
2059         struct perf_script *script = container_of(tool, struct perf_script, tool);
2060
2061         if (script->cpus) {
2062                 pr_warning("Extra cpu map event, ignoring.\n");
2063                 return 0;
2064         }
2065
2066         script->cpus = cpu_map__new_data(&event->cpu_map.data);
2067         if (!script->cpus)
2068                 return -ENOMEM;
2069
2070         return set_maps(script);
2071 }
2072
2073 int cmd_script(int argc, const char **argv, const char *prefix __maybe_unused)
2074 {
2075         bool show_full_info = false;
2076         bool header = false;
2077         bool header_only = false;
2078         bool script_started = false;
2079         char *rec_script_path = NULL;
2080         char *rep_script_path = NULL;
2081         struct perf_session *session;
2082         struct itrace_synth_opts itrace_synth_opts = { .set = false, };
2083         char *script_path = NULL;
2084         const char **__argv;
2085         int i, j, err = 0;
2086         struct perf_script script = {
2087                 .tool = {
2088                         .sample          = process_sample_event,
2089                         .mmap            = perf_event__process_mmap,
2090                         .mmap2           = perf_event__process_mmap2,
2091                         .comm            = perf_event__process_comm,
2092                         .exit            = perf_event__process_exit,
2093                         .fork            = perf_event__process_fork,
2094                         .attr            = process_attr,
2095                         .event_update   = perf_event__process_event_update,
2096                         .tracing_data    = perf_event__process_tracing_data,
2097                         .build_id        = perf_event__process_build_id,
2098                         .id_index        = perf_event__process_id_index,
2099                         .auxtrace_info   = perf_event__process_auxtrace_info,
2100                         .auxtrace        = perf_event__process_auxtrace,
2101                         .auxtrace_error  = perf_event__process_auxtrace_error,
2102                         .stat            = perf_event__process_stat_event,
2103                         .stat_round      = process_stat_round_event,
2104                         .stat_config     = process_stat_config_event,
2105                         .thread_map      = process_thread_map_event,
2106                         .cpu_map         = process_cpu_map_event,
2107                         .ordered_events  = true,
2108                         .ordering_requires_timestamps = true,
2109                 },
2110         };
2111         struct perf_data_file file = {
2112                 .mode = PERF_DATA_MODE_READ,
2113         };
2114         const struct option options[] = {
2115         OPT_BOOLEAN('D', "dump-raw-trace", &dump_trace,
2116                     "dump raw trace in ASCII"),
2117         OPT_INCR('v', "verbose", &verbose,
2118                  "be more verbose (show symbol address, etc)"),
2119         OPT_BOOLEAN('L', "Latency", &latency_format,
2120                     "show latency attributes (irqs/preemption disabled, etc)"),
2121         OPT_CALLBACK_NOOPT('l', "list", NULL, NULL, "list available scripts",
2122                            list_available_scripts),
2123         OPT_CALLBACK('s', "script", NULL, "name",
2124                      "script file name (lang:script name, script name, or *)",
2125                      parse_scriptname),
2126         OPT_STRING('g', "gen-script", &generate_script_lang, "lang",
2127                    "generate perf-script.xx script in specified language"),
2128         OPT_STRING('i', "input", &input_name, "file", "input file name"),
2129         OPT_BOOLEAN('d', "debug-mode", &debug_mode,
2130                    "do various checks like samples ordering and lost events"),
2131         OPT_BOOLEAN(0, "header", &header, "Show data header."),
2132         OPT_BOOLEAN(0, "header-only", &header_only, "Show only data header."),
2133         OPT_STRING('k', "vmlinux", &symbol_conf.vmlinux_name,
2134                    "file", "vmlinux pathname"),
2135         OPT_STRING(0, "kallsyms", &symbol_conf.kallsyms_name,
2136                    "file", "kallsyms pathname"),
2137         OPT_BOOLEAN('G', "hide-call-graph", &no_callchain,
2138                     "When printing symbols do not display call chain"),
2139         OPT_CALLBACK(0, "symfs", NULL, "directory",
2140                      "Look for files with symbols relative to this directory",
2141                      symbol__config_symfs),
2142         OPT_CALLBACK('F', "fields", NULL, "str",
2143                      "comma separated output fields prepend with 'type:'. "
2144                      "Valid types: hw,sw,trace,raw. "
2145                      "Fields: comm,tid,pid,time,cpu,event,trace,ip,sym,dso,"
2146                      "addr,symoff,period,iregs,brstack,brstacksym,flags,"
2147                      "bpf-output,callindent,insn,insnlen", parse_output_fields),
2148         OPT_BOOLEAN('a', "all-cpus", &system_wide,
2149                     "system-wide collection from all CPUs"),
2150         OPT_STRING('S', "symbols", &symbol_conf.sym_list_str, "symbol[,symbol...]",
2151                    "only consider these symbols"),
2152         OPT_STRING('C', "cpu", &cpu_list, "cpu", "list of cpus to profile"),
2153         OPT_STRING('c', "comms", &symbol_conf.comm_list_str, "comm[,comm...]",
2154                    "only display events for these comms"),
2155         OPT_STRING(0, "pid", &symbol_conf.pid_list_str, "pid[,pid...]",
2156                    "only consider symbols in these pids"),
2157         OPT_STRING(0, "tid", &symbol_conf.tid_list_str, "tid[,tid...]",
2158                    "only consider symbols in these tids"),
2159         OPT_UINTEGER(0, "max-stack", &scripting_max_stack,
2160                      "Set the maximum stack depth when parsing the callchain, "
2161                      "anything beyond the specified depth will be ignored. "
2162                      "Default: kernel.perf_event_max_stack or " __stringify(PERF_MAX_STACK_DEPTH)),
2163         OPT_BOOLEAN('I', "show-info", &show_full_info,
2164                     "display extended information from perf.data file"),
2165         OPT_BOOLEAN('\0', "show-kernel-path", &symbol_conf.show_kernel_path,
2166                     "Show the path of [kernel.kallsyms]"),
2167         OPT_BOOLEAN('\0', "show-task-events", &script.show_task_events,
2168                     "Show the fork/comm/exit events"),
2169         OPT_BOOLEAN('\0', "show-mmap-events", &script.show_mmap_events,
2170                     "Show the mmap events"),
2171         OPT_BOOLEAN('\0', "show-switch-events", &script.show_switch_events,
2172                     "Show context switch events (if recorded)"),
2173         OPT_BOOLEAN('f', "force", &file.force, "don't complain, do it"),
2174         OPT_BOOLEAN(0, "ns", &nanosecs,
2175                     "Use 9 decimal places when displaying time"),
2176         OPT_CALLBACK_OPTARG(0, "itrace", &itrace_synth_opts, NULL, "opts",
2177                             "Instruction Tracing options",
2178                             itrace_parse_synth_opts),
2179         OPT_BOOLEAN(0, "full-source-path", &srcline_full_filename,
2180                         "Show full source file name path for source lines"),
2181         OPT_BOOLEAN(0, "demangle", &symbol_conf.demangle,
2182                         "Enable symbol demangling"),
2183         OPT_BOOLEAN(0, "demangle-kernel", &symbol_conf.demangle_kernel,
2184                         "Enable kernel symbol demangling"),
2185
2186         OPT_END()
2187         };
2188         const char * const script_subcommands[] = { "record", "report", NULL };
2189         const char *script_usage[] = {
2190                 "perf script [<options>]",
2191                 "perf script [<options>] record <script> [<record-options>] <command>",
2192                 "perf script [<options>] report <script> [script-args]",
2193                 "perf script [<options>] <script> [<record-options>] <command>",
2194                 "perf script [<options>] <top-script> [script-args]",
2195                 NULL
2196         };
2197
2198         setup_scripting();
2199
2200         argc = parse_options_subcommand(argc, argv, options, script_subcommands, script_usage,
2201                              PARSE_OPT_STOP_AT_NON_OPTION);
2202
2203         file.path = input_name;
2204
2205         if (argc > 1 && !strncmp(argv[0], "rec", strlen("rec"))) {
2206                 rec_script_path = get_script_path(argv[1], RECORD_SUFFIX);
2207                 if (!rec_script_path)
2208                         return cmd_record(argc, argv, NULL);
2209         }
2210
2211         if (argc > 1 && !strncmp(argv[0], "rep", strlen("rep"))) {
2212                 rep_script_path = get_script_path(argv[1], REPORT_SUFFIX);
2213                 if (!rep_script_path) {
2214                         fprintf(stderr,
2215                                 "Please specify a valid report script"
2216                                 "(see 'perf script -l' for listing)\n");
2217                         return -1;
2218                 }
2219         }
2220
2221         if (itrace_synth_opts.callchain &&
2222             itrace_synth_opts.callchain_sz > scripting_max_stack)
2223                 scripting_max_stack = itrace_synth_opts.callchain_sz;
2224
2225         /* make sure PERF_EXEC_PATH is set for scripts */
2226         set_argv_exec_path(get_argv_exec_path());
2227
2228         if (argc && !script_name && !rec_script_path && !rep_script_path) {
2229                 int live_pipe[2];
2230                 int rep_args;
2231                 pid_t pid;
2232
2233                 rec_script_path = get_script_path(argv[0], RECORD_SUFFIX);
2234                 rep_script_path = get_script_path(argv[0], REPORT_SUFFIX);
2235
2236                 if (!rec_script_path && !rep_script_path) {
2237                         usage_with_options_msg(script_usage, options,
2238                                 "Couldn't find script `%s'\n\n See perf"
2239                                 " script -l for available scripts.\n", argv[0]);
2240                 }
2241
2242                 if (is_top_script(argv[0])) {
2243                         rep_args = argc - 1;
2244                 } else {
2245                         int rec_args;
2246
2247                         rep_args = has_required_arg(rep_script_path);
2248                         rec_args = (argc - 1) - rep_args;
2249                         if (rec_args < 0) {
2250                                 usage_with_options_msg(script_usage, options,
2251                                         "`%s' script requires options."
2252                                         "\n\n See perf script -l for available "
2253                                         "scripts and options.\n", argv[0]);
2254                         }
2255                 }
2256
2257                 if (pipe(live_pipe) < 0) {
2258                         perror("failed to create pipe");
2259                         return -1;
2260                 }
2261
2262                 pid = fork();
2263                 if (pid < 0) {
2264                         perror("failed to fork");
2265                         return -1;
2266                 }
2267
2268                 if (!pid) {
2269                         j = 0;
2270
2271                         dup2(live_pipe[1], 1);
2272                         close(live_pipe[0]);
2273
2274                         if (is_top_script(argv[0])) {
2275                                 system_wide = true;
2276                         } else if (!system_wide) {
2277                                 if (have_cmd(argc - rep_args, &argv[rep_args]) != 0) {
2278                                         err = -1;
2279                                         goto out;
2280                                 }
2281                         }
2282
2283                         __argv = malloc((argc + 6) * sizeof(const char *));
2284                         if (!__argv) {
2285                                 pr_err("malloc failed\n");
2286                                 err = -ENOMEM;
2287                                 goto out;
2288                         }
2289
2290                         __argv[j++] = "/bin/sh";
2291                         __argv[j++] = rec_script_path;
2292                         if (system_wide)
2293                                 __argv[j++] = "-a";
2294                         __argv[j++] = "-q";
2295                         __argv[j++] = "-o";
2296                         __argv[j++] = "-";
2297                         for (i = rep_args + 1; i < argc; i++)
2298                                 __argv[j++] = argv[i];
2299                         __argv[j++] = NULL;
2300
2301                         execvp("/bin/sh", (char **)__argv);
2302                         free(__argv);
2303                         exit(-1);
2304                 }
2305
2306                 dup2(live_pipe[0], 0);
2307                 close(live_pipe[1]);
2308
2309                 __argv = malloc((argc + 4) * sizeof(const char *));
2310                 if (!__argv) {
2311                         pr_err("malloc failed\n");
2312                         err = -ENOMEM;
2313                         goto out;
2314                 }
2315
2316                 j = 0;
2317                 __argv[j++] = "/bin/sh";
2318                 __argv[j++] = rep_script_path;
2319                 for (i = 1; i < rep_args + 1; i++)
2320                         __argv[j++] = argv[i];
2321                 __argv[j++] = "-i";
2322                 __argv[j++] = "-";
2323                 __argv[j++] = NULL;
2324
2325                 execvp("/bin/sh", (char **)__argv);
2326                 free(__argv);
2327                 exit(-1);
2328         }
2329
2330         if (rec_script_path)
2331                 script_path = rec_script_path;
2332         if (rep_script_path)
2333                 script_path = rep_script_path;
2334
2335         if (script_path) {
2336                 j = 0;
2337
2338                 if (!rec_script_path)
2339                         system_wide = false;
2340                 else if (!system_wide) {
2341                         if (have_cmd(argc - 1, &argv[1]) != 0) {
2342                                 err = -1;
2343                                 goto out;
2344                         }
2345                 }
2346
2347                 __argv = malloc((argc + 2) * sizeof(const char *));
2348                 if (!__argv) {
2349                         pr_err("malloc failed\n");
2350                         err = -ENOMEM;
2351                         goto out;
2352                 }
2353
2354                 __argv[j++] = "/bin/sh";
2355                 __argv[j++] = script_path;
2356                 if (system_wide)
2357                         __argv[j++] = "-a";
2358                 for (i = 2; i < argc; i++)
2359                         __argv[j++] = argv[i];
2360                 __argv[j++] = NULL;
2361
2362                 execvp("/bin/sh", (char **)__argv);
2363                 free(__argv);
2364                 exit(-1);
2365         }
2366
2367         if (!script_name)
2368                 setup_pager();
2369
2370         session = perf_session__new(&file, false, &script.tool);
2371         if (session == NULL)
2372                 return -1;
2373
2374         if (header || header_only) {
2375                 perf_session__fprintf_info(session, stdout, show_full_info);
2376                 if (header_only)
2377                         goto out_delete;
2378         }
2379
2380         if (symbol__init(&session->header.env) < 0)
2381                 goto out_delete;
2382
2383         script.session = session;
2384         script__setup_sample_type(&script);
2385
2386         if (output[PERF_TYPE_HARDWARE].fields & PERF_OUTPUT_CALLINDENT)
2387                 itrace_synth_opts.thread_stack = true;
2388
2389         session->itrace_synth_opts = &itrace_synth_opts;
2390
2391         if (cpu_list) {
2392                 err = perf_session__cpu_bitmap(session, cpu_list, cpu_bitmap);
2393                 if (err < 0)
2394                         goto out_delete;
2395         }
2396
2397         if (!no_callchain)
2398                 symbol_conf.use_callchain = true;
2399         else
2400                 symbol_conf.use_callchain = false;
2401
2402         if (session->tevent.pevent &&
2403             pevent_set_function_resolver(session->tevent.pevent,
2404                                          machine__resolve_kernel_addr,
2405                                          &session->machines.host) < 0) {
2406                 pr_err("%s: failed to set libtraceevent function resolver\n", __func__);
2407                 return -1;
2408         }
2409
2410         if (generate_script_lang) {
2411                 struct stat perf_stat;
2412                 int input;
2413
2414                 if (output_set_by_user()) {
2415                         fprintf(stderr,
2416                                 "custom fields not supported for generated scripts");
2417                         err = -EINVAL;
2418                         goto out_delete;
2419                 }
2420
2421                 input = open(file.path, O_RDONLY);      /* input_name */
2422                 if (input < 0) {
2423                         err = -errno;
2424                         perror("failed to open file");
2425                         goto out_delete;
2426                 }
2427
2428                 err = fstat(input, &perf_stat);
2429                 if (err < 0) {
2430                         perror("failed to stat file");
2431                         goto out_delete;
2432                 }
2433
2434                 if (!perf_stat.st_size) {
2435                         fprintf(stderr, "zero-sized file, nothing to do!\n");
2436                         goto out_delete;
2437                 }
2438
2439                 scripting_ops = script_spec__lookup(generate_script_lang);
2440                 if (!scripting_ops) {
2441                         fprintf(stderr, "invalid language specifier");
2442                         err = -ENOENT;
2443                         goto out_delete;
2444                 }
2445
2446                 err = scripting_ops->generate_script(session->tevent.pevent,
2447                                                      "perf-script");
2448                 goto out_delete;
2449         }
2450
2451         if (script_name) {
2452                 err = scripting_ops->start_script(script_name, argc, argv);
2453                 if (err)
2454                         goto out_delete;
2455                 pr_debug("perf script started with script %s\n\n", script_name);
2456                 script_started = true;
2457         }
2458
2459
2460         err = perf_session__check_output_opt(session);
2461         if (err < 0)
2462                 goto out_delete;
2463
2464         err = __cmd_script(&script);
2465
2466         flush_scripting();
2467
2468 out_delete:
2469         perf_evlist__free_stats(session->evlist);
2470         perf_session__delete(session);
2471
2472         if (script_started)
2473                 cleanup_scripting();
2474 out:
2475         return err;
2476 }
This page took 0.177603 seconds and 4 git commands to generate.