昨晚上终于作出来了,回头一想也不难。把思路整理清楚了就好办了。
传附后也麻烦,直接上原题吧
import random
import os
from Crypto.Cipher import DES
from Crypto.Util.number import *
def encode(m,k):
s=[]
for i in m:
s.append(sbox[i])
s=s[3:]+s[0:3]
assert len(s)==len(k)
r = []
for i in range(len(m)):
r.append(s[i]^k[i])
return r
def encrypto(m,k):
y = encode(m,k)
y = encode(y,k)
return y
sbox=list(range(256))
random.shuffle(sbox)
print(sbox)
key=os.urandom(8)
secret=[1,2,3,4,5,6,7,8]
r = encrypto(secret,key)
print(r)
secret=os.urandom(8)
r = encrypto(secret,key)
print(r)
d=DES.new(secret,DES.MODE_ECB)
flag=b"DASCTF{*}"
print(d.encrypt(flag).hex())
'''
[53, 215, 0, 67, 172, 88, 48, 103, 188, 205, 12, 249, 204, 146, 66, 189, 165, 71, 124, 197, 134, 44, 30, 191, 106, 243, 64, 152, 113, 40, 184, 163, 176, 180, 175, 168, 105, 229, 220, 150, 238, 181, 52, 51, 61, 65, 56, 62, 136, 92, 164, 158, 99, 209, 166, 244, 125, 195, 57, 224, 8, 154, 20, 241, 126, 1, 83, 202, 72, 148, 171, 45, 4, 34, 69, 70, 248, 161, 59, 68, 107, 60, 253, 81, 225, 26, 42, 31, 22, 157, 206, 19, 76, 196, 117, 246, 120, 222, 16, 39, 122, 41, 162, 24, 192, 95, 233, 177, 10, 77, 85, 247, 130, 109, 245, 211, 21, 237, 82, 252, 58, 221, 135, 28, 93, 207, 242, 174, 111, 138, 153, 208, 32, 214, 80, 129, 194, 179, 6, 144, 199, 55, 160, 141, 73, 110, 218, 5, 35, 186, 15, 132, 149, 96, 29, 74, 156, 143, 54, 131, 167, 116, 25, 23, 147, 47, 94, 203, 7, 178, 102, 75, 250, 173, 9, 213, 200, 231, 89, 254, 49, 97, 43, 217, 239, 155, 127, 219, 90, 112, 101, 223, 128, 234, 159, 193, 37, 236, 232, 170, 86, 11, 46, 121, 133, 63, 118, 228, 91, 198, 27, 3, 201, 119, 255, 36, 212, 251, 50, 2, 104, 33, 235, 140, 14, 84, 98, 151, 226, 240, 137, 114, 78, 13, 185, 18, 123, 190, 79, 216, 183, 139, 210, 182, 87, 115, 100, 187, 17, 230, 142, 108, 169, 38, 227, 145]
[149, 52, 49, 137, 136, 226, 194, 207]
[50, 151, 237, 63, 223, 12, 118, 138]
4cc917e07ec87f5a481843e3a21ef0f1178bb3b5712b25637359bb9e66b684af5f922520066f9e8b
'''
加密过程:
- 先生成个码表 已知
- 先用书知的secret和随机的key加密得到r1 已知
- 再用key和随机的secret加密得到r2 已知
- 再通过secret进行des加密得到密文
加密函数:
- 将secret查码表得到m
- m向前循环移3位
- 对应的m与key异或得到y
- 重复第2次
看下第一步的具体过程:
- 以secret[0]为例,先查码表得到 m[0]=sbox[secret[0]]
- 再进行一次移位 m[5] = m[0]
- 再与对应的key进行异或 y[5]=m[5]^key[5]
- 因为加密是进行两次,所以接下来用y[5]作为secret再进行一次
- m[5] = sbox[y[5]]
- m[2] = m[5]
- y[2] = m[2]^key[2] 这时y[2]已经给出
secret[0]先后与key[5],key[2]运算得到r1[2]所以一次并不能得到对应的key,但可以得到key[2],key[5]的对由于是异或运算,这种对有256组
第一步的解密过程:
- 先求出8组对应的key对
- 然后从0开始找链,也就是说假设key[0]正确,找到对应的key[3],再根据key[3]找到key[6],最后找到key[0] 这个key[0]如果跟一开始假设的key[0]是同一个则说明暴出的key是正确的
sbox = [...原题上有...]
r1 = [149, 52, 49, 137, 136, 226, 194, 207]
secret=[1,2,3,4,5,6,7,8]
#找到key对存入tk
tk = []
for k in range(8):
ttk = []
for i in range(256): #0
for j in range(256): #5
v1 = (k+3)%8
s0 = sbox[secret[v1]] ^ i
s1 = sbox[s0] ^j
if s1 == r1[(k+5)%8]:
#print('0,',i,',5,',j )
ttk.append(j)
tk.append(ttk)
#key对的顺序
srd = [0,5,2,7,4,1,6,3]
key =[0,0,0,0,0,0,0,0]
for v in range(1):
srd = srd[1:]+srd[:1]
for i in range(256):
tmp = i
for j in srd:
tmp = tk[j][tmp]
if tmp == i:
t = i
print(t)
t2 = t
tmpkey = [0,0,0,0,0,0,0,0]
for t1 in srd:
print(t2,end=',')
tmpkey[t1]=t2
t2 = tk[t1][t2]
print("")
print(tmpkey)
print(encrypto(secret,tmpkey))
#key = [72, 133, 21, 30, 215, 0, 227, 42]
第二步的加密过程:
- 第二步是key已知(上一步已得到)然后求secret
- 同样是第一步的过程secret[0]查表得到 m[5] = m[0]=sbox[secret[0]]
- y[5] = m[5]^key[5]
- m[2]=m[5]=sbox[y[5]]
- y[2] = m[2]^key[2] == r2[2]
- 但这里key是已知的,所以可以直接逆向求到secret
第二步的解密过程:
- 按相反顺序先将r2[0]^key[0]
- 然后反查码表再移位改为3
- 再用y[3]^key[3]得到secret[6]
r2 = [50, 151, 237, 63, 223, 12, 118, 138]
secret = [0,0,0,0,0,0,0,0]
for i in range(8):
secret[(i+6)%8] = sbox.index(sbox.index(r2[i]^key[i]) ^ key[(i+3)%8])
print(secret)
print(encrypto(secret,key))
#secret = [92, 47, 88, 14, 154, 185, 100, 81]
第二步处理完后,下边就是已知密钥的情况下des解密
d=DES.new(bytes(secret),DES.MODE_ECB)
print(d.decrypt(bytes.fromhex('4cc917e07ec87f5a481843e3a21ef0f1178bb3b5712b25637359bb9e66b684af5f922520066f9e8b')))
#DASCTF{a242ef7a9aa9f4416fa2b0401558b846}