Skip to content
KitploitKITPLOIT
工具漏洞利用博客
Log in
提交
工具漏洞利用博客
提交

黑客、渗透测试和网络安全工具,武装您的安全武器库!

Kitploit 是一个黑客、网络安全和渗透测试工具的目录。发现最新的项目更新,查找漏洞、分析系统、自动化测试并加强你的安全。

··订阅源·联系·隐私·© 2026 Kitploit

工具目录

分类

查看所有分类
Loading categories
CVE-2023-32233-reproduction — CVE-2023-32233 的复现与根因分析:Linux 内核 nf_tables 释放后使用漏洞,可实现本地权限提升,附 PoC 与利用说明。 | Kitploit
工具/GitHubGitHub/adeadukagi/cve-2023-32233-reproduction
防御工具权限提升内存取证漏洞分析漏洞利用论文与研究学习与教育二进制利用

最受欢迎

查看全部 →

发现我们社区最常用的工具。

探索所有工具

浏览我们的工具集合

查看所有工具 →
分享
GitHub
adeadukagi/cve-2023-32233-reproduction

CVE-2023-32233-reproduction

CVE-2023-32233 的复现与根因分析:Linux 内核 nf_tables 释放后使用漏洞,可实现本地权限提升,附 PoC 与利用说明。

查看仓库
11个月前尚未审核

CVE-2023-32233 — nf_tables 释放后使用:复现与根因分析

本仓库内容: 我对 CVE-2023-32233 的动手复现与研究。该漏洞是 Linux 内核 Netfilter nf_tables 子系统中的一个释放后使用漏洞,可导致本地权限提升,由 Patryk Sondej 和 Piotr Krysiuk 于 2023 年 5 月公开披露。

致谢: PoC(exploit.c)及原始分析文章由 @Liuk3r 编写。本仓库中我的工作是在自己的实验环境(Ubuntu 23.04,内核 6.2.0-20)中复现该漏洞利用,并在下文记录根因与利用链。所有测试均在专用实验机器上完成。


我的分析笔记

根因

nf_tables 将配置更新作为原子批次处理。对每个操作相对于同一批次中先前操作所导致的状态变化的校验不充分。具体而言:

  1. 初始状态为一个 nft_rule,其中包含针对某个持有若干元素的匿名 nft_set 的 lookup 表达式。
  2. 发送包含两个操作的批次:
    • NFT_MSG_DELRULE — 删除该规则,这会隐式删除 lookup 表达式以及匿名 nft_set;
    • NFT_MSG_DELSETELEM — 删除已被删除的匿名集合中的一个元素。
  3. 该批次被接受。nf_tables_commit_release() 将资源排入 nf_tables_destroy_list,稍后由 nf_tables_trans_destroy_work() 处理:
    • 首先 nft_commit_release() → nf_tables_rule_destroy() → nft_lookup_destroy() → nft_set_destroy() → kvfree() 释放 nft_set;

    • 然后,针对 NFT_MSG_DELSETELEM,nf_tables_set_elem_destroy() 调用 nft_set_elem_ext(),该函数解引用已释放的 nft_set:

      root@kitploit:~
      static inline struct nft_set_ext *nft_set_elem_ext(const struct nft_set *set,
                                                         void *elem)
      {
          return elem + set->ops->elemsize;
      }
      

如果 set->ops->elemsize 被破坏,攻击者选定的内存位置就会被解释为一个 nft_set_ext —— 这是后续一切利用所依赖的原语。

利用链(复现结果)

  1. 与运行在后台工作线程上的 nf_tables_trans_destroy_work() 竞争:插入一个大型集合销毁操作作为可控延迟,让其他 CPU 保持忙碌,并在同一 CPU 上用不同类型(不同 elemsize)的 nft_set 重新分配已释放的 nft_set 内存块 → 类型混淆。
  2. 构造被破坏的 nft_set_ext 头部,使用越界偏移,使 nf_tables_set_elem_destroy() 将相邻内存块当作待销毁的 nft_expr 列表来遍历。
  3. 喷射带有可控 NFTA_LOG_PREFIX 的 nft_log 表达式;nft_log_destroy() 释放 priv->prefix,从而在 kmalloc-{8..192} 中提供重叠分配原语(起初受 NULL 字节限制)。
  4. 用 nft_object->udata 回收,以解除悬空读取上的 NULL 字节限制。
  5. nft_dynset 元素喷射,针对两种有状态表达式类型:

值得注意的是,所选择的各种原语都避开了 CFI 会拦截的操作 —— 任何步骤都不需要劫持间接调用。

防御要点

  • 修复:上游已改为根据完整事务状态校验批次操作;打过补丁的内核会拒绝针对匿名集合的 DELRULE+DELSETELEM 序列。参见 NVD 条目中引用的修复提交。
  • 提高门槛的缓解措施:slab freelist 加固(SLAB_FREELIST_HARDENED)、INIT_ON_FREE 以及按 CPU 的 slab 重用限制都会攻击步骤 1;CFI(在存在的情况下)会限制步骤 3 及之后。
  • 检测思路:对包含针对匿名集合的 DELRULE+DELSETELEM 的 nf_tables 批次 netlink 消息设置审计规则;在栈中出现 nft_set_elem_ext / nf_tables_trans_destroy_work 时进行崩溃分析。
  • 减少攻击面:nftables 需要 CAP_NET_ADMIN,但非特权用户命名空间会授予该权限 —— 这就是 kernel.unprivileged_userns_clone=0 成为一个有意义加固开关的原因。

复现指南

在 Ubuntu 23.04(Lunar Lobster)、内核 6.2.0-20-generic 下测试通过。

安装构建依赖

root@kitploit:~
sudo apt install gcc libmnl-dev libnftnl-dev

构建二进制文件

root@kitploit:~
gcc -Wall -o exploit exploit.c -lmnl -lnftnl

Profile

内置 profile 针对 Ubuntu 23.04 二进制内核(linux-image-6.2.0-20-generic 6.2.0-20.20)。要测试其他内核,请将符号提取到 profile 文件中:

root@kitploit:~
modprobe nf_tables
egrep ' (nft_counter_ops|nft_counter_destroy|free_percpu|modprobe_path)(\s|$)' /proc/kallsyms > profile

nft_counter_destroy() 的机器码布局随编译器和选项而变化;完整参数参考(nft_counter_destroy_call_offset/mask/check)和竞争调优参数(race_lead_sleep 等)见 ORIGIN.md。在空闲的裸机 Intel 系统上报告的成功率 ≥80%;某些微架构(例如 Alder Lake)需要额外调优。

安全警告

成功运行后,PoC 会使内核处于内存被破坏的不稳定状态。仅在专用的、可丢弃的系统或 VM 快照上测试 —— 绝不要在任何存有你关心的数据的系统上测试。


文件

  • exploit.c — PoC 源码(由 @Liuk3r 编写)
  • ORIGIN.md — 原始漏洞与利用分析文章(由 Liuk3r 编写)
  • README.md — 本文件:复现 + 我的分析笔记

参考资料

  • NVD — CVE-2023-32233
  • Liuk3r/CVE-2023-32233 — 原始 PoC 与分析文章
  • Theori — CVE-2023-32233: Linux Kernel Privilege Escalation Analysis

研究在隔离的实验环境中出于防御/教育目的进行。

下载工具
  • nft_counter — 泄露 nft_counter_ops → nf_tables.ko 基址(绕过该模块的 KASLR);
  • nft_quota — consumed 指针提供任意读(NFT_MSG_GETSETELEM → nft_quota_do_dump() → NFTA_QUOTA_CONSUMED)和任意写(nft_overquota() 在回环流量上将 skb->len 加到 *priv->consumed)。
  • 覆写 modprobe_path("/sbin/modprobe" → "//tmp/modprobe")→ 以攻击者控制的内容执行 root 进程。