通过 how2heap 复习堆利用 (一)
字数 2194 2025-08-20 18:17:48

堆利用技术详解:从基础到高级技巧

0x01 First Fit 算法利用

基本原理

glibc 使用 first-fit 算法选择空闲 chunk。如果一个 chunk 空闲且足够大,malloc 会选择这个 chunk。这在 use-after-free 场景中可以被利用。

关键步骤

  1. 分配两个缓冲区:512字节和256字节
  2. 在第一个 chunk 中写入数据 "this is A!"
  3. 释放第一个 chunk
  4. 分配500字节的新 chunk (小于512)
  5. 在新 chunk 中写入 "this is C!"
  6. 原始指针仍然指向相同内存,但内容已被修改

调试观察

  • 释放后 chunk 进入 unsorted bin
  • 再次分配时会从 unsorted bin 中取出相同 chunk
  • 原始指针仍然有效,导致 use-after-free

利用要点

  • UAF 漏洞成因:指针释放后未置零
  • 可通过重用已释放内存修改原始数据

0x02 Fastbin Double Free

基本原理

通过滥用 fastbin freelist,使 malloc 返回已分配的堆指针。

关键步骤

  1. 分配三个 8 字节缓冲区
  2. 释放第一个 (a)
  3. 释放第二个 (b)
  4. 再次释放第一个 (a) - 形成循环链表
  5. 三次 malloc 将两次返回相同地址

绕过检查技巧

  • 不能连续两次 free 同一个 chunk
  • 在两次 free 之间插入对其他 chunk 的 free
  • 形成 a -> b -> a 的循环链表

利用效果

  • 可以在同一地址 malloc 两次
  • 获得两个指向同一内存区域的指针

0x03 Fastbin Dup Into Stack

基本原理

通过伪造 fastbin chunk 使 malloc 返回到可控位置(如栈)

关键步骤

  1. 创建三个 8 字节缓冲区
  2. 通过 double free 形成循环链表
  3. 分配并修改链表中的 fd 指针
  4. 伪造栈上的 chunk 元数据
  5. 再次分配获取栈地址指针

伪造 chunk 要求

  • size 域:0x20-0x80 字节(64位)
  • nextsize 检查:>16 且 <128KB
  • 地址必须16字节对齐

利用效果

  • 将栈地址放入 fastbin
  • 后续分配可获取栈空间控制权
  • 可用于覆盖返回地址等关键数据

0x04 Fastbin Dup Consolidate

基本原理

利用 malloc_consolidate 机制绕过 fastbin double free 检查

关键步骤

  1. 分配两个 fastbin (0x40字节)
  2. 释放第一个 (p1)
  3. 分配 large bin (0x400)触发 consolidate
  4. p1 被移到 unsorted bin
  5. 再次 free(p1) - 现在同时在 fastbin 和 unsorted bin
  6. 两次 malloc 获取同一指针两次

核心机制

  • 分配 large chunk 时触发 malloc_consolidate
  • fastbin 中的 chunk 被合并并移到 unsorted bin
  • 绕过 fastbin 的 double free 检查

0x05 Unsafe Unlink

基本原理

利用 free 操作对损坏 chunk 的处理实现任意写

关键步骤

  1. 创建两个 chunk (chunk0 和 chunk1)
  2. 在 chunk0 中伪造 fake chunk
  3. 设置伪造的 fd 和 bk 绕过检查
  4. 修改 chunk1 的 prev_size 和 size 标志位
  5. free(chunk1) 触发 unlink
  6. 全局指针被修改指向自身附近
  7. 通过指针操作实现任意地址写

伪造 chunk 技巧

  • fd = &P - 24
  • bk = &P - 16
  • 满足 P->fd->bk == P && P->bk->fd == P 检查

利用效果

  • 获得一个指向自身附近的指针
  • 通过修改该指针实现任意内存写
  • 可劫持 GOT 表等关键位置

0x06 House of Spirit

基本原理

释放伪造的 fastbin chunk 使 malloc 返回近乎任意的指针

关键步骤

  1. 在栈上伪造 fastbin chunk
  2. 设置合理的 size (0x40)和 nextsize (0x1234)
  3. 修改指针指向伪造的 chunk
  4. 释放该指针
  5. 下次 malloc 返回伪造 chunk 地址

伪造要求

  • size: 32-128字节(64位)
  • nextsize: >16 且 <128KB
  • IS_MMAPPED 和 NON_MAIN_ARENA 位必须为0
  • 地址16字节对齐

典型应用场景

  • 配合栈溢出使用
  • 当栈溢出无法直接覆盖返回地址时
  • 通过控制即将被 free 的堆指针实现利用

总结

这些技术展示了 glibc 堆分配器的各种利用方法,从基本的 first-fit 特性利用到复杂的伪造元数据攻击。关键点包括:

  1. 理解不同 bin 的行为特性(fastbin, unsorted bin, small bin, large bin)
  2. 掌握 chunk 元数据的结构和检查机制
  3. 学会构造特定场景绕过安全检查
  4. 将内存破坏转化为实际的读写原语

在实际漏洞利用中,这些技术往往需要组合使用,并配合信息泄露等技巧才能实现完整的攻击链。

堆利用技术详解:从基础到高级技巧 0x01 First Fit 算法利用 基本原理 glibc 使用 first-fit 算法选择空闲 chunk。如果一个 chunk 空闲且足够大,malloc 会选择这个 chunk。这在 use-after-free 场景中可以被利用。 关键步骤 分配两个缓冲区:512字节和256字节 在第一个 chunk 中写入数据 "this is A !" 释放第一个 chunk 分配500字节的新 chunk (小于512) 在新 chunk 中写入 "this is C !" 原始指针仍然指向相同内存,但内容已被修改 调试观察 释放后 chunk 进入 unsorted bin 再次分配时会从 unsorted bin 中取出相同 chunk 原始指针仍然有效,导致 use-after-free 利用要点 UAF 漏洞成因:指针释放后未置零 可通过重用已释放内存修改原始数据 0x02 Fastbin Double Free 基本原理 通过滥用 fastbin freelist,使 malloc 返回已分配的堆指针。 关键步骤 分配三个 8 字节缓冲区 释放第一个 (a) 释放第二个 (b) 再次释放第一个 (a) - 形成循环链表 三次 malloc 将两次返回相同地址 绕过检查技巧 不能连续两次 free 同一个 chunk 在两次 free 之间插入对其他 chunk 的 free 形成 a -> b -> a 的循环链表 利用效果 可以在同一地址 malloc 两次 获得两个指向同一内存区域的指针 0x03 Fastbin Dup Into Stack 基本原理 通过伪造 fastbin chunk 使 malloc 返回到可控位置(如栈) 关键步骤 创建三个 8 字节缓冲区 通过 double free 形成循环链表 分配并修改链表中的 fd 指针 伪造栈上的 chunk 元数据 再次分配获取栈地址指针 伪造 chunk 要求 size 域:0x20-0x80 字节(64位) nextsize 检查:>16 且 <128KB 地址必须16字节对齐 利用效果 将栈地址放入 fastbin 后续分配可获取栈空间控制权 可用于覆盖返回地址等关键数据 0x04 Fastbin Dup Consolidate 基本原理 利用 malloc_ consolidate 机制绕过 fastbin double free 检查 关键步骤 分配两个 fastbin (0x40字节) 释放第一个 (p1) 分配 large bin (0x400)触发 consolidate p1 被移到 unsorted bin 再次 free(p1) - 现在同时在 fastbin 和 unsorted bin 两次 malloc 获取同一指针两次 核心机制 分配 large chunk 时触发 malloc_ consolidate fastbin 中的 chunk 被合并并移到 unsorted bin 绕过 fastbin 的 double free 检查 0x05 Unsafe Unlink 基本原理 利用 free 操作对损坏 chunk 的处理实现任意写 关键步骤 创建两个 chunk (chunk0 和 chunk1) 在 chunk0 中伪造 fake chunk 设置伪造的 fd 和 bk 绕过检查 修改 chunk1 的 prev_ size 和 size 标志位 free(chunk1) 触发 unlink 全局指针被修改指向自身附近 通过指针操作实现任意地址写 伪造 chunk 技巧 fd = &P - 24 bk = &P - 16 满足 P->fd->bk == P && P->bk->fd == P 检查 利用效果 获得一个指向自身附近的指针 通过修改该指针实现任意内存写 可劫持 GOT 表等关键位置 0x06 House of Spirit 基本原理 释放伪造的 fastbin chunk 使 malloc 返回近乎任意的指针 关键步骤 在栈上伪造 fastbin chunk 设置合理的 size (0x40)和 nextsize (0x1234) 修改指针指向伪造的 chunk 释放该指针 下次 malloc 返回伪造 chunk 地址 伪造要求 size: 32-128字节(64位) nextsize: >16 且 <128KB IS_ MMAPPED 和 NON_ MAIN_ ARENA 位必须为0 地址16字节对齐 典型应用场景 配合栈溢出使用 当栈溢出无法直接覆盖返回地址时 通过控制即将被 free 的堆指针实现利用 总结 这些技术展示了 glibc 堆分配器的各种利用方法,从基本的 first-fit 特性利用到复杂的伪造元数据攻击。关键点包括: 理解不同 bin 的行为特性(fastbin, unsorted bin, small bin, large bin) 掌握 chunk 元数据的结构和检查机制 学会构造特定场景绕过安全检查 将内存破坏转化为实际的读写原语 在实际漏洞利用中,这些技术往往需要组合使用,并配合信息泄露等技巧才能实现完整的攻击链。