如何用简单测试程序触发CPU存储缓冲区停顿?及perf验证方案
验证AMD EPYC 7443存储缓冲区停顿事件的方法
一、先验证内核对CPU PMU的支持
- 确认CPU识别:
确保输出包含cat /proc/cpuinfo | grep 'model name'AMD EPYC 7443,说明内核已正确识别CPU。 - 检查PMU相关内核模块与设备:
若输出有lsmod | grep amd_uncore ls /sys/bus/event_source/devices/ | grep amd_amd_uncore、amd_ibs等设备,说明内核对AMD特定PMU有基础支持。5.x内核(尤其是5.10及以上)对Zen3架构的PMU支持较完善,4.x内核可能需要补丁才能支持全部Zen3事件。 - 查看内核日志的PMU初始化信息:
若日志中无dmesg | grep -i pmuunsupported PMU类错误,说明基础PMU功能正常。
二、编写程序触发存储缓冲区停顿
存储缓冲区溢出/缺失通常由密集的写操作+写后立即读(跨缓存行)触发,以下是一个简单的C程序:
#include <stdio.h> #include <stdlib.h> #include <string.h> #define MEM_SIZE (64 * 1024 * 1024) // 64MB,超过EPYC 7443的L3缓存(32MB/核心组),避免缓存命中 int main() { char *mem = malloc(MEM_SIZE); if (!mem) { perror("malloc failed"); return 1; } memset(mem, 0, MEM_SIZE); // 循环执行跨缓存行的写+读,持续占用存储缓冲区 while (1) { for (int i = 0; i < MEM_SIZE; i += 64) { mem[i] = 0xFF; // 写一个缓存行 volatile char dummy = mem[(i + 2048) % MEM_SIZE]; // 读另一个不相关的缓存行 } } free(mem); return 0; }
编译运行:
gcc -O2 -o store_stress store_stress.c ./store_stress
这个程序会持续制造存储压力,触发存储缓冲区相关的停顿事件。
三、用Perf验证事件有效性
- 首先确保Perf有权限:
echo 0 > /proc/sys/kernel/perf_event_paranoid - 使用你的自定义PMU事件进行采样:
假设你找到的事件寄存器值为rXXXXXX(比如AMD Zen3中存储缓冲区溢出的raw事件格式为r<event_code>,<umask>),执行:
运行几秒后按perf record -e rXXXXXX -g ./store_stressCtrl+C停止采样,然后用perf report查看事件计数。如果有非零的事件记录,说明你的事件寄存器正确且内核支持。 - 用Perf统计事件次数:
运行几秒后终止,若输出的事件计数有明显数值(而非0或报错),则验证成功。perf stat -e rXXXXXX ./store_stress
常见问题处理
- 若Perf报错
event not supported,说明内核不支持该PMU事件,建议升级内核到5.10+版本,或查找对应4.x/5.x内核的Zen3 PMU补丁。 - 若事件计数为0,可能是事件寄存器值错误,需核对AMD官方的Zen3 PMU事件手册。
内容的提问来源于stack exchange,提问作者Brave
相关产品推荐
相关产品推荐

