当我想在 WSL 下运行 perf 时,我遇到了以下问题:
警告:未找到内核 4.4.0-18362 的性能
您可能需要为此特定内核安装以下软件包:
linux-tools-4.4.0-18362-微软
linux-cloud-tools-4.4.0-18362-微软
您可能还需要安装以下软件包之一以保持最新:
linux-工具-微软
linux-cloud-tools-微软
但是我找不到名为
linux-tools-4.4.0-18362-Microsoft
或 linux-cloud-tools-4.4.0-18362-Microsoft
的软件包。我猜包名是自动生成的。
我还尝试在 docker 容器中使用 perf。但是,docker 容器使用与主机相同的内核。
有没有办法在WSL下运行perf?
听说WSL2中可以使用perf。但是当我升级到 WSL2 后,它显示了类似的错误消息:
警告:未找到内核 4.19.84-microsoft 的性能
您可能需要为此特定安装以下软件包 内核:
linux-tools-4.19.84-microsoft-standard linux-cloud-tools-4.19.84-microsoft-standard
您可能还想安装以下软件包之一以保留 最新:
linux-tools-standard linux-cloud-tools-standard
警告:未找到内核 4.19.84-microsoft 的性能
因为 WSL2 使用自定义 Linux 内核。它的源代码可以在这里找到 微软/WSL2-Linux-内核。我们必须从中编译性能工具。
sudo apt install build-essential flex bison libssl-dev libelf-dev
git clone --depth=1 https://github.com/microsoft/WSL2-Linux-Kernel.git
cd WSL2-Linux-Kernel/tools/perf
make
perf
可执行文件将位于该文件夹中。
linux-tools-generic
。
apt install linux-tools-generic
然后使用安装路径
perf
运行/usr/lib/linux-tools/<linux-version>-generic/perf
。
flamegraph
,将使用环境变量 PERF
作为 perf
路径。
PERF=/usr/lib/linux-tools/<linux-version>-generic/perf flamegraph -- my_program
接受的答案有效。但是,缺少一些功能。
为了获得有用且经过整理的信息,我必须安装以下库,然后再次运行
make
。
libbabeltrace-dev
libunwind-dev
libdw-dev
binutils-dev
libiberty-dev
我不确定是否所有这些都有必要。然而,这些足以让
cargo-flamegraph
(我的用例)工作。
您可以安装一些通用版本的 perf,而不是 WSL2 版本,例如:
sudo apt install linux-tools-5.4.0-126-generic linux-tools-common
然后当你运行 perf 时,它会出错,比如:
$ perf
WARNING: perf not found for kernel 5.10.16.3-microsoft
You may need to install the following packages for this specific kernel:
linux-tools-5.10.16.3-microsoft-standard-WSL2
linux-cloud-tools-5.10.16.3-microsoft-standard-WSL2
这是因为脚本
/usr/bin/perf
总是尝试从 uname -r
获取性能二进制文件
$ grep uname `which perf`
full_version=`uname -r`
我们可以用实际的 perf 替换 /usr/bin/perf :
mv /usr/bin/perf /usr/bin/perf.bk && ln -s /usr/lib/linux-tools/5.4.0-126-generic/perf /usr/bin/perf
然后:
$ perf stat ls 1>/dev/null
Performance counter stats for 'ls':
1.79 msec task-clock:u # 0.827 CPUs utilized
0 context-switches:u # 0.000 K/sec
0 cpu-migrations:u # 0.000 K/sec
112 page-faults:u # 0.063 M/sec
<not supported> cycles:u
<not supported> instructions:u
<not supported> branches:u
<not supported> branch-misses:u
0.002158900 seconds time elapsed
0.002182000 seconds user
0.000000000 seconds sys
我认为硬件/缓存计数器在 WSL2 上不可用
如果您遵循接受的答案,请确保您阅读了 make 命令在开始时打印的抱怨,因为它可能会丢失一些标头并禁用功能。
对我来说,它禁用了 tui、gtk 和 demangling 等功能。
我在尝试使用编译版本和
perf stat
版本运行 linux-tools-generic
时遇到错误:
./perf stat -d ls
Error:
The sys_perf_event_open() syscall returned with 22 (Invalid argument) for event (slots:u).
/bin/dmesg | grep -i perf may provide additional information.
任何更新/启用/禁用 WSL2 或重新安装 Ubuntu 映像的仪式都无法解决该问题。
我在一些newsletter中找到了解释:
添加 [电子邮件受保护],因为此问题存在于虚拟化环境中。
自提交 42641d6f4d15 以来,自上而下的指标事件成为默认值 (“perf stat:将自上而下指标事件添加为默认事件”)。性能 如果 /sys/bus/event_source/devices/cpu/events/slots 将使用“slots” 可用。
不幸的是,虚拟化可能不支持“插槽” 环境。虚拟机管理程序可能不会将“插槽”计数器暴露给 虚拟机的 cpuid。因此,内核可能会禁用自上而下的插槽并 如果插槽事件不在 CPUID 中,则 intel_pmu_init() 中的指标事件。 例如,c->weight 和 c->idxmsk64 都设置为 0。
由于“slots”是领导者,Icelake VM 上将会出现以下错误:
$ perf stat 错误:sys_perf_event_open() 系统调用返回 22 事件(槽)的(无效参数)。 /bin/dmesg | grep -i 性能可能 提供更多信息。
这是因为 stat_handle_error() 在以下情况下返回 COUNTER_FATAL: “slots”被用作事件的领导者。
有三个选项可以解决此问题。
不要将 /sys/bus/event_source/devices/cpu/events/slots 暴露给用户空间,以便 pmu_have_event(pmu->name, "slots") 返回 false。
在 perf 用户空间运行 cpuid,如果 cpuid 不支持,请避免使用“插槽”。
如果领导者失败,不要致命。如果 evsel 的领导者已经失败,请勿为其创建事件。
所以我尝试手动指定事件,而不是指定
slots
:
./perf stat -e cache-misses -d ls
Performance counter stats for 'ls':
20145 cache-misses
555870 L1-dcache-loads
25832 L1-dcache-load-misses # 4.65% of all L1-dcache accesses
<not supported> LLC-loads
<not supported> LLC-load-misses
0.000948558 seconds time elapsed
0.001025000 seconds user
0.000000000 seconds sys
所以,
perf
终于可以在我的WSL中使用了。希望这可以帮助有类似错误的人。