1 // SPDX-License-Identifier: GPL-2.0 2 #include <errno.h> 3 #include <linux/kernel.h> 4 #include <linux/types.h> 5 #include <inttypes.h> 6 #include <stdlib.h> 7 #include <unistd.h> 8 #include <stdio.h> 9 #include <string.h> 10 #include <sys/param.h> 11 #include <perf/cpumap.h> 12 #include <perf/evlist.h> 13 14 #include "parse-events.h" 15 #include "evlist.h" 16 #include "evsel.h" 17 #include "thread_map.h" 18 #include "cpumap.h" 19 #include "machine.h" 20 #include "map.h" 21 #include "symbol.h" 22 #include "event.h" 23 #include "record.h" 24 #include "thread.h" 25 26 #include "tests.h" 27 28 #include <linux/ctype.h> 29 30 #define BUFSZ 1024 31 #define READLEN 128 32 33 struct state { 34 u64 done[1024]; 35 size_t done_cnt; 36 }; 37 38 static unsigned int hex(char c) 39 { 40 if (c >= '0' && c <= '9') 41 return c - '0'; 42 if (c >= 'a' && c <= 'f') 43 return c - 'a' + 10; 44 return c - 'A' + 10; 45 } 46 47 static size_t read_objdump_chunk(const char **line, unsigned char **buf, 48 size_t *buf_len) 49 { 50 size_t bytes_read = 0; 51 unsigned char *chunk_start = *buf; 52 53 /* Read bytes */ 54 while (*buf_len > 0) { 55 char c1, c2; 56 57 /* Get 2 hex digits */ 58 c1 = *(*line)++; 59 if (!isxdigit(c1)) 60 break; 61 c2 = *(*line)++; 62 if (!isxdigit(c2)) 63 break; 64 65 /* Store byte and advance buf */ 66 **buf = (hex(c1) << 4) | hex(c2); 67 (*buf)++; 68 (*buf_len)--; 69 bytes_read++; 70 71 /* End of chunk? */ 72 if (isspace(**line)) 73 break; 74 } 75 76 /* 77 * objdump will display raw insn as LE if code endian 78 * is LE and bytes_per_chunk > 1. In that case reverse 79 * the chunk we just read. 80 * 81 * see disassemble_bytes() at binutils/objdump.c for details 82 * how objdump chooses display endian) 83 */ 84 if (bytes_read > 1 && !bigendian()) { 85 unsigned char *chunk_end = chunk_start + bytes_read - 1; 86 unsigned char tmp; 87 88 while (chunk_start < chunk_end) { 89 tmp = *chunk_start; 90 *chunk_start = *chunk_end; 91 *chunk_end = tmp; 92 chunk_start++; 93 chunk_end--; 94 } 95 } 96 97 return bytes_read; 98 } 99 100 static size_t read_objdump_line(const char *line, unsigned char *buf, 101 size_t buf_len) 102 { 103 const char *p; 104 size_t ret, bytes_read = 0; 105 106 /* Skip to a colon */ 107 p = strchr(line, ':'); 108 if (!p) 109 return 0; 110 p++; 111 112 /* Skip initial spaces */ 113 while (*p) { 114 if (!isspace(*p)) 115 break; 116 p++; 117 } 118 119 do { 120 ret = read_objdump_chunk(&p, &buf, &buf_len); 121 bytes_read += ret; 122 p++; 123 } while (ret > 0); 124 125 /* return number of successfully read bytes */ 126 return bytes_read; 127 } 128 129 static int read_objdump_output(FILE *f, void *buf, size_t *len, u64 start_addr) 130 { 131 char *line = NULL; 132 size_t line_len, off_last = 0; 133 ssize_t ret; 134 int err = 0; 135 u64 addr, last_addr = start_addr; 136 137 while (off_last < *len) { 138 size_t off, read_bytes, written_bytes; 139 unsigned char tmp[BUFSZ]; 140 141 ret = getline(&line, &line_len, f); 142 if (feof(f)) 143 break; 144 if (ret < 0) { 145 pr_debug("getline failed\n"); 146 err = -1; 147 break; 148 } 149 150 /* read objdump data into temporary buffer */ 151 read_bytes = read_objdump_line(line, tmp, sizeof(tmp)); 152 if (!read_bytes) 153 continue; 154 155 if (sscanf(line, "%"PRIx64, &addr) != 1) 156 continue; 157 if (addr < last_addr) { 158 pr_debug("addr going backwards, read beyond section?\n"); 159 break; 160 } 161 last_addr = addr; 162 163 /* copy it from temporary buffer to 'buf' according 164 * to address on current objdump line */ 165 off = addr - start_addr; 166 if (off >= *len) 167 break; 168 written_bytes = MIN(read_bytes, *len - off); 169 memcpy(buf + off, tmp, written_bytes); 170 off_last = off + written_bytes; 171 } 172 173 /* len returns number of bytes that could not be read */ 174 *len -= off_last; 175 176 free(line); 177 178 return err; 179 } 180 181 static int read_via_objdump(const char *filename, u64 addr, void *buf, 182 size_t len) 183 { 184 char cmd[PATH_MAX * 2]; 185 const char *fmt; 186 FILE *f; 187 int ret; 188 189 fmt = "%s -z -d --start-address=0x%"PRIx64" --stop-address=0x%"PRIx64" %s"; 190 ret = snprintf(cmd, sizeof(cmd), fmt, "objdump", addr, addr + len, 191 filename); 192 if (ret <= 0 || (size_t)ret >= sizeof(cmd)) 193 return -1; 194 195 pr_debug("Objdump command is: %s\n", cmd); 196 197 /* Ignore objdump errors */ 198 strcat(cmd, " 2>/dev/null"); 199 200 f = popen(cmd, "r"); 201 if (!f) { 202 pr_debug("popen failed\n"); 203 return -1; 204 } 205 206 ret = read_objdump_output(f, buf, &len, addr); 207 if (len) { 208 pr_debug("objdump read too few bytes: %zd\n", len); 209 if (!ret) 210 ret = len; 211 } 212 213 pclose(f); 214 215 return ret; 216 } 217 218 static void dump_buf(unsigned char *buf, size_t len) 219 { 220 size_t i; 221 222 for (i = 0; i < len; i++) { 223 pr_debug("0x%02x ", buf[i]); 224 if (i % 16 == 15) 225 pr_debug("\n"); 226 } 227 pr_debug("\n"); 228 } 229 230 static int read_object_code(u64 addr, size_t len, u8 cpumode, 231 struct thread *thread, struct state *state) 232 { 233 struct addr_location al; 234 unsigned char buf1[BUFSZ]; 235 unsigned char buf2[BUFSZ]; 236 size_t ret_len; 237 u64 objdump_addr; 238 const char *objdump_name; 239 char decomp_name[KMOD_DECOMP_LEN]; 240 bool decomp = false; 241 int ret; 242 243 pr_debug("Reading object code for memory address: %#"PRIx64"\n", addr); 244 245 if (!thread__find_map(thread, cpumode, addr, &al) || !al.map->dso) { 246 if (cpumode == PERF_RECORD_MISC_HYPERVISOR) { 247 pr_debug("Hypervisor address can not be resolved - skipping\n"); 248 return 0; 249 } 250 251 pr_debug("thread__find_map failed\n"); 252 return -1; 253 } 254 255 pr_debug("File is: %s\n", al.map->dso->long_name); 256 257 if (al.map->dso->symtab_type == DSO_BINARY_TYPE__KALLSYMS && 258 !dso__is_kcore(al.map->dso)) { 259 pr_debug("Unexpected kernel address - skipping\n"); 260 return 0; 261 } 262 263 pr_debug("On file address is: %#"PRIx64"\n", al.addr); 264 265 if (len > BUFSZ) 266 len = BUFSZ; 267 268 /* Do not go off the map */ 269 if (addr + len > al.map->end) 270 len = al.map->end - addr; 271 272 /* Read the object code using perf */ 273 ret_len = dso__data_read_offset(al.map->dso, thread->mg->machine, 274 al.addr, buf1, len); 275 if (ret_len != len) { 276 pr_debug("dso__data_read_offset failed\n"); 277 return -1; 278 } 279 280 /* 281 * Converting addresses for use by objdump requires more information. 282 * map__load() does that. See map__rip_2objdump() for details. 283 */ 284 if (map__load(al.map)) 285 return -1; 286 287 /* objdump struggles with kcore - try each map only once */ 288 if (dso__is_kcore(al.map->dso)) { 289 size_t d; 290 291 for (d = 0; d < state->done_cnt; d++) { 292 if (state->done[d] == al.map->start) { 293 pr_debug("kcore map tested already"); 294 pr_debug(" - skipping\n"); 295 return 0; 296 } 297 } 298 if (state->done_cnt >= ARRAY_SIZE(state->done)) { 299 pr_debug("Too many kcore maps - skipping\n"); 300 return 0; 301 } 302 state->done[state->done_cnt++] = al.map->start; 303 } 304 305 objdump_name = al.map->dso->long_name; 306 if (dso__needs_decompress(al.map->dso)) { 307 if (dso__decompress_kmodule_path(al.map->dso, objdump_name, 308 decomp_name, 309 sizeof(decomp_name)) < 0) { 310 pr_debug("decompression failed\n"); 311 return -1; 312 } 313 314 decomp = true; 315 objdump_name = decomp_name; 316 } 317 318 /* Read the object code using objdump */ 319 objdump_addr = map__rip_2objdump(al.map, al.addr); 320 ret = read_via_objdump(objdump_name, objdump_addr, buf2, len); 321 322 if (decomp) 323 unlink(objdump_name); 324 325 if (ret > 0) { 326 /* 327 * The kernel maps are inaccurate - assume objdump is right in 328 * that case. 329 */ 330 if (cpumode == PERF_RECORD_MISC_KERNEL || 331 cpumode == PERF_RECORD_MISC_GUEST_KERNEL) { 332 len -= ret; 333 if (len) { 334 pr_debug("Reducing len to %zu\n", len); 335 } else if (dso__is_kcore(al.map->dso)) { 336 /* 337 * objdump cannot handle very large segments 338 * that may be found in kcore. 339 */ 340 pr_debug("objdump failed for kcore"); 341 pr_debug(" - skipping\n"); 342 return 0; 343 } else { 344 return -1; 345 } 346 } 347 } 348 if (ret < 0) { 349 pr_debug("read_via_objdump failed\n"); 350 return -1; 351 } 352 353 /* The results should be identical */ 354 if (memcmp(buf1, buf2, len)) { 355 pr_debug("Bytes read differ from those read by objdump\n"); 356 pr_debug("buf1 (dso):\n"); 357 dump_buf(buf1, len); 358 pr_debug("buf2 (objdump):\n"); 359 dump_buf(buf2, len); 360 return -1; 361 } 362 pr_debug("Bytes read match those read by objdump\n"); 363 364 return 0; 365 } 366 367 static int process_sample_event(struct machine *machine, 368 struct evlist *evlist, 369 union perf_event *event, struct state *state) 370 { 371 struct perf_sample sample; 372 struct thread *thread; 373 int ret; 374 375 if (perf_evlist__parse_sample(evlist, event, &sample)) { 376 pr_debug("perf_evlist__parse_sample failed\n"); 377 return -1; 378 } 379 380 thread = machine__findnew_thread(machine, sample.pid, sample.tid); 381 if (!thread) { 382 pr_debug("machine__findnew_thread failed\n"); 383 return -1; 384 } 385 386 ret = read_object_code(sample.ip, READLEN, sample.cpumode, thread, state); 387 thread__put(thread); 388 return ret; 389 } 390 391 static int process_event(struct machine *machine, struct evlist *evlist, 392 union perf_event *event, struct state *state) 393 { 394 if (event->header.type == PERF_RECORD_SAMPLE) 395 return process_sample_event(machine, evlist, event, state); 396 397 if (event->header.type == PERF_RECORD_THROTTLE || 398 event->header.type == PERF_RECORD_UNTHROTTLE) 399 return 0; 400 401 if (event->header.type < PERF_RECORD_MAX) { 402 int ret; 403 404 ret = machine__process_event(machine, event, NULL); 405 if (ret < 0) 406 pr_debug("machine__process_event failed, event type %u\n", 407 event->header.type); 408 return ret; 409 } 410 411 return 0; 412 } 413 414 static int process_events(struct machine *machine, struct evlist *evlist, 415 struct state *state) 416 { 417 union perf_event *event; 418 struct perf_mmap *md; 419 int i, ret; 420 421 for (i = 0; i < evlist->nr_mmaps; i++) { 422 md = &evlist->mmap[i]; 423 if (perf_mmap__read_init(md) < 0) 424 continue; 425 426 while ((event = perf_mmap__read_event(md)) != NULL) { 427 ret = process_event(machine, evlist, event, state); 428 perf_mmap__consume(md); 429 if (ret < 0) 430 return ret; 431 } 432 perf_mmap__read_done(md); 433 } 434 return 0; 435 } 436 437 static int comp(const void *a, const void *b) 438 { 439 return *(int *)a - *(int *)b; 440 } 441 442 static void do_sort_something(void) 443 { 444 int buf[40960], i; 445 446 for (i = 0; i < (int)ARRAY_SIZE(buf); i++) 447 buf[i] = ARRAY_SIZE(buf) - i - 1; 448 449 qsort(buf, ARRAY_SIZE(buf), sizeof(int), comp); 450 451 for (i = 0; i < (int)ARRAY_SIZE(buf); i++) { 452 if (buf[i] != i) { 453 pr_debug("qsort failed\n"); 454 break; 455 } 456 } 457 } 458 459 static void sort_something(void) 460 { 461 int i; 462 463 for (i = 0; i < 10; i++) 464 do_sort_something(); 465 } 466 467 static void syscall_something(void) 468 { 469 int pipefd[2]; 470 int i; 471 472 for (i = 0; i < 1000; i++) { 473 if (pipe(pipefd) < 0) { 474 pr_debug("pipe failed\n"); 475 break; 476 } 477 close(pipefd[1]); 478 close(pipefd[0]); 479 } 480 } 481 482 static void fs_something(void) 483 { 484 const char *test_file_name = "temp-perf-code-reading-test-file--"; 485 FILE *f; 486 int i; 487 488 for (i = 0; i < 1000; i++) { 489 f = fopen(test_file_name, "w+"); 490 if (f) { 491 fclose(f); 492 unlink(test_file_name); 493 } 494 } 495 } 496 497 static const char *do_determine_event(bool excl_kernel) 498 { 499 const char *event = excl_kernel ? "cycles:u" : "cycles"; 500 501 #ifdef __s390x__ 502 char cpuid[128], model[16], model_c[16], cpum_cf_v[16]; 503 unsigned int family; 504 int ret, cpum_cf_a; 505 506 if (get_cpuid(cpuid, sizeof(cpuid))) 507 goto out_clocks; 508 ret = sscanf(cpuid, "%*[^,],%u,%[^,],%[^,],%[^,],%x", &family, model_c, 509 model, cpum_cf_v, &cpum_cf_a); 510 if (ret != 5) /* Not available */ 511 goto out_clocks; 512 if (excl_kernel && (cpum_cf_a & 4)) 513 return event; 514 if (!excl_kernel && (cpum_cf_a & 2)) 515 return event; 516 517 /* Fall through: missing authorization */ 518 out_clocks: 519 event = excl_kernel ? "cpu-clock:u" : "cpu-clock"; 520 521 #endif 522 return event; 523 } 524 525 static void do_something(void) 526 { 527 fs_something(); 528 529 sort_something(); 530 531 syscall_something(); 532 } 533 534 enum { 535 TEST_CODE_READING_OK, 536 TEST_CODE_READING_NO_VMLINUX, 537 TEST_CODE_READING_NO_KCORE, 538 TEST_CODE_READING_NO_ACCESS, 539 TEST_CODE_READING_NO_KERNEL_OBJ, 540 }; 541 542 static int do_test_code_reading(bool try_kcore) 543 { 544 struct machine *machine; 545 struct thread *thread; 546 struct record_opts opts = { 547 .mmap_pages = UINT_MAX, 548 .user_freq = UINT_MAX, 549 .user_interval = ULLONG_MAX, 550 .freq = 500, 551 .target = { 552 .uses_mmap = true, 553 }, 554 }; 555 struct state state = { 556 .done_cnt = 0, 557 }; 558 struct perf_thread_map *threads = NULL; 559 struct perf_cpu_map *cpus = NULL; 560 struct evlist *evlist = NULL; 561 struct evsel *evsel = NULL; 562 int err = -1, ret; 563 pid_t pid; 564 struct map *map; 565 bool have_vmlinux, have_kcore, excl_kernel = false; 566 567 pid = getpid(); 568 569 machine = machine__new_host(); 570 machine->env = &perf_env; 571 572 ret = machine__create_kernel_maps(machine); 573 if (ret < 0) { 574 pr_debug("machine__create_kernel_maps failed\n"); 575 goto out_err; 576 } 577 578 /* Force the use of kallsyms instead of vmlinux to try kcore */ 579 if (try_kcore) 580 symbol_conf.kallsyms_name = "/proc/kallsyms"; 581 582 /* Load kernel map */ 583 map = machine__kernel_map(machine); 584 ret = map__load(map); 585 if (ret < 0) { 586 pr_debug("map__load failed\n"); 587 goto out_err; 588 } 589 have_vmlinux = dso__is_vmlinux(map->dso); 590 have_kcore = dso__is_kcore(map->dso); 591 592 /* 2nd time through we just try kcore */ 593 if (try_kcore && !have_kcore) 594 return TEST_CODE_READING_NO_KCORE; 595 596 /* No point getting kernel events if there is no kernel object */ 597 if (!have_vmlinux && !have_kcore) 598 excl_kernel = true; 599 600 threads = thread_map__new_by_tid(pid); 601 if (!threads) { 602 pr_debug("thread_map__new_by_tid failed\n"); 603 goto out_err; 604 } 605 606 ret = perf_event__synthesize_thread_map(NULL, threads, 607 perf_event__process, machine, false); 608 if (ret < 0) { 609 pr_debug("perf_event__synthesize_thread_map failed\n"); 610 goto out_err; 611 } 612 613 thread = machine__findnew_thread(machine, pid, pid); 614 if (!thread) { 615 pr_debug("machine__findnew_thread failed\n"); 616 goto out_put; 617 } 618 619 cpus = perf_cpu_map__new(NULL); 620 if (!cpus) { 621 pr_debug("perf_cpu_map__new failed\n"); 622 goto out_put; 623 } 624 625 while (1) { 626 const char *str; 627 628 evlist = evlist__new(); 629 if (!evlist) { 630 pr_debug("perf_evlist__new failed\n"); 631 goto out_put; 632 } 633 634 perf_evlist__set_maps(&evlist->core, cpus, threads); 635 636 str = do_determine_event(excl_kernel); 637 pr_debug("Parsing event '%s'\n", str); 638 ret = parse_events(evlist, str, NULL); 639 if (ret < 0) { 640 pr_debug("parse_events failed\n"); 641 goto out_put; 642 } 643 644 perf_evlist__config(evlist, &opts, NULL); 645 646 evsel = perf_evlist__first(evlist); 647 648 evsel->core.attr.comm = 1; 649 evsel->core.attr.disabled = 1; 650 evsel->core.attr.enable_on_exec = 0; 651 652 ret = evlist__open(evlist); 653 if (ret < 0) { 654 if (!excl_kernel) { 655 excl_kernel = true; 656 /* 657 * Both cpus and threads are now owned by evlist 658 * and will be freed by following perf_evlist__set_maps 659 * call. Getting refference to keep them alive. 660 */ 661 perf_cpu_map__get(cpus); 662 perf_thread_map__get(threads); 663 perf_evlist__set_maps(&evlist->core, NULL, NULL); 664 evlist__delete(evlist); 665 evlist = NULL; 666 continue; 667 } 668 669 if (verbose > 0) { 670 char errbuf[512]; 671 perf_evlist__strerror_open(evlist, errno, errbuf, sizeof(errbuf)); 672 pr_debug("perf_evlist__open() failed!\n%s\n", errbuf); 673 } 674 675 goto out_put; 676 } 677 break; 678 } 679 680 ret = perf_evlist__mmap(evlist, UINT_MAX); 681 if (ret < 0) { 682 pr_debug("perf_evlist__mmap failed\n"); 683 goto out_put; 684 } 685 686 evlist__enable(evlist); 687 688 do_something(); 689 690 evlist__disable(evlist); 691 692 ret = process_events(machine, evlist, &state); 693 if (ret < 0) 694 goto out_put; 695 696 if (!have_vmlinux && !have_kcore && !try_kcore) 697 err = TEST_CODE_READING_NO_KERNEL_OBJ; 698 else if (!have_vmlinux && !try_kcore) 699 err = TEST_CODE_READING_NO_VMLINUX; 700 else if (excl_kernel) 701 err = TEST_CODE_READING_NO_ACCESS; 702 else 703 err = TEST_CODE_READING_OK; 704 out_put: 705 thread__put(thread); 706 out_err: 707 708 if (evlist) { 709 evlist__delete(evlist); 710 } else { 711 perf_cpu_map__put(cpus); 712 perf_thread_map__put(threads); 713 } 714 machine__delete_threads(machine); 715 machine__delete(machine); 716 717 return err; 718 } 719 720 int test__code_reading(struct test *test __maybe_unused, int subtest __maybe_unused) 721 { 722 int ret; 723 724 ret = do_test_code_reading(false); 725 if (!ret) 726 ret = do_test_code_reading(true); 727 728 switch (ret) { 729 case TEST_CODE_READING_OK: 730 return 0; 731 case TEST_CODE_READING_NO_VMLINUX: 732 pr_debug("no vmlinux\n"); 733 return 0; 734 case TEST_CODE_READING_NO_KCORE: 735 pr_debug("no kcore\n"); 736 return 0; 737 case TEST_CODE_READING_NO_ACCESS: 738 pr_debug("no access\n"); 739 return 0; 740 case TEST_CODE_READING_NO_KERNEL_OBJ: 741 pr_debug("no kernel obj\n"); 742 return 0; 743 default: 744 return -1; 745 }; 746 } 747