sctf 2019 warmup

server.py

#!/usr/bin/python
# -*- coding: utf-8 -*-

from Crypto.Cipher import AES
from Crypto.Util.strxor import strxor
from Crypto.Random import get_random_bytes
from FLAG import flag

class MAC:
    def __init__(self):
        self.key = get_random_bytes(16)
        self.iv = get_random_bytes(16)

    def pad(self, msg):
        pad_length = 16 - len(msg) % 16
        return msg + chr(pad_length) * pad_length

    def unpad(self, msg):
        return msg[:-ord(msg[-1])]

    def code(self, msg):
        res = chr(0)*16
        for i in range(len(msg)/16):
            res = strxor(msg[i*16:(i+1)*16], res)
        aes = AES.new(self.key, AES.MODE_CBC, self.iv)
        return aes.encrypt(res).encode('hex')

    def identity(self, msg, code):
        if self.code(msg) == code:
            msg = self.unpad(msg)
            if msg == 'please send me your flag':
                print 'remote: ok, here is your flag:%s' % flag
            else:
                print 'remote: I got it'
        else:
            print 'remote: hacker!'


if __name__ == '__main__':
    mac = MAC()
    message = 'see you at three o\'clock tomorrow'
    print 'you seem to have intercepted something:{%s:%s}' %(mac.pad(message).encode('hex'), mac.code(mac.pad(message)))
    print 'so send your message:'
    msg = raw_input()
    print 'and your code:'
    code = raw_input()
    mac.identity(msg.decode('hex'), code)
    exit()

这里主要用到一个如下原理:

C = A xor B。若我们想得到X,则有以下推导
C = A xor B ==>> C xor A xor B = 0 ===>> C xor A xor B xor X = X
而整个解密过程中,B(密文)是我们可以控制的,A由于key未知,而无法准确控制,C是原始的明文,在输出端,无法控制。
所以,我们可以控制B,让B首先变成C xor B xor X (这里的C是指原始的明文),这样最终A与B的异或操作就能变成X

参考文献: http://momomoxiaoxi.com/2016/12/08/WebCrypt/
https://www.anquanke.com/post/id/158233
在这道题中我们进行伪造,伪造主要绕过一下两个条件:

  • 使用code()的函数加完密的要等于你自己提供的code的值
  • 使用unpad(msg.decode('hex'))消除填充之后,必须等于:please send me your flag
    sctf 2019 warmup_第1张图片
    图片.png

进行伪造:
题目中会给出两组数据,如下图所示:


图片.png

伪造条件如下:

  • 构造 A xor B,也就是:
    1.A的每十六字节“异或”并使用pad()填充:
msg=('706c656173652073656e64206d6520796f757220666c6167'+'8'*16).decode('hex')
print c
res = chr(0)*16
for i in range(len(msg)/16):
    res = strxor(msg[i*16:(i+1)*16], res)
  1. B的每十六进制“异或”并使用pad()填充“”
res1 = chr(0)*16
msg1=('73656520796f75206174207468726565206f27636c6f636b20746f6d6f72726f77'+'0f'*15).decode('hex')
for i in range(len(msg1)/16):
    res1 = strxor(msg1[i*16:(i+1)*16], res1)

3.最终将他们异或 A xor B:

last_res = strxor(res1, res).encode('hex')
  • 构造第一个输入:
    1.由前一组16位和后一组16位异或:


    sctf 2019 warmup_第2张图片
    图片.png

    2.我们只要构造(A xor B) xor A =B:

(A xor B):

last_res = strxor(res1, res).encode('hex')

A:

msg

payload = (msg.encode('hex')+last_res).ljust(124,"a")+'27'
  • 绕过 msg = self.unpad(msg)的检测:
  1. 可以看出:他用来填充的单位使用的是16的差值.
def pad(self, msg):
        pad_length = 16 - len(msg) % 16
        return msg + chr(pad_length) * pad_length

2.去除填充函数,通过最后一位的数值,进行去除,这里可以伪造:
'''
def unpad(self, msg):
return msg[:-ord(msg[-1])]
'''
3.伪造内容在最后加一个数值,数值等于去掉“please send me your flag”之后,即可绕过保护。

图片.png

代码我借用一下别人的,代码如下:

from pwn import *
from Crypto.Util.strxor import strxor

p=remote('47.240.41.112',12345)

p.recvuntil('0f:')
c = p.recv(32)
msg=('706c656173652073656e64206d6520796f757220666c6167'+'8'*16).decode('hex')
print c1
res = chr(0)*16
for i in range(len(msg)/16):
    res = strxor(msg[i*16:(i+1)*16], res)

res1 = chr(0)*16
msg1=('73656520796f75206174207468726565206f27636c6f636b20746f6d6f72726f77'+'0f'*15).decode('hex')
for i in range(len(msg1)/16):
    res1 = strxor(msg1[i*16:(i+1)*16], res1)

last_res = strxor(res1, res).encode('hex')

payload = (msg.encode('hex')+last_res).ljust(124,"a")+'27'
print payload
p.recvuntil("so send your message:\n")
p.sendline(payload)
p.recvuntil("and your code:\n")
p.sendline(c)
p.interactive()

参考网站:
https://www.jianshu.com/p/02ef24117d7b
。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。
基础知识:
异或两个bytes

from Crypto.Util.strxor import strxor
strxor(b'abc', b'def')

参考网站:
https://www.jianshu.com/p/02ef24117d7b
https://code.felinae98.cn/ctf/crypto/python%E4%B8%AD%E7%9A%84crypto%E5%9C%A8ctf%E4%B8%AD%E7%9A%84%E5%BA%94%E7%94%A8/

你可能感兴趣的:(sctf 2019 warmup)