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