setcontext+orw 大致可以把2.27,2.29做为两个分界点
2.27下的setcontext
内容如图,
作用是通过rdi寄存器里地址来设置各个寄存器的值。该版本下我们通常从setcontext+53开始利用,因为前面的fldenv byte pte [rcx]会导致程序crash。
值得注意的是,mov rcx,[rdi+0A8h]和push rcx实际是给我们的rip赋值。不过我们无法控制rax寄存器,或者说我们必然会将其设置为0。不过我们通过控制rsp和rip就已经可以很轻易地劫持程序流。
那么该版本下,我们通常会把setcontext+53写进_free_hook
或者_malloc_hook
中,然后建立或释放一个堆块,此时的rdi是该堆块的chunk头,通常情况下我们提前布置好堆就可以控制寄存器并劫持程序的执行流。
2.29版本下的setcontext
该版本最大的变动就是setcontext里控制寄存器由rdi变成了rdx,这也意味着我们无法通过直接控制堆块来控制寄存器,所以我们需要用到一些gadget把rdi和rdx转换一下。这里有俩个推荐的magic_gadget
2.31版本下的setcontext
该版本的变动在于可利用的setcontext的位置变成了setcontext+61
另外就是之前推荐的magic_gadget只剩一个了
setcontext + orw
一般而言,有两种思路,第一种是直接控制程序执行流去执行ROP链,另一种是先用 mprotect 函数开辟一段可读可写可执行的空间再跳到上面去执行 shellcode。
2.34版本_hook的终结
glibc 中的 __malloc_hook
函数指针变量,在 glibc 2.34 的补丁中被移除了。这意味着从 glibc 版本 2.34 开始,__malloc_hook
、__free_hook
、__realloc_hook
、__memalign_hook
和 __after_morecore_hook
等钩子函数不再可用。
此外,虽然在 glibc 2.23 版本中,这些钩子函数仍然存在,但在链接时可能会找不到定义,导致无法通过链接环节。这可能是因为 glibc 考虑到了与之前使用钩子程序的兼容性