1 // SPDX-License-Identifier: GPL-2.0 2 #include "builtin.h" 3 #include "perf.h" 4 5 #include <dwarf-regs.h> 6 #include "util/build-id.h" 7 #include "util/evsel.h" 8 #include "util/evlist.h" 9 #include "util/mmap.h" 10 #include "util/term.h" 11 #include "util/symbol.h" 12 #include "util/thread.h" 13 #include "util/header.h" 14 #include "util/session.h" 15 #include "util/intlist.h" 16 #include <subcmd/pager.h> 17 #include <subcmd/parse-options.h> 18 #include "util/trace-event.h" 19 #include "util/debug.h" 20 #include "util/tool.h" 21 #include "util/stat.h" 22 #include "util/synthetic-events.h" 23 #include "util/top.h" 24 #include "util/data.h" 25 #include "util/event.h" 26 #include "util/ordered-events.h" 27 #include "util/kvm-stat.h" 28 #include "util/util.h" 29 #include "ui/browsers/hists.h" 30 #include "ui/progress.h" 31 #include "ui/ui.h" 32 #include "util/string2.h" 33 34 #include <sys/prctl.h> 35 #ifdef HAVE_TIMERFD_SUPPORT 36 #include <sys/timerfd.h> 37 #endif 38 #include <sys/time.h> 39 #include <sys/types.h> 40 #include <sys/stat.h> 41 #include <fcntl.h> 42 43 #include <linux/err.h> 44 #include <linux/kernel.h> 45 #include <linux/string.h> 46 #include <linux/time64.h> 47 #include <linux/zalloc.h> 48 #include <errno.h> 49 #include <inttypes.h> 50 #include <poll.h> 51 #include <termios.h> 52 #include <semaphore.h> 53 #include <signal.h> 54 #include <math.h> 55 #include <perf/mmap.h> 56 57 #if defined(HAVE_LIBTRACEEVENT) 58 #define GET_EVENT_KEY(func, field) \ 59 static u64 get_event_ ##func(struct kvm_event *event, int vcpu) \ 60 { \ 61 if (vcpu == -1) \ 62 return event->total.field; \ 63 \ 64 if (vcpu >= event->max_vcpu) \ 65 return 0; \ 66 \ 67 return event->vcpu[vcpu].field; \ 68 } 69 70 #define COMPARE_EVENT_KEY(func, field) \ 71 GET_EVENT_KEY(func, field) \ 72 static int64_t cmp_event_ ## func(struct kvm_event *one, \ 73 struct kvm_event *two, int vcpu) \ 74 { \ 75 return get_event_ ##func(one, vcpu) - \ 76 get_event_ ##func(two, vcpu); \ 77 } 78 79 COMPARE_EVENT_KEY(time, time); 80 COMPARE_EVENT_KEY(max, stats.max); 81 COMPARE_EVENT_KEY(min, stats.min); 82 COMPARE_EVENT_KEY(count, stats.n); 83 COMPARE_EVENT_KEY(mean, stats.mean); 84 85 struct kvm_hists { 86 struct hists hists; 87 struct perf_hpp_list list; 88 }; 89 90 struct kvm_dimension { 91 const char *name; 92 const char *header; 93 int width; 94 int64_t (*cmp)(struct perf_hpp_fmt *fmt, struct hist_entry *left, 95 struct hist_entry *right); 96 int (*entry)(struct perf_hpp_fmt *fmt, struct perf_hpp *hpp, 97 struct hist_entry *he); 98 }; 99 100 struct kvm_fmt { 101 struct perf_hpp_fmt fmt; 102 struct kvm_dimension *dim; 103 }; 104 105 static struct kvm_hists kvm_hists; 106 107 static int64_t ev_name_cmp(struct perf_hpp_fmt *fmt __maybe_unused, 108 struct hist_entry *left, 109 struct hist_entry *right) 110 { 111 /* Return opposite number for sorting in alphabetical order */ 112 return -strcmp(left->kvm_info->name, right->kvm_info->name); 113 } 114 115 static int fmt_width(struct perf_hpp_fmt *fmt, 116 struct perf_hpp *hpp __maybe_unused, 117 struct hists *hists __maybe_unused); 118 119 static int ev_name_entry(struct perf_hpp_fmt *fmt, struct perf_hpp *hpp, 120 struct hist_entry *he) 121 { 122 int width = fmt_width(fmt, hpp, he->hists); 123 124 return scnprintf(hpp->buf, hpp->size, "%*s", width, he->kvm_info->name); 125 } 126 127 static struct kvm_dimension dim_event = { 128 .header = "Event name", 129 .name = "ev_name", 130 .cmp = ev_name_cmp, 131 .entry = ev_name_entry, 132 .width = 40, 133 }; 134 135 #define EV_METRIC_CMP(metric) \ 136 static int64_t ev_cmp_##metric(struct perf_hpp_fmt *fmt __maybe_unused, \ 137 struct hist_entry *left, \ 138 struct hist_entry *right) \ 139 { \ 140 struct kvm_event *event_left; \ 141 struct kvm_event *event_right; \ 142 struct perf_kvm_stat *perf_kvm; \ 143 \ 144 event_left = container_of(left, struct kvm_event, he); \ 145 event_right = container_of(right, struct kvm_event, he); \ 146 \ 147 perf_kvm = event_left->perf_kvm; \ 148 return cmp_event_##metric(event_left, event_right, \ 149 perf_kvm->trace_vcpu); \ 150 } 151 152 EV_METRIC_CMP(time) 153 EV_METRIC_CMP(count) 154 EV_METRIC_CMP(max) 155 EV_METRIC_CMP(min) 156 EV_METRIC_CMP(mean) 157 158 #define EV_METRIC_ENTRY(metric) \ 159 static int ev_entry_##metric(struct perf_hpp_fmt *fmt, \ 160 struct perf_hpp *hpp, \ 161 struct hist_entry *he) \ 162 { \ 163 struct kvm_event *event; \ 164 int width = fmt_width(fmt, hpp, he->hists); \ 165 struct perf_kvm_stat *perf_kvm; \ 166 \ 167 event = container_of(he, struct kvm_event, he); \ 168 perf_kvm = event->perf_kvm; \ 169 return scnprintf(hpp->buf, hpp->size, "%*lu", width, \ 170 get_event_##metric(event, perf_kvm->trace_vcpu)); \ 171 } 172 173 EV_METRIC_ENTRY(time) 174 EV_METRIC_ENTRY(count) 175 EV_METRIC_ENTRY(max) 176 EV_METRIC_ENTRY(min) 177 178 static struct kvm_dimension dim_time = { 179 .header = "Time (ns)", 180 .name = "time", 181 .cmp = ev_cmp_time, 182 .entry = ev_entry_time, 183 .width = 12, 184 }; 185 186 static struct kvm_dimension dim_count = { 187 .header = "Samples", 188 .name = "sample", 189 .cmp = ev_cmp_count, 190 .entry = ev_entry_count, 191 .width = 12, 192 }; 193 194 static struct kvm_dimension dim_max_time = { 195 .header = "Max Time (ns)", 196 .name = "max_t", 197 .cmp = ev_cmp_max, 198 .entry = ev_entry_max, 199 .width = 14, 200 }; 201 202 static struct kvm_dimension dim_min_time = { 203 .header = "Min Time (ns)", 204 .name = "min_t", 205 .cmp = ev_cmp_min, 206 .entry = ev_entry_min, 207 .width = 14, 208 }; 209 210 static int ev_entry_mean(struct perf_hpp_fmt *fmt, struct perf_hpp *hpp, 211 struct hist_entry *he) 212 { 213 struct kvm_event *event; 214 int width = fmt_width(fmt, hpp, he->hists); 215 struct perf_kvm_stat *perf_kvm; 216 217 event = container_of(he, struct kvm_event, he); 218 perf_kvm = event->perf_kvm; 219 return scnprintf(hpp->buf, hpp->size, "%*lu", width, 220 get_event_mean(event, perf_kvm->trace_vcpu)); 221 } 222 223 static struct kvm_dimension dim_mean_time = { 224 .header = "Mean Time (ns)", 225 .name = "mean_t", 226 .cmp = ev_cmp_mean, 227 .entry = ev_entry_mean, 228 .width = 14, 229 }; 230 231 #define PERC_STR(__s, __v) \ 232 ({ \ 233 scnprintf(__s, sizeof(__s), "%.2F%%", __v); \ 234 __s; \ 235 }) 236 237 static double percent(u64 st, u64 tot) 238 { 239 return tot ? 100. * (double) st / (double) tot : 0; 240 } 241 242 #define EV_METRIC_PERCENT(metric) \ 243 static int ev_percent_##metric(struct hist_entry *he) \ 244 { \ 245 struct kvm_event *event; \ 246 struct perf_kvm_stat *perf_kvm; \ 247 \ 248 event = container_of(he, struct kvm_event, he); \ 249 perf_kvm = event->perf_kvm; \ 250 \ 251 return percent(get_event_##metric(event, perf_kvm->trace_vcpu), \ 252 perf_kvm->total_##metric); \ 253 } 254 255 EV_METRIC_PERCENT(time) 256 EV_METRIC_PERCENT(count) 257 258 static int ev_entry_time_precent(struct perf_hpp_fmt *fmt, 259 struct perf_hpp *hpp, 260 struct hist_entry *he) 261 { 262 int width = fmt_width(fmt, hpp, he->hists); 263 double per; 264 char buf[10]; 265 266 per = ev_percent_time(he); 267 return scnprintf(hpp->buf, hpp->size, "%*s", width, PERC_STR(buf, per)); 268 } 269 270 static int64_t 271 ev_cmp_time_precent(struct perf_hpp_fmt *fmt __maybe_unused, 272 struct hist_entry *left, struct hist_entry *right) 273 { 274 double per_left; 275 double per_right; 276 277 per_left = ev_percent_time(left); 278 per_right = ev_percent_time(right); 279 280 return per_left - per_right; 281 } 282 283 static struct kvm_dimension dim_time_percent = { 284 .header = "Time%", 285 .name = "percent_time", 286 .cmp = ev_cmp_time_precent, 287 .entry = ev_entry_time_precent, 288 .width = 12, 289 }; 290 291 static int ev_entry_count_precent(struct perf_hpp_fmt *fmt, 292 struct perf_hpp *hpp, 293 struct hist_entry *he) 294 { 295 int width = fmt_width(fmt, hpp, he->hists); 296 double per; 297 char buf[10]; 298 299 per = ev_percent_count(he); 300 return scnprintf(hpp->buf, hpp->size, "%*s", width, PERC_STR(buf, per)); 301 } 302 303 static int64_t 304 ev_cmp_count_precent(struct perf_hpp_fmt *fmt __maybe_unused, 305 struct hist_entry *left, struct hist_entry *right) 306 { 307 double per_left; 308 double per_right; 309 310 per_left = ev_percent_count(left); 311 per_right = ev_percent_count(right); 312 313 return per_left - per_right; 314 } 315 316 static struct kvm_dimension dim_count_percent = { 317 .header = "Sample%", 318 .name = "percent_sample", 319 .cmp = ev_cmp_count_precent, 320 .entry = ev_entry_count_precent, 321 .width = 12, 322 }; 323 324 static struct kvm_dimension *dimensions[] = { 325 &dim_event, 326 &dim_time, 327 &dim_time_percent, 328 &dim_count, 329 &dim_count_percent, 330 &dim_max_time, 331 &dim_min_time, 332 &dim_mean_time, 333 NULL, 334 }; 335 336 static int fmt_width(struct perf_hpp_fmt *fmt, 337 struct perf_hpp *hpp __maybe_unused, 338 struct hists *hists __maybe_unused) 339 { 340 struct kvm_fmt *kvm_fmt; 341 342 kvm_fmt = container_of(fmt, struct kvm_fmt, fmt); 343 return kvm_fmt->dim->width; 344 } 345 346 static int fmt_header(struct perf_hpp_fmt *fmt, struct perf_hpp *hpp, 347 struct hists *hists, int line __maybe_unused, 348 int *span __maybe_unused) 349 { 350 struct kvm_fmt *kvm_fmt; 351 struct kvm_dimension *dim; 352 int width = fmt_width(fmt, hpp, hists); 353 354 kvm_fmt = container_of(fmt, struct kvm_fmt, fmt); 355 dim = kvm_fmt->dim; 356 357 return scnprintf(hpp->buf, hpp->size, "%*s", width, dim->header); 358 } 359 360 static bool fmt_equal(struct perf_hpp_fmt *a, struct perf_hpp_fmt *b) 361 { 362 struct kvm_fmt *kvm_fmt_a = container_of(a, struct kvm_fmt, fmt); 363 struct kvm_fmt *kvm_fmt_b = container_of(b, struct kvm_fmt, fmt); 364 365 return kvm_fmt_a->dim == kvm_fmt_b->dim; 366 } 367 368 static void fmt_free(struct perf_hpp_fmt *fmt) 369 { 370 struct kvm_fmt *kvm_fmt; 371 372 kvm_fmt = container_of(fmt, struct kvm_fmt, fmt); 373 free(kvm_fmt); 374 } 375 376 static struct kvm_dimension *get_dimension(const char *name) 377 { 378 unsigned int i; 379 380 for (i = 0; dimensions[i] != NULL; i++) { 381 if (!strcmp(dimensions[i]->name, name)) 382 return dimensions[i]; 383 } 384 385 return NULL; 386 } 387 388 static struct kvm_fmt *get_format(const char *name) 389 { 390 struct kvm_dimension *dim = get_dimension(name); 391 struct kvm_fmt *kvm_fmt; 392 struct perf_hpp_fmt *fmt; 393 394 if (!dim) 395 return NULL; 396 397 kvm_fmt = zalloc(sizeof(*kvm_fmt)); 398 if (!kvm_fmt) 399 return NULL; 400 401 kvm_fmt->dim = dim; 402 403 fmt = &kvm_fmt->fmt; 404 INIT_LIST_HEAD(&fmt->list); 405 INIT_LIST_HEAD(&fmt->sort_list); 406 fmt->cmp = dim->cmp; 407 fmt->sort = dim->cmp; 408 fmt->color = NULL; 409 fmt->entry = dim->entry; 410 fmt->header = fmt_header; 411 fmt->width = fmt_width; 412 fmt->collapse = dim->cmp; 413 fmt->equal = fmt_equal; 414 fmt->free = fmt_free; 415 416 return kvm_fmt; 417 } 418 419 static int kvm_hists__init_output(struct perf_hpp_list *hpp_list, char *name) 420 { 421 struct kvm_fmt *kvm_fmt = get_format(name); 422 423 if (!kvm_fmt) { 424 pr_warning("Fail to find format for output field %s.\n", name); 425 return -EINVAL; 426 } 427 428 perf_hpp_list__column_register(hpp_list, &kvm_fmt->fmt); 429 return 0; 430 } 431 432 static int kvm_hists__init_sort(struct perf_hpp_list *hpp_list, char *name) 433 { 434 struct kvm_fmt *kvm_fmt = get_format(name); 435 436 if (!kvm_fmt) { 437 pr_warning("Fail to find format for sorting %s.\n", name); 438 return -EINVAL; 439 } 440 441 perf_hpp_list__register_sort_field(hpp_list, &kvm_fmt->fmt); 442 return 0; 443 } 444 445 static int kvm_hpp_list__init(char *list, 446 struct perf_hpp_list *hpp_list, 447 int (*fn)(struct perf_hpp_list *hpp_list, 448 char *name)) 449 { 450 char *tmp, *tok; 451 int ret; 452 453 if (!list || !fn) 454 return 0; 455 456 for (tok = strtok_r(list, ", ", &tmp); tok; 457 tok = strtok_r(NULL, ", ", &tmp)) { 458 ret = fn(hpp_list, tok); 459 if (!ret) 460 continue; 461 462 /* Handle errors */ 463 if (ret == -EINVAL) 464 pr_err("Invalid field key: '%s'", tok); 465 else if (ret == -ESRCH) 466 pr_err("Unknown field key: '%s'", tok); 467 else 468 pr_err("Fail to initialize for field key: '%s'", tok); 469 470 break; 471 } 472 473 return ret; 474 } 475 476 static int kvm_hpp_list__parse(struct perf_hpp_list *hpp_list, 477 const char *output_, const char *sort_) 478 { 479 char *output = output_ ? strdup(output_) : NULL; 480 char *sort = sort_ ? strdup(sort_) : NULL; 481 int ret; 482 483 ret = kvm_hpp_list__init(output, hpp_list, kvm_hists__init_output); 484 if (ret) 485 goto out; 486 487 ret = kvm_hpp_list__init(sort, hpp_list, kvm_hists__init_sort); 488 if (ret) 489 goto out; 490 491 /* Copy sort keys to output fields */ 492 perf_hpp__setup_output_field(hpp_list); 493 494 /* and then copy output fields to sort keys */ 495 perf_hpp__append_sort_keys(hpp_list); 496 out: 497 free(output); 498 free(sort); 499 return ret; 500 } 501 502 static int kvm_hists__init(void) 503 { 504 kvm_hists.list.nr_header_lines = 1; 505 __hists__init(&kvm_hists.hists, &kvm_hists.list); 506 perf_hpp_list__init(&kvm_hists.list); 507 return kvm_hpp_list__parse(&kvm_hists.list, NULL, "ev_name"); 508 } 509 510 static int kvm_hists__reinit(const char *output, const char *sort) 511 { 512 perf_hpp__reset_output_field(&kvm_hists.list); 513 return kvm_hpp_list__parse(&kvm_hists.list, output, sort); 514 } 515 static void print_result(struct perf_kvm_stat *kvm); 516 517 #ifdef HAVE_SLANG_SUPPORT 518 static void kvm_browser__update_nr_entries(struct hist_browser *hb) 519 { 520 struct rb_node *nd = rb_first_cached(&hb->hists->entries); 521 u64 nr_entries = 0; 522 523 for (; nd; nd = rb_next(nd)) { 524 struct hist_entry *he = rb_entry(nd, struct hist_entry, 525 rb_node); 526 527 if (!he->filtered) 528 nr_entries++; 529 } 530 531 hb->nr_non_filtered_entries = nr_entries; 532 } 533 534 static int kvm_browser__title(struct hist_browser *browser, 535 char *buf, size_t size) 536 { 537 scnprintf(buf, size, "KVM event statistics (%lu entries)", 538 browser->nr_non_filtered_entries); 539 return 0; 540 } 541 542 static struct hist_browser* 543 perf_kvm_browser__new(struct hists *hists) 544 { 545 struct hist_browser *browser = hist_browser__new(hists); 546 547 if (browser) 548 browser->title = kvm_browser__title; 549 550 return browser; 551 } 552 553 static int kvm__hists_browse(struct hists *hists) 554 { 555 struct hist_browser *browser; 556 int key = -1; 557 558 browser = perf_kvm_browser__new(hists); 559 if (browser == NULL) 560 return -1; 561 562 /* reset abort key so that it can get Ctrl-C as a key */ 563 SLang_reset_tty(); 564 SLang_init_tty(0, 0, 0); 565 566 kvm_browser__update_nr_entries(browser); 567 568 while (1) { 569 key = hist_browser__run(browser, "? - help", true, 0); 570 571 switch (key) { 572 case 'q': 573 goto out; 574 default: 575 break; 576 } 577 } 578 579 out: 580 hist_browser__delete(browser); 581 return 0; 582 } 583 584 static void kvm_display(struct perf_kvm_stat *kvm) 585 { 586 if (!use_browser) 587 print_result(kvm); 588 else 589 kvm__hists_browse(&kvm_hists.hists); 590 } 591 592 #else 593 594 static void kvm_display(struct perf_kvm_stat *kvm) 595 { 596 use_browser = 0; 597 print_result(kvm); 598 } 599 600 #endif /* HAVE_SLANG_SUPPORT */ 601 602 #endif // defined(HAVE_LIBTRACEEVENT) 603 604 static const char *get_filename_for_perf_kvm(void) 605 { 606 const char *filename; 607 608 if (perf_host && !perf_guest) 609 filename = strdup("perf.data.host"); 610 else if (!perf_host && perf_guest) 611 filename = strdup("perf.data.guest"); 612 else 613 filename = strdup("perf.data.kvm"); 614 615 return filename; 616 } 617 618 #if defined(HAVE_LIBTRACEEVENT) 619 620 static bool register_kvm_events_ops(struct perf_kvm_stat *kvm, uint16_t e_machine) 621 { 622 const struct kvm_reg_events_ops *events_ops; 623 624 for (events_ops = kvm_reg_events_ops(e_machine); events_ops->name; events_ops++) { 625 if (!strcmp(events_ops->name, kvm->report_event)) { 626 kvm->events_ops = events_ops->ops; 627 return true; 628 } 629 } 630 631 return false; 632 } 633 634 struct vcpu_event_record { 635 int vcpu_id; 636 u64 start_time; 637 struct kvm_event *last_event; 638 }; 639 640 #ifdef HAVE_TIMERFD_SUPPORT 641 static void clear_events_cache_stats(void) 642 { 643 struct rb_root_cached *root; 644 struct rb_node *nd; 645 struct kvm_event *event; 646 int i; 647 648 if (hists__has(&kvm_hists.hists, need_collapse)) 649 root = &kvm_hists.hists.entries_collapsed; 650 else 651 root = kvm_hists.hists.entries_in; 652 653 for (nd = rb_first_cached(root); nd; nd = rb_next(nd)) { 654 struct hist_entry *he; 655 656 he = rb_entry(nd, struct hist_entry, rb_node_in); 657 event = container_of(he, struct kvm_event, he); 658 659 /* reset stats for event */ 660 event->total.time = 0; 661 init_stats(&event->total.stats); 662 663 for (i = 0; i < event->max_vcpu; ++i) { 664 event->vcpu[i].time = 0; 665 init_stats(&event->vcpu[i].stats); 666 } 667 } 668 } 669 #endif 670 671 static bool kvm_event_expand(struct kvm_event *event, int vcpu_id) 672 { 673 int old_max_vcpu = event->max_vcpu; 674 void *prev; 675 676 if (vcpu_id < event->max_vcpu) 677 return true; 678 679 while (event->max_vcpu <= vcpu_id) 680 event->max_vcpu += DEFAULT_VCPU_NUM; 681 682 prev = event->vcpu; 683 event->vcpu = realloc(event->vcpu, 684 event->max_vcpu * sizeof(*event->vcpu)); 685 if (!event->vcpu) { 686 free(prev); 687 pr_err("Not enough memory\n"); 688 return false; 689 } 690 691 memset(event->vcpu + old_max_vcpu, 0, 692 (event->max_vcpu - old_max_vcpu) * sizeof(*event->vcpu)); 693 return true; 694 } 695 696 static void *kvm_he_zalloc(size_t size) 697 { 698 struct kvm_event *kvm_ev; 699 700 kvm_ev = zalloc(size + sizeof(*kvm_ev)); 701 if (!kvm_ev) 702 return NULL; 703 704 init_stats(&kvm_ev->total.stats); 705 hists__inc_nr_samples(&kvm_hists.hists, 0); 706 return &kvm_ev->he; 707 } 708 709 static void kvm_he_free(void *he) 710 { 711 struct kvm_event *kvm_ev; 712 713 kvm_ev = container_of(he, struct kvm_event, he); 714 free(kvm_ev); 715 } 716 717 static struct hist_entry_ops kvm_ev_entry_ops = { 718 .new = kvm_he_zalloc, 719 .free = kvm_he_free, 720 }; 721 722 static struct kvm_event *find_create_kvm_event(struct perf_kvm_stat *kvm, 723 struct event_key *key, 724 struct perf_sample *sample) 725 { 726 struct kvm_event *event; 727 struct hist_entry *he; 728 struct kvm_info *ki; 729 730 BUG_ON(key->key == INVALID_KEY); 731 732 ki = kvm_info__new(); 733 if (!ki) { 734 pr_err("Failed to allocate kvm info\n"); 735 return NULL; 736 } 737 738 kvm->events_ops->decode_key(kvm, key, ki->name); 739 he = hists__add_entry_ops(&kvm_hists.hists, &kvm_ev_entry_ops, 740 &kvm->al, NULL, NULL, NULL, ki, sample, true); 741 if (he == NULL) { 742 pr_err("Failed to allocate hist entry\n"); 743 free(ki); 744 return NULL; 745 } 746 747 event = container_of(he, struct kvm_event, he); 748 if (!event->perf_kvm) { 749 event->perf_kvm = kvm; 750 event->key = *key; 751 } 752 753 return event; 754 } 755 756 static bool handle_begin_event(struct perf_kvm_stat *kvm, 757 struct vcpu_event_record *vcpu_record, 758 struct event_key *key, 759 struct perf_sample *sample) 760 { 761 struct kvm_event *event = NULL; 762 763 if (key->key != INVALID_KEY) 764 event = find_create_kvm_event(kvm, key, sample); 765 766 vcpu_record->last_event = event; 767 vcpu_record->start_time = sample->time; 768 return true; 769 } 770 771 static void 772 kvm_update_event_stats(struct kvm_event_stats *kvm_stats, u64 time_diff) 773 { 774 kvm_stats->time += time_diff; 775 update_stats(&kvm_stats->stats, time_diff); 776 } 777 778 static double kvm_event_rel_stddev(int vcpu_id, struct kvm_event *event) 779 { 780 struct kvm_event_stats *kvm_stats = &event->total; 781 782 if (vcpu_id != -1) 783 kvm_stats = &event->vcpu[vcpu_id]; 784 785 return rel_stddev_stats(stddev_stats(&kvm_stats->stats), 786 avg_stats(&kvm_stats->stats)); 787 } 788 789 static bool update_kvm_event(struct perf_kvm_stat *kvm, 790 struct kvm_event *event, int vcpu_id, 791 u64 time_diff) 792 { 793 /* Update overall statistics */ 794 kvm->total_count++; 795 kvm->total_time += time_diff; 796 797 if (vcpu_id == -1) { 798 kvm_update_event_stats(&event->total, time_diff); 799 return true; 800 } 801 802 if (!kvm_event_expand(event, vcpu_id)) 803 return false; 804 805 kvm_update_event_stats(&event->vcpu[vcpu_id], time_diff); 806 return true; 807 } 808 809 static bool is_child_event(struct perf_kvm_stat *kvm, 810 struct perf_sample *sample, 811 struct event_key *key) 812 { 813 const struct child_event_ops *child_ops; 814 815 child_ops = kvm->events_ops->child_ops; 816 817 if (!child_ops) 818 return false; 819 820 for (; child_ops->name; child_ops++) { 821 if (evsel__name_is(sample->evsel, child_ops->name)) { 822 child_ops->get_key(sample, key); 823 return true; 824 } 825 } 826 827 return false; 828 } 829 830 static bool handle_child_event(struct perf_kvm_stat *kvm, 831 struct vcpu_event_record *vcpu_record, 832 struct event_key *key, 833 struct perf_sample *sample) 834 { 835 struct kvm_event *event = NULL; 836 837 if (key->key != INVALID_KEY) 838 event = find_create_kvm_event(kvm, key, sample); 839 840 vcpu_record->last_event = event; 841 842 return true; 843 } 844 845 static bool skip_event(uint16_t e_machine, const char *event) 846 { 847 const char * const *skip_events; 848 849 for (skip_events = kvm_skip_events(e_machine); *skip_events; skip_events++) 850 if (!strcmp(event, *skip_events)) 851 return true; 852 853 return false; 854 } 855 856 static bool handle_end_event(struct perf_kvm_stat *kvm, 857 struct vcpu_event_record *vcpu_record, 858 struct event_key *key, 859 struct perf_sample *sample) 860 { 861 struct kvm_event *event; 862 u64 time_begin, time_diff; 863 int vcpu; 864 865 if (kvm->trace_vcpu == -1) 866 vcpu = -1; 867 else 868 vcpu = vcpu_record->vcpu_id; 869 870 event = vcpu_record->last_event; 871 time_begin = vcpu_record->start_time; 872 873 /* The begin event is not caught. */ 874 if (!time_begin) 875 return true; 876 877 /* 878 * In some case, the 'begin event' only records the start timestamp, 879 * the actual event is recognized in the 'end event' (e.g. mmio-event). 880 */ 881 882 /* Both begin and end events did not get the key. */ 883 if (!event && key->key == INVALID_KEY) 884 return true; 885 886 if (!event) 887 event = find_create_kvm_event(kvm, key, sample); 888 889 if (!event) 890 return false; 891 892 vcpu_record->last_event = NULL; 893 vcpu_record->start_time = 0; 894 895 /* seems to happen once in a while during live mode */ 896 if (sample->time < time_begin) { 897 pr_debug("End time before begin time; skipping event.\n"); 898 return true; 899 } 900 901 time_diff = sample->time - time_begin; 902 903 if (kvm->duration && time_diff > kvm->duration) { 904 char decode[KVM_EVENT_NAME_LEN]; 905 uint16_t e_machine = perf_session__e_machine(kvm->session, /*e_flags=*/NULL); 906 907 kvm->events_ops->decode_key(kvm, &event->key, decode); 908 if (!skip_event(e_machine, decode)) { 909 pr_info("%" PRIu64 " VM %d, vcpu %d: %s event took %" PRIu64 "usec\n", 910 sample->time, sample->pid, vcpu_record->vcpu_id, 911 decode, time_diff / NSEC_PER_USEC); 912 } 913 } 914 915 return update_kvm_event(kvm, event, vcpu, time_diff); 916 } 917 918 static 919 struct vcpu_event_record *per_vcpu_record(struct thread *thread, 920 struct perf_sample *sample) 921 { 922 /* Only kvm_entry records vcpu id. */ 923 if (!thread__priv(thread) && kvm_entry_event(sample->evsel)) { 924 struct vcpu_event_record *vcpu_record; 925 struct machine *machine = maps__machine(thread__maps(thread)); 926 uint16_t e_machine = thread__e_machine(thread, machine, /*e_flags=*/NULL); 927 928 vcpu_record = zalloc(sizeof(*vcpu_record)); 929 if (!vcpu_record) { 930 pr_err("%s: Not enough memory\n", __func__); 931 return NULL; 932 } 933 934 vcpu_record->vcpu_id = perf_sample__intval(sample, vcpu_id_str(e_machine)); 935 thread__set_priv(thread, vcpu_record); 936 } 937 938 return thread__priv(thread); 939 } 940 941 static bool handle_kvm_event(struct perf_kvm_stat *kvm, 942 struct thread *thread, 943 struct perf_sample *sample) 944 { 945 struct vcpu_event_record *vcpu_record; 946 struct event_key key = { .key = INVALID_KEY, 947 .exit_reasons = kvm->exit_reasons }; 948 949 vcpu_record = per_vcpu_record(thread, sample); 950 if (!vcpu_record) 951 return true; 952 953 /* only process events for vcpus user cares about */ 954 if ((kvm->trace_vcpu != -1) && 955 (kvm->trace_vcpu != vcpu_record->vcpu_id)) 956 return true; 957 958 if (kvm->events_ops->is_begin_event(sample, &key)) 959 return handle_begin_event(kvm, vcpu_record, &key, sample); 960 961 if (is_child_event(kvm, sample, &key)) 962 return handle_child_event(kvm, vcpu_record, &key, sample); 963 964 if (kvm->events_ops->is_end_event(sample, &key)) 965 return handle_end_event(kvm, vcpu_record, &key, sample); 966 967 return true; 968 } 969 970 static bool is_valid_key(struct perf_kvm_stat *kvm) 971 { 972 static const char *key_array[] = { 973 "ev_name", "sample", "time", "max_t", "min_t", "mean_t", 974 }; 975 unsigned int i; 976 977 for (i = 0; i < ARRAY_SIZE(key_array); i++) 978 if (!strcmp(key_array[i], kvm->sort_key)) 979 return true; 980 981 pr_err("Unsupported sort key: %s\n", kvm->sort_key); 982 return false; 983 } 984 985 static bool event_is_valid(struct kvm_event *event, int vcpu) 986 { 987 return !!get_event_count(event, vcpu); 988 } 989 990 static int filter_cb(struct hist_entry *he, void *arg __maybe_unused) 991 { 992 struct kvm_event *event; 993 struct perf_kvm_stat *perf_kvm; 994 995 event = container_of(he, struct kvm_event, he); 996 perf_kvm = event->perf_kvm; 997 if (!event_is_valid(event, perf_kvm->trace_vcpu)) 998 he->filtered = 1; 999 else 1000 he->filtered = 0; 1001 return 0; 1002 } 1003 1004 static void sort_result(struct perf_kvm_stat *kvm) 1005 { 1006 struct ui_progress prog; 1007 const char *output_columns = "ev_name,sample,percent_sample," 1008 "time,percent_time,max_t,min_t,mean_t"; 1009 1010 kvm_hists__reinit(output_columns, kvm->sort_key); 1011 ui_progress__init(&prog, kvm_hists.hists.nr_entries, "Sorting..."); 1012 hists__collapse_resort(&kvm_hists.hists, NULL); 1013 hists__output_resort_cb(&kvm_hists.hists, NULL, filter_cb); 1014 ui_progress__finish(); 1015 } 1016 1017 static void print_vcpu_info(struct perf_kvm_stat *kvm) 1018 { 1019 int vcpu = kvm->trace_vcpu; 1020 1021 pr_info("Analyze events for "); 1022 1023 if (kvm->opts.target.system_wide) 1024 pr_info("all VMs, "); 1025 else if (kvm->opts.target.pid) 1026 pr_info("pid(s) %s, ", kvm->opts.target.pid); 1027 else 1028 pr_info("dazed and confused on what is monitored, "); 1029 1030 if (vcpu == -1) 1031 pr_info("all VCPUs:\n\n"); 1032 else 1033 pr_info("VCPU %d:\n\n", vcpu); 1034 } 1035 1036 static void show_timeofday(void) 1037 { 1038 char date[64]; 1039 struct timeval tv; 1040 struct tm ltime; 1041 1042 gettimeofday(&tv, NULL); 1043 if (localtime_r(&tv.tv_sec, <ime)) { 1044 strftime(date, sizeof(date), "%H:%M:%S", <ime); 1045 pr_info("%s.%06ld", date, tv.tv_usec); 1046 } else 1047 pr_info("00:00:00.000000"); 1048 1049 return; 1050 } 1051 1052 static void print_result(struct perf_kvm_stat *kvm) 1053 { 1054 char decode[KVM_EVENT_NAME_LEN]; 1055 struct kvm_event *event; 1056 int vcpu = kvm->trace_vcpu; 1057 struct rb_node *nd; 1058 1059 if (kvm->live) { 1060 puts(CONSOLE_CLEAR); 1061 show_timeofday(); 1062 } 1063 1064 pr_info("\n\n"); 1065 print_vcpu_info(kvm); 1066 pr_info("%*s ", KVM_EVENT_NAME_LEN, kvm->events_ops->name); 1067 pr_info("%10s ", "Samples"); 1068 pr_info("%9s ", "Samples%"); 1069 1070 pr_info("%9s ", "Time%"); 1071 pr_info("%11s ", "Min Time"); 1072 pr_info("%11s ", "Max Time"); 1073 pr_info("%16s ", "Avg time"); 1074 pr_info("\n\n"); 1075 1076 for (nd = rb_first_cached(&kvm_hists.hists.entries); nd; nd = rb_next(nd)) { 1077 struct hist_entry *he; 1078 u64 ecount, etime, max, min; 1079 1080 he = rb_entry(nd, struct hist_entry, rb_node); 1081 if (he->filtered) 1082 continue; 1083 1084 event = container_of(he, struct kvm_event, he); 1085 ecount = get_event_count(event, vcpu); 1086 etime = get_event_time(event, vcpu); 1087 max = get_event_max(event, vcpu); 1088 min = get_event_min(event, vcpu); 1089 1090 kvm->events_ops->decode_key(kvm, &event->key, decode); 1091 pr_info("%*s ", KVM_EVENT_NAME_LEN, decode); 1092 pr_info("%10llu ", (unsigned long long)ecount); 1093 pr_info("%8.2f%% ", (double)ecount / kvm->total_count * 100); 1094 pr_info("%8.2f%% ", (double)etime / kvm->total_time * 100); 1095 pr_info("%9.2fus ", (double)min / NSEC_PER_USEC); 1096 pr_info("%9.2fus ", (double)max / NSEC_PER_USEC); 1097 pr_info("%9.2fus ( +-%7.2f%% )", (double)etime / ecount / NSEC_PER_USEC, 1098 kvm_event_rel_stddev(vcpu, event)); 1099 pr_info("\n"); 1100 } 1101 1102 pr_info("\nTotal Samples:%" PRIu64 ", Total events handled time:%.2fus.\n\n", 1103 kvm->total_count, kvm->total_time / (double)NSEC_PER_USEC); 1104 1105 if (kvm->lost_events) 1106 pr_info("\nLost events: %" PRIu64 "\n\n", kvm->lost_events); 1107 } 1108 1109 #if defined(HAVE_TIMERFD_SUPPORT) && defined(HAVE_LIBTRACEEVENT) 1110 static int process_lost_event(const struct perf_tool *tool, 1111 union perf_event *event __maybe_unused, 1112 struct perf_sample *sample __maybe_unused, 1113 struct machine *machine __maybe_unused) 1114 { 1115 struct perf_kvm_stat *kvm = container_of(tool, struct perf_kvm_stat, tool); 1116 1117 kvm->lost_events++; 1118 return 0; 1119 } 1120 #endif 1121 1122 static bool skip_sample(struct perf_kvm_stat *kvm, 1123 struct perf_sample *sample) 1124 { 1125 if (kvm->pid_list && intlist__find(kvm->pid_list, sample->pid) == NULL) 1126 return true; 1127 1128 return false; 1129 } 1130 1131 static int process_sample_event(const struct perf_tool *tool, 1132 union perf_event *event, 1133 struct perf_sample *sample, 1134 struct machine *machine) 1135 { 1136 int err = 0; 1137 struct thread *thread; 1138 struct perf_kvm_stat *kvm = container_of(tool, struct perf_kvm_stat, 1139 tool); 1140 1141 if (skip_sample(kvm, sample)) 1142 return 0; 1143 1144 if (machine__resolve(machine, &kvm->al, sample) < 0) { 1145 pr_warning("WARNING: at offset %#" PRIx64 ": fail to resolve address location, skipping sample\n", 1146 sample->file_offset); 1147 return 0; 1148 } 1149 1150 thread = machine__findnew_thread(machine, sample->pid, sample->tid); 1151 if (thread == NULL) { 1152 pr_debug("problem processing %s (%u) event at offset %#" PRIx64 ", skipping it.\n", 1153 perf_event__name(event->header.type), event->header.type, 1154 sample->file_offset); 1155 return -1; 1156 } 1157 1158 if (!handle_kvm_event(kvm, thread, sample)) 1159 err = -1; 1160 1161 thread__put(thread); 1162 return err; 1163 } 1164 1165 static int cpu_isa_config(struct perf_kvm_stat *kvm) 1166 { 1167 char buf[128], *cpuid; 1168 int err; 1169 uint16_t e_machine; 1170 1171 if (kvm->live) { 1172 struct perf_cpu cpu = {-1}; 1173 1174 err = get_cpuid(buf, sizeof(buf), cpu); 1175 if (err != 0) { 1176 pr_err("Failed to look up CPU type: %s\n", 1177 str_error_r(err, buf, sizeof(buf))); 1178 return -err; 1179 } 1180 cpuid = buf; 1181 } else 1182 cpuid = perf_session__env(kvm->session)->cpuid; 1183 1184 if (!cpuid) { 1185 pr_err("Failed to look up CPU type\n"); 1186 return -EINVAL; 1187 } 1188 1189 e_machine = perf_session__e_machine(kvm->session, /*e_flags=*/NULL); 1190 err = cpu_isa_init(kvm, e_machine, cpuid); 1191 if (err == -ENOTSUP) 1192 pr_err("CPU %s is not supported.\n", cpuid); 1193 1194 return err; 1195 } 1196 1197 static bool verify_vcpu(int vcpu) 1198 { 1199 if (vcpu != -1 && vcpu < 0) { 1200 pr_err("Invalid vcpu:%d.\n", vcpu); 1201 return false; 1202 } 1203 1204 return true; 1205 } 1206 1207 #if defined(HAVE_TIMERFD_SUPPORT) && defined(HAVE_LIBTRACEEVENT) 1208 /* keeping the max events to a modest level to keep 1209 * the processing of samples per mmap smooth. 1210 */ 1211 #define PERF_KVM__MAX_EVENTS_PER_MMAP 25 1212 1213 static s64 perf_kvm__mmap_read_idx(struct perf_kvm_stat *kvm, int idx, 1214 u64 *mmap_time) 1215 { 1216 struct evlist *evlist = kvm->evlist; 1217 union perf_event *event; 1218 struct mmap *md; 1219 u64 timestamp; 1220 s64 n = 0; 1221 int err; 1222 1223 *mmap_time = ULLONG_MAX; 1224 md = &evlist->mmap[idx]; 1225 err = perf_mmap__read_init(&md->core); 1226 if (err < 0) 1227 return (err == -EAGAIN) ? 0 : -1; 1228 1229 while ((event = perf_mmap__read_event(&md->core)) != NULL) { 1230 err = evlist__parse_sample_timestamp(evlist, event, ×tamp); 1231 if (err) { 1232 perf_mmap__consume(&md->core); 1233 pr_err("Failed to parse sample\n"); 1234 return -1; 1235 } 1236 1237 err = perf_session__queue_event(kvm->session, event, timestamp, 0, NULL); 1238 /* 1239 * FIXME: Here we can't consume the event, as perf_session__queue_event will 1240 * point to it, and it'll get possibly overwritten by the kernel. 1241 */ 1242 perf_mmap__consume(&md->core); 1243 1244 if (err) { 1245 pr_err("Failed to enqueue sample: %d\n", err); 1246 return -1; 1247 } 1248 1249 /* save time stamp of our first sample for this mmap */ 1250 if (n == 0) 1251 *mmap_time = timestamp; 1252 1253 /* limit events per mmap handled all at once */ 1254 n++; 1255 if (n == PERF_KVM__MAX_EVENTS_PER_MMAP) 1256 break; 1257 } 1258 1259 perf_mmap__read_done(&md->core); 1260 return n; 1261 } 1262 1263 static int perf_kvm__mmap_read(struct perf_kvm_stat *kvm) 1264 { 1265 int i, err, throttled = 0; 1266 s64 n, ntotal = 0; 1267 u64 flush_time = ULLONG_MAX, mmap_time; 1268 1269 for (i = 0; i < kvm->evlist->core.nr_mmaps; i++) { 1270 n = perf_kvm__mmap_read_idx(kvm, i, &mmap_time); 1271 if (n < 0) 1272 return -1; 1273 1274 /* flush time is going to be the minimum of all the individual 1275 * mmap times. Essentially, we flush all the samples queued up 1276 * from the last pass under our minimal start time -- that leaves 1277 * a very small race for samples to come in with a lower timestamp. 1278 * The ioctl to return the perf_clock timestamp should close the 1279 * race entirely. 1280 */ 1281 if (mmap_time < flush_time) 1282 flush_time = mmap_time; 1283 1284 ntotal += n; 1285 if (n == PERF_KVM__MAX_EVENTS_PER_MMAP) 1286 throttled = 1; 1287 } 1288 1289 /* flush queue after each round in which we processed events */ 1290 if (ntotal) { 1291 struct ordered_events *oe = &kvm->session->ordered_events; 1292 1293 oe->next_flush = flush_time; 1294 err = ordered_events__flush(oe, OE_FLUSH__ROUND); 1295 if (err) { 1296 if (kvm->lost_events) 1297 pr_info("\nLost events: %" PRIu64 "\n\n", 1298 kvm->lost_events); 1299 return err; 1300 } 1301 } 1302 1303 return throttled; 1304 } 1305 1306 static volatile int done; 1307 1308 static void sig_handler(int sig __maybe_unused) 1309 { 1310 done = 1; 1311 } 1312 1313 static int perf_kvm__timerfd_create(struct perf_kvm_stat *kvm) 1314 { 1315 struct itimerspec new_value; 1316 int rc = -1; 1317 1318 kvm->timerfd = timerfd_create(CLOCK_MONOTONIC, TFD_NONBLOCK); 1319 if (kvm->timerfd < 0) { 1320 pr_err("timerfd_create failed\n"); 1321 goto out; 1322 } 1323 1324 new_value.it_value.tv_sec = kvm->display_time; 1325 new_value.it_value.tv_nsec = 0; 1326 new_value.it_interval.tv_sec = kvm->display_time; 1327 new_value.it_interval.tv_nsec = 0; 1328 1329 if (timerfd_settime(kvm->timerfd, 0, &new_value, NULL) != 0) { 1330 pr_err("timerfd_settime failed: %d\n", errno); 1331 close(kvm->timerfd); 1332 goto out; 1333 } 1334 1335 rc = 0; 1336 out: 1337 return rc; 1338 } 1339 1340 static int perf_kvm__handle_timerfd(struct perf_kvm_stat *kvm) 1341 { 1342 uint64_t c; 1343 int rc; 1344 1345 rc = read(kvm->timerfd, &c, sizeof(uint64_t)); 1346 if (rc < 0) { 1347 if (errno == EAGAIN) 1348 return 0; 1349 1350 pr_err("Failed to read timer fd: %d\n", errno); 1351 return -1; 1352 } 1353 1354 if (rc != sizeof(uint64_t)) { 1355 pr_err("Error reading timer fd - invalid size returned\n"); 1356 return -1; 1357 } 1358 1359 if (c != 1) 1360 pr_debug("Missed timer beats: %" PRIu64 "\n", c-1); 1361 1362 /* update display */ 1363 sort_result(kvm); 1364 print_result(kvm); 1365 1366 /* Reset sort list to "ev_name" */ 1367 kvm_hists__reinit(NULL, "ev_name"); 1368 1369 /* reset counts */ 1370 clear_events_cache_stats(); 1371 kvm->total_count = 0; 1372 kvm->total_time = 0; 1373 kvm->lost_events = 0; 1374 1375 return 0; 1376 } 1377 1378 static int fd_set_nonblock(int fd) 1379 { 1380 long arg = 0; 1381 1382 arg = fcntl(fd, F_GETFL); 1383 if (arg < 0) { 1384 pr_err("Failed to get current flags for fd %d\n", fd); 1385 return -1; 1386 } 1387 1388 if (fcntl(fd, F_SETFL, arg | O_NONBLOCK) < 0) { 1389 pr_err("Failed to set non-block option on fd %d\n", fd); 1390 return -1; 1391 } 1392 1393 return 0; 1394 } 1395 1396 static int perf_kvm__handle_stdin(void) 1397 { 1398 int c; 1399 1400 c = getc(stdin); 1401 if (c == 'q') 1402 return 1; 1403 1404 return 0; 1405 } 1406 1407 static int kvm_events_live_report(struct perf_kvm_stat *kvm) 1408 { 1409 int nr_stdin, ret, err = -EINVAL; 1410 struct termios save; 1411 1412 /* live flag must be set first */ 1413 kvm->live = true; 1414 1415 ret = cpu_isa_config(kvm); 1416 if (ret < 0) 1417 return ret; 1418 1419 if (!verify_vcpu(kvm->trace_vcpu) || 1420 !is_valid_key(kvm) || 1421 !register_kvm_events_ops(kvm, EM_HOST)) { 1422 goto out; 1423 } 1424 1425 set_term_quiet_input(&save); 1426 1427 kvm_hists__init(); 1428 1429 signal(SIGINT, sig_handler); 1430 signal(SIGTERM, sig_handler); 1431 1432 /* add timer fd */ 1433 if (perf_kvm__timerfd_create(kvm) < 0) { 1434 err = -1; 1435 goto out; 1436 } 1437 1438 if (evlist__add_pollfd(kvm->evlist, kvm->timerfd) < 0) 1439 goto out; 1440 1441 nr_stdin = evlist__add_pollfd(kvm->evlist, fileno(stdin)); 1442 if (nr_stdin < 0) 1443 goto out; 1444 1445 if (fd_set_nonblock(fileno(stdin)) != 0) 1446 goto out; 1447 1448 /* everything is good - enable the events and process */ 1449 evlist__enable(kvm->evlist); 1450 1451 while (!done) { 1452 struct fdarray *fda = &kvm->evlist->core.pollfd; 1453 int rc; 1454 1455 rc = perf_kvm__mmap_read(kvm); 1456 if (rc < 0) 1457 break; 1458 1459 err = perf_kvm__handle_timerfd(kvm); 1460 if (err) 1461 goto out; 1462 1463 if (fda->entries[nr_stdin].revents & POLLIN) 1464 done = perf_kvm__handle_stdin(); 1465 1466 if (!rc && !done) 1467 err = evlist__poll(kvm->evlist, 100); 1468 } 1469 1470 evlist__disable(kvm->evlist); 1471 1472 if (err == 0) { 1473 sort_result(kvm); 1474 print_result(kvm); 1475 } 1476 1477 out: 1478 hists__delete_entries(&kvm_hists.hists); 1479 1480 if (kvm->timerfd >= 0) 1481 close(kvm->timerfd); 1482 1483 tcsetattr(0, TCSAFLUSH, &save); 1484 return err; 1485 } 1486 1487 static int kvm_live_open_events(struct perf_kvm_stat *kvm) 1488 { 1489 int err, rc = -1; 1490 struct evsel *pos; 1491 struct evlist *evlist = kvm->evlist; 1492 char sbuf[STRERR_BUFSIZE]; 1493 1494 evlist__config(evlist, &kvm->opts, NULL); 1495 1496 /* 1497 * Note: exclude_{guest,host} do not apply here. 1498 * This command processes KVM tracepoints from host only 1499 */ 1500 evlist__for_each_entry(evlist, pos) { 1501 struct perf_event_attr *attr = &pos->core.attr; 1502 1503 /* make sure these *are* set */ 1504 evsel__set_sample_bit(pos, TID); 1505 evsel__set_sample_bit(pos, TIME); 1506 evsel__set_sample_bit(pos, CPU); 1507 evsel__set_sample_bit(pos, RAW); 1508 /* make sure these are *not*; want as small a sample as possible */ 1509 evsel__reset_sample_bit(pos, PERIOD); 1510 evsel__reset_sample_bit(pos, IP); 1511 evsel__reset_sample_bit(pos, CALLCHAIN); 1512 evsel__reset_sample_bit(pos, ADDR); 1513 evsel__reset_sample_bit(pos, READ); 1514 attr->mmap = 0; 1515 attr->comm = 0; 1516 attr->task = 0; 1517 1518 attr->sample_period = 1; 1519 1520 attr->watermark = 0; 1521 attr->wakeup_events = 1000; 1522 1523 /* will enable all once we are ready */ 1524 attr->disabled = 1; 1525 } 1526 1527 err = evlist__open(evlist); 1528 if (err < 0) { 1529 printf("Couldn't create the events: %s\n", 1530 str_error_r(errno, sbuf, sizeof(sbuf))); 1531 goto out; 1532 } 1533 1534 if (evlist__mmap(evlist, kvm->opts.mmap_pages) < 0) { 1535 ui__error("Failed to mmap the events: %s\n", 1536 str_error_r(errno, sbuf, sizeof(sbuf))); 1537 evlist__close(evlist); 1538 goto out; 1539 } 1540 1541 rc = 0; 1542 1543 out: 1544 return rc; 1545 } 1546 #endif 1547 1548 static int read_events(struct perf_kvm_stat *kvm) 1549 { 1550 int ret; 1551 uint16_t e_machine; 1552 struct perf_data file = { 1553 .path = kvm->file_name, 1554 .mode = PERF_DATA_MODE_READ, 1555 .force = kvm->force, 1556 }; 1557 1558 perf_tool__init(&kvm->tool, /*ordered_events=*/true); 1559 kvm->tool.sample = process_sample_event; 1560 kvm->tool.comm = perf_event__process_comm; 1561 kvm->tool.namespaces = perf_event__process_namespaces; 1562 1563 kvm->session = perf_session__new(&file, &kvm->tool); 1564 if (IS_ERR(kvm->session)) { 1565 pr_err("Initializing perf session failed\n"); 1566 return PTR_ERR(kvm->session); 1567 } 1568 1569 symbol__init(perf_session__env(kvm->session)); 1570 1571 if (!perf_session__has_traces(kvm->session, "kvm record")) { 1572 ret = -EINVAL; 1573 goto out_delete; 1574 } 1575 1576 e_machine = perf_session__e_machine(kvm->session, /*e_flags=*/NULL); 1577 if (!register_kvm_events_ops(kvm, e_machine)) { 1578 ret = -EINVAL; 1579 goto out_delete; 1580 } 1581 1582 /* 1583 * Do not use 'isa' recorded in kvm_exit tracepoint since it is not 1584 * traced in the old kernel. 1585 */ 1586 ret = cpu_isa_config(kvm); 1587 if (ret < 0) 1588 goto out_delete; 1589 1590 ret = perf_session__process_events(kvm->session); 1591 1592 out_delete: 1593 perf_session__delete(kvm->session); 1594 return ret; 1595 } 1596 1597 static int parse_target_str(struct perf_kvm_stat *kvm) 1598 { 1599 if (kvm->opts.target.pid) { 1600 kvm->pid_list = intlist__new(kvm->opts.target.pid); 1601 if (kvm->pid_list == NULL) { 1602 pr_err("Error parsing process id string\n"); 1603 return -EINVAL; 1604 } 1605 } 1606 1607 return 0; 1608 } 1609 1610 static int kvm_events_report_vcpu(struct perf_kvm_stat *kvm) 1611 { 1612 int ret = -EINVAL; 1613 int vcpu = kvm->trace_vcpu; 1614 1615 if (parse_target_str(kvm) != 0) 1616 goto exit; 1617 1618 if (!verify_vcpu(vcpu)) 1619 goto exit; 1620 1621 if (!is_valid_key(kvm)) 1622 goto exit; 1623 1624 if (kvm->use_stdio) { 1625 use_browser = 0; 1626 setup_pager(); 1627 } else { 1628 use_browser = 1; 1629 } 1630 1631 setup_browser(false); 1632 1633 kvm_hists__init(); 1634 1635 ret = read_events(kvm); 1636 if (ret) 1637 goto exit; 1638 1639 sort_result(kvm); 1640 kvm_display(kvm); 1641 1642 exit: 1643 hists__delete_entries(&kvm_hists.hists); 1644 return ret; 1645 } 1646 1647 static int 1648 kvm_events_record(struct perf_kvm_stat *kvm, int argc, const char **argv) 1649 { 1650 unsigned int rec_argc, i, j, events_tp_size; 1651 const char **rec_argv; 1652 const char * const record_args[] = { 1653 "record", 1654 "-R", 1655 "-m", "1024", 1656 "-c", "1", 1657 }; 1658 const char * const kvm_stat_record_usage[] = { 1659 "perf kvm stat record [<options>]", 1660 NULL 1661 }; 1662 const char * const *events_tp; 1663 int ret; 1664 uint16_t e_machine = EM_HOST; 1665 1666 events_tp_size = 0; 1667 ret = setup_kvm_events_tp(kvm, e_machine); 1668 if (ret < 0) { 1669 pr_err("Unable to setup the kvm tracepoints\n"); 1670 return ret; 1671 } 1672 1673 for (events_tp = kvm_events_tp(e_machine); *events_tp; events_tp++) 1674 events_tp_size++; 1675 1676 rec_argc = ARRAY_SIZE(record_args) + argc + 2 + 1677 2 * events_tp_size; 1678 rec_argv = calloc(rec_argc + 1, sizeof(char *)); 1679 1680 if (rec_argv == NULL) 1681 return -ENOMEM; 1682 1683 for (i = 0; i < ARRAY_SIZE(record_args); i++) 1684 rec_argv[i] = STRDUP_FAIL_EXIT(record_args[i]); 1685 1686 for (j = 0; j < events_tp_size; j++) { 1687 rec_argv[i++] = STRDUP_FAIL_EXIT("-e"); 1688 rec_argv[i++] = STRDUP_FAIL_EXIT(kvm_events_tp(e_machine)[j]); 1689 } 1690 1691 rec_argv[i++] = STRDUP_FAIL_EXIT("-o"); 1692 rec_argv[i++] = STRDUP_FAIL_EXIT(kvm->file_name); 1693 1694 for (j = 1; j < (unsigned int)argc; j++, i++) 1695 rec_argv[i] = STRDUP_FAIL_EXIT(argv[j]); 1696 1697 set_option_flag(record_options, 'e', "event", PARSE_OPT_HIDDEN); 1698 set_option_flag(record_options, 0, "filter", PARSE_OPT_HIDDEN); 1699 set_option_flag(record_options, 'R', "raw-samples", PARSE_OPT_HIDDEN); 1700 1701 set_option_flag(record_options, 'F', "freq", PARSE_OPT_DISABLED); 1702 set_option_flag(record_options, 0, "group", PARSE_OPT_DISABLED); 1703 set_option_flag(record_options, 'g', NULL, PARSE_OPT_DISABLED); 1704 set_option_flag(record_options, 0, "call-graph", PARSE_OPT_DISABLED); 1705 set_option_flag(record_options, 'd', "data", PARSE_OPT_DISABLED); 1706 set_option_flag(record_options, 'T', "timestamp", PARSE_OPT_DISABLED); 1707 set_option_flag(record_options, 'P', "period", PARSE_OPT_DISABLED); 1708 set_option_flag(record_options, 'n', "no-samples", PARSE_OPT_DISABLED); 1709 set_option_flag(record_options, 'N', "no-buildid-cache", PARSE_OPT_DISABLED); 1710 set_option_flag(record_options, 'B', "no-buildid", PARSE_OPT_DISABLED); 1711 set_option_flag(record_options, 'G', "cgroup", PARSE_OPT_DISABLED); 1712 set_option_flag(record_options, 'b', "branch-any", PARSE_OPT_DISABLED); 1713 set_option_flag(record_options, 'j', "branch-filter", PARSE_OPT_DISABLED); 1714 set_option_flag(record_options, 'W', "weight", PARSE_OPT_DISABLED); 1715 set_option_flag(record_options, 0, "transaction", PARSE_OPT_DISABLED); 1716 1717 record_usage = kvm_stat_record_usage; 1718 ret = cmd_record(i, rec_argv); 1719 1720 EXIT: 1721 for (i = 0; i < rec_argc; i++) 1722 free((void *)rec_argv[i]); 1723 free(rec_argv); 1724 return ret; 1725 } 1726 1727 static int 1728 kvm_events_report(struct perf_kvm_stat *kvm, int argc, const char **argv) 1729 { 1730 const struct option kvm_events_report_options[] = { 1731 OPT_STRING(0, "event", &kvm->report_event, "report event", 1732 "event for reporting: vmexit, " 1733 "mmio (x86 only), ioport (x86 only)"), 1734 OPT_INTEGER(0, "vcpu", &kvm->trace_vcpu, 1735 "vcpu id to report"), 1736 OPT_STRING('k', "key", &kvm->sort_key, "sort-key", 1737 "key for sorting: sample(sort by samples number)" 1738 " time (sort by avg time)"), 1739 OPT_STRING('p', "pid", &kvm->opts.target.pid, "pid", 1740 "analyze events only for given process id(s)"), 1741 OPT_BOOLEAN('f', "force", &kvm->force, "don't complain, do it"), 1742 OPT_BOOLEAN(0, "stdio", &kvm->use_stdio, "use the stdio interface"), 1743 OPT_END() 1744 }; 1745 1746 const char * const kvm_events_report_usage[] = { 1747 "perf kvm stat report [<options>]", 1748 NULL 1749 }; 1750 1751 if (argc) { 1752 argc = parse_options(argc, argv, 1753 kvm_events_report_options, 1754 kvm_events_report_usage, 0); 1755 if (argc) 1756 usage_with_options(kvm_events_report_usage, 1757 kvm_events_report_options); 1758 } 1759 1760 #ifndef HAVE_SLANG_SUPPORT 1761 kvm->use_stdio = true; 1762 #endif 1763 1764 if (!kvm->opts.target.pid) 1765 kvm->opts.target.system_wide = true; 1766 1767 return kvm_events_report_vcpu(kvm); 1768 } 1769 1770 #if defined(HAVE_TIMERFD_SUPPORT) && defined(HAVE_LIBTRACEEVENT) 1771 static struct evlist *kvm_live_event_list(void) 1772 { 1773 struct evlist *evlist; 1774 char *tp, *name, *sys; 1775 int err = -1; 1776 const char * const *events_tp; 1777 1778 evlist = evlist__new(); 1779 if (evlist == NULL) 1780 return NULL; 1781 1782 for (events_tp = kvm_events_tp(EM_HOST); *events_tp; events_tp++) { 1783 1784 tp = strdup(*events_tp); 1785 if (tp == NULL) 1786 goto out; 1787 1788 /* split tracepoint into subsystem and name */ 1789 sys = tp; 1790 name = strchr(tp, ':'); 1791 if (name == NULL) { 1792 pr_err("Error parsing %s tracepoint: subsystem delimiter not found\n", 1793 *events_tp); 1794 free(tp); 1795 goto out; 1796 } 1797 *name = '\0'; 1798 name++; 1799 1800 if (evlist__add_newtp(evlist, sys, name, NULL)) { 1801 pr_err("Failed to add %s tracepoint to the list\n", *events_tp); 1802 free(tp); 1803 goto out; 1804 } 1805 1806 free(tp); 1807 } 1808 1809 err = 0; 1810 1811 out: 1812 if (err) { 1813 evlist__delete(evlist); 1814 evlist = NULL; 1815 } 1816 1817 return evlist; 1818 } 1819 1820 static int kvm_events_live(struct perf_kvm_stat *kvm, 1821 int argc, const char **argv) 1822 { 1823 char errbuf[BUFSIZ]; 1824 int err; 1825 1826 const struct option live_options[] = { 1827 OPT_STRING('p', "pid", &kvm->opts.target.pid, "pid", 1828 "record events on existing process id"), 1829 OPT_CALLBACK('m', "mmap-pages", &kvm->opts.mmap_pages, "pages", 1830 "number of mmap data pages", evlist__parse_mmap_pages), 1831 OPT_INCR('v', "verbose", &verbose, 1832 "be more verbose (show counter open errors, etc)"), 1833 OPT_BOOLEAN('a', "all-cpus", &kvm->opts.target.system_wide, 1834 "system-wide collection from all CPUs"), 1835 OPT_UINTEGER('d', "display", &kvm->display_time, 1836 "time in seconds between display updates"), 1837 OPT_STRING(0, "event", &kvm->report_event, "report event", 1838 "event for reporting: " 1839 "vmexit, mmio (x86 only), ioport (x86 only)"), 1840 OPT_INTEGER(0, "vcpu", &kvm->trace_vcpu, 1841 "vcpu id to report"), 1842 OPT_STRING('k', "key", &kvm->sort_key, "sort-key", 1843 "key for sorting: sample(sort by samples number)" 1844 " time (sort by avg time)"), 1845 OPT_U64(0, "duration", &kvm->duration, 1846 "show events other than" 1847 " HLT (x86 only) or Wait state (s390 only)" 1848 " that take longer than duration usecs"), 1849 OPT_UINTEGER(0, "proc-map-timeout", &proc_map_timeout, 1850 "per thread proc mmap processing timeout in ms"), 1851 OPT_END() 1852 }; 1853 const char * const live_usage[] = { 1854 "perf kvm stat live [<options>]", 1855 NULL 1856 }; 1857 struct perf_data data = { 1858 .mode = PERF_DATA_MODE_WRITE, 1859 }; 1860 1861 1862 /* event handling */ 1863 perf_tool__init(&kvm->tool, /*ordered_events=*/true); 1864 kvm->tool.sample = process_sample_event; 1865 kvm->tool.comm = perf_event__process_comm; 1866 kvm->tool.exit = perf_event__process_exit; 1867 kvm->tool.fork = perf_event__process_fork; 1868 kvm->tool.lost = process_lost_event; 1869 kvm->tool.namespaces = perf_event__process_namespaces; 1870 1871 /* set defaults */ 1872 kvm->display_time = 1; 1873 kvm->opts.user_interval = 1; 1874 kvm->opts.mmap_pages = 512; 1875 kvm->opts.target.uses_mmap = false; 1876 1877 symbol__init(NULL); 1878 disable_buildid_cache(); 1879 1880 use_browser = 0; 1881 1882 if (argc) { 1883 argc = parse_options(argc, argv, live_options, 1884 live_usage, 0); 1885 if (argc) 1886 usage_with_options(live_usage, live_options); 1887 } 1888 1889 kvm->duration *= NSEC_PER_USEC; /* convert usec to nsec */ 1890 1891 /* 1892 * target related setups 1893 */ 1894 err = target__validate(&kvm->opts.target); 1895 if (err) { 1896 target__strerror(&kvm->opts.target, err, errbuf, BUFSIZ); 1897 ui__warning("%s", errbuf); 1898 } 1899 1900 if (target__none(&kvm->opts.target)) 1901 kvm->opts.target.system_wide = true; 1902 1903 1904 /* 1905 * generate the event list 1906 */ 1907 err = setup_kvm_events_tp(kvm, EM_HOST); 1908 if (err < 0) { 1909 pr_err("Unable to setup the kvm tracepoints\n"); 1910 return err; 1911 } 1912 1913 kvm->evlist = kvm_live_event_list(); 1914 if (kvm->evlist == NULL) { 1915 err = -1; 1916 goto out; 1917 } 1918 1919 if (evlist__create_maps(kvm->evlist, &kvm->opts.target) < 0) 1920 usage_with_options(live_usage, live_options); 1921 1922 /* 1923 * perf session 1924 */ 1925 kvm->session = perf_session__new(&data, &kvm->tool); 1926 if (IS_ERR(kvm->session)) { 1927 err = PTR_ERR(kvm->session); 1928 goto out; 1929 } 1930 kvm->session->evlist = kvm->evlist; 1931 perf_session__set_id_hdr_size(kvm->session); 1932 ordered_events__set_copy_on_queue(&kvm->session->ordered_events, true); 1933 machine__synthesize_threads(&kvm->session->machines.host, &kvm->opts.target, 1934 kvm->evlist->core.threads, true, false, 1); 1935 err = kvm_live_open_events(kvm); 1936 if (err) 1937 goto out; 1938 1939 err = kvm_events_live_report(kvm); 1940 1941 out: 1942 perf_session__delete(kvm->session); 1943 kvm->session = NULL; 1944 evlist__delete(kvm->evlist); 1945 1946 return err; 1947 } 1948 #endif 1949 1950 static void print_kvm_stat_usage(void) 1951 { 1952 printf("Usage: perf kvm stat <command>\n\n"); 1953 1954 printf("# Available commands:\n"); 1955 printf("\trecord: record kvm events\n"); 1956 printf("\treport: report statistical data of kvm events\n"); 1957 printf("\tlive: live reporting of statistical data of kvm events\n"); 1958 1959 printf("\nOtherwise, it is the alias of 'perf stat':\n"); 1960 } 1961 1962 static int kvm_cmd_stat(const char *file_name, int argc, const char **argv) 1963 { 1964 struct perf_kvm_stat kvm = { 1965 .file_name = file_name, 1966 1967 .trace_vcpu = -1, 1968 .report_event = "vmexit", 1969 .sort_key = "sample", 1970 1971 }; 1972 1973 if (argc == 1) { 1974 print_kvm_stat_usage(); 1975 goto perf_stat; 1976 } 1977 1978 if (strlen(argv[1]) > 2 && strstarts("record", argv[1])) 1979 return kvm_events_record(&kvm, argc - 1, argv + 1); 1980 1981 if (strlen(argv[1]) > 2 && strstarts("report", argv[1])) 1982 return kvm_events_report(&kvm, argc - 1 , argv + 1); 1983 1984 #if defined(HAVE_TIMERFD_SUPPORT) && defined(HAVE_LIBTRACEEVENT) 1985 if (!strncmp(argv[1], "live", 4)) 1986 return kvm_events_live(&kvm, argc - 1 , argv + 1); 1987 #endif 1988 1989 perf_stat: 1990 return cmd_stat(argc, argv); 1991 } 1992 #endif /* HAVE_LIBTRACEEVENT */ 1993 1994 static int __cmd_record(const char *file_name, int argc, const char **argv) 1995 { 1996 int rec_argc, i = 0, j, ret; 1997 const char **rec_argv; 1998 1999 /* 2000 * Besides the 2 more options "-o" and "filename", 2001 * kvm_add_default_arch_event() may add 2 extra options, 2002 * so allocate 4 more items. 2003 */ 2004 rec_argc = argc + 2 + 2; 2005 rec_argv = calloc(rec_argc + 1, sizeof(char *)); 2006 if (!rec_argv) 2007 return -ENOMEM; 2008 2009 rec_argv[i++] = STRDUP_FAIL_EXIT("record"); 2010 rec_argv[i++] = STRDUP_FAIL_EXIT("-o"); 2011 rec_argv[i++] = STRDUP_FAIL_EXIT(file_name); 2012 for (j = 1; j < argc; j++, i++) 2013 rec_argv[i] = STRDUP_FAIL_EXIT(argv[j]); 2014 2015 BUG_ON(i + 2 != rec_argc); 2016 2017 ret = kvm_add_default_arch_event(EM_HOST, &i, rec_argv); 2018 if (ret) 2019 goto EXIT; 2020 2021 ret = cmd_record(i, rec_argv); 2022 2023 EXIT: 2024 for (i = 0; i < rec_argc; i++) 2025 free((void *)rec_argv[i]); 2026 free(rec_argv); 2027 return ret; 2028 } 2029 2030 static int __cmd_report(const char *file_name, int argc, const char **argv) 2031 { 2032 int rec_argc, i = 0, j, ret; 2033 const char **rec_argv; 2034 2035 rec_argc = argc + 2; 2036 rec_argv = calloc(rec_argc + 1, sizeof(char *)); 2037 if (!rec_argv) 2038 return -ENOMEM; 2039 2040 rec_argv[i++] = STRDUP_FAIL_EXIT("report"); 2041 rec_argv[i++] = STRDUP_FAIL_EXIT("-i"); 2042 rec_argv[i++] = STRDUP_FAIL_EXIT(file_name); 2043 for (j = 1; j < argc; j++, i++) 2044 rec_argv[i] = STRDUP_FAIL_EXIT(argv[j]); 2045 2046 BUG_ON(i != rec_argc); 2047 2048 ret = cmd_report(i, rec_argv); 2049 2050 EXIT: 2051 for (i = 0; i < rec_argc; i++) 2052 free((void *)rec_argv[i]); 2053 free(rec_argv); 2054 return ret; 2055 } 2056 2057 static int 2058 __cmd_buildid_list(const char *file_name, int argc, const char **argv) 2059 { 2060 int rec_argc, i = 0, j, ret; 2061 const char **rec_argv; 2062 2063 rec_argc = argc + 2; 2064 rec_argv = calloc(rec_argc + 1, sizeof(char *)); 2065 if (!rec_argv) 2066 return -ENOMEM; 2067 2068 rec_argv[i++] = STRDUP_FAIL_EXIT("buildid-list"); 2069 rec_argv[i++] = STRDUP_FAIL_EXIT("-i"); 2070 rec_argv[i++] = STRDUP_FAIL_EXIT(file_name); 2071 for (j = 1; j < argc; j++, i++) 2072 rec_argv[i] = STRDUP_FAIL_EXIT(argv[j]); 2073 2074 BUG_ON(i != rec_argc); 2075 2076 ret = cmd_buildid_list(i, rec_argv); 2077 2078 EXIT: 2079 for (i = 0; i < rec_argc; i++) 2080 free((void *)rec_argv[i]); 2081 free(rec_argv); 2082 return ret; 2083 } 2084 2085 static int __cmd_top(int argc, const char **argv) 2086 { 2087 int rec_argc, i = 0, ret; 2088 const char **rec_argv; 2089 2090 /* 2091 * kvm_add_default_arch_event() may add 2 extra options, so 2092 * allocate 2 more pointers in adavance. 2093 */ 2094 rec_argc = argc + 2; 2095 rec_argv = calloc(rec_argc + 1, sizeof(char *)); 2096 if (!rec_argv) 2097 return -ENOMEM; 2098 2099 for (i = 0; i < argc; i++) 2100 rec_argv[i] = STRDUP_FAIL_EXIT(argv[i]); 2101 2102 BUG_ON(i != argc); 2103 2104 ret = kvm_add_default_arch_event(EM_HOST, &i, rec_argv); 2105 if (ret) 2106 goto EXIT; 2107 2108 ret = cmd_top(i, rec_argv); 2109 2110 EXIT: 2111 for (i = 0; i < rec_argc; i++) 2112 free((void *)rec_argv[i]); 2113 free(rec_argv); 2114 return ret; 2115 } 2116 2117 int cmd_kvm(int argc, const char **argv) 2118 { 2119 const char *file_name = NULL; 2120 const struct option kvm_options[] = { 2121 OPT_STRING('i', "input", &file_name, "file", 2122 "Input file name"), 2123 OPT_STRING('o', "output", &file_name, "file", 2124 "Output file name"), 2125 OPT_BOOLEAN(0, "guest", &perf_guest, 2126 "Collect guest os data"), 2127 OPT_BOOLEAN(0, "host", &perf_host, 2128 "Collect host os data"), 2129 OPT_STRING(0, "guestmount", &symbol_conf.guestmount, "directory", 2130 "guest mount directory under which every guest os" 2131 " instance has a subdir"), 2132 OPT_STRING(0, "guestvmlinux", &symbol_conf.default_guest_vmlinux_name, 2133 "file", "file saving guest os vmlinux"), 2134 OPT_STRING(0, "guestkallsyms", &symbol_conf.default_guest_kallsyms, 2135 "file", "file saving guest os /proc/kallsyms"), 2136 OPT_STRING(0, "guestmodules", &symbol_conf.default_guest_modules, 2137 "file", "file saving guest os /proc/modules"), 2138 OPT_BOOLEAN(0, "guest-code", &symbol_conf.guest_code, 2139 "Guest code can be found in hypervisor process"), 2140 OPT_INCR('v', "verbose", &verbose, 2141 "be more verbose (show counter open errors, etc)"), 2142 OPT_END() 2143 }; 2144 2145 const char *const kvm_subcommands[] = { "top", "record", "report", "diff", 2146 "buildid-list", "stat", NULL }; 2147 const char *kvm_usage[] = { NULL, NULL }; 2148 2149 exclude_GH_default = true; 2150 perf_host = 0; 2151 perf_guest = 1; 2152 2153 argc = parse_options_subcommand(argc, argv, kvm_options, kvm_subcommands, kvm_usage, 2154 PARSE_OPT_STOP_AT_NON_OPTION); 2155 if (!argc) 2156 usage_with_options(kvm_usage, kvm_options); 2157 2158 if (!perf_host) 2159 perf_guest = 1; 2160 2161 if (!file_name) { 2162 file_name = get_filename_for_perf_kvm(); 2163 2164 if (!file_name) { 2165 pr_err("Failed to allocate memory for filename\n"); 2166 return -ENOMEM; 2167 } 2168 } 2169 2170 if (strlen(argv[0]) > 2 && strstarts("record", argv[0])) 2171 return __cmd_record(file_name, argc, argv); 2172 else if (strlen(argv[0]) > 2 && strstarts("report", argv[0])) 2173 return __cmd_report(file_name, argc, argv); 2174 else if (strlen(argv[0]) > 2 && strstarts("diff", argv[0])) 2175 return cmd_diff(argc, argv); 2176 else if (!strcmp(argv[0], "top")) 2177 return __cmd_top(argc, argv); 2178 else if (strlen(argv[0]) > 2 && strstarts("buildid-list", argv[0])) 2179 return __cmd_buildid_list(file_name, argc, argv); 2180 #if defined(HAVE_LIBTRACEEVENT) 2181 else if (strlen(argv[0]) > 2 && strstarts("stat", argv[0])) 2182 return kvm_cmd_stat(file_name, argc, argv); 2183 #endif 2184 else 2185 usage_with_options(kvm_usage, kvm_options); 2186 2187 /* free usage string allocated by parse_options_subcommand */ 2188 free((void *)kvm_usage[0]); 2189 2190 return 0; 2191 } 2192