mcpField
C
ctf-pwn

ctf-pwn

github.com/ljagiello安全3.6k9.5k 次安装2 天前更新
代码仓库

关于 ctf-pwn

面向 CTF pwn 题参赛者的二进制利用速查技能,将简明技巧概述与 ROP、堆、内核等利用路径的详细笔记结合起来。

主要功能

  1. 01二进制初查与缓解措施检查
  2. 02ROP 与 Shellcode 技术
  3. 03堆与格式字符串利用
  4. 04内核及沙箱利用笔记
  5. 05可选 MCP 调试指引

适用场景

  1. 01根据保护机制评估利用路径
  2. 02为题目构造 ROP 链
  3. 03调查堆或格式字符串漏洞
  4. 04调试 Windows 崩溃转储或实时目标

MCP 相关

文档介绍了用于崩溃转储、实时目标和内核调试的可选 WinDbg MCP,以及用于反编译易受攻击函数的 IDA Pro MCP 和 Ghidra MCP。

安装

复制下面的命令,在终端中运行。

$npx skills add https://github.com/ljagiello/ctf-skills --skill ctf-pwn

安装后在 Claude Code 中输入/ctf-pwn确认已加载。

包含的文件

除 SKILL.md 外,安装时一起下载的参考资料和脚本。

advanced-exploits-2.md
advanced-exploits-3.md
advanced-exploits-4.md
advanced-exploits-5.md
advanced-exploits.md
advanced.md
attack-playbook.md
field-notes.md
format-string.md
heap-fsop.md
heap-techniques-2.md
heap-techniques.md
kernel-bypass.md
kernel-techniques.md
kernel.md
overflow-basics.md
pwnable-tw/
3x17.md
alive_note.md
applestore.md
babyallocator.md
babystack.md
bash_revenge.md
bash.md
bookwriter.md
bounty_program_a.md
bounty_program_b.md
break_out.md
calc.md
caov.md
criticalheap_pp.md

详细介绍

CTF 二进制漏洞利用(Pwn)

CTF 二进制漏洞利用(pwn)挑战的速查参考。这里每种技术都用一句话说明;完整详情请参阅配套文件。

前置条件

Python 软件包(所有平台):

pip install "pwntools==4.15.0" "ROPgadget==7.7" "ropper==1.13.13"
# or via script: bash scripts/install_ctf_tools.sh python

uv 替代方案:

uv venv && uv pip install "pwntools==4.15.0" "ROPgadget==7.7" "ropper==1.13.13"

Linux(apt):

apt install gdb binutils strace ltrace qemu-system-x86

可选的跨架构支持(ARM/MIPS — Debian/Ubuntu):

apt install qemu-user qemu-user-static gdb-multiarch binutils-multiarch libc6-armhf-cross libc6-arm64-cross libc6-mips-cross

macOS(Homebrew):

brew install gdb binutils qemu

Ruby gem(所有平台):

gem install one_gadget seccomp-tools

手动安装:

  • pwndbg — Linux:GitHub,macOS:brew install pwndbg/tap/pwndbg-gdb
  • checksec — 包含在 pwntools 中(checksec --file=binary)

MCP 服务(可选): WinDbg MCP(svnscha/mcp-windbg),用于分析 Windows 崩溃转储、实时断点驱动的漏洞利用,以及内核/驱动程序调试;IDA Pro MCP / Ghidra MCP 可用于反编译存在漏洞的函数,详见 tools-mcp.md。

其他资源

  • overflow-basics.md - 栈/全局缓冲区溢出、ret2win、canary 绕过、在 fork 服务器上逐字节暴力破解 canary、结构体指针覆盖、有符号整数绕过、隐藏 gadget、基于步长的 OOB 读取泄露、通过未检查的 memcpy 长度造成解析器栈溢出并恢复被调用者保存的寄存器
  • rop-and-shellcode.md - 核心 ROP 链(ret2libc、syscall ROP、rdx 控制、shell 交互)、ret2csu、坏字符 XOR 绕过、特殊 x86 gadget(BEXTR/XLAT/STOSB/PEXT)、通过 xchg rax,esp 进行栈迁移、使用 sprintf() gadget 链绕过坏字符、将 canary XOR 尾声用作 RDX 清零 gadget、通过 read() 返回值将 stub_execveat syscall 作为 execve 替代方案
  • rop-advanced.md - 高级 ROP 技术:通过 leave;ret 将栈二次迁移到 BSS、带 UTF-8 限制的 SROP(Sigreturn-Oriented Programming)、seccomp 绕过、通过 RETF 架构切换(x64→x32)绕过 seccomp、输入反转型 shellcode、.fini_array 劫持、ret2vdso、pwntools 模板、通过 x32 ABI syscall 别名绕过 seccomp、基于时间的盲 shellcode 数据外传
  • format-string.md - 格式字符串利用(泄露、GOT 覆盖、盲 pwn、过滤器绕过、canary 泄露、__free_hook、.rela.plt 修补、覆盖保存的 EBP 以迁移到 .bss、覆盖 argv[0] 以泄露栈破坏信息、利用 .fini_array 循环进行多阶段利用、通过连续的 %p 绕过 __printf_chk、单次调用泄露 + GOT 覆盖、通过输入转换利用 ROT13 编码的格式字符串)
  • advanced.md - Seccomp 高级技术、UAF、JIT、特殊 GOT、通过进制转换造成堆重叠、树形数据结构栈分配不足、ret2dlresolve、内核利用(基础)
  • heap-techniques.md - House of Apple 2(+ setcontext SUID 变体)、House of Einherjar、House of Orange/Spirit/Lore/Force、堆整理、自定义分配器(nginx、talloc)、经典 unlink、musl libc 堆(meta 指针 + atexit 劫持)、tcache stashing unlink 攻击、unsafe unlink + top chunk 合并
  • heap-techniques-2.md - CTF writeup 中的堆利用变体:UAF vtable 指针编码 shell 参数、未初始化 chunk 残留指针泄露、tcache strcpy 空字节溢出 + 向后合并、相邻结构体 fn 指针溢出以泄露 libc + 覆盖 GOT、隐藏菜单 tcache poisoning、tcache double-free + 伪造 _IO_FILE vtable 劫持 stdout、tcache-to-fastbin 提升跨 bin 攻击、6 位索引 OOB + written_bytes 累加器、翻转 IS_MMAPED 位以泄露 calloc'd chunk 的 unsorted bin、通过仅覆盖 LSB 的堆指针实现受文件名正则表达式约束的 fastbin、自定义分配器 unsafe unlink 到 GOT
  • heap-fsop.md - FILE 结构(_IO_FILE)利用:fastbin stdout vtable 两阶段劫持以应对 PIE + Full RELRO、通过 _IO_buf_base 空字节劫持 stdin、绕过 glibc 2.24+ 的 _IO_FILE vtable 验证、针对 stdin IO_buf_end 的 unsorted-bin 攻击、通过 mp 结构损坏 unsorted bin、将 realloc(ptr, 0) 用作 free() UAF、单字节引用计数器回绕 UAF
  • advanced-exploits.md - 高级利用技术(第 1 部分):VM 有符号比较、BF JIT shellcode、类型混淆、索引 off-by-one 损坏、DNS 溢出、ASAN shadow memory、带编码限制的格式字符串、自定义 canary 保留、有符号整数绕过、感知 canary 的部分溢出、CSV 注入、MD5 原像 gadget、VM GC UAF slab 重用、路径遍历清理器绕过、通过 openat/mmap/write 绕过 FSOP + seccomp
  • advanced-exploits-2.md - 高级利用技术(第 2 部分):通过自修改绕过字节码验证器、通过 SQE 注入实现 io_uring UAF、整数截断 int32->int16、GC 空引用级联损坏、通过多次 fgets 覆盖 stdout FILE 实现无泄露 libc 利用、有符号/无符号 char 下溢堆溢出、XOR 密钥流暴力破解写入原语、tcache 指针解密堆泄露、通过伪造 chunk 大小提升 unsorted bin、FSOP stdout TLS 泄露、通过 __call_tls_dtors 劫持 TLS 析构函数、自定义 shadow stack 指针溢出绕过、有符号 int 溢出导致负数 OOB 堆写入、XSS 到二进制 pwn 桥接
  • advanced-exploits-4.md - 高级利用技术(第 4 部分):Windows SEH 覆盖 + pushad VirtualAlloc ROP、基于 IAT 的相对解析、分离进程 shell 稳定性、SeDebugPrivilege SYSTEM 提权、使用 Thumb shellcode 的 ARM 缓冲区溢出、Forth 解释器 system 字操作利用、用于多轮 tcache poisoning 的 GF(2) 高斯消元、单比特翻转利用原语(mprotect + 迭代代码修补)、通过静物演化 Game of Life shellcode、通过菜单驱动的 strdup/free 顺序实现 UAF、通过将 system() 用作有效调用目标绕过 Windows CFG、神经网络输出作为函数指针索引导致 OOB、通过计数器溢出绕过 shellcode 唯一字节数限制
  • advanced-exploits-3.md - 高级利用技术(第 3 部分):栈变量重叠/进位损坏 OOB、通过 8 位循环计数器实现 1 字节溢出、游戏 AI 算术平均值 OOB 读取、任意读/写 GOT 覆盖以获取 shell、通过 __environ + memcpy 溢出泄露栈地址、通过 uint16 跳转截断逃逸 JIT 沙箱、带多问题 ROP 的 DNS 压缩指针栈溢出、通过操作程序头绕过 ELF 代码签名、游戏关卡格式有符号/无符号坐标不匹配、因缺少 O_CLOEXEC 导致文件描述符继承、元数据解析中符号扩展造成整数下溢、使用只读原语构造 ROP 链、通过持久寄存器和时序侧信道实现 4 字节 shellcode、CRC oracle 作为任意读取原语、UTF-8 大小写转换缓冲区溢出
  • advanced-exploits-5.md - 高级利用技术(第 5 部分):数据解释型利用——Chip-8 模拟器 OOB 内存实现 ret2libc、双精度浮点快速排序重新定位 canary、布隆过滤器 abs(INT_MIN) 负索引 OOB 写入
  • sandbox-escape.md - 自定义 VM 利用、FUSE/CUSE 设备、busybox/受限 shell、shell 技巧、process_vm_readv 沙箱绕过、命名管道文件大小绕过、CPU 模拟器打印 opcode Python eval 注入(交叉引用 ctf-misc/pyjails.md 中的 Python jail 技术)
  • kernel.md - Linux 内核利用基础:环境搭建、QEMU 调试、堆喷射结构(tty_struct、poll_list、user_key_payload、seq_operations)、内核栈溢出、canary 泄露、提权(ret2usr、内核 ROP)、覆盖 modprobe_path、覆盖 core_pattern、kmalloc 大小不匹配堆溢出 + struct file f_op 损坏
  • kernel-techniques.md - 内核利用技术:tty_struct kROP(伪造 vtable + 栈迁移)、通过 ioctl 寄存器控制实现 AAW、userfaultfd 竞态稳定化、SLUB 分配器内部机制(freelist 强化/混淆)、通过内核 panic 泄露、延长 MADV_DONTNEED 竞态窗口(DiceCTF 2026)、跨缓存 CPU 分割攻击(DiceCTF 2026)、PTE 重叠文件写入(DiceCTF 2026)、通过文件打开失败绕过 addr_limit 以读写内核内存
  • kernel-bypass.md - 内核保护绕过:KASLR/FGKASLR 绕过(__ksymtab)、KPTI 绕过(swapgs trampoline、信号处理程序、通过 ROP 修改 modprobe_path/core_pattern)、SMEP/SMAP 绕过、GDB 内核模块调试、initramfs/virtio-9p 工作流、利用模板、利用投递
  • field-notes.md - 详细 pwn 笔记:堆利用速查、补充利用笔记、实用命令
  • attack-playbook.md - Linux 用户态攻击手册:侦察输入/权限边界、根据缓解措施选择泄露方式、原语优先级排序工作流
  • static-signals.md - 与利用相关的静态信号(libc 版本、seccomp 策略、RELRO/PIE/canary/NX 证据),用于评估可利用性
  • pwnable-tw/README.md - 43 篇 pwnable.tw writeup(orw、start、calc、hacknote、babystack、tcache_tear、death_note、dubblesort、applestore、bookwriter 等),包含各挑战的环境、防护措施、根本缺陷和具体利用链
  • tools-mcp.md - pwn 的 MCP 服务集成:WinDbg MCP 会话模型(open_cdb_dump/open_cdb_remote/open_kd_session + session_id)、崩溃转储初步分析、转储内存中的 flag{ 扫描、实时断点/硬件观察点/内存修补利用、使用 !dh -f 检查 Windows 缓解措施(相当于 checksec)、使用 kd 在内核模式下窃取令牌;用于漏洞开发的 IDA/Ghidra MCP(先反编译易受攻击的函数,只有在需要确认确切 gadget 字节时才查看汇编)

何时切换方向

  • 如果你还不了解二进制文件的功能,请先切换到 /ctf-reverse,再尝试利用它。
  • 如果服务实际上是受限 shell、编码谜题或沙箱语言挑战,请切换到 /ctf-misc。
  • 如果利用路径主要依赖 Web 端点、会话漏洞或上传原语,而不是内存损坏,请切换到 /ctf-web。
  • 如果漏洞利用需要先破解密码学原语,请切换到 /ctf-crypto。

快速入门命令

# Binary analysis
checksec --file=binary
file binary
readelf -h binary

# Find gadgets
ROPgadget --binary binary | grep "pop rdi"
ropper -f binary --search "pop rdi"
one_gadget /lib/x86_64-linux-gnu/libc.so.6

# Debug
gdb -q binary -ex 'start' -ex 'checksec'

# Pattern for offset finding
python3 -c "from pwn import *; print(cyclic(200))"
python3 -c "from pwn import *; print(cyclic_find(0x61616168))"

# libc identification
./libc-database/find puts <leaked_addr_last_3_nibbles>

源代码中的危险信号

  • 线程处理/pthread -> 竞态条件
  • usleep()/sleep() -> 时序窗口
  • 多个线程中的全局变量 -> TOCTOU

竞态条件利用

bash -c '{ echo "cmd1"; echo "cmd2"; sleep 1; } | nc host port'

常见漏洞

  • 缓冲区溢出:gets()、scanf("%s")、strcpy()
  • 格式化字符串:printf(user_input)
  • 整数溢出、UAF、竞态条件

防护机制对利用策略的影响

防护机制状态影响
PIE已禁用所有地址(GOT、PLT、函数)都是固定的——可以直接覆盖
RELRO部分GOT 可写——可以进行 GOT 覆盖攻击
RELRO完整GOT 只读——需要使用替代目标(hooks、vtables、返回地址)
NX已启用无法在栈/堆上执行 shellcode——使用 ROP 或 ret2win
Canary存在会检测栈破坏——需要泄露 Canary 或避免栈溢出(使用堆)

快速决策树:

  • 部分 RELRO + 无 PIE -> GOT 覆盖(最简单,使用固定地址)
  • 完整 RELRO -> 以 __free_hook、__malloc_hook(glibc < 2.34)或返回地址为目标
  • 存在栈 Canary -> 优先使用基于堆的攻击,或先泄露 Canary

栈缓冲区溢出

  1. 查找偏移量:cyclic 200,然后运行 cyclic -l <value>
  2. 检查防护机制:checksec --file=binary
  3. 无 PIE + 无 Canary = 直接使用 ROP
  4. 通过格式化字符串泄露 Canary,或进行部分覆盖
  5. 在 fork 服务器上逐字节暴力破解 Canary(最多尝试 7*256 次)

**使用魔法值的 ret2win:**溢出 -> ret(对齐)-> pop rdi; ret -> 魔法值 -> win()。栈对齐:movaps 导致 SIGSEGV = 添加额外的 ret gadget。**偏移量:**缓冲区位于 rbp - N,返回地址位于 rbp + 8,总计 = N + 8。**输入过滤:**断言 payload 不包含 memmem() 禁止的字符串。Gadget:ROPgadget --binary binary | grep "pop rdi",或者使用 pwntools 的 ROP() 查找 CMP 立即数中的隐藏 gadget。完整利用代码请参阅 overflow-basics.md。

解析器栈溢出(未检查的 memcpy)

**模式:**自定义文件解析器(PCAP、图像、归档)分配固定大小的栈缓冲区,但输入记录可能超出其大小。memcpy 在验证长度之前就进行复制,导致保存的寄存器和返回地址溢出。必须恢复被调用者保存的寄存器:将 rbx 设为可读内存(BSS),将循环计数器设为退出值,然后使用 ret gadget + win 函数。请参阅 overflow-basics.md。

结构体指针覆盖(堆菜单挑战)

**模式:**菜单提供结构体的创建/修改/删除操作,结构体包含数据缓冲区和指针。将名称溢出到指针字段中并写入 GOT 地址,然后通过修改操作写入 win 地址。完整利用方法和 GOT 目标选择表请参阅 overflow-basics.md。

有符号整数绕过

模式:scanf("%d") 未检查符号;负数量 * 价格 = 负总额,从而绕过余额检查。请参阅 overflow-basics.md。

感知 Canary 的部分溢出

**模式:**溢出缓冲区和 Canary 之间的 valid 标志。使用 ./ 作为无操作路径填充,以精确控制长度。完整利用链请参阅 overflow-basics.md 和 advanced.md。

全局缓冲区溢出(CSV 注入)

**模式:**相邻的全局变量;通过额外的 CSV 分隔符溢出,修改文件名指针。完整利用方法请参阅 overflow-basics.md 和 advanced.md。

ROP 链构建

通过 puts@PLT(puts@GOT) 泄露 libc,返回到漏洞点,再用第二阶段执行 system("/bin/sh")。完整的两阶段 ret2libc 模式、泄露解析和返回目标选择,请参阅 rop-and-shellcode.md。

DynELF libc 发现: pwntools.DynELF(leak_func, pointer_in_libc) 无需知道 libc 版本,即可远程解析 libc 符号。请参阅 rop-and-shellcode.md。

小缓冲区中的受限 shellcode: 当缓冲区太小时,使用 read() shellcode 存根(< 20 字节)来读取完整的第二阶段 shellcode。请参阅 rop-and-shellcode.md。

原始系统调用 ROP: 当 system()/execve() 崩溃(CET/IBT)时,使用 libc 中的 pop rax; ret + syscall; ret。请参阅 rop-and-shellcode.md。

ret2csu: __libc_csu_init 小工具可控制 rdx、rsi、edi 并调用任意 GOT 函数,无需 libc 小工具即可进行通用的三参数调用。请参阅 rop-and-shellcode.md。

通过 XOR 绕过坏字符: 在写入 .data 前,使用密钥对 payload 数据进行 XOR,再用 ROP 小工具原地还原。这样可以避开空字节、换行符和其他经过过滤的字符。请参阅 rop-and-shellcode.md。

特殊小工具(BEXTR/XLAT/STOSB/PEXT): 当标准 mov 写入小工具不可用时,可串联冷门的 x86 指令,逐字节写入内存。请参阅 rop-and-shellcode.md。

栈 pivot(xchg rax,esp): 当溢出数据不足以容纳完整 ROP 链时,将栈指针切换到攻击者控制的堆或缓冲区。需要先用 pop rax; ret 加载 pivot 地址。请参阅 rop-and-shellcode.md。

控制 rdx: puts() 执行后,rdx 会被改写为 1。可使用 libc 中的 pop rdx; pop rbx; ret,或重新进入二进制文件的 read 初始化流程并进行栈 pivot。请参阅 rop-and-shellcode.md。

将 Canary XOR 尾声用作 rdx 清零小工具: 当不存在 pop rdx; ret 时,可跳转到 Canary 检查尾声 xor rdx, fs:28h —— Canary 完好时,它会将 RDX 清零。请参阅 rop-and-shellcode.md。

用 stub_execveat 替代 execve: 当不存在 pop rax; ret 时,可使用 stub_execveat(系统调用 322/0x142)替代 execve —— 精确发送 0x142 字节,使 read() 的返回值设置 rax。请参阅 rop-and-shellcode.md。

Shell 交互: execve 后,执行 sleep(1),然后执行 sendline(b'cat /flag*')。请参阅 rop-and-shellcode.md。

输入变换中的格式字符串

ROT13 编码的格式字符串: 当输入在传给 printf 前经过 ROT13/Caesar 变换时,先用逆变换预编码格式字符串 payload,使其到达时保持原样。请参阅 format-string.md。

内核利用

通过文件打开失败绕过 addr_limit: 当内核模块设置 addr_limit = KERNEL_DS,却未在错误路径中恢复它时,可触发错误(例如,将目标文件设为目录),以便继续从用户态通过 read()/write() 访问内核内存。请参阅 kernel-techniques.md。

沙箱与模拟器逃逸

CPU 模拟器 eval 注入: 当模拟器的 print 操作码使用 eval('"' + buf + '"') 处理转义序列时,可通过 ADD 操作码在模拟器内存中构造 "+__import__("os").system("cmd")#,以跳出字符串并执行 Python。请参阅 sandbox-escape.md。

高级利用原语

神经网络函数指针越界读取: 如果二进制程序将神经网络输出用作函数指针数组的索引,却未进行边界检查,可以重新训练权重和偏置,使其生成越界索引,从偏置数组中读取目标地址。参见 advanced-exploits-4.md。

通过计数器溢出绕过 Shellcode 唯一字节数限制: 如果 Shellcode 限制为 N 个唯一字节,可以用数据填满栈以破坏 seen[256] 计数器,然后重新执行 main(跳过 memset),这样计数器溢出后,第二次运行时就能使用任意字节。参见 advanced-exploits-4.md。

深入笔记

确认挑战确实以漏洞利用为主后,使用 field-notes.md。

  • 堆和分配器笔记:House of Apple、tcache、unsafe unlink、talloc、UAF、FSOP
  • 高级漏洞利用笔记:seccomp 绕过、ret2vdso、io_uring、整数截断、ASAN、计时预言机
  • 沙箱和混合环境笔记:pyjail 跨界、busybox 逃逸、自定义 VM、Shell 技巧、路径净化器
  • 内核和 Windows 笔记:内核操作手册、SEH、CFG 绕过、权限提升
  • 历史案例笔记:较早但仍可复用的 CTF 漏洞利用模式

评论

支持 Markdown