CVE-2023-53614CVE-2023-53614是Linux内核内存管理子系统(mm/ksm,Kernel Samepage Merging)中的一个竞争条件漏洞。该漏洞存在于KSM模块处理VMA(虚拟内存区域)迭代的过程中,与mm_struct结构体的销毁之间存在时序竞争问题。具体而言,exit_mmap()函数在持有mmap_lock写锁的情况下会销毁VMA和maple tree数据结构。然而,KSM代码在以读模式获取mmap_lock后,未能及时检查mm_struct是否已经被标记为退出状态(即调用ksm_test_exit()),便直接通过for_each_vma()迭代器解引用已被销毁的maple tree。由于maple tree在销毁后,用于通知lockdep检查外部锁的标志位已被清除,此时继续执行for_each_vma()迭代器将解引用一个不再具有外部锁标志的maple tree,从而触发lockdep警告并可能导致内核崩溃。该漏洞需要本地低权限用户触发,攻击者可通过精心设计的时序操作利用此竞争条件影响系统可用性。CVSS评分为4.7,属于中危级别,主要影响系统的可用性(Availability: High),对机密性和完整性无影响。
该漏洞的技术核心在于Linux内核KSM(Kernel Samepage Merging)模块中mmap_lock与mm_struct生命周期管理之间的竞争条件。
**漏洞原理:**
在Linux内核中,exit_mmap()函数负责在进程退出时清理其内存映射。当该函数被调用时,它会在持有mmap_lock写锁的状态下销毁进程的所有VMA和底层的maple tree数据结构。
KSM模块中的相关代码路径会执行以下操作序列:
1. 以读模式获取mmap_lock
2. 调用for_each_vma()迭代器遍历VMA
3. 在迭代过程中解引用maple tree
问题在于步骤1和步骤2之间存在一个时间窗口:另一个CPU核心上的exit_mmap()可能在KSM代码获取读锁后但尚未开始迭代前销毁maple tree。修复方案要求在获取mmap_lock读锁之后、for_each_vma()迭代器解引用maple tree之前,调用ksm_test_exit()检查mm_struct是否已被标记为退出状态。
**利用方式:**
攻击者作为本地低权限用户,可通过以下方式触发该漏洞:
1. 启动一个持续运行KSM相关操作的进程(如启用KSM的内存密集型应用)
2. 同时频繁触发另一个进程的退出操作(exit_mmap)
3. 利用时序竞争使KSM的VMA迭代与mm_struct销毁重叠
4. 当KSM代码在maple tree已被销毁后尝试解引用时,触发内核panic或lockdep警告
由于maple tree的外部锁标志已被清除,继续迭代将触发lockdep子系统检测到不一致状态,可能导致系统不稳定或拒绝服务。