@john-lee
2023-07-11T07:43:45.000000Z
字数 1426
阅读 741
WISE二维码
CR200
字节 | 值 | 描述 |
---|---|---|
byte 0 | 0x30 | 鉴权参数,可用于区别身份。 |
0x31 | ||
0x32 | ||
0x33 | ||
byte 1~4 | W ,I ,S ,E | 识别码。 |
byte 5~8 | - | 有效截止时间戳,自 2001-1-1 00:00:00 起的秒数。 |
byte 9~12 | - | 鉴权ID号 |
从原始数据生成二维码数据需要经过以下两步过程:
使用 XTEA 加密算法,密钥长度为 128 bits,具体值待定。明文与密文使用同一个内存区(加密后,密文将覆盖明文),加密从 byte 1 开始(byte 0 不加密),需要进行两次:第一次加密 byte 1~8,第二次加密 byte 5~12。
加密算法的 C 语言实现:
/*
XTEA 加密函数
参数:
text: 输入的明文缓冲区和输出的密文缓冲区
key: 密钥
*/
void encipher(uint32_t text[2], const uint32_t key[4])
{
unsigned i;
uint32_t v0 = text[0], v1 = text[1], sum = 0, delta = 0x9E3779B9;
for (i = 0; i < 32; i++) {
v0 += (((v1 << 4) ^ (v1 >> 5)) + v1) ^ (sum + key[sum & 3]);
sum += delta;
v1 += (((v0 << 4) ^ (v0 >> 5)) + v0) ^ (sum + key[(sum >> 11) & 3]);
}
text[0] = v0;
text[1] = v1;
}
加密过程得到的数据长度与原始数据长度相同,都是 13 字节。文本化从 byte 1 开始(byte 0 不变),
每个字节分为高 4 位和低 4 位,先高后低,分别按如下映射规则得到映射后的字符数据:
0000 -> '0'
0001 -> '1'
0010 -> '2'
0011 -> '3'
0100 -> '4'
0101 -> '5'
0110 -> '6'
0111 -> '7'
1000 -> '8'
1001 -> '9'
1010 -> 'A'
1011 -> 'B'
1100 -> 'C'
1101 -> 'D'
1110 -> 'E'
1111 -> 'F'
并将所有得到的字符按先后排列,得到一个 24 字节的文本,加上 byte 0 为 25 字节。该文本即为 WISE 二维码。例如加密后的数据为:
0x30, 0xFC, 0x07, 0x6C, 0x95, 0xDE, 0xC8, 0xE8, 0xAB, 0x75, 0x3D, 0xF1, 0x9A
文本化后为:
0FC076C95DEC8E8AB753DF19A
二维码数据还原为原始数据也需要经过两步过程:
解密算法的 C 语言实现:
/*
XTEA 解密函数
参数:
text: 输入的密文缓冲区和输出的明文缓冲区
key: 密钥
*/
void decipher(uint32_t text[2], const uint32_t key[4])
{
unsigned i;
uint32_t v0 = text[0], v1 = text[1], delta = 0x9E3779B9, sum = delta * 32;
for (i = 0; i < 32; i++) {
v1 -= (((v0 << 4) ^ (v0 >> 5)) + v0) ^ (sum + key[(sum >> 11) & 3]);
sum -= delta;
v0 -= (((v1 << 4) ^ (v1 >> 5)) + v1) ^ (sum + key[sum & 3]);
}
text[0] = v0;
text[1] = v1;
}