Only in /var/lib/copr-rpmbuild/results/i2pd-git/srpm-unpacked/i2pd-openssl.tar.gz-extract/i2pd-openssl/libi2pd: CPU.cpp diff -U2 -r /var/lib/copr-rpmbuild/results/i2pd-git/upstream-unpacked/Source0/i2pd-openssl/libi2pd/CPU.h /var/lib/copr-rpmbuild/results/i2pd-git/srpm-unpacked/i2pd-openssl.tar.gz-extract/i2pd-openssl/libi2pd/CPU.h --- /var/lib/copr-rpmbuild/results/i2pd-git/upstream-unpacked/Source0/i2pd-openssl/libi2pd/CPU.h 2024-12-07 01:25:22.000000000 +0000 +++ /var/lib/copr-rpmbuild/results/i2pd-git/srpm-unpacked/i2pd-openssl.tar.gz-extract/i2pd-openssl/libi2pd/CPU.h 2024-12-07 01:15:25.000000000 +0000 @@ -1,4 +1,4 @@ /* -* Copyright (c) 2013-2024, The PurpleI2P Project +* Copyright (c) 2013-2023, The PurpleI2P Project * * This file is part of Purple i2pd project and licensed under BSD3 @@ -22,3 +22,19 @@ #endif +#if defined(__AES__) && !defined(_MSC_VER) && IS_X86 +# define SUPPORTS_AES 1 +#else +# define SUPPORTS_AES 0 +#endif + +namespace i2p +{ +namespace cpu +{ + extern bool aesni; + + void Detect(bool AesSwitch, bool force); +} +} + #endif diff -U2 -r /var/lib/copr-rpmbuild/results/i2pd-git/upstream-unpacked/Source0/i2pd-openssl/libi2pd/Crypto.cpp /var/lib/copr-rpmbuild/results/i2pd-git/srpm-unpacked/i2pd-openssl.tar.gz-extract/i2pd-openssl/libi2pd/Crypto.cpp --- /var/lib/copr-rpmbuild/results/i2pd-git/upstream-unpacked/Source0/i2pd-openssl/libi2pd/Crypto.cpp 2024-12-07 01:25:22.000000000 +0000 +++ /var/lib/copr-rpmbuild/results/i2pd-git/srpm-unpacked/i2pd-openssl.tar.gz-extract/i2pd-openssl/libi2pd/Crypto.cpp 2024-12-07 01:15:25.000000000 +0000 @@ -20,5 +20,4 @@ #include #endif -#include "CPU.h" #include "Crypto.h" #include "Ed25519.h" @@ -517,103 +516,427 @@ // AES - ECBEncryption::ECBEncryption () +#if SUPPORTS_AES + #define KeyExpansion256(round0,round1) \ + "pshufd $0xff, %%xmm2, %%xmm2 \n" \ + "movaps %%xmm1, %%xmm4 \n" \ + "pslldq $4, %%xmm4 \n" \ + "pxor %%xmm4, %%xmm1 \n" \ + "pslldq $4, %%xmm4 \n" \ + "pxor %%xmm4, %%xmm1 \n" \ + "pslldq $4, %%xmm4 \n" \ + "pxor %%xmm4, %%xmm1 \n" \ + "pxor %%xmm2, %%xmm1 \n" \ + "movaps %%xmm1, "#round0"(%[sched]) \n" \ + "aeskeygenassist $0, %%xmm1, %%xmm4 \n" \ + "pshufd $0xaa, %%xmm4, %%xmm2 \n" \ + "movaps %%xmm3, %%xmm4 \n" \ + "pslldq $4, %%xmm4 \n" \ + "pxor %%xmm4, %%xmm3 \n" \ + "pslldq $4, %%xmm4 \n" \ + "pxor %%xmm4, %%xmm3 \n" \ + "pslldq $4, %%xmm4 \n" \ + "pxor %%xmm4, %%xmm3 \n" \ + "pxor %%xmm2, %%xmm3 \n" \ + "movaps %%xmm3, "#round1"(%[sched]) \n" +#endif + +#if SUPPORTS_AES + void ECBCryptoAESNI::ExpandKey (const AESKey& key) { - m_Ctx = EVP_CIPHER_CTX_new (); + __asm__ + ( + "movups (%[key]), %%xmm1 \n" + "movups 16(%[key]), %%xmm3 \n" + "movaps %%xmm1, (%[sched]) \n" + "movaps %%xmm3, 16(%[sched]) \n" + "aeskeygenassist $1, %%xmm3, %%xmm2 \n" + KeyExpansion256(32,48) + "aeskeygenassist $2, %%xmm3, %%xmm2 \n" + KeyExpansion256(64,80) + "aeskeygenassist $4, %%xmm3, %%xmm2 \n" + KeyExpansion256(96,112) + "aeskeygenassist $8, %%xmm3, %%xmm2 \n" + KeyExpansion256(128,144) + "aeskeygenassist $16, %%xmm3, %%xmm2 \n" + KeyExpansion256(160,176) + "aeskeygenassist $32, %%xmm3, %%xmm2 \n" + KeyExpansion256(192,208) + "aeskeygenassist $64, %%xmm3, %%xmm2 \n" + // key expansion final + "pshufd $0xff, %%xmm2, %%xmm2 \n" + "movaps %%xmm1, %%xmm4 \n" + "pslldq $4, %%xmm4 \n" + "pxor %%xmm4, %%xmm1 \n" + "pslldq $4, %%xmm4 \n" + "pxor %%xmm4, %%xmm1 \n" + "pslldq $4, %%xmm4 \n" + "pxor %%xmm4, %%xmm1 \n" + "pxor %%xmm2, %%xmm1 \n" + "movups %%xmm1, 224(%[sched]) \n" + : // output + : [key]"r"((const uint8_t *)key), [sched]"r"(GetKeySchedule ()) // input + : "%xmm1", "%xmm2", "%xmm3", "%xmm4", "memory" // clogged + ); } - - ECBEncryption::~ECBEncryption () - { - if (m_Ctx) - EVP_CIPHER_CTX_free (m_Ctx); - } - - void ECBEncryption::Encrypt (const uint8_t * in, uint8_t * out) +#endif + + +#if SUPPORTS_AES + #define EncryptAES256(sched) \ + "pxor (%["#sched"]), %%xmm0 \n" \ + "aesenc 16(%["#sched"]), %%xmm0 \n" \ + "aesenc 32(%["#sched"]), %%xmm0 \n" \ + "aesenc 48(%["#sched"]), %%xmm0 \n" \ + "aesenc 64(%["#sched"]), %%xmm0 \n" \ + "aesenc 80(%["#sched"]), %%xmm0 \n" \ + "aesenc 96(%["#sched"]), %%xmm0 \n" \ + "aesenc 112(%["#sched"]), %%xmm0 \n" \ + "aesenc 128(%["#sched"]), %%xmm0 \n" \ + "aesenc 144(%["#sched"]), %%xmm0 \n" \ + "aesenc 160(%["#sched"]), %%xmm0 \n" \ + "aesenc 176(%["#sched"]), %%xmm0 \n" \ + "aesenc 192(%["#sched"]), %%xmm0 \n" \ + "aesenc 208(%["#sched"]), %%xmm0 \n" \ + "aesenclast 224(%["#sched"]), %%xmm0 \n" +#endif + + void ECBEncryption::Encrypt (const ChipherBlock * in, ChipherBlock * out) { - EVP_EncryptInit_ex (m_Ctx, EVP_aes_256_ecb(), NULL, m_Key, NULL); - EVP_CIPHER_CTX_set_padding (m_Ctx, 0); - int len; - EVP_EncryptUpdate (m_Ctx, out, &len, in, 16); - EVP_EncryptFinal_ex (m_Ctx, out + len, &len); +#if SUPPORTS_AES + if(i2p::cpu::aesni) + { + __asm__ + ( + "movups (%[in]), %%xmm0 \n" + EncryptAES256(sched) + "movups %%xmm0, (%[out]) \n" + : + : [sched]"r"(GetKeySchedule ()), [in]"r"(in), [out]"r"(out) + : "%xmm0", "memory" + ); + } + else +#endif + { + AES_encrypt (in->buf, out->buf, &m_Key); + } } - ECBDecryption::ECBDecryption () +#if SUPPORTS_AES + #define DecryptAES256(sched) \ + "pxor 224(%["#sched"]), %%xmm0 \n" \ + "aesdec 208(%["#sched"]), %%xmm0 \n" \ + "aesdec 192(%["#sched"]), %%xmm0 \n" \ + "aesdec 176(%["#sched"]), %%xmm0 \n" \ + "aesdec 160(%["#sched"]), %%xmm0 \n" \ + "aesdec 144(%["#sched"]), %%xmm0 \n" \ + "aesdec 128(%["#sched"]), %%xmm0 \n" \ + "aesdec 112(%["#sched"]), %%xmm0 \n" \ + "aesdec 96(%["#sched"]), %%xmm0 \n" \ + "aesdec 80(%["#sched"]), %%xmm0 \n" \ + "aesdec 64(%["#sched"]), %%xmm0 \n" \ + "aesdec 48(%["#sched"]), %%xmm0 \n" \ + "aesdec 32(%["#sched"]), %%xmm0 \n" \ + "aesdec 16(%["#sched"]), %%xmm0 \n" \ + "aesdeclast (%["#sched"]), %%xmm0 \n" +#endif + + void ECBDecryption::Decrypt (const ChipherBlock * in, ChipherBlock * out) { - m_Ctx = EVP_CIPHER_CTX_new (); +#if SUPPORTS_AES + if(i2p::cpu::aesni) + { + __asm__ + ( + "movups (%[in]), %%xmm0 \n" + DecryptAES256(sched) + "movups %%xmm0, (%[out]) \n" + : + : [sched]"r"(GetKeySchedule ()), [in]"r"(in), [out]"r"(out) + : "%xmm0", "memory" + ); + } + else +#endif + { + AES_decrypt (in->buf, out->buf, &m_Key); + } } - - ECBDecryption::~ECBDecryption () - { - if (m_Ctx) - EVP_CIPHER_CTX_free (m_Ctx); - } - - void ECBDecryption::Decrypt (const uint8_t * in, uint8_t * out) + +#if SUPPORTS_AES + #define CallAESIMC(offset) \ + "movaps "#offset"(%[shed]), %%xmm0 \n" \ + "aesimc %%xmm0, %%xmm0 \n" \ + "movaps %%xmm0, "#offset"(%[shed]) \n" +#endif + + void ECBEncryption::SetKey (const AESKey& key) { - EVP_DecryptInit_ex (m_Ctx, EVP_aes_256_ecb(), NULL, m_Key, NULL); - EVP_CIPHER_CTX_set_padding (m_Ctx, 0); - int len; - EVP_DecryptUpdate (m_Ctx, out, &len, in, 16); - EVP_DecryptFinal_ex (m_Ctx, out + len, &len); +#if SUPPORTS_AES + if(i2p::cpu::aesni) + { + ExpandKey (key); + } + else +#endif + { + AES_set_encrypt_key (key, 256, &m_Key); + } } - - CBCEncryption::CBCEncryption () - { - m_Ctx = EVP_CIPHER_CTX_new (); - //memset ((uint8_t *)m_LastBlock, 0, 16); + void ECBDecryption::SetKey (const AESKey& key) + { +#if SUPPORTS_AES + if(i2p::cpu::aesni) + { + ExpandKey (key); // expand encryption key first + // then invert it using aesimc + __asm__ + ( + CallAESIMC(16) + CallAESIMC(32) + CallAESIMC(48) + CallAESIMC(64) + CallAESIMC(80) + CallAESIMC(96) + CallAESIMC(112) + CallAESIMC(128) + CallAESIMC(144) + CallAESIMC(160) + CallAESIMC(176) + CallAESIMC(192) + CallAESIMC(208) + : + : [shed]"r"(GetKeySchedule ()) + : "%xmm0", "memory" + ); + } + else +#endif + { + AES_set_decrypt_key (key, 256, &m_Key); + } } - - CBCEncryption::~CBCEncryption () + + void CBCEncryption::Encrypt (int numBlocks, const ChipherBlock * in, ChipherBlock * out) { - if (m_Ctx) - EVP_CIPHER_CTX_free (m_Ctx); - } - +#if SUPPORTS_AES + if(i2p::cpu::aesni) + { + __asm__ + ( + "movups (%[iv]), %%xmm1 \n" + "1: \n" + "movups (%[in]), %%xmm0 \n" + "pxor %%xmm1, %%xmm0 \n" + EncryptAES256(sched) + "movaps %%xmm0, %%xmm1 \n" + "movups %%xmm0, (%[out]) \n" + "add $16, %[in] \n" + "add $16, %[out] \n" + "dec %[num] \n" + "jnz 1b \n" + "movups %%xmm1, (%[iv]) \n" + : + : [iv]"r"((uint8_t *)m_LastBlock), [sched]"r"(m_ECBEncryption.GetKeySchedule ()), + [in]"r"(in), [out]"r"(out), [num]"r"(numBlocks) + : "%xmm0", "%xmm1", "cc", "memory" + ); + } + else +#endif + { + for (int i = 0; i < numBlocks; i++) + { + *m_LastBlock.GetChipherBlock () ^= in[i]; + m_ECBEncryption.Encrypt (m_LastBlock.GetChipherBlock (), m_LastBlock.GetChipherBlock ()); + out[i] = *m_LastBlock.GetChipherBlock (); + } + } + } + void CBCEncryption::Encrypt (const uint8_t * in, std::size_t len, uint8_t * out) { // len/16 - EVP_EncryptInit_ex (m_Ctx, EVP_aes_256_cbc(), NULL, m_Key, m_IV); - EVP_CIPHER_CTX_set_padding (m_Ctx, 0); - int l; - EVP_EncryptUpdate (m_Ctx, out, &l, in, len); - EVP_EncryptFinal_ex (m_Ctx, out + l, &l); - } - - CBCDecryption::CBCDecryption () - { - m_Ctx = EVP_CIPHER_CTX_new (); - //memset ((uint8_t *)m_IV, 0, 16); - } - - CBCDecryption::~CBCDecryption () - { - if (m_Ctx) - EVP_CIPHER_CTX_free (m_Ctx); - } - + int numBlocks = len >> 4; + if (numBlocks > 0) + Encrypt (numBlocks, (const ChipherBlock *)in, (ChipherBlock *)out); + } + + void CBCEncryption::Encrypt (const uint8_t * in, uint8_t * out) + { +#if SUPPORTS_AES + if(i2p::cpu::aesni) + { + __asm__ + ( + "movups (%[iv]), %%xmm1 \n" + "movups (%[in]), %%xmm0 \n" + "pxor %%xmm1, %%xmm0 \n" + EncryptAES256(sched) + "movups %%xmm0, (%[out]) \n" + "movups %%xmm0, (%[iv]) \n" + : + : [iv]"r"((uint8_t *)m_LastBlock), [sched]"r"(m_ECBEncryption.GetKeySchedule ()), + [in]"r"(in), [out]"r"(out) + : "%xmm0", "%xmm1", "memory" + ); + } + else +#endif + Encrypt (1, (const ChipherBlock *)in, (ChipherBlock *)out); + } + + void CBCDecryption::Decrypt (int numBlocks, const ChipherBlock * in, ChipherBlock * out) + { +#if SUPPORTS_AES + if(i2p::cpu::aesni) + { + __asm__ + ( + "movups (%[iv]), %%xmm1 \n" + "1: \n" + "movups (%[in]), %%xmm0 \n" + "movaps %%xmm0, %%xmm2 \n" + DecryptAES256(sched) + "pxor %%xmm1, %%xmm0 \n" + "movups %%xmm0, (%[out]) \n" + "movaps %%xmm2, %%xmm1 \n" + "add $16, %[in] \n" + "add $16, %[out] \n" + "dec %[num] \n" + "jnz 1b \n" + "movups %%xmm1, (%[iv]) \n" + : + : [iv]"r"((uint8_t *)m_IV), [sched]"r"(m_ECBDecryption.GetKeySchedule ()), + [in]"r"(in), [out]"r"(out), [num]"r"(numBlocks) + : "%xmm0", "%xmm1", "%xmm2", "cc", "memory" + ); + } + else +#endif + { + for (int i = 0; i < numBlocks; i++) + { + ChipherBlock tmp = in[i]; + m_ECBDecryption.Decrypt (in + i, out + i); + out[i] ^= *m_IV.GetChipherBlock (); + *m_IV.GetChipherBlock () = tmp; + } + } + } + void CBCDecryption::Decrypt (const uint8_t * in, std::size_t len, uint8_t * out) { - // len/16 - EVP_DecryptInit_ex (m_Ctx, EVP_aes_256_cbc(), NULL, m_Key, m_IV); - EVP_CIPHER_CTX_set_padding (m_Ctx, 0); - int l; - EVP_DecryptUpdate (m_Ctx, out, &l, in, len); - EVP_DecryptFinal_ex (m_Ctx, out + l, &l); + int numBlocks = len >> 4; + if (numBlocks > 0) + Decrypt (numBlocks, (const ChipherBlock *)in, (ChipherBlock *)out); + } + + void CBCDecryption::Decrypt (const uint8_t * in, uint8_t * out) + { +#if SUPPORTS_AES + if(i2p::cpu::aesni) + { + __asm__ + ( + "movups (%[iv]), %%xmm1 \n" + "movups (%[in]), %%xmm0 \n" + "movups %%xmm0, (%[iv]) \n" + DecryptAES256(sched) + "pxor %%xmm1, %%xmm0 \n" + "movups %%xmm0, (%[out]) \n" + : + : [iv]"r"((uint8_t *)m_IV), [sched]"r"(m_ECBDecryption.GetKeySchedule ()), + [in]"r"(in), [out]"r"(out) + : "%xmm0", "%xmm1", "memory" + ); + } + else +#endif + Decrypt (1, (const ChipherBlock *)in, (ChipherBlock *)out); } void TunnelEncryption::Encrypt (const uint8_t * in, uint8_t * out) { - m_IVEncryption.Encrypt (in, out); // iv - m_LayerEncryption.SetIV (out); - m_LayerEncryption.Encrypt (in + 16, i2p::tunnel::TUNNEL_DATA_ENCRYPTED_SIZE, out + 16); // data - m_IVEncryption.Encrypt (out, out); // double iv +#if SUPPORTS_AES + if(i2p::cpu::aesni) + { + __asm__ + ( + // encrypt IV + "movups (%[in]), %%xmm0 \n" + EncryptAES256(sched_iv) + "movaps %%xmm0, %%xmm1 \n" + // double IV encryption + EncryptAES256(sched_iv) + "movups %%xmm0, (%[out]) \n" + // encrypt data, IV is xmm1 + "1: \n" + "add $16, %[in] \n" + "add $16, %[out] \n" + "movups (%[in]), %%xmm0 \n" + "pxor %%xmm1, %%xmm0 \n" + EncryptAES256(sched_l) + "movaps %%xmm0, %%xmm1 \n" + "movups %%xmm0, (%[out]) \n" + "dec %[num] \n" + "jnz 1b \n" + : + : [sched_iv]"r"(m_IVEncryption.GetKeySchedule ()), [sched_l]"r"(m_LayerEncryption.ECB().GetKeySchedule ()), + [in]"r"(in), [out]"r"(out), [num]"r"(63) // 63 blocks = 1008 bytes + : "%xmm0", "%xmm1", "cc", "memory" + ); + } + else +#endif + { + m_IVEncryption.Encrypt ((const ChipherBlock *)in, (ChipherBlock *)out); // iv + m_LayerEncryption.SetIV (out); + m_LayerEncryption.Encrypt (in + 16, i2p::tunnel::TUNNEL_DATA_ENCRYPTED_SIZE, out + 16); // data + m_IVEncryption.Encrypt ((ChipherBlock *)out, (ChipherBlock *)out); // double iv + } } void TunnelDecryption::Decrypt (const uint8_t * in, uint8_t * out) { - m_IVDecryption.Decrypt (in, out); // iv - m_LayerDecryption.SetIV (out); - m_LayerDecryption.Decrypt (in + 16, i2p::tunnel::TUNNEL_DATA_ENCRYPTED_SIZE, out + 16); // data - m_IVDecryption.Decrypt (out, out); // double iv +#if SUPPORTS_AES + if(i2p::cpu::aesni) + { + __asm__ + ( + // decrypt IV + "movups (%[in]), %%xmm0 \n" + DecryptAES256(sched_iv) + "movaps %%xmm0, %%xmm1 \n" + // double IV encryption + DecryptAES256(sched_iv) + "movups %%xmm0, (%[out]) \n" + // decrypt data, IV is xmm1 + "1: \n" + "add $16, %[in] \n" + "add $16, %[out] \n" + "movups (%[in]), %%xmm0 \n" + "movaps %%xmm0, %%xmm2 \n" + DecryptAES256(sched_l) + "pxor %%xmm1, %%xmm0 \n" + "movups %%xmm0, (%[out]) \n" + "movaps %%xmm2, %%xmm1 \n" + "dec %[num] \n" + "jnz 1b \n" + : + : [sched_iv]"r"(m_IVDecryption.GetKeySchedule ()), [sched_l]"r"(m_LayerDecryption.ECB().GetKeySchedule ()), + [in]"r"(in), [out]"r"(out), [num]"r"(63) // 63 blocks = 1008 bytes + : "%xmm0", "%xmm1", "%xmm2", "cc", "memory" + ); + } + else +#endif + { + m_IVDecryption.Decrypt ((const ChipherBlock *)in, (ChipherBlock *)out); // iv + m_LayerDecryption.SetIV (out); + m_LayerDecryption.Decrypt (in + 16, i2p::tunnel::TUNNEL_DATA_ENCRYPTED_SIZE, out + 16); // data + m_IVDecryption.Decrypt ((ChipherBlock *)out, (ChipherBlock *)out); // double iv + } } @@ -837,4 +1160,5 @@ void InitCrypto (bool precomputation, bool aesni, bool force) { + i2p::cpu::Detect (aesni, force); /* auto numLocks = CRYPTO_num_locks(); for (int i = 0; i < numLocks; i++) diff -U2 -r /var/lib/copr-rpmbuild/results/i2pd-git/upstream-unpacked/Source0/i2pd-openssl/libi2pd/Crypto.h /var/lib/copr-rpmbuild/results/i2pd-git/srpm-unpacked/i2pd-openssl.tar.gz-extract/i2pd-openssl/libi2pd/Crypto.h --- /var/lib/copr-rpmbuild/results/i2pd-git/upstream-unpacked/Source0/i2pd-openssl/libi2pd/Crypto.h 2024-12-07 01:25:22.000000000 +0000 +++ /var/lib/copr-rpmbuild/results/i2pd-git/srpm-unpacked/i2pd-openssl.tar.gz-extract/i2pd-openssl/libi2pd/Crypto.h 2024-12-07 01:15:25.000000000 +0000 @@ -26,4 +26,5 @@ #include "Base.h" #include "Tag.h" +#include "CPU.h" // recognize openssl version and features @@ -85,36 +86,95 @@ // AES + struct ChipherBlock + { + uint8_t buf[16]; + + void operator^=(const ChipherBlock& other) // XOR + { + if (!(((size_t)buf | (size_t)other.buf) & 0x03)) // multiple of 4 ? + { + for (int i = 0; i < 4; i++) + reinterpret_cast(buf)[i] ^= reinterpret_cast(other.buf)[i]; + } + else + { + for (int i = 0; i < 16; i++) + buf[i] ^= other.buf[i]; + } + } + }; + typedef i2p::data::Tag<32> AESKey; - - class ECBEncryption + + template + class AESAlignedBuffer // 16 bytes alignment + { + public: + + AESAlignedBuffer () + { + m_Buf = m_UnalignedBuffer; + uint8_t rem = ((size_t)m_Buf) & 0x0f; + if (rem) + m_Buf += (16 - rem); + } + + operator uint8_t * () { return m_Buf; }; + operator const uint8_t * () const { return m_Buf; }; + ChipherBlock * GetChipherBlock () { return (ChipherBlock *)m_Buf; }; + const ChipherBlock * GetChipherBlock () const { return (const ChipherBlock *)m_Buf; }; + + private: + + uint8_t m_UnalignedBuffer[sz + 15]; // up to 15 bytes alignment + uint8_t * m_Buf; + }; + + +#if SUPPORTS_AES + class ECBCryptoAESNI { public: - ECBEncryption (); - ~ECBEncryption (); - - void SetKey (const AESKey& key) { m_Key = key; }; - void Encrypt(const uint8_t * in, uint8_t * out); + uint8_t * GetKeySchedule () { return m_KeySchedule; }; + + protected: + + void ExpandKey (const AESKey& key); private: - AESKey m_Key; - EVP_CIPHER_CTX * m_Ctx; + AESAlignedBuffer<240> m_KeySchedule; // 14 rounds for AES-256, 240 bytes }; +#endif +#if SUPPORTS_AES + class ECBEncryption: public ECBCryptoAESNI +#else + class ECBEncryption +#endif + { + public: + + void SetKey (const AESKey& key); + + void Encrypt(const ChipherBlock * in, ChipherBlock * out); + + private: + AES_KEY m_Key; + }; + +#if SUPPORTS_AES + class ECBDecryption: public ECBCryptoAESNI +#else class ECBDecryption +#endif { public: - ECBDecryption (); - ~ECBDecryption (); - - void SetKey (const AESKey& key) { m_Key = key; }; - void Decrypt (const uint8_t * in, uint8_t * out); - - private: - - AESKey m_Key; - EVP_CIPHER_CTX * m_Ctx; + void SetKey (const AESKey& key); + void Decrypt (const ChipherBlock * in, ChipherBlock * out); + private: + AES_KEY m_Key; }; @@ -123,17 +183,21 @@ public: - CBCEncryption (); - ~CBCEncryption (); + CBCEncryption () { memset ((uint8_t *)m_LastBlock, 0, 16); }; - void SetKey (const AESKey& key) { m_Key = key; }; // 32 bytes - void SetIV (const uint8_t * iv) { m_IV = iv; }; // 16 bytes - + void SetKey (const AESKey& key) { m_ECBEncryption.SetKey (key); }; // 32 bytes + void SetIV (const uint8_t * iv) { memcpy ((uint8_t *)m_LastBlock, iv, 16); }; // 16 bytes + void GetIV (uint8_t * iv) const { memcpy (iv, (const uint8_t *)m_LastBlock, 16); }; + + void Encrypt (int numBlocks, const ChipherBlock * in, ChipherBlock * out); void Encrypt (const uint8_t * in, std::size_t len, uint8_t * out); - + void Encrypt (const uint8_t * in, uint8_t * out); // one block + + ECBEncryption & ECB() { return m_ECBEncryption; } + private: - AESKey m_Key; - i2p::data::Tag<16> m_IV; - EVP_CIPHER_CTX * m_Ctx; + AESAlignedBuffer<16> m_LastBlock; + + ECBEncryption m_ECBEncryption; }; @@ -142,17 +206,20 @@ public: - CBCDecryption (); - ~CBCDecryption (); - - void SetKey (const AESKey& key) { m_Key = key; }; // 32 bytes - void SetIV (const uint8_t * iv) { m_IV = iv; }; // 16 bytes + CBCDecryption () { memset ((uint8_t *)m_IV, 0, 16); }; + void SetKey (const AESKey& key) { m_ECBDecryption.SetKey (key); }; // 32 bytes + void SetIV (const uint8_t * iv) { memcpy ((uint8_t *)m_IV, iv, 16); }; // 16 bytes + void GetIV (uint8_t * iv) const { memcpy (iv, (const uint8_t *)m_IV, 16); }; + + void Decrypt (int numBlocks, const ChipherBlock * in, ChipherBlock * out); void Decrypt (const uint8_t * in, std::size_t len, uint8_t * out); + void Decrypt (const uint8_t * in, uint8_t * out); // one block + + ECBDecryption & ECB() { return m_ECBDecryption; } private: - AESKey m_Key; - i2p::data::Tag<16> m_IV; - EVP_CIPHER_CTX * m_Ctx; + AESAlignedBuffer<16> m_IV; + ECBDecryption m_ECBDecryption; }; diff -U2 -r /var/lib/copr-rpmbuild/results/i2pd-git/upstream-unpacked/Source0/i2pd-openssl/libi2pd/NTCP2.cpp /var/lib/copr-rpmbuild/results/i2pd-git/srpm-unpacked/i2pd-openssl.tar.gz-extract/i2pd-openssl/libi2pd/NTCP2.cpp --- /var/lib/copr-rpmbuild/results/i2pd-git/upstream-unpacked/Source0/i2pd-openssl/libi2pd/NTCP2.cpp 2024-12-07 01:25:22.000000000 +0000 +++ /var/lib/copr-rpmbuild/results/i2pd-git/srpm-unpacked/i2pd-openssl.tar.gz-extract/i2pd-openssl/libi2pd/NTCP2.cpp 2024-12-07 01:15:25.000000000 +0000 @@ -123,5 +123,5 @@ encryption.SetIV (m_IV); encryption.Encrypt (GetPub (), 32, m_SessionRequestBuffer); // X - memcpy (m_IV, m_SessionRequestBuffer + 16, 16); // save last block as IV for SessionCreated + encryption.GetIV (m_IV); // save IV for SessionCreated // encryption key for next block if (!KDF1Alice ()) return false; @@ -211,5 +211,5 @@ decryption.SetIV (i2p::context.GetNTCP2IV ()); decryption.Decrypt (m_SessionRequestBuffer, 32, GetRemotePub ()); - memcpy (m_IV, m_SessionRequestBuffer + 16, 16); // save last block as IV for SessionCreated + decryption.GetIV (m_IV); // save IV for SessionCreated // decryption key for next block if (!KDF1Bob ())