TEA
加密使用的数据为2个32位无符号整数,密钥为4个32位无符号整数即密钥长度为128位
void encrypt(unsigned int* v, unsigned int* key) {
unsigned int l = v[0], r = v[1], sum = 0, delta = 0x9e3779b9;
for (size_t i = 0; i < 32; i++) {
sum += delta;
l += ((r << 4) + key[0]) ^ (r + sum) ^ ((r >> 5) + key[1]);
r += ((l << 4) + key[2]) ^ (l + sum) ^ ((l >> 5) + key[3]);
}
v[0] = l;
v[1] = r;
}
void decrypt(unsigned int* v, unsigned int* key) {
unsigned int l = v[0], r = v[1], sum = 0, delta = 0x9e3779b9;
sum = delta *32;
for (size_t i = 0; i < 32; i++) {
r -= ((l << 4) + key[2]) ^ (l + sum) ^ ((l >> 5) + key[3]);
l -= ((r << 4) + key[0]) ^ (r + sum) ^ ((r >> 5) + key[1]);
sum -= delta;
}
v[0] = l;
v[1] = r;
}
XTEA
TEA的迭代版本增加了更多的密钥表,移位和异或操作等等
void encrypt(unsigned int* v, unsigned int* key) {
unsigned int l = v[0], r = v[1], sum = 0, delta = 0x9e3779b9;
for (size_t i = 0; i < 32; i++) {
l += (((r << 4) ^ (r >> 5)) + r) ^ (sum + key[sum & 3]);
sum += delta;
r += (((l << 4) ^ (l >> 5)) + l) ^ (sum + key[(sum >> 11) & 3]);
}
v[0] = l;
v[1] = r;
}
void decrypt(unsigned int* v, unsigned int* key) {
unsigned int l = v[0], r = v[1], sum = 0, delta = 0x9e3779b9;
sum = delta * 32;
for (size_t i = 0; i < 32; i++) {
r -= (((l << 4) ^ (l >> 5)) + l) ^ (sum + key[(sum >> 11) & 3]);
sum -= delta;
l -= (((r << 4) ^ (r >> 5)) + r) ^ (sum + key[sum & 3]);
}
v[0] = l;
v[1] = r;
}
代码借鉴于Link
XXTEA
XXTEA是一个非平衡Feistel网络分组密码,在可变长度块上运行,这些块是32位大小的任意倍数(最小64位),使用128位密钥
我个菜鸡,只能搜的别人的模板 Link
我解题就以这个改了( * ^ ▽ ^ * )
#include <stdio.h>
#include <stdlib.h>
#define delta 0x9e3779b9
int main()
{
unsigned int v[8] = {0x10BD3B47, 0x6155E0F9, 0x6AF7EBC5, 0x8D23435F, 0x1A091605, 0xD43D40EF, 0xB4B16A67, 0x6B3578A9};
unsigned int key[4] = {0x00001234, 0x00002345, 0x00004567, 0x00006789};
unsigned int sum = 0;
unsigned int y,z,p,rounds,e;
int n = 8;
int i = 0;
rounds = 6 + 52/n;
y = v[0];
sum = rounds*delta;
do
{
e = sum >> 2 & 3;
for(p=n-1;p>0;p--)
{
z = v[p-1];
v[p] -= ((((z>>5)^(y<<2))+((y>>3)^(z<<4))) ^ ((key[(p&3)^e]^z)+(y ^ sum)));
y = v[p];
}
z = v[n-1];
v[0] -= (((key[(p^e)&3]^z)+(y ^ sum)) ^ (((y<<2)^(z>>5))+((z<<4)^(y>>3))));
y = v[0];
sum = sum-delta;
}while(--rounds);
for(i=0;i<n;i++)
{
printf("%c%c%c%c",*((char*)&v[i]+0),*((char*)&v[i]+1),*((char*)&v[i]+2),*((char*)&v[i]+3));
//printf("%c%c%c%c",*((char*)&v[i]+3),*((char*)&v[i]+2),*((char*)&v[i]+1),*((char*)&v[i]+0));
}
return 0;
}
例题
1.New Star Week 3 EZTEA
key已知,虽然数字很臭,我们还知道密文。还有一个一个一个delta=289739776
(转成十六进制更臭了)
加密部分小小的魔改了一下。
小改一下脚本,直接run
#include <stdio.h>
#include <stdlib.h>
#define delta 289739776
int main()
{
unsigned int v[9] = {0x38FA8A82, 0xD7501380, 0xE40969D, 0x4E169120, 0x713A29AB, 0x6CE5393D, 0xB69D752E, 0x841A88E6, 0x6F31B459};
unsigned int key[4] = {0x19,0x19,8,0x10};
unsigned int sum = 0;
unsigned int y,z,p,rounds,e;
int n = 9;
int i = 0;
rounds = 6 + 52/n;
y = v[0];
sum = (rounds*delta)& 0xffffffff;
do
{
e = sum >> 2 & 3;
for(p=n-1;p>0;p--)
{
z = v[p-1];
v[p] -= ((((z<<5)^(y>>3))+((y<<2)^(z>>4))) ^ ((key[(p&3)^e]^z)+(y ^ sum)))& 0xffffffff;
y = v[p];
}
z = v[n-1];
v[0] -= (((key[(p^e)&3]^z)+(y ^ sum)) ^ (((y>>3)^(z<<5))+((z>>4)^(y<<2))))& 0xffffffff;
y = v[0];
sum = (sum-delta)& 0xffffffff;
}while(--rounds);
for(i=0;i<n;i++)
{
printf("%c%c%c%c",*((char*)&v[i]+0),*((char*)&v[i]+1),*((char*)&v[i]+2),*((char*)&v[i]+3));
//printf("%c%c%c%c",*((char*)&v[i]+3),*((char*)&v[i]+2),*((char*)&v[i]+1),*((char*)&v[i]+0));
}
return 0;
}
2022年浙江省信息安全竞赛技能赛初赛re2
赛后复盘做出来的,so不知flag是不是对的。
此题是python逆向。
使用pyinstxtractor解析exe文件,然后使用pycdc将解析包里的re.pyc转成可读的py代码。uncompyle6是解析不出来滴。省赛还是断网比赛,找不到对的工具,直接G了。
from ctypes import *
import binascii
def encrypt(n, v, key):
de = 1311062073
ro = 6 + 52 // n
total = c_uint32(0)
z = c_uint32(v[n - 1])
e = c_uint32(0)
if ro > 0:
total.value += de
e.value = total.value >> 2 & 3
for p in range(n - 1):
y = c_uint32(v[p + 1])
v[p] = c_uint32(v[p] + XX(z, y, total, key, p, e).value).value
z.value = v[p]
y = c_uint32(v[0])
v[n - 1] = c_uint32(v[n - 1] + XX(z, y, total, key, n - 1, e).value).value
z.value = v[n - 1]
ro -= 1
continue
return v
def XX(z, y, total, key, p, e):
xx = c_uint32((z.value >> 6 ^ y.value << 3) + (y.value >> 3 ^ z.value << 4) ^ (total.value ^ y.value) + key[p & 3 ^ e.value])
return xx
if __name__ == '__main__':
k = [
4,
3,
2,
1]
n = 2
xx = input('plz input your flag(DASCTF{*}):')
vvalue = [
722695011,
893015348,
0xFB586025L,
752171035,
1118151735,
0x916AAD6EL,
0xC3F6A656L,
0xA3E014EFL]
for i in range(1):
if len(xx) != 40:
print('error')
else:
xx = xx[7:39]
comppare = []
for i in range(0, 32, 8):
value = []
xxx = xx[i:i + 8]
xxx1 = xxx[0:4].encode()
xxx2 = xxx[4:].encode()
hexvalue1 = binascii.b2a_hex(xxx1).decode()
hexvalue2 = binascii.b2a_hex(xxx2).decode()
value.append(int(hexvalue1, 16))
value.append(int(hexvalue2, 16))
res = encrypt(n, value, k)
comppare.append(res[0])
comppare.append(res[1])
if comppare == vvalue:
print('correct')
continue
print('error')
return None
对着模板小改一波
#include <stdio.h>
#include <stdlib.h>
#define delta 1311062073
int main()
{ //每次解密2个32位无符号数字
unsigned int v[8] = {722695011,893015348};//0xFB586025L,752171035,1118151735,0x916AAD6EL,0xC3F6A656L,0xA3E014EFL
unsigned int key[4] = {4,3,2,1};
unsigned int sum = 0;
unsigned int y,z,p,rounds,e;
int n = 2;
int i = 0;
rounds = 6 + 52/n;
y = v[0];
sum = rounds*delta;
do
{
e = sum >> 2 & 3;
for(p=n-1;p>0;p--)
{
z = v[p-1];
v[p] -= (((z>>6)^(y<<3))+((y>>3)^(z<<4))^(y ^ sum) + ((key[(p&3)^e])));
y = v[p];
}
z = v[n-1];
v[0] -= (((z>>6)^(y<<3))+((y>>3)^(z<<4))^(y ^ sum) + (key[(p&3)^e]));
y = v[0];
sum = sum-delta;
}while(--rounds);
for(i=0;i<n;i++)
{
//printf("%c%c%c%c",*((char*)&v[i]+0),*((char*)&v[i]+1),*((char*)&v[i]+2),*((char*)&v[i]+3));
/*此题要逆着输出,不然会得到
3txx_444
p_n13hty
s1_ns3e_
1r_y?thg
拼起来是
3txx_444p_n13htys1_ns3e_1r_y?thg
怎么看都不像flag,看着像逆序,试了一下逆序就对了,虽然我不知道为什么。(若有懂哥,评论区教教我Thanks♪(・ω・)ノ)
*/
printf("%c%c%c%c",*((char*)&v[i]+3),*((char*)&v[i]+2),*((char*)&v[i]+1),*((char*)&v[i]+0));
}
return 0;
}
8个数字,每次解密两个,得
xxt3444_
1n_pyth3
n_1s_e3s
y_r1ght?
DASCTF{xxt3444_1n_pyth3n_1s_e3sy_r1ght?}
感觉应该是对的。
评论区