mirror of
https://github.com/korenkonder/ReDIVA.git
synced 2026-09-30 10:47:59 +03:00
Replaced code from tiny-AES-c with prj::Rijndael
This commit is contained in:
-1346
File diff suppressed because it is too large
Load Diff
@@ -1,90 +0,0 @@
|
||||
/*
|
||||
Original: https://github.com/kokke/tiny-AES-c
|
||||
*/
|
||||
|
||||
#ifndef _AES_H_
|
||||
#define _AES_H_
|
||||
|
||||
#include "default.hpp"
|
||||
#include <immintrin.h>
|
||||
|
||||
//#define AES128 1
|
||||
//#define AES192 1
|
||||
//#define AES256 1
|
||||
|
||||
#define AES_BLOCKLEN 16 // Block length in bytes - AES is 128b block only
|
||||
|
||||
#define AES128_KEYLEN 16 // Key length in bytes
|
||||
#define AES128_keyExpSize 176
|
||||
#define AES192_KEYLEN 24
|
||||
#define AES192_keyExpSize 208
|
||||
#define AES256_KEYLEN 32
|
||||
#define AES256_keyExpSize 240
|
||||
|
||||
struct aes128_ctx {
|
||||
union {
|
||||
uint8_t RoundKey[AES128_keyExpSize];
|
||||
__m128i RoundKeyNI[AES128_keyExpSize / sizeof(__m128i) + 9];
|
||||
};
|
||||
uint8_t Iv[AES_BLOCKLEN];
|
||||
};
|
||||
|
||||
struct aes192_ctx {
|
||||
union {
|
||||
uint8_t RoundKey[AES192_keyExpSize];
|
||||
__m128i RoundKeyNI[AES192_keyExpSize / sizeof(__m128i) + 11];
|
||||
};
|
||||
uint8_t Iv[AES_BLOCKLEN];
|
||||
};
|
||||
|
||||
struct aes256_ctx {
|
||||
union {
|
||||
uint8_t RoundKey[AES256_keyExpSize];
|
||||
__m128i RoundKeyNI[AES256_keyExpSize / sizeof(__m128i) + 13];
|
||||
};
|
||||
uint8_t Iv[AES_BLOCKLEN];
|
||||
};
|
||||
|
||||
void aes128_init_ctx(aes128_ctx* ctx, const uint8_t* key);
|
||||
void aes192_init_ctx(aes192_ctx* ctx, const uint8_t* key);
|
||||
void aes256_init_ctx(aes256_ctx* ctx, const uint8_t* key);
|
||||
void aes128_init_ctx_iv(aes128_ctx* ctx, const uint8_t* key, const uint8_t* iv);
|
||||
void aes192_init_ctx_iv(aes192_ctx* ctx, const uint8_t* key, const uint8_t* iv);
|
||||
void aes256_init_ctx_iv(aes256_ctx* ctx, const uint8_t* key, const uint8_t* iv);
|
||||
void aes128_ctx_set_iv(aes128_ctx* ctx, const uint8_t* iv);
|
||||
void aes192_ctx_set_iv(aes192_ctx* ctx, const uint8_t* iv);
|
||||
void aes256_ctx_set_iv(aes256_ctx* ctx, const uint8_t* iv);
|
||||
|
||||
// buffer size is exactly AES_BLOCKLEN bytes;
|
||||
// you need only AES_init_ctx as IV is not used in ECB
|
||||
void aes128_ecb_encrypt(aes128_ctx* ctx, uint8_t* buf);
|
||||
void aes192_ecb_encrypt(aes192_ctx* ctx, uint8_t* buf);
|
||||
void aes256_ecb_encrypt(aes256_ctx* ctx, uint8_t* buf);
|
||||
void aes128_ecb_decrypt(aes128_ctx* ctx, uint8_t* buf);
|
||||
void aes192_ecb_decrypt(aes192_ctx* ctx, uint8_t* buf);
|
||||
void aes256_ecb_decrypt(aes256_ctx* ctx, uint8_t* buf);
|
||||
void aes128_ecb_encrypt_buffer(aes128_ctx* ctx, uint8_t* buf, size_t length);
|
||||
void aes192_ecb_encrypt_buffer(aes192_ctx* ctx, uint8_t* buf, size_t length);
|
||||
void aes256_ecb_encrypt_buffer(aes256_ctx* ctx, uint8_t* buf, size_t length);
|
||||
void aes128_ecb_decrypt_buffer(aes128_ctx* ctx, uint8_t* buf, size_t length);
|
||||
void aes192_ecb_decrypt_buffer(aes192_ctx* ctx, uint8_t* buf, size_t length);
|
||||
void aes256_ecb_decrypt_buffer(aes256_ctx* ctx, uint8_t* buf, size_t length);
|
||||
|
||||
void aes128_cbc_encrypt(aes128_ctx* ctx, uint8_t buf[AES_BLOCKLEN]);
|
||||
void aes192_cbc_encrypt(aes192_ctx* ctx, uint8_t buf[AES_BLOCKLEN]);
|
||||
void aes256_cbc_encrypt(aes256_ctx* ctx, uint8_t buf[AES_BLOCKLEN]);
|
||||
void aes128_cbc_decrypt(aes128_ctx* ctx, uint8_t buf[AES_BLOCKLEN]);
|
||||
void aes192_cbc_decrypt(aes192_ctx* ctx, uint8_t buf[AES_BLOCKLEN]);
|
||||
void aes256_cbc_decrypt(aes256_ctx* ctx, uint8_t buf[AES_BLOCKLEN]);
|
||||
void aes128_cbc_encrypt_buffer(aes128_ctx* ctx, uint8_t* buf, size_t length);
|
||||
void aes192_cbc_encrypt_buffer(aes192_ctx* ctx, uint8_t* buf, size_t length);
|
||||
void aes256_cbc_encrypt_buffer(aes256_ctx* ctx, uint8_t* buf, size_t length);
|
||||
void aes128_cbc_decrypt_buffer(aes128_ctx* ctx, uint8_t* buf, size_t length);
|
||||
void aes192_cbc_decrypt_buffer(aes192_ctx* ctx, uint8_t* buf, size_t length);
|
||||
void aes256_cbc_decrypt_buffer(aes256_ctx* ctx, uint8_t* buf, size_t length);
|
||||
|
||||
void aes128_ctr_xcrypt_buffer(aes128_ctx* ctx, uint8_t* buf, uint32_t length);
|
||||
void aes192_ctr_xcrypt_buffer(aes192_ctx* ctx, uint8_t* buf, uint32_t length);
|
||||
void aes256_ctr_xcrypt_buffer(aes256_ctx* ctx, uint8_t* buf, uint32_t length);
|
||||
|
||||
#endif // _AES_H_
|
||||
+16
-16
@@ -5,7 +5,7 @@
|
||||
|
||||
#include "divafile.hpp"
|
||||
#include "io/file_stream.hpp"
|
||||
#include "aes.hpp"
|
||||
#include "prj/rijndael.hpp"
|
||||
#include "str_utils.hpp"
|
||||
|
||||
namespace divafile {
|
||||
@@ -35,9 +35,9 @@ namespace divafile {
|
||||
void* data = force_malloc(stream_length);
|
||||
s_enc.read(data, stream_length);
|
||||
|
||||
aes128_ctx ctx;
|
||||
aes128_init_ctx(&ctx, key);
|
||||
aes128_ecb_decrypt_buffer(&ctx, (uint8_t*)data, stream_length);
|
||||
prj::Rijndael rijndael(prj::Rijndael_Nb, prj::Rijndael_Nk128, key);
|
||||
for (size_t i = 0; i < stream_length; i += prj::Rijndael_Nlen)
|
||||
rijndael.decrypt16((uint8_t*)data + i);
|
||||
|
||||
file_stream s_dec;
|
||||
s_dec.open(file_temp, L"wb");
|
||||
@@ -66,9 +66,9 @@ namespace divafile {
|
||||
void* data = force_malloc(stream_length);
|
||||
memcpy(data, (void*)(d + 16), stream_length);
|
||||
|
||||
aes128_ctx ctx;
|
||||
aes128_init_ctx(&ctx, key);
|
||||
aes128_ecb_decrypt_buffer(&ctx, (uint8_t*)data, stream_length);
|
||||
prj::Rijndael rijndael(prj::Rijndael_Nb, prj::Rijndael_Nk128, key);
|
||||
for (size_t i = 0; i < stream_length; i += prj::Rijndael_Nlen)
|
||||
rijndael.decrypt16((uint8_t*)data + i);
|
||||
|
||||
*dec_data = data;
|
||||
*dec_size = file_length;
|
||||
@@ -93,9 +93,9 @@ namespace divafile {
|
||||
void* data = force_malloc(stream_length);
|
||||
enc.read(data, stream_length);
|
||||
|
||||
aes128_ctx ctx;
|
||||
aes128_init_ctx(&ctx, key);
|
||||
aes128_ecb_decrypt_buffer(&ctx, (uint8_t*)data, stream_length);
|
||||
prj::Rijndael rijndael(prj::Rijndael_Nb, prj::Rijndael_Nk128, key);
|
||||
for (size_t i = 0; i < stream_length; i += prj::Rijndael_Nlen)
|
||||
rijndael.decrypt16((uint8_t*)data + i);
|
||||
|
||||
dec.open(data, file_length);
|
||||
free_def(data);
|
||||
@@ -121,9 +121,9 @@ namespace divafile {
|
||||
void* data = force_malloc(len_align);
|
||||
s_dec.read(data, len);
|
||||
|
||||
aes128_ctx ctx;
|
||||
aes128_init_ctx(&ctx, key);
|
||||
aes128_ecb_encrypt_buffer(&ctx, (uint8_t*)data, len_align);
|
||||
prj::Rijndael rijndael(prj::Rijndael_Nb, prj::Rijndael_Nk128, key);
|
||||
for (size_t i = 0; i < len_align; i += prj::Rijndael_Nlen)
|
||||
rijndael.encrypt16((uint8_t*)data + i);
|
||||
|
||||
file_stream s_enc;
|
||||
s_enc.open(file_temp, L"wb");
|
||||
@@ -147,9 +147,9 @@ namespace divafile {
|
||||
size_t d = (size_t)data;
|
||||
memcpy((void*)(d + 16), dec_data, len);
|
||||
|
||||
aes128_ctx ctx;
|
||||
aes128_init_ctx(&ctx, key);
|
||||
aes128_ecb_encrypt_buffer(&ctx, (uint8_t*)(d + 16), len_align);
|
||||
prj::Rijndael rijndael(prj::Rijndael_Nb, prj::Rijndael_Nk128, key);
|
||||
for (size_t i = 0; i < len_align; i += prj::Rijndael_Nlen)
|
||||
rijndael.encrypt16((uint8_t*)data + i);
|
||||
|
||||
*(uint64_t*)d = 0x454C494641564944;
|
||||
*(uint32_t*)(d + 8) = (uint32_t)len_align;
|
||||
|
||||
+52
-21
@@ -7,7 +7,6 @@
|
||||
#include "io/path.hpp"
|
||||
#include "io/file_stream.hpp"
|
||||
#include "io/memory_stream.hpp"
|
||||
#include "aes.hpp"
|
||||
#include "deflate.hpp"
|
||||
#include "hash.hpp"
|
||||
#include "str_utils.hpp"
|
||||
@@ -506,9 +505,9 @@ static void farc_pack_files(farc* f, stream& s, farc_signature signature, farc_f
|
||||
s.set_position(align, SEEK_SET);
|
||||
size_t dir_len = f->directory_path.size();
|
||||
|
||||
aes128_ctx ctx;
|
||||
prj::Rijndael rijndael;
|
||||
if (signature == FARC_FARC)
|
||||
aes128_init_ctx(&ctx, f->ft ? key_ft : key);
|
||||
rijndael = prj::Rijndael(prj::Rijndael_Nb, prj::Rijndael_Nk128, f->ft ? key_ft : key);
|
||||
|
||||
f->compression_level = clamp_def(f->compression_level, 0, 12);
|
||||
|
||||
@@ -592,8 +591,14 @@ static void farc_pack_files(farc* f, stream& s, farc_signature signature, farc_f
|
||||
const int32_t pkcs7_pad_len = (int32_t)(t2_len - t1_len - 0x10);
|
||||
memset(t2 + 0x10 + t1_len, pkcs7_pad_len, pkcs7_pad_len); // PKCS7 Padding
|
||||
|
||||
aes128_ctx_set_iv(&ctx, t2);
|
||||
aes128_cbc_encrypt_buffer(&ctx, t2 + 0x10, t2_len - 0x10);
|
||||
uint8_t iv[prj::Rijndael_Nlen];
|
||||
memcpy(iv, t2, prj::Rijndael_Nlen);
|
||||
for (size_t j = 0; j < t2_len - 0x10; j += prj::Rijndael_Nlen) {
|
||||
for (uint32_t k = 0; k < prj::Rijndael_Nlen / sizeof(uint32_t); k++)
|
||||
((uint32_t*)(t2 + 0x10 + j))[k] ^= ((uint32_t*)iv)[k];
|
||||
rijndael.encrypt16(t2 + 0x10 + j);
|
||||
memcpy(iv, t2 + 0x10 + j, prj::Rijndael_Nlen);
|
||||
}
|
||||
|
||||
s.write(t2, t2_len);
|
||||
free_def(t2);
|
||||
@@ -606,7 +611,8 @@ static void farc_pack_files(farc* f, stream& s, farc_signature signature, farc_f
|
||||
memcpy(t2, t1, t1_len);
|
||||
memset(t2 + t1_len, 0x78, t2_len - t1_len);
|
||||
|
||||
aes128_ecb_encrypt_buffer(&ctx, t2, t2_len);
|
||||
for (size_t j = 0; j < t2_len; j += prj::Rijndael_Nlen)
|
||||
rijndael.encrypt16(t2 + j);
|
||||
|
||||
s.write(t2, t2_len);
|
||||
free_def(t2);
|
||||
@@ -683,8 +689,14 @@ static void farc_pack_files(farc* f, stream& s, farc_signature signature, farc_f
|
||||
const int32_t pkcs7_pad_len = (int32_t)(head_data_len - (dt - head_data));
|
||||
memset(dt, pkcs7_pad_len, pkcs7_pad_len); // PKCS7 Padding
|
||||
|
||||
aes128_ctx_set_iv(&ctx, head_data);
|
||||
aes128_cbc_encrypt_buffer(&ctx, head_data + 0x10, head_data_len - 0x10);
|
||||
uint8_t iv[prj::Rijndael_Nlen];
|
||||
memcpy(iv, head_data, prj::Rijndael_Nlen);
|
||||
for (size_t i = 0; i < head_data_len - 0x10; i += prj::Rijndael_Nlen) {
|
||||
for (uint32_t j = 0; j < prj::Rijndael_Nlen / sizeof(uint32_t); j++)
|
||||
((uint32_t*)(head_data + 0x10 + i))[j] ^= ((uint32_t*)iv)[j];
|
||||
rijndael.encrypt16(head_data + 0x10 + i);
|
||||
memcpy(iv, head_data + 0x10 + i, prj::Rijndael_Nlen);
|
||||
}
|
||||
}
|
||||
|
||||
s.write(head_data, head_data_len);
|
||||
@@ -802,10 +814,19 @@ static errno_t farc_read_header(farc* f, stream& s) {
|
||||
if (f->ft) {
|
||||
header_length -= 0x10;
|
||||
|
||||
aes128_ctx ctx;
|
||||
aes128_init_ctx_iv(&ctx, key_ft, dt);
|
||||
prj::Rijndael rijndael(prj::Rijndael_Nb, prj::Rijndael_Nk128, key_ft);
|
||||
|
||||
uint8_t iv[prj::Rijndael_Nlen];
|
||||
uint8_t next_iv[prj::Rijndael_Nlen];
|
||||
memcpy(iv, dt, prj::Rijndael_Nlen);
|
||||
dt += 0x10;
|
||||
aes128_cbc_decrypt_buffer(&ctx, dt, header_length);
|
||||
for (size_t i = 0; i < header_length; i += prj::Rijndael_Nlen) {
|
||||
memcpy(next_iv, dt + i, prj::Rijndael_Nlen);
|
||||
rijndael.decrypt16(dt + i);
|
||||
for (uint32_t j = 0; j < prj::Rijndael_Nlen / sizeof(uint32_t); j++)
|
||||
((uint32_t*)(dt + i))[j] ^= ((uint32_t*)iv)[j];
|
||||
memcpy(iv, next_iv, prj::Rijndael_Nlen);
|
||||
}
|
||||
|
||||
header_length -= ((uint8_t*)dt)[header_length - 1]; // PKCS7 Padding
|
||||
}
|
||||
@@ -1017,34 +1038,44 @@ static void farc_unpack_file(farc* f, stream& s, farc_file* ff, bool save, char*
|
||||
void* temp = force_malloc(temp_s);
|
||||
s.read(temp, temp_s);
|
||||
|
||||
size_t t = (size_t)temp;
|
||||
uint8_t* t = (uint8_t*)temp;
|
||||
if (ff->encrypted)
|
||||
if (f->ft) {
|
||||
temp_s -= 0x10;
|
||||
t += 0x10;
|
||||
|
||||
aes128_ctx ctx;
|
||||
aes128_init_ctx_iv(&ctx, key_ft, (uint8_t*)temp);
|
||||
aes128_cbc_decrypt_buffer(&ctx, (uint8_t*)t, temp_s);
|
||||
prj::Rijndael rijndael(prj::Rijndael_Nb, prj::Rijndael_Nk128, key_ft);
|
||||
|
||||
ff->size_compressed = temp_s - ((uint8_t*)t)[temp_s - 1]; // PKCS7 Padding
|
||||
uint8_t iv[prj::Rijndael_Nlen];
|
||||
uint8_t next_iv[prj::Rijndael_Nlen];
|
||||
memcpy(iv, (uint8_t*)temp, prj::Rijndael_Nlen);
|
||||
for (size_t i = 0; i < temp_s; i += prj::Rijndael_Nlen) {
|
||||
memcpy(next_iv, t + i, prj::Rijndael_Nlen);
|
||||
rijndael.decrypt16(t + i);
|
||||
for (uint32_t j = 0; j < prj::Rijndael_Nlen / sizeof(uint32_t); j++)
|
||||
((uint32_t*)(t + i))[j] ^= ((uint32_t*)iv)[j];
|
||||
memcpy(iv, next_iv, prj::Rijndael_Nlen);
|
||||
}
|
||||
|
||||
ff->size_compressed = temp_s - t[temp_s - 1]; // PKCS7 Padding
|
||||
}
|
||||
else {
|
||||
aes128_ctx ctx;
|
||||
aes128_init_ctx(&ctx, key);
|
||||
aes128_ecb_decrypt_buffer(&ctx, (uint8_t*)t, temp_s);
|
||||
prj::Rijndael rijndael(prj::Rijndael_Nb, prj::Rijndael_Nk128, key);
|
||||
|
||||
for (size_t i = 0; i < temp_s; i += prj::Rijndael_Nlen)
|
||||
rijndael.decrypt16(t + i);
|
||||
}
|
||||
|
||||
if (ff->compressed) {
|
||||
ff->data_compressed = force_malloc(ff->size_compressed);
|
||||
memcpy(ff->data_compressed, (void*)t, ff->size_compressed);
|
||||
memcpy(ff->data_compressed, t, ff->size_compressed);
|
||||
deflate::decompress(ff->data_compressed, ff->size_compressed,
|
||||
ff->data, ff->size, deflate::MODE_GZIP);
|
||||
}
|
||||
else {
|
||||
ff->data_compressed = 0;
|
||||
ff->data = force_malloc(ff->size);
|
||||
memcpy(ff->data, (void*)t, ff->size);
|
||||
memcpy(ff->data, t, ff->size);
|
||||
}
|
||||
free_def(temp);
|
||||
}
|
||||
|
||||
+7
-6
@@ -8,12 +8,7 @@
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include "default.hpp"
|
||||
|
||||
enum farc_signature {
|
||||
FARC_FArc = 'FArc',
|
||||
FARC_FArC = 'FArC',
|
||||
FARC_FARC = 'FARC',
|
||||
};
|
||||
#include "prj/rijndael.hpp"
|
||||
|
||||
enum farc_flags {
|
||||
FARC_NONE = 0x00,
|
||||
@@ -21,6 +16,12 @@ enum farc_flags {
|
||||
FARC_AES = 0x04,
|
||||
};
|
||||
|
||||
enum farc_signature {
|
||||
FARC_FArc = 'FArc',
|
||||
FARC_FArC = 'FArC',
|
||||
FARC_FARC = 'FARC',
|
||||
};
|
||||
|
||||
struct farc_file {
|
||||
std::string name;
|
||||
size_t offset;
|
||||
|
||||
@@ -0,0 +1,392 @@
|
||||
/*
|
||||
by korenkonder
|
||||
GitHub/GitLab: korenkonder
|
||||
*/
|
||||
|
||||
#include "rijndael.hpp"
|
||||
#include <wmmintrin.h> // Added
|
||||
|
||||
namespace prj_rijndael_detail {
|
||||
union StateUnion {
|
||||
uint32_t word[0x4];
|
||||
uint8_t byte[0x10];
|
||||
};
|
||||
}
|
||||
|
||||
namespace {
|
||||
struct PrjRijdaelTest {
|
||||
PrjRijdaelTest();
|
||||
|
||||
void test();
|
||||
};
|
||||
}
|
||||
|
||||
static const uint32_t r_con[] = {
|
||||
0x00, 0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x40,
|
||||
0x80, 0x1B, 0x36, 0x6C, 0xD8, 0xAB, 0x4D, 0x9A,
|
||||
0x2F, 0x5E, 0xBC, 0x63, 0xC6, 0x97, 0x35, 0x6A,
|
||||
0xD4, 0xB3, 0x7D, 0xFA, 0xEF, 0xC5, 0x91, 0x39,
|
||||
};
|
||||
|
||||
static const uint8_t s_box[] = {
|
||||
0x63, 0x7C, 0x77, 0x7B, 0xF2, 0x6B, 0x6F, 0xC5, 0x30, 0x01, 0x67, 0x2B, 0xFE, 0xD7, 0xAB, 0x76,
|
||||
0xCA, 0x82, 0xC9, 0x7D, 0xFA, 0x59, 0x47, 0xF0, 0xAD, 0xD4, 0xA2, 0xAF, 0x9C, 0xA4, 0x72, 0xC0,
|
||||
0xB7, 0xFD, 0x93, 0x26, 0x36, 0x3F, 0xF7, 0xCC, 0x34, 0xA5, 0xE5, 0xF1, 0x71, 0xD8, 0x31, 0x15,
|
||||
0x04, 0xC7, 0x23, 0xC3, 0x18, 0x96, 0x05, 0x9A, 0x07, 0x12, 0x80, 0xE2, 0xEB, 0x27, 0xB2, 0x75,
|
||||
0x09, 0x83, 0x2C, 0x1A, 0x1B, 0x6E, 0x5A, 0xA0, 0x52, 0x3B, 0xD6, 0xB3, 0x29, 0xE3, 0x2F, 0x84,
|
||||
0x53, 0xD1, 0x00, 0xED, 0x20, 0xFC, 0xB1, 0x5B, 0x6A, 0xCB, 0xBE, 0x39, 0x4A, 0x4C, 0x58, 0xCF,
|
||||
0xD0, 0xEF, 0xAA, 0xFB, 0x43, 0x4D, 0x33, 0x85, 0x45, 0xF9, 0x02, 0x7F, 0x50, 0x3C, 0x9F, 0xA8,
|
||||
0x51, 0xA3, 0x40, 0x8F, 0x92, 0x9D, 0x38, 0xF5, 0xBC, 0xB6, 0xDA, 0x21, 0x10, 0xFF, 0xF3, 0xD2,
|
||||
0xCD, 0x0C, 0x13, 0xEC, 0x5F, 0x97, 0x44, 0x17, 0xC4, 0xA7, 0x7E, 0x3D, 0x64, 0x5D, 0x19, 0x73,
|
||||
0x60, 0x81, 0x4F, 0xDC, 0x22, 0x2A, 0x90, 0x88, 0x46, 0xEE, 0xB8, 0x14, 0xDE, 0x5E, 0x0B, 0xDB,
|
||||
0xE0, 0x32, 0x3A, 0x0A, 0x49, 0x06, 0x24, 0x5C, 0xC2, 0xD3, 0xAC, 0x62, 0x91, 0x95, 0xE4, 0x79,
|
||||
0xE7, 0xC8, 0x37, 0x6D, 0x8D, 0xD5, 0x4E, 0xA9, 0x6C, 0x56, 0xF4, 0xEA, 0x65, 0x7A, 0xAE, 0x08,
|
||||
0xBA, 0x78, 0x25, 0x2E, 0x1C, 0xA6, 0xB4, 0xC6, 0xE8, 0xDD, 0x74, 0x1F, 0x4B, 0xBD, 0x8B, 0x8A,
|
||||
0x70, 0x3E, 0xB5, 0x66, 0x48, 0x03, 0xF6, 0x0E, 0x61, 0x35, 0x57, 0xB9, 0x86, 0xC1, 0x1D, 0x9E,
|
||||
0xE1, 0xF8, 0x98, 0x11, 0x69, 0xD9, 0x8E, 0x94, 0x9B, 0x1E, 0x87, 0xE9, 0xCE, 0x55, 0x28, 0xDF,
|
||||
0x8C, 0xA1, 0x89, 0x0D, 0xBF, 0xE6, 0x42, 0x68, 0x41, 0x99, 0x2D, 0x0F, 0xB0, 0x54, 0xBB, 0x16,
|
||||
};
|
||||
|
||||
static const uint8_t inv_s_box[256] = {
|
||||
0x52, 0x09, 0x6A, 0xD5, 0x30, 0x36, 0xA5, 0x38, 0xBF, 0x40, 0xA3, 0x9E, 0x81, 0xF3, 0xD7, 0xFB,
|
||||
0x7C, 0xE3, 0x39, 0x82, 0x9B, 0x2F, 0xFF, 0x87, 0x34, 0x8E, 0x43, 0x44, 0xC4, 0xDE, 0xE9, 0xCB,
|
||||
0x54, 0x7B, 0x94, 0x32, 0xA6, 0xC2, 0x23, 0x3D, 0xEE, 0x4C, 0x95, 0x0B, 0x42, 0xFA, 0xC3, 0x4E,
|
||||
0x08, 0x2E, 0xA1, 0x66, 0x28, 0xD9, 0x24, 0xB2, 0x76, 0x5B, 0xA2, 0x49, 0x6D, 0x8B, 0xD1, 0x25,
|
||||
0x72, 0xF8, 0xF6, 0x64, 0x86, 0x68, 0x98, 0x16, 0xD4, 0xA4, 0x5C, 0xCC, 0x5D, 0x65, 0xB6, 0x92,
|
||||
0x6C, 0x70, 0x48, 0x50, 0xFD, 0xED, 0xB9, 0xDA, 0x5E, 0x15, 0x46, 0x57, 0xA7, 0x8D, 0x9D, 0x84,
|
||||
0x90, 0xD8, 0xAB, 0x00, 0x8C, 0xBC, 0xD3, 0x0A, 0xF7, 0xE4, 0x58, 0x05, 0xB8, 0xB3, 0x45, 0x06,
|
||||
0xD0, 0x2C, 0x1E, 0x8F, 0xCA, 0x3F, 0x0F, 0x02, 0xC1, 0xAF, 0xBD, 0x03, 0x01, 0x13, 0x8A, 0x6B,
|
||||
0x3A, 0x91, 0x11, 0x41, 0x4F, 0x67, 0xDC, 0xEA, 0x97, 0xF2, 0xCF, 0xCE, 0xF0, 0xB4, 0xE6, 0x73,
|
||||
0x96, 0xAC, 0x74, 0x22, 0xE7, 0xAD, 0x35, 0x85, 0xE2, 0xF9, 0x37, 0xE8, 0x1C, 0x75, 0xDF, 0x6E,
|
||||
0x47, 0xF1, 0x1A, 0x71, 0x1D, 0x29, 0xC5, 0x89, 0x6F, 0xB7, 0x62, 0x0E, 0xAA, 0x18, 0xBE, 0x1B,
|
||||
0xFC, 0x56, 0x3E, 0x4B, 0xC6, 0xD2, 0x79, 0x20, 0x9A, 0xDB, 0xC0, 0xFE, 0x78, 0xCD, 0x5A, 0xF4,
|
||||
0x1F, 0xDD, 0xA8, 0x33, 0x88, 0x07, 0xC7, 0x31, 0xB1, 0x12, 0x10, 0x59, 0x27, 0x80, 0xEC, 0x5F,
|
||||
0x60, 0x51, 0x7F, 0xA9, 0x19, 0xB5, 0x4A, 0x0D, 0x2D, 0xE5, 0x7A, 0x9F, 0x93, 0xC9, 0x9C, 0xEF,
|
||||
0xA0, 0xE0, 0x3B, 0x4D, 0xAE, 0x2A, 0xF5, 0xB0, 0xC8, 0xEB, 0xBB, 0x3C, 0x83, 0x53, 0x99, 0x61,
|
||||
0x17, 0x2B, 0x04, 0x7E, 0xBA, 0x77, 0xD6, 0x26, 0xE1, 0x69, 0x14, 0x63, 0x55, 0x21, 0x0C, 0x7D,
|
||||
};
|
||||
|
||||
static const uint32_t mix_col[] = {
|
||||
0x00000000, 0x03010102, 0x06020204, 0x05030306, 0x0C040408, 0x0F05050A, 0x0A06060C, 0x0907070E,
|
||||
0x18080810, 0x1B090912, 0x1E0A0A14, 0x1D0B0B16, 0x140C0C18, 0x170D0D1A, 0x120E0E1C, 0x110F0F1E,
|
||||
0x30101020, 0x33111122, 0x36121224, 0x35131326, 0x3C141428, 0x3F15152A, 0x3A16162C, 0x3917172E,
|
||||
0x28181830, 0x2B191932, 0x2E1A1A34, 0x2D1B1B36, 0x241C1C38, 0x271D1D3A, 0x221E1E3C, 0x211F1F3E,
|
||||
0x60202040, 0x63212142, 0x66222244, 0x65232346, 0x6C242448, 0x6F25254A, 0x6A26264C, 0x6927274E,
|
||||
0x78282850, 0x7B292952, 0x7E2A2A54, 0x7D2B2B56, 0x742C2C58, 0x772D2D5A, 0x722E2E5C, 0x712F2F5E,
|
||||
0x50303060, 0x53313162, 0x56323264, 0x55333366, 0x5C343468, 0x5F35356A, 0x5A36366C, 0x5937376E,
|
||||
0x48383870, 0x4B393972, 0x4E3A3A74, 0x4D3B3B76, 0x443C3C78, 0x473D3D7A, 0x423E3E7C, 0x413F3F7E,
|
||||
0xC0404080, 0xC3414182, 0xC6424284, 0xC5434386, 0xCC444488, 0xCF45458A, 0xCA46468C, 0xC947478E,
|
||||
0xD8484890, 0xDB494992, 0xDE4A4A94, 0xDD4B4B96, 0xD44C4C98, 0xD74D4D9A, 0xD24E4E9C, 0xD14F4F9E,
|
||||
0xF05050A0, 0xF35151A2, 0xF65252A4, 0xF55353A6, 0xFC5454A8, 0xFF5555AA, 0xFA5656AC, 0xF95757AE,
|
||||
0xE85858B0, 0xEB5959B2, 0xEE5A5AB4, 0xED5B5BB6, 0xE45C5CB8, 0xE75D5DBA, 0xE25E5EBC, 0xE15F5FBE,
|
||||
0xA06060C0, 0xA36161C2, 0xA66262C4, 0xA56363C6, 0xAC6464C8, 0xAF6565CA, 0xAA6666CC, 0xA96767CE,
|
||||
0xB86868D0, 0xBB6969D2, 0xBE6A6AD4, 0xBD6B6BD6, 0xB46C6CD8, 0xB76D6DDA, 0xB26E6EDC, 0xB16F6FDE,
|
||||
0x907070E0, 0x937171E2, 0x967272E4, 0x957373E6, 0x9C7474E8, 0x9F7575EA, 0x9A7676EC, 0x997777EE,
|
||||
0x887878F0, 0x8B7979F2, 0x8E7A7AF4, 0x8D7B7BF6, 0x847C7CF8, 0x877D7DFA, 0x827E7EFC, 0x817F7FFE,
|
||||
0x9B80801B, 0x98818119, 0x9D82821F, 0x9E83831D, 0x97848413, 0x94858511, 0x91868617, 0x92878715,
|
||||
0x8388880B, 0x80898909, 0x858A8A0F, 0x868B8B0D, 0x8F8C8C03, 0x8C8D8D01, 0x898E8E07, 0x8A8F8F05,
|
||||
0xAB90903B, 0xA8919139, 0xAD92923F, 0xAE93933D, 0xA7949433, 0xA4959531, 0xA1969637, 0xA2979735,
|
||||
0xB398982B, 0xB0999929, 0xB59A9A2F, 0xB69B9B2D, 0xBF9C9C23, 0xBC9D9D21, 0xB99E9E27, 0xBA9F9F25,
|
||||
0xFBA0A05B, 0xF8A1A159, 0xFDA2A25F, 0xFEA3A35D, 0xF7A4A453, 0xF4A5A551, 0xF1A6A657, 0xF2A7A755,
|
||||
0xE3A8A84B, 0xE0A9A949, 0xE5AAAA4F, 0xE6ABAB4D, 0xEFACAC43, 0xECADAD41, 0xE9AEAE47, 0xEAAFAF45,
|
||||
0xCBB0B07B, 0xC8B1B179, 0xCDB2B27F, 0xCEB3B37D, 0xC7B4B473, 0xC4B5B571, 0xC1B6B677, 0xC2B7B775,
|
||||
0xD3B8B86B, 0xD0B9B969, 0xD5BABA6F, 0xD6BBBB6D, 0xDFBCBC63, 0xDCBDBD61, 0xD9BEBE67, 0xDABFBF65,
|
||||
0x5BC0C09B, 0x58C1C199, 0x5DC2C29F, 0x5EC3C39D, 0x57C4C493, 0x54C5C591, 0x51C6C697, 0x52C7C795,
|
||||
0x43C8C88B, 0x40C9C989, 0x45CACA8F, 0x46CBCB8D, 0x4FCCCC83, 0x4CCDCD81, 0x49CECE87, 0x4ACFCF85,
|
||||
0x6BD0D0BB, 0x68D1D1B9, 0x6DD2D2BF, 0x6ED3D3BD, 0x67D4D4B3, 0x64D5D5B1, 0x61D6D6B7, 0x62D7D7B5,
|
||||
0x73D8D8AB, 0x70D9D9A9, 0x75DADAAF, 0x76DBDBAD, 0x7FDCDCA3, 0x7CDDDDA1, 0x79DEDEA7, 0x7ADFDFA5,
|
||||
0x3BE0E0DB, 0x38E1E1D9, 0x3DE2E2DF, 0x3EE3E3DD, 0x37E4E4D3, 0x34E5E5D1, 0x31E6E6D7, 0x32E7E7D5,
|
||||
0x23E8E8CB, 0x20E9E9C9, 0x25EAEACF, 0x26EBEBCD, 0x2FECECC3, 0x2CEDEDC1, 0x29EEEEC7, 0x2AEFEFC5,
|
||||
0x0BF0F0FB, 0x08F1F1F9, 0x0DF2F2FF, 0x0EF3F3FD, 0x07F4F4F3, 0x04F5F5F1, 0x01F6F6F7, 0x02F7F7F5,
|
||||
0x13F8F8EB, 0x10F9F9E9, 0x15FAFAEF, 0x16FBFBED, 0x1FFCFCE3, 0x1CFDFDE1, 0x19FEFEE7, 0x1AFFFFE5,
|
||||
};
|
||||
|
||||
static const uint32_t inv_mix_col[] = {
|
||||
0x00000000, 0x0B0D090E, 0x161A121C, 0x1D171B12, 0x2C342438, 0x27392D36, 0x3A2E3624, 0x31233F2A,
|
||||
0x58684870, 0x5365417E, 0x4E725A6C, 0x457F5362, 0x745C6C48, 0x7F516546, 0x62467E54, 0x694B775A,
|
||||
0xB0D090E0, 0xBBDD99EE, 0xA6CA82FC, 0xADC78BF2, 0x9CE4B4D8, 0x97E9BDD6, 0x8AFEA6C4, 0x81F3AFCA,
|
||||
0xE8B8D890, 0xE3B5D19E, 0xFEA2CA8C, 0xF5AFC382, 0xC48CFCA8, 0xCF81F5A6, 0xD296EEB4, 0xD99BE7BA,
|
||||
0x7BBB3BDB, 0x70B632D5, 0x6DA129C7, 0x66AC20C9, 0x578F1FE3, 0x5C8216ED, 0x41950DFF, 0x4A9804F1,
|
||||
0x23D373AB, 0x28DE7AA5, 0x35C961B7, 0x3EC468B9, 0x0FE75793, 0x04EA5E9D, 0x19FD458F, 0x12F04C81,
|
||||
0xCB6BAB3B, 0xC066A235, 0xDD71B927, 0xD67CB029, 0xE75F8F03, 0xEC52860D, 0xF1459D1F, 0xFA489411,
|
||||
0x9303E34B, 0x980EEA45, 0x8519F157, 0x8E14F859, 0xBF37C773, 0xB43ACE7D, 0xA92DD56F, 0xA220DC61,
|
||||
0xF66D76AD, 0xFD607FA3, 0xE07764B1, 0xEB7A6DBF, 0xDA595295, 0xD1545B9B, 0xCC434089, 0xC74E4987,
|
||||
0xAE053EDD, 0xA50837D3, 0xB81F2CC1, 0xB31225CF, 0x82311AE5, 0x893C13EB, 0x942B08F9, 0x9F2601F7,
|
||||
0x46BDE64D, 0x4DB0EF43, 0x50A7F451, 0x5BAAFD5F, 0x6A89C275, 0x6184CB7B, 0x7C93D069, 0x779ED967,
|
||||
0x1ED5AE3D, 0x15D8A733, 0x08CFBC21, 0x03C2B52F, 0x32E18A05, 0x39EC830B, 0x24FB9819, 0x2FF69117,
|
||||
0x8DD64D76, 0x86DB4478, 0x9BCC5F6A, 0x90C15664, 0xA1E2694E, 0xAAEF6040, 0xB7F87B52, 0xBCF5725C,
|
||||
0xD5BE0506, 0xDEB30C08, 0xC3A4171A, 0xC8A91E14, 0xF98A213E, 0xF2872830, 0xEF903322, 0xE49D3A2C,
|
||||
0x3D06DD96, 0x360BD498, 0x2B1CCF8A, 0x2011C684, 0x1132F9AE, 0x1A3FF0A0, 0x0728EBB2, 0x0C25E2BC,
|
||||
0x656E95E6, 0x6E639CE8, 0x737487FA, 0x78798EF4, 0x495AB1DE, 0x4257B8D0, 0x5F40A3C2, 0x544DAACC,
|
||||
0xF7DAEC41, 0xFCD7E54F, 0xE1C0FE5D, 0xEACDF753, 0xDBEEC879, 0xD0E3C177, 0xCDF4DA65, 0xC6F9D36B,
|
||||
0xAFB2A431, 0xA4BFAD3F, 0xB9A8B62D, 0xB2A5BF23, 0x83868009, 0x888B8907, 0x959C9215, 0x9E919B1B,
|
||||
0x470A7CA1, 0x4C0775AF, 0x51106EBD, 0x5A1D67B3, 0x6B3E5899, 0x60335197, 0x7D244A85, 0x7629438B,
|
||||
0x1F6234D1, 0x146F3DDF, 0x097826CD, 0x02752FC3, 0x335610E9, 0x385B19E7, 0x254C02F5, 0x2E410BFB,
|
||||
0x8C61D79A, 0x876CDE94, 0x9A7BC586, 0x9176CC88, 0xA055F3A2, 0xAB58FAAC, 0xB64FE1BE, 0xBD42E8B0,
|
||||
0xD4099FEA, 0xDF0496E4, 0xC2138DF6, 0xC91E84F8, 0xF83DBBD2, 0xF330B2DC, 0xEE27A9CE, 0xE52AA0C0,
|
||||
0x3CB1477A, 0x37BC4E74, 0x2AAB5566, 0x21A65C68, 0x10856342, 0x1B886A4C, 0x069F715E, 0x0D927850,
|
||||
0x64D90F0A, 0x6FD40604, 0x72C31D16, 0x79CE1418, 0x48ED2B32, 0x43E0223C, 0x5EF7392E, 0x55FA3020,
|
||||
0x01B79AEC, 0x0ABA93E2, 0x17AD88F0, 0x1CA081FE, 0x2D83BED4, 0x268EB7DA, 0x3B99ACC8, 0x3094A5C6,
|
||||
0x59DFD29C, 0x52D2DB92, 0x4FC5C080, 0x44C8C98E, 0x75EBF6A4, 0x7EE6FFAA, 0x63F1E4B8, 0x68FCEDB6,
|
||||
0xB1670A0C, 0xBA6A0302, 0xA77D1810, 0xAC70111E, 0x9D532E34, 0x965E273A, 0x8B493C28, 0x80443526,
|
||||
0xE90F427C, 0xE2024B72, 0xFF155060, 0xF418596E, 0xC53B6644, 0xCE366F4A, 0xD3217458, 0xD82C7D56,
|
||||
0x7A0CA137, 0x7101A839, 0x6C16B32B, 0x671BBA25, 0x5638850F, 0x5D358C01, 0x40229713, 0x4B2F9E1D,
|
||||
0x2264E947, 0x2969E049, 0x347EFB5B, 0x3F73F255, 0x0E50CD7F, 0x055DC471, 0x184ADF63, 0x1347D66D,
|
||||
0xCADC31D7, 0xC1D138D9, 0xDCC623CB, 0xD7CB2AC5, 0xE6E815EF, 0xEDE51CE1, 0xF0F207F3, 0xFBFF0EFD,
|
||||
0x92B479A7, 0x99B970A9, 0x84AE6BBB, 0x8FA362B5, 0xBE805D9F, 0xB58D5491, 0xA89A4F83, 0xA397468D,
|
||||
};
|
||||
|
||||
namespace {
|
||||
PrjRijdaelTest prj_rijdael_test_obj;
|
||||
}
|
||||
|
||||
extern bool cpu_caps_aes_ni; // Added
|
||||
|
||||
static void prj_rij_inv_mix_columns(uint32_t* key);
|
||||
|
||||
static void prj_rij_mix_columns_add_round_key(prj_rijndael_detail::StateUnion* state, const uint32_t* key);
|
||||
static void prj_rij_inv_mix_columns_add_round_key(prj_rijndael_detail::StateUnion* state, const uint32_t* key);
|
||||
|
||||
static void prj_rij_sub_bytes_shift_rows(prj_rijndael_detail::StateUnion* state);
|
||||
static void prj_rij_inv_sub_bytes_shift_rows(prj_rijndael_detail::StateUnion* state);
|
||||
|
||||
static uint32_t prj_rij_mix_columns(uint32_t word);
|
||||
static uint32_t prj_rij_inv_mix_columns(uint32_t word);
|
||||
static uint32_t prj_rij_rot_word(uint32_t word);
|
||||
static uint32_t prj_rij_sub_word(uint32_t word);
|
||||
|
||||
void prj_rij_gkey(PrjRijKeyParam* kp, size_t nb, size_t nk, const void* key) {
|
||||
*kp = {};
|
||||
kp->num_key = (uint32_t)nk;
|
||||
kp->num_block = (uint32_t)nb;
|
||||
if (nk == prj::Rijndael_Nk128)
|
||||
kp->num_round = prj::Rijndael_Nr128;
|
||||
else if (nk == prj::Rijndael_Nk192)
|
||||
kp->num_round = prj::Rijndael_Nr192;
|
||||
else
|
||||
kp->num_round = prj::Rijndael_Nr256;
|
||||
|
||||
memmove(kp->enc_key, key, nk * sizeof(uint32_t));
|
||||
|
||||
for (size_t i = nk; i < prj::Rijndael_Nb * (kp->num_round + 1ULL); i++) {
|
||||
uint32_t temp = kp->enc_key[i - 1];
|
||||
if (!(i % nk))
|
||||
temp = prj_rij_sub_word(prj_rij_rot_word(temp)) ^ r_con[i / nk];
|
||||
else if (nk > 6 && (i % nk) == 4)
|
||||
temp = prj_rij_sub_word(temp);
|
||||
|
||||
kp->enc_key[i] = kp->enc_key[i - nk] ^ temp;
|
||||
}
|
||||
|
||||
for (size_t i = 0; i < prj::Rijndael_Nb * (kp->num_round + 1ULL); i++)
|
||||
kp->dec_key[i] = kp->enc_key[i];
|
||||
|
||||
for (uint32_t i = 1; i < kp->num_round; i++)
|
||||
prj_rij_inv_mix_columns(&kp->dec_key[prj::Rijndael_Nb * i]);
|
||||
}
|
||||
|
||||
void prj_rij_decrypt(PrjRijKeyParam* kp, const void* in_buff16, void* out_buff16) {
|
||||
if (cpu_caps_aes_ni) { // Added
|
||||
__m128i* dec_key = (__m128i*)kp->dec_key;
|
||||
__m128i m = _mm_loadu_si128((__m128i*)in_buff16);
|
||||
m = _mm_xor_si128(m, dec_key[kp->num_round]);
|
||||
|
||||
for (uint32_t i = 1, j = kp->num_round - 1; i < kp->num_round; i++, j--)
|
||||
m = _mm_aesdec_si128(m, dec_key[j]);
|
||||
|
||||
m = _mm_aesdeclast_si128(m, dec_key[0]);
|
||||
_mm_storeu_si128((__m128i*)out_buff16, m);
|
||||
return;
|
||||
}
|
||||
|
||||
prj_rijndael_detail::StateUnion state;
|
||||
memcpy(state.byte, in_buff16, prj::Rijndael_Nb * sizeof(uint32_t));
|
||||
|
||||
uint32_t* dec_key = &kp->dec_key[prj::Rijndael_Nb * kp->num_round];
|
||||
for (size_t i = 0; i < prj::Rijndael_Nb; i++)
|
||||
state.word[i] ^= dec_key[i];
|
||||
|
||||
for (uint32_t i = 1, j = kp->num_round - 1; i < kp->num_round; i++, j--) {
|
||||
prj_rij_inv_sub_bytes_shift_rows(&state);
|
||||
prj_rij_inv_mix_columns_add_round_key(&state, &kp->dec_key[prj::Rijndael_Nb * j]);
|
||||
}
|
||||
|
||||
prj_rij_inv_sub_bytes_shift_rows(&state);
|
||||
|
||||
for (size_t i = 0; i < prj::Rijndael_Nb; i++)
|
||||
state.word[i] ^= kp->dec_key[i];
|
||||
|
||||
memcpy(out_buff16, state.byte, prj::Rijndael_Nb * sizeof(uint32_t));
|
||||
}
|
||||
|
||||
void prj_rij_encrypt(PrjRijKeyParam* kp, const void* in_buff16, void* out_buff16) {
|
||||
if (cpu_caps_aes_ni) { // Added
|
||||
const __m128i* enc_key = (const __m128i*)kp->enc_key;
|
||||
__m128i m = _mm_loadu_si128((__m128i*)in_buff16);
|
||||
m = _mm_xor_si128(m, enc_key[0]);
|
||||
|
||||
for (uint32_t i = 1; i < kp->num_round; i++)
|
||||
m = _mm_aesenc_si128(m, enc_key[i]);
|
||||
|
||||
m = _mm_aesenclast_si128(m, enc_key[kp->num_round]);
|
||||
_mm_storeu_si128((__m128i*)out_buff16, m);
|
||||
return;
|
||||
}
|
||||
|
||||
prj_rijndael_detail::StateUnion state;
|
||||
memcpy(state.byte, in_buff16, prj::Rijndael_Nb * sizeof(uint32_t));
|
||||
|
||||
for (size_t i = 0; i < prj::Rijndael_Nb; i++)
|
||||
state.word[i] ^= kp->dec_key[i];
|
||||
|
||||
for (uint32_t i = 1; i < kp->num_round; i++) {
|
||||
prj_rij_sub_bytes_shift_rows(&state);
|
||||
prj_rij_mix_columns_add_round_key(&state, &kp->enc_key[prj::Rijndael_Nb * i]);
|
||||
}
|
||||
|
||||
prj_rij_sub_bytes_shift_rows(&state);
|
||||
|
||||
uint32_t* enc_key = &kp->dec_key[prj::Rijndael_Nb * kp->num_round];
|
||||
for (size_t i = 0; i < prj::Rijndael_Nb; i++)
|
||||
state.word[i] ^= enc_key[i];
|
||||
|
||||
memcpy(out_buff16, state.byte, prj::Rijndael_Nb * sizeof(uint32_t));
|
||||
}
|
||||
|
||||
void prj_rij_test_encrypt_decrypt(PrjRijKeyParam* kp, const void* plain) {
|
||||
uint8_t encoded[16];
|
||||
uint8_t decoded[16];
|
||||
|
||||
prj_rij_encrypt(kp, plain, encoded);
|
||||
prj_rij_decrypt(kp, encoded, decoded);
|
||||
}
|
||||
|
||||
PrjRijdaelTest::PrjRijdaelTest() {
|
||||
test();
|
||||
}
|
||||
|
||||
void PrjRijdaelTest::test() {
|
||||
static const uint8_t key[] = {
|
||||
0x00,
|
||||
0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
|
||||
0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F,
|
||||
0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
|
||||
0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F,
|
||||
};
|
||||
|
||||
static const uint8_t plain[] = {
|
||||
0x00, 0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77,
|
||||
0x88, 0x99, 0xAA, 0xBB, 0xCC, 0xDD, 0xEE, 0xFF,
|
||||
};
|
||||
|
||||
{
|
||||
prj::Rijndael kp128(prj::Rijndael_Nb, prj::Rijndael_Nk128, &key[0x01]);
|
||||
kp128.test_encrypt_decrypt(plain);
|
||||
}
|
||||
|
||||
{
|
||||
prj::Rijndael kp192(prj::Rijndael_Nb, prj::Rijndael_Nk192, &key[0x01]);
|
||||
kp192.test_encrypt_decrypt(plain);
|
||||
}
|
||||
|
||||
{
|
||||
prj::Rijndael kp256(prj::Rijndael_Nb, prj::Rijndael_Nk256, &key[0x01]);
|
||||
kp256.test_encrypt_decrypt(plain);
|
||||
}
|
||||
}
|
||||
|
||||
static void prj_rij_inv_mix_columns(uint32_t* key) {
|
||||
for (size_t i = 0; i < prj::Rijndael_Nb; i++)
|
||||
key[i] = prj_rij_inv_mix_columns(key[i]);
|
||||
}
|
||||
|
||||
static void prj_rij_mix_columns_add_round_key(prj_rijndael_detail::StateUnion* state, const uint32_t* key) {
|
||||
for (size_t i = 0; i < prj::Rijndael_Nb; i++)
|
||||
state->word[i] = prj_rij_mix_columns(state->word[i]) ^ key[i];
|
||||
}
|
||||
|
||||
static void prj_rij_inv_mix_columns_add_round_key(prj_rijndael_detail::StateUnion* state, const uint32_t* key) {
|
||||
for (size_t i = 0; i < prj::Rijndael_Nb; i++)
|
||||
state->word[i] = prj_rij_inv_mix_columns(state->word[i]) ^ key[i];
|
||||
}
|
||||
|
||||
static void prj_rij_sub_bytes_shift_rows(prj_rijndael_detail::StateUnion* state) {
|
||||
uint8_t temp, temp1, temp2;
|
||||
|
||||
state->byte[0x00] = s_box[state->byte[0x00]];
|
||||
state->byte[0x04] = s_box[state->byte[0x04]];
|
||||
state->byte[0x08] = s_box[state->byte[0x08]];
|
||||
state->byte[0x0C] = s_box[state->byte[0x0C]];
|
||||
|
||||
temp1 = s_box[state->byte[0x01]];
|
||||
state->byte[0x01] = s_box[state->byte[0x05]];
|
||||
state->byte[0x05] = s_box[state->byte[0x09]];
|
||||
temp2 = s_box[state->byte[0x0D]];
|
||||
state->byte[0x0D] = temp1;
|
||||
state->byte[0x09] = temp2;
|
||||
|
||||
temp = s_box[state->byte[0x0A]];
|
||||
state->byte[0x0A] = s_box[state->byte[0x02]];
|
||||
state->byte[0x02] = temp;
|
||||
|
||||
temp = s_box[state->byte[0x0E]];
|
||||
state->byte[0x0E] = s_box[state->byte[0x06]];
|
||||
state->byte[0x06] = temp;
|
||||
|
||||
temp1 = s_box[state->byte[0x0F]];
|
||||
state->byte[0x0F] = s_box[state->byte[0x0B]];
|
||||
state->byte[0x0B] = s_box[state->byte[0x07]];
|
||||
temp2 = s_box[state->byte[0x03]];
|
||||
state->byte[0x03] = temp1;
|
||||
state->byte[0x07] = temp2;
|
||||
}
|
||||
|
||||
static void prj_rij_inv_sub_bytes_shift_rows(prj_rijndael_detail::StateUnion* state) {
|
||||
uint8_t temp, temp1, temp2;
|
||||
|
||||
state->byte[0x00] = inv_s_box[state->byte[0x00]];
|
||||
state->byte[0x04] = inv_s_box[state->byte[0x04]];
|
||||
state->byte[0x08] = inv_s_box[state->byte[0x08]];
|
||||
state->byte[0x0C] = inv_s_box[state->byte[0x0C]];
|
||||
|
||||
temp1 = inv_s_box[state->byte[0x0D]];
|
||||
state->byte[0x0D] = inv_s_box[state->byte[0x09]];
|
||||
state->byte[0x09] = inv_s_box[state->byte[0x05]];
|
||||
temp2 = inv_s_box[state->byte[0x01]];
|
||||
state->byte[0x01] = temp1;
|
||||
state->byte[0x05] = temp2;
|
||||
|
||||
temp = inv_s_box[state->byte[0x06]];
|
||||
state->byte[0x06] = inv_s_box[state->byte[0x0E]];
|
||||
state->byte[0x0E] = temp;
|
||||
|
||||
temp = inv_s_box[state->byte[0x02]];
|
||||
state->byte[0x02] = inv_s_box[state->byte[0x0A]];
|
||||
state->byte[0x0A] = temp;
|
||||
|
||||
temp1 = inv_s_box[state->byte[0x03]];
|
||||
state->byte[0x03] = inv_s_box[state->byte[0x07]];
|
||||
state->byte[0x07] = inv_s_box[state->byte[0x0B]];
|
||||
temp2 = inv_s_box[state->byte[0x0F]];
|
||||
state->byte[0x0F] = temp1;
|
||||
state->byte[0x0B] = temp2;
|
||||
}
|
||||
|
||||
inline static uint32_t prj_rij_mix_columns(uint32_t word) {
|
||||
return mix_col[word & 0xFFu] ^ _rotl(mix_col[(word >> 8u) & 0xFFu], 8u)
|
||||
^ _rotl(mix_col[(word >> 16u) & 0xFFu], 16u) ^ _rotr(mix_col[(word >> 24u) & 0xFFu], 8u);
|
||||
}
|
||||
|
||||
inline static uint32_t prj_rij_inv_mix_columns(uint32_t word) {
|
||||
return inv_mix_col[word & 0xFFu] ^ _rotl(inv_mix_col[(word >> 8u) & 0xFFu], 8u)
|
||||
^ _rotl(inv_mix_col[(word >> 16u) & 0xFFu], 16u) ^ _rotr(inv_mix_col[(word >> 24u) & 0xFFu], 8u);
|
||||
}
|
||||
|
||||
inline static uint32_t prj_rij_rot_word(uint32_t word) {
|
||||
return _rotr(word, 8);
|
||||
}
|
||||
|
||||
inline static uint32_t prj_rij_sub_word(uint32_t word) {
|
||||
return (((((s_box[(word >> 24u) & 0xFFu] << 8u) | s_box[(word >> 16u) & 0xFFu]) << 8u)
|
||||
| s_box[(word >> 8u) & 0xFFu]) << 8u) | s_box[word & 0xFF];
|
||||
}
|
||||
@@ -0,0 +1,84 @@
|
||||
/*
|
||||
by korenkonder
|
||||
GitHub/GitLab: korenkonder
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "../default.hpp"
|
||||
|
||||
namespace prj {
|
||||
static constexpr size_t Rijndael_Nb = 4;
|
||||
|
||||
static constexpr uint32_t Rijndael_Nk128 = 4;
|
||||
static constexpr uint32_t Rijndael_Nr128 = 10;
|
||||
static constexpr uint32_t Rijndael_Nk192 = 6;
|
||||
static constexpr uint32_t Rijndael_Nr192 = 12;
|
||||
static constexpr uint32_t Rijndael_Nk256 = 8;
|
||||
static constexpr uint32_t Rijndael_Nr256 = 14;
|
||||
|
||||
static constexpr size_t Rijndael_Nlen = Rijndael_Nb * sizeof(uint32_t);
|
||||
}
|
||||
|
||||
struct alignas(prj::Rijndael_Nlen) PrjRijKeyParam {
|
||||
uint32_t num_key;
|
||||
uint32_t num_round;
|
||||
uint32_t num_block;
|
||||
uint32_t pad0;
|
||||
uint32_t enc_key[(prj::Rijndael_Nr256 + 1ULL) * prj::Rijndael_Nb];
|
||||
uint32_t dec_key[(prj::Rijndael_Nr256 + 1ULL) * prj::Rijndael_Nb];
|
||||
uint32_t pad1[4];
|
||||
};
|
||||
|
||||
static_assert(offsetof(PrjRijKeyParam, enc_key) % prj::Rijndael_Nlen == 0, "\"PrjRijKeyParam\" struct should have \"enc_key\" field aligned to prj::Rijndael_Nlen");
|
||||
static_assert(offsetof(PrjRijKeyParam, dec_key) % prj::Rijndael_Nlen == 0, "\"PrjRijKeyParam\" struct should have \"dec_key\" field aligned to prj::Rijndael_Nlen");
|
||||
|
||||
namespace prj {
|
||||
class Rijndael {
|
||||
PrjRijKeyParam M_kp;
|
||||
|
||||
public:
|
||||
Rijndael();
|
||||
Rijndael(size_t nb, size_t nk, const void* key);
|
||||
|
||||
void encrypt16(const void* in_buff16, void* out_buff16);
|
||||
void encrypt16(void* buff16);
|
||||
void decrypt16(const void* in_buff16, void* out_buff16);
|
||||
void decrypt16(void* buff16);
|
||||
|
||||
void test_encrypt_decrypt(const void* plain);
|
||||
};
|
||||
}
|
||||
|
||||
extern void prj_rij_gkey(PrjRijKeyParam* kp, size_t nb, size_t nk, const void* key);
|
||||
extern void prj_rij_decrypt(PrjRijKeyParam* kp, const void* in_buff16, void* out_buff16);
|
||||
extern void prj_rij_encrypt(PrjRijKeyParam* kp, const void* in_buff16, void* out_buff16);
|
||||
extern void prj_rij_test_encrypt_decrypt(PrjRijKeyParam* kp, const void* plain);
|
||||
|
||||
namespace prj {
|
||||
inline Rijndael::Rijndael() : M_kp() { }
|
||||
|
||||
inline Rijndael::Rijndael(size_t nb, size_t nk, const void* key) : M_kp() {
|
||||
prj_rij_gkey(&M_kp, nb, nk, key);
|
||||
}
|
||||
|
||||
inline void Rijndael::encrypt16(const void* in_buff16, void* out_buff16) {
|
||||
prj_rij_encrypt(&M_kp, in_buff16, out_buff16);
|
||||
}
|
||||
|
||||
inline void Rijndael::encrypt16(void* buff16) {
|
||||
prj_rij_encrypt(&M_kp, buff16, buff16);
|
||||
}
|
||||
|
||||
inline void Rijndael::decrypt16(const void* in_buff16, void* out_buff16) {
|
||||
prj_rij_decrypt(&M_kp, in_buff16, out_buff16);
|
||||
}
|
||||
|
||||
inline void Rijndael::decrypt16(void* buff16) {
|
||||
prj_rij_decrypt(&M_kp, buff16, buff16);
|
||||
}
|
||||
|
||||
inline void Rijndael::test_encrypt_decrypt(const void* plain) {
|
||||
prj_rij_test_encrypt_decrypt(&M_kp, plain);
|
||||
}
|
||||
}
|
||||
@@ -6,7 +6,7 @@
|
||||
#include "x_save.hpp"
|
||||
#include "f2/header.hpp"
|
||||
#include "io/file_stream.hpp"
|
||||
#include "aes.hpp"
|
||||
#include "prj/rijndael.hpp"
|
||||
#include "deflate.hpp"
|
||||
|
||||
static const uint8_t savedata_key[] = {
|
||||
@@ -171,9 +171,9 @@ static bool x_save_decode(std::vector<uint8_t>& data, void*& dec, size_t& dec_le
|
||||
uint8_t* section_data = head->get_section_data();
|
||||
uint32_t section_size = head->get_section_size();
|
||||
if (section_data && section_size == align_val(section_size, 0x20)) {
|
||||
aes256_ctx aes;
|
||||
aes256_init_ctx(&aes, savedata_key);
|
||||
aes256_ecb_decrypt_buffer(&aes, section_data, section_size);
|
||||
prj::Rijndael rijndael(prj::Rijndael_Nb, prj::Rijndael_Nk256, savedata_key);
|
||||
for (size_t i = 0; i < section_size; i += prj::Rijndael_Nlen)
|
||||
rijndael.decrypt16(section_data + i);
|
||||
head->attrib.set_aes(false);
|
||||
}
|
||||
}
|
||||
@@ -270,9 +270,9 @@ static bool x_save_encode(std::vector<uint8_t>& data, void*& enc, x_save_encode_
|
||||
uint8_t* section_data = head->get_section_data();
|
||||
uint32_t section_size = head->get_section_size();
|
||||
if (section_data && section_size == align_val(section_size, 0x20)) {
|
||||
aes256_ctx aes;
|
||||
aes256_init_ctx(&aes, savedata_key);
|
||||
aes256_ecb_encrypt_buffer(&aes, section_data, section_size);
|
||||
prj::Rijndael rijndael(prj::Rijndael_Nb, prj::Rijndael_Nk256, savedata_key);
|
||||
for (size_t i = 0; i < section_size; i += prj::Rijndael_Nlen)
|
||||
rijndael.encrypt16(section_data + i);
|
||||
head->attrib.set_aes(true);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -10,7 +10,7 @@
|
||||
#include "../KKdLib/default.hpp"
|
||||
#include "../KKdLib/io/file_stream.hpp"
|
||||
#include "../KKdLib/io/path.hpp"
|
||||
#include "../KKdLib/aes.hpp"
|
||||
#include "../KKdLib/prj/rijndael.hpp"
|
||||
#include "../KKdLib/str_utils.hpp"
|
||||
#include <intrin.h>
|
||||
|
||||
@@ -67,8 +67,7 @@ int32_t wmain(int32_t argc, wchar_t** argv) {
|
||||
cpu_caps_aes_ni = (cpuid_data[2] & (1 << 25)) ? true : false;
|
||||
cpu_caps_f16c = (cpuid_data[2] & (1 << 29)) ? true : false;
|
||||
|
||||
aes256_ctx ctx;
|
||||
aes256_init_ctx(&ctx, mmplus_key);
|
||||
prj::Rijndael rijndael(prj::Rijndael_Nb, prj::Rijndael_Nk256, mmplus_key);
|
||||
|
||||
{
|
||||
std::vector<std::wstring> files = path_get_files(indir.c_str());
|
||||
@@ -85,7 +84,9 @@ int32_t wmain(int32_t argc, wchar_t** argv) {
|
||||
if (in_file.check_not_null() && out_file.check_not_null()) {
|
||||
printf(encrypt ? "Encrypting %ls\n" : "Decrypting %ls\n", i.c_str());
|
||||
|
||||
aes256_ctx_set_iv(&ctx, mmplus_iv);
|
||||
uint8_t iv[prj::Rijndael_Nlen];
|
||||
uint8_t next_iv[prj::Rijndael_Nlen];
|
||||
memcpy(iv, mmplus_iv, prj::Rijndael_Nlen);
|
||||
|
||||
size_t length = in_file.get_length();
|
||||
|
||||
@@ -100,7 +101,13 @@ int32_t wmain(int32_t argc, wchar_t** argv) {
|
||||
size += align;
|
||||
}
|
||||
|
||||
aes256_cbc_encrypt_buffer(&ctx, buf, size);
|
||||
for (size_t j = 0; j < size; j += prj::Rijndael_Nlen) {
|
||||
for (uint32_t k = 0; k < prj::Rijndael_Nlen / sizeof(uint32_t); k++)
|
||||
((uint32_t*)(buf + j))[k] ^= ((uint32_t*)iv)[k];
|
||||
rijndael.encrypt16(buf + j);
|
||||
memcpy(iv, buf + j, prj::Rijndael_Nlen);
|
||||
}
|
||||
|
||||
out_file.write(buf, size);
|
||||
|
||||
length -= min_def(length, size);
|
||||
@@ -108,7 +115,13 @@ int32_t wmain(int32_t argc, wchar_t** argv) {
|
||||
}
|
||||
else {
|
||||
while (length && (size = in_file.read_data(buf))) {
|
||||
aes256_cbc_decrypt_buffer(&ctx, buf, size);
|
||||
for (size_t j = 0; j < size; j += prj::Rijndael_Nlen) {
|
||||
memcpy(next_iv, buf + j, prj::Rijndael_Nlen);
|
||||
rijndael.decrypt16(buf + j);
|
||||
for (uint32_t k = 0; k < prj::Rijndael_Nlen / sizeof(uint32_t); k++)
|
||||
((uint32_t*)(buf + j))[k] ^= ((uint32_t*)iv)[k];
|
||||
memcpy(iv, next_iv, prj::Rijndael_Nlen);
|
||||
}
|
||||
|
||||
if (length == size) // PKCS7 Padding
|
||||
size -= buf[size - 1];
|
||||
@@ -145,7 +158,9 @@ int32_t wmain(int32_t argc, wchar_t** argv) {
|
||||
if (in_file.check_not_null() && out_file.check_not_null()) {
|
||||
printf(encrypt ? "Encrypting %ls\\%ls\n" : "Decrypting %ls\\%ls\n", i.c_str(), j.c_str());
|
||||
|
||||
aes256_ctx_set_iv(&ctx, mmplus_iv);
|
||||
uint8_t iv[prj::Rijndael_Nlen];
|
||||
uint8_t next_iv[prj::Rijndael_Nlen];
|
||||
memcpy(iv, mmplus_iv, prj::Rijndael_Nlen);
|
||||
|
||||
size_t length = in_file.get_length();
|
||||
|
||||
@@ -160,7 +175,13 @@ int32_t wmain(int32_t argc, wchar_t** argv) {
|
||||
size += align;
|
||||
}
|
||||
|
||||
aes256_cbc_encrypt_buffer(&ctx, buf, size);
|
||||
for (size_t j = 0; j < size; j += prj::Rijndael_Nlen) {
|
||||
for (uint32_t k = 0; k < prj::Rijndael_Nlen / sizeof(uint32_t); k++)
|
||||
((uint32_t*)(buf + j))[k] ^= ((uint32_t*)iv)[k];
|
||||
rijndael.encrypt16(buf + j);
|
||||
memcpy(iv, buf + j, prj::Rijndael_Nlen);
|
||||
}
|
||||
|
||||
out_file.write(buf, size);
|
||||
|
||||
length -= size;
|
||||
@@ -168,7 +189,13 @@ int32_t wmain(int32_t argc, wchar_t** argv) {
|
||||
}
|
||||
else {
|
||||
while (length && (size = in_file.read_data(buf))) {
|
||||
aes256_cbc_decrypt_buffer(&ctx, buf, size);
|
||||
for (size_t j = 0; j < size; j += prj::Rijndael_Nlen) {
|
||||
memcpy(next_iv, buf + j, prj::Rijndael_Nlen);
|
||||
rijndael.decrypt16(buf + j);
|
||||
for (uint32_t k = 0; k < prj::Rijndael_Nlen / sizeof(uint32_t); k++)
|
||||
((uint32_t*)(buf + j))[k] ^= ((uint32_t*)iv)[k];
|
||||
memcpy(iv, next_iv, prj::Rijndael_Nlen);
|
||||
}
|
||||
|
||||
if (length == size) // PKCS7 Padding
|
||||
size -= buf[size - 1];
|
||||
|
||||
@@ -35,7 +35,7 @@
|
||||
#if BAKE_X_PACK
|
||||
#include "../KKdLib/f2/header.hpp"
|
||||
#include "../KKdLib/io/memory_stream.hpp"
|
||||
#include "../KKdLib/aes.hpp"
|
||||
#include "../KKdLib/prj/rijndael.hpp"
|
||||
#include "../KKdLib/deflate.hpp"
|
||||
#include "../KKdLib/waitable_timer.hpp"
|
||||
#include <meshoptimizer/meshoptimizer.h>
|
||||
@@ -10005,9 +10005,18 @@ void obj_set_reflect::pack_file(void** data, size_t* size, bool mmp,
|
||||
for (uint32_t i = 0; i < 0x10; i += sizeof(uint32_t))
|
||||
*(uint32_t*)(iv + i) = rand_state_array_get_int(4);
|
||||
|
||||
aes256_ctx aes;
|
||||
aes256_init_ctx_iv(&aes, key, iv);
|
||||
aes256_cbc_encrypt_buffer(&aes, section_data, section_size);
|
||||
|
||||
prj::Rijndael rijndael(prj::Rijndael_Nb, prj::Rijndael_Nk128, key);
|
||||
|
||||
uint8_t _iv[prj::Rijndael_Nlen];
|
||||
memcpy(_iv, iv, prj::Rijndael_Nlen);
|
||||
for (size_t i = 0; i < section_size; i += prj::Rijndael_Nlen) {
|
||||
for (uint32_t j = 0; j < prj::Rijndael_Nlen / sizeof(uint32_t); j++)
|
||||
((uint32_t*)(section_data + i))[j] ^= ((uint32_t*)_iv)[j];
|
||||
rijndael.encrypt16(section_data + i);
|
||||
memcpy(_iv, section_data + i, prj::Rijndael_Nlen);
|
||||
}
|
||||
|
||||
head->attrib.set_aes(true);
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user