非栈上格式化字符串漏洞利用
有时候输入的字符串并不是保存在栈上的,这样没法直接在栈上布置地址去控制printf函数的参数,这种情况下的利用相对比较复杂。
程序在调用时会将rbp压入栈中或者将一些指针变量存在栈中等操作,所以栈上会有很多保存着栈上地址的指针,而且容易找到三个指针p1、p2、p3,形成p1指向p2、p2指向p3的情况,这时我们可以先利用p1修改p2最低1字节,可以使p2指向p3指针8字节中的任意1字节并修改它,这样可以逐字节地修改p3成为任意值,简洁的控制了栈上的数据。
在bss段上的情况
在堆上的情况
这种不在栈上的情况,泄露地址还是一样,发生变化的部分是对于任意地址的编写。
利用技巧总结
如何利用
任意地址读还是不变,任意地址写,因为不能写入到栈上,所以需要间接写(找替身~)。
A——>B——>C
而C和D长得很像,像兄弟,于是来个偷天换日
A——>B——>D
例:0xff8b0428——>0xff8b0438——>0x804a070
经过格式化字符串漏洞利用,写双字节得到
0xff8b0428——>0xff8b0438——>0x804cb20
技巧
改ret地址中的libc_start_main为onegadget
改printf的got为system/onegadget