Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Merge tag 'perf-tools-fixes-for-v6.18-2-2025-11-16' of git://git.kernel.org/pub/scm/linux/kernel/git/perf/perf-tools

Pull perf tools fixes from Arnaldo Carvalho de Melo:

- Fix writing bpf_prog (infos|btfs)_cnt to data file, to not generate
invalid perf.data files in some corner cases.

- Fix 'perf top' segfault by ensuring libbfd is initialized. This is an
opt-in feature due to license incompatibilities.

- Fix segfault in 'perf lock' due to missing kernel map.

- Fix 'perf lock contention' test.

- Don't fail fast path detection if binutils-devel isn't available.

- Sync KVM's vmx.h with the kernel to pick SEAMCALL exit reason.

* tag 'perf-tools-fixes-for-v6.18-2-2025-11-16' of git://git.kernel.org/pub/scm/linux/kernel/git/perf/perf-tools:
perf libbfd: Ensure libbfd is initialized prior to use
perf test: Fix lock contention test
perf lock: Fix segfault due to missing kernel map
tools headers UAPI: Sync KVM's vmx.h with the kernel to pick SEAMCALL exit reason
perf build: Don't fail fast path feature detection when binutils-devel is not available
perf header: Write bpf_prog (infos|btfs)_cnt to data file

+68 -22
+1
tools/arch/x86/include/uapi/asm/vmx.h
··· 93 93 #define EXIT_REASON_TPAUSE 68 94 94 #define EXIT_REASON_BUS_LOCK 74 95 95 #define EXIT_REASON_NOTIFY 75 96 + #define EXIT_REASON_SEAMCALL 76 96 97 #define EXIT_REASON_TDCALL 77 97 98 #define EXIT_REASON_MSR_READ_IMM 84 98 99 #define EXIT_REASON_MSR_WRITE_IMM 85
+2 -2
tools/build/feature/Makefile
··· 107 107 __BUILD = $(CC) $(CFLAGS) -MD -Wall -Werror -o $@ $(patsubst %.bin,%.c,$(@F)) $(LDFLAGS) 108 108 BUILD = $(__BUILD) > $(@:.bin=.make.output) 2>&1 109 109 BUILD_BFD = $(BUILD) -DPACKAGE='"perf"' -lbfd -ldl 110 - BUILD_ALL = $(BUILD) -fstack-protector-all -O2 -D_FORTIFY_SOURCE=2 -ldw -lelf -lnuma -lelf -lslang $(FLAGS_PERL_EMBED) $(FLAGS_PYTHON_EMBED) -DPACKAGE='"perf"' -lbfd -ldl -lz -llzma -lzstd 110 + BUILD_ALL = $(BUILD) -fstack-protector-all -O2 -D_FORTIFY_SOURCE=2 -ldw -lelf -lnuma -lelf -lslang $(FLAGS_PERL_EMBED) $(FLAGS_PYTHON_EMBED) -ldl -lz -llzma -lzstd 111 111 112 112 __BUILDXX = $(CXX) $(CXXFLAGS) -MD -Wall -Werror -o $@ $(patsubst %.bin,%.cpp,$(@F)) $(LDFLAGS) 113 113 BUILDXX = $(__BUILDXX) > $(@:.bin=.make.output) 2>&1 ··· 115 115 ############################### 116 116 117 117 $(OUTPUT)test-all.bin: 118 - $(BUILD_ALL) || $(BUILD_ALL) -lopcodes -liberty 118 + $(BUILD_ALL) 119 119 120 120 $(OUTPUT)test-hello.bin: 121 121 $(BUILD)
+2 -3
tools/perf/Makefile.config
··· 354 354 355 355 FEATURE_CHECK_LDFLAGS-libaio = -lrt 356 356 357 - FEATURE_CHECK_LDFLAGS-disassembler-four-args = -lbfd -lopcodes -ldl 358 - FEATURE_CHECK_LDFLAGS-disassembler-init-styled = -lbfd -lopcodes -ldl 359 - 360 357 CORE_CFLAGS += -fno-omit-frame-pointer 361 358 CORE_CFLAGS += -Wall 362 359 CORE_CFLAGS += -Wextra ··· 927 930 928 931 ifeq ($(feature-libbfd), 1) 929 932 EXTLIBS += -lbfd -lopcodes 933 + FEATURE_CHECK_LDFLAGS-disassembler-four-args = -lbfd -lopcodes -ldl 934 + FEATURE_CHECK_LDFLAGS-disassembler-init-styled = -lbfd -lopcodes -ldl 930 935 else 931 936 # we are on a system that requires -liberty and (maybe) -lz 932 937 # to link against -lbfd; test each case individually here
+2
tools/perf/builtin-lock.c
··· 1867 1867 eops.sample = process_sample_event; 1868 1868 eops.comm = perf_event__process_comm; 1869 1869 eops.mmap = perf_event__process_mmap; 1870 + eops.mmap2 = perf_event__process_mmap2; 1870 1871 eops.namespaces = perf_event__process_namespaces; 1871 1872 eops.tracing_data = perf_event__process_tracing_data; 1872 1873 session = perf_session__new(&data, &eops); ··· 2024 2023 eops.sample = process_sample_event; 2025 2024 eops.comm = perf_event__process_comm; 2026 2025 eops.mmap = perf_event__process_mmap; 2026 + eops.mmap2 = perf_event__process_mmap2; 2027 2027 eops.tracing_data = perf_event__process_tracing_data; 2028 2028 2029 2029 perf_env__init(&host_env);
+9 -5
tools/perf/tests/shell/lock_contention.sh
··· 13 13 rm -f ${perfdata} 14 14 rm -f ${result} 15 15 rm -f ${errout} 16 - trap - EXIT TERM INT 16 + trap - EXIT TERM INT ERR 17 17 } 18 18 19 19 trap_cleanup() { 20 + if (( $? == 139 )); then #SIGSEGV 21 + err=1 22 + fi 20 23 echo "Unexpected signal in ${FUNCNAME[1]}" 21 24 cleanup 22 25 exit ${err} 23 26 } 24 - trap trap_cleanup EXIT TERM INT 27 + trap trap_cleanup EXIT TERM INT ERR 25 28 26 29 check() { 27 30 if [ "$(id -u)" != 0 ]; then ··· 148 145 fi 149 146 150 147 # the perf lock contention output goes to the stderr 151 - perf lock con -a -b -g -E 1 -q -- perf bench sched messaging -p > /dev/null 2> ${result} 148 + perf lock con -a -b --lock-cgroup -E 1 -q -- perf bench sched messaging -p > /dev/null 2> ${result} 152 149 if [ "$(cat "${result}" | wc -l)" != "1" ]; then 153 150 echo "[Fail] BPF result count is not 1:" "$(cat "${result}" | wc -l)" 154 151 err=1 ··· 274 271 return 275 272 fi 276 273 277 - perf lock con -a -b -g -E 1 -F wait_total -q -- perf bench sched messaging -p > /dev/null 2> ${result} 274 + perf lock con -a -b --lock-cgroup -E 1 -F wait_total -q -- perf bench sched messaging -p > /dev/null 2> ${result} 278 275 if [ "$(cat "${result}" | wc -l)" != "1" ]; then 279 276 echo "[Fail] BPF result should have a cgroup result:" "$(cat "${result}")" 280 277 err=1 ··· 282 279 fi 283 280 284 281 cgroup=$(cat "${result}" | awk '{ print $3 }') 285 - perf lock con -a -b -g -E 1 -G "${cgroup}" -q -- perf bench sched messaging -p > /dev/null 2> ${result} 282 + perf lock con -a -b --lock-cgroup -E 1 -G "${cgroup}" -q -- perf bench sched messaging -p > /dev/null 2> ${result} 286 283 if [ "$(cat "${result}" | wc -l)" != "1" ]; then 287 284 echo "[Fail] BPF result should have a result with cgroup filter:" "$(cat "${cgroup}")" 288 285 err=1 ··· 341 338 test_cgroup_filter 342 339 test_csv_output 343 340 341 + cleanup 344 342 exit ${err}
+2 -8
tools/perf/util/header.c
··· 1022 1022 1023 1023 down_read(&env->bpf_progs.lock); 1024 1024 1025 - if (env->bpf_progs.infos_cnt == 0) 1026 - goto out; 1027 - 1028 1025 ret = do_write(ff, &env->bpf_progs.infos_cnt, 1029 1026 sizeof(env->bpf_progs.infos_cnt)); 1030 - if (ret < 0) 1027 + if (ret < 0 || env->bpf_progs.infos_cnt == 0) 1031 1028 goto out; 1032 1029 1033 1030 root = &env->bpf_progs.infos; ··· 1064 1067 1065 1068 down_read(&env->bpf_progs.lock); 1066 1069 1067 - if (env->bpf_progs.btfs_cnt == 0) 1068 - goto out; 1069 - 1070 1070 ret = do_write(ff, &env->bpf_progs.btfs_cnt, 1071 1071 sizeof(env->bpf_progs.btfs_cnt)); 1072 1072 1073 - if (ret < 0) 1073 + if (ret < 0 || env->bpf_progs.btfs_cnt == 0) 1074 1074 goto out; 1075 1075 1076 1076 root = &env->bpf_progs.btfs;
+38
tools/perf/util/libbfd.c
··· 38 38 asymbol **syms; 39 39 }; 40 40 41 + static bool perf_bfd_lock(void *bfd_mutex) 42 + { 43 + mutex_lock(bfd_mutex); 44 + return true; 45 + } 46 + 47 + static bool perf_bfd_unlock(void *bfd_mutex) 48 + { 49 + mutex_unlock(bfd_mutex); 50 + return true; 51 + } 52 + 53 + static void perf_bfd_init(void) 54 + { 55 + static struct mutex bfd_mutex; 56 + 57 + mutex_init_recursive(&bfd_mutex); 58 + 59 + if (bfd_init() != BFD_INIT_MAGIC) { 60 + pr_err("Error initializing libbfd\n"); 61 + return; 62 + } 63 + if (!bfd_thread_init(perf_bfd_lock, perf_bfd_unlock, &bfd_mutex)) 64 + pr_err("Error initializing libbfd threading\n"); 65 + } 66 + 67 + static void ensure_bfd_init(void) 68 + { 69 + static pthread_once_t bfd_init_once = PTHREAD_ONCE_INIT; 70 + 71 + pthread_once(&bfd_init_once, perf_bfd_init); 72 + } 73 + 41 74 static int bfd_error(const char *string) 42 75 { 43 76 const char *errmsg; ··· 165 132 bfd *abfd; 166 133 struct a2l_data *a2l = NULL; 167 134 135 + ensure_bfd_init(); 168 136 abfd = bfd_openr(path, NULL); 169 137 if (abfd == NULL) 170 138 return NULL; ··· 322 288 bfd *abfd; 323 289 u64 start, len; 324 290 291 + ensure_bfd_init(); 325 292 abfd = bfd_openr(debugfile, NULL); 326 293 if (!abfd) 327 294 return -1; ··· 428 393 if (fd < 0) 429 394 return -1; 430 395 396 + ensure_bfd_init(); 431 397 abfd = bfd_fdopenr(filename, /*target=*/NULL, fd); 432 398 if (!abfd) 433 399 return -1; ··· 457 421 asection *section; 458 422 bfd *abfd; 459 423 424 + ensure_bfd_init(); 460 425 abfd = bfd_openr(filename, NULL); 461 426 if (!abfd) 462 427 return -1; ··· 517 480 memset(tpath, 0, sizeof(tpath)); 518 481 perf_exe(tpath, sizeof(tpath)); 519 482 483 + ensure_bfd_init(); 520 484 bfdf = bfd_openr(tpath, NULL); 521 485 if (bfdf == NULL) 522 486 abort();
+10 -4
tools/perf/util/mutex.c
··· 17 17 18 18 #define CHECK_ERR(err) check_err(__func__, err) 19 19 20 - static void __mutex_init(struct mutex *mtx, bool pshared) 20 + static void __mutex_init(struct mutex *mtx, bool pshared, bool recursive) 21 21 { 22 22 pthread_mutexattr_t attr; 23 23 ··· 27 27 /* In normal builds enable error checking, such as recursive usage. */ 28 28 CHECK_ERR(pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_ERRORCHECK)); 29 29 #endif 30 + if (recursive) 31 + CHECK_ERR(pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_RECURSIVE)); 30 32 if (pshared) 31 33 CHECK_ERR(pthread_mutexattr_setpshared(&attr, PTHREAD_PROCESS_SHARED)); 32 - 33 34 CHECK_ERR(pthread_mutex_init(&mtx->lock, &attr)); 34 35 CHECK_ERR(pthread_mutexattr_destroy(&attr)); 35 36 } 36 37 37 38 void mutex_init(struct mutex *mtx) 38 39 { 39 - __mutex_init(mtx, /*pshared=*/false); 40 + __mutex_init(mtx, /*pshared=*/false, /*recursive=*/false); 40 41 } 41 42 42 43 void mutex_init_pshared(struct mutex *mtx) 43 44 { 44 - __mutex_init(mtx, /*pshared=*/true); 45 + __mutex_init(mtx, /*pshared=*/true, /*recursive=*/false); 46 + } 47 + 48 + void mutex_init_recursive(struct mutex *mtx) 49 + { 50 + __mutex_init(mtx, /*pshared=*/false, /*recursive=*/true); 45 51 } 46 52 47 53 void mutex_destroy(struct mutex *mtx)
+2
tools/perf/util/mutex.h
··· 104 104 * process-private attribute. 105 105 */ 106 106 void mutex_init_pshared(struct mutex *mtx); 107 + /* Initializes a mutex that may be recursively held on the same thread. */ 108 + void mutex_init_recursive(struct mutex *mtx); 107 109 void mutex_destroy(struct mutex *mtx); 108 110 109 111 void mutex_lock(struct mutex *mtx) EXCLUSIVE_LOCK_FUNCTION(*mtx);