M4苹果硅设备kpc.config系统调用返回-1的问题求助
M4 MacBook Pro上Apple Silicon PMU计数器配置失败(sysctlbyname "kpc.config"返回-1)
问题概述
运行macOS Sequoia 15.2的M4 MacBook Pro上,使用读取Apple Silicon PMU计数器的代码时出现报错,核心错误为Failed set kpc config: -1。经调试发现,错误源于kpc_set_config函数中调用sysctlbyname("kpc.config")返回-1;而同系统版本的M1/M2 MacBook Pro上代码运行正常。
报错输出:
loaded db: as4-1 (Apple silicon) number of fixed counters: 2 number of configurable counters: 8 Failed set kpc config: -1.
kpc_set_config的LLVM反汇编代码:
kperf`kpc_set_config: 0x1d3564cd4 <+0>: pacibsp 0x1d3564cd8 <+4>: sub sp, sp, #0x60 0x1d3564cdc <+8>: stp x24, x23, [sp, #0x20] 0x1d3564ce0 <+12>: stp x22, x21, [sp, #0x30] 0x1d3564ce4 <+16>: stp x20, x19, [sp, #0x40] 0x1d3564ce8 <+20>: stp x29, x30, [sp, #0x50] 0x1d3564cec <+24>: add x29, sp, #0x50 0x1d3564cf0 <+28>: mov x19, x1 0x1d3564cf4 <+32>: mov x20, x0 0x1d3564cf8 <+36>: str wzr, [sp, #0xc] 0x1d3564cfc <+40>: str w0, [sp, #0x1c] 0x1d3564d00 <+44>: mov w8, #0x4 ; =4 0x1d3564d04 <+48>: str x8, [sp, #0x10] 0x1d3564d08 <+52>: adrp x0, 4 0x1d3564d0c <+56>: add x0, x0, #0x9af ; "kpc.config_count" 0x1d3564d10 <+60>: add x1, sp, #0xc 0x1d3564d14 <+64>: add x2, sp, #0x10 0x1d3564d18 <+68>: add x3, sp, #0x1c 0x1d3564d1c <+72>: mov w4, #0x4 ; =4 0x1d3564d20 <+76>: bl 0x1d35687a0 ; symbol stub for: sysctlbyname 0x1d3564d24 <+80>: mov w21, #-0x1 ; =-1 0x1d3564d28 <+84>: tbnz w0, #0x1f, 0x1d3564d98 ; <+196> 0x1d3564d2c <+88>: ldr w8, [sp, #0xc] 0x1d3564d30 <+92>: cbz w8, 0x1d3564d98 ; <+196> 0x1d3564d34 <+96>: lsl w23, w8, #3 0x1d3564d38 <+100>: add w21, w23, #0x8 0x1d3564d3c <+104>: mov x0, x21 0x1d3564d40 <+108>: mov w1, #0x3c4a ; =15434 0x1d3564d44 <+112>: movk w1, #0x1d54, lsl #16 0x1d3564d48 <+116>: bl 0x1d35686e0 ; symbol stub for: malloc_type_malloc 0x1d3564d4c <+120>: cbz x0, 0x1d3564d94 ; <+192> 0x1d3564d50 <+124>: mov x22, x0 0x1d3564d54 <+128>: mov w8, w20 0x1d3564d58 <+132>: str x8, [x0], #0x8 0x1d3564d5c <+136>: mov x1, x19 0x1d3564d60 <+140>: mov x2, x23 0x1d3564d64 <+144>: bl 0x1d35686f0 ; symbol stub for: memcpy 0x1d3564d68 <+148>: adrp x0, 4 0x1d3564d6c <+152>: add x0, x0, #0x9a4 ; "kpc.config" 0x1d3564d70 <+156>: mov x1, #0x0 ; =0 0x1d3564d74 <+160>: mov x2, #0x0 ; =0 0x1d3564d78 <+164>: mov x3, x22 0x1d3564d7c <+168>: mov x4, x21 0x1d3564d80 <+172>: bl 0x1d35687a0 ; symbol stub for: sysctlbyname 0x1d3564d84 <+176>: mov x21, x0 0x1d3564d88 <+180>: mov x0, x22 0x1d3564d8c <+184>: bl 0x1d35686a0 ; symbol stub for: free 0x1d3564d90 <+188>: b 0x1d3564d98 ; <+196> 0x1d3564d94 <+192>: mov w21, #-0x1 ; =-1 0x1d3564d98 <+196>: mov x0, x21 0x1d3564d9c <+200>: ldp x29, x30, [sp, #0x50] 0x1d3564da0 <+204>: ldp x20, x19, [sp, #0x40] 0x1d3564da4 <+208>: ldp x22, x21, [sp, #0x30] 0x1d3564da8 <+212>: ldp x24, x23, [sp, #0x20] 0x1d3564dac <+216>: add sp, sp, #0x60 0x1d3564db0 <+220>: retab
排查方向与解决方案
1. 适配M4的PMU硬件架构变更
- M4的PMU计数器可能在数量、事件编码或配置结构体上与M1/M2存在差异,原代码中的
as4-1配置数据库可能不再适配。需更新对应M4的PMU事件定义,或调整配置结构体的字段与大小。 - 执行
sysctl kpc命令,对比M4与M1/M2的输出,重点查看kpc.config_count、kpc.counter_count等参数的差异,确认配置逻辑是否需要调整。
2. 验证权限与系统限制
- 确保代码以root权限运行,M4可能强化了PMU配置的权限校验,普通用户权限无法完成
kpc.config的系统调用。 - 检查系统完整性保护(SIP)状态,部分PMU操作需要SIP处于禁用或部分禁用状态,但此操作会降低系统安全性,需谨慎执行。
3. 定位具体错误原因
- 修改代码,在
sysctlbyname("kpc.config")调用失败后,通过strerror(errno)输出具体错误信息,比如:
错误码(如if (sysctlbyname("kpc.config", ...) == -1) { fprintf(stderr, "sysctlbyname error: %s\n", strerror(errno)); return -1; }EINVAL表示参数无效、EPERM表示权限不足)能精准指向问题根源。
4. 适配kperf框架的版本变化
- macOS Sequoia 15.2在M4上的kperf框架内部实现可能有更新,原代码调用
kpc_set_config的逻辑不再兼容。可参考Apple开源的kperf工具或LLVM中的PMU相关代码,调整配置参数的构造方式。 - 从反汇编代码看,
kpc_set_config先通过kpc.config_count确定配置结构体大小,再构造数据传入kpc.config,需确认M4上该结构体的字段是否有新增或调整。
5. 检查系统版本兼容性
- 确认M4的macOS Sequoia 15.2为最新补丁版本,Apple可能已发布修复PMU兼容性的更新;或尝试升级/降级系统版本,验证是否为特定版本的兼容性问题。
内容的提问来源于stack exchange,提问作者Alex Fan
相关产品推荐
相关产品推荐

