void SHARK::Base::UncheckedSetKey(CipherDir dir, const byte *key, unsigned int keyLen, unsigned int rounds) { AssertValidKeyLength(keyLen); AssertValidRounds(rounds); m_rounds = rounds; m_roundKeys.New(m_rounds+1); // concatenate key enought times to fill a for (unsigned int i=0; i<(m_rounds+1)*8; i++) ((byte *)m_roundKeys.begin())[i] = key[i%keyLen]; SHARK::Encryption e; e.InitForKeySetup(); byte IV[8] = {0,0,0,0,0,0,0,0}; CFB_Mode_ExternalCipher::Encryption cfb(e, IV); cfb.ProcessString((byte *)m_roundKeys.begin(), (m_rounds+1)*8); ConditionalByteReverse(BIG_ENDIAN_ORDER, m_roundKeys.begin(), m_roundKeys.begin(), (m_rounds+1)*8); m_roundKeys[m_rounds] = SHARKTransform(m_roundKeys[m_rounds]); if (dir == DECRYPTION) { unsigned int i; // transform encryption round keys into decryption round keys for (i=0; i<m_rounds/2; i++) std::swap(m_roundKeys[i], m_roundKeys[m_rounds-i]); for (i=1; i<m_rounds; i++) m_roundKeys[i] = SHARKTransform(m_roundKeys[i]); } #ifdef IS_LITTLE_ENDIAN m_roundKeys[0] = ByteReverse(m_roundKeys[0]); m_roundKeys[m_rounds] = ByteReverse(m_roundKeys[m_rounds]); #endif }
// construct an SHARKEncryption object with fixed round keys, to be used to initialize actual round keys SHARKEncryption::SHARKEncryption() : SHARKBase(DEFAULT_ROUNDS) { for (unsigned int i=0; i<DEFAULT_ROUNDS; i++) roundkeys[i] = cbox[0][i]; roundkeys[DEFAULT_ROUNDS] = SHARKTransform(cbox[0][DEFAULT_ROUNDS]); #ifdef IS_LITTLE_ENDIAN roundkeys[0] = byteReverse(roundkeys[0]); roundkeys[DEFAULT_ROUNDS] = byteReverse(roundkeys[DEFAULT_ROUNDS]); #endif }
// construct an SHARK_Enc object with fixed round keys, to be used to initialize actual round keys void SHARK::Enc::InitForKeySetup() { m_rounds = DEFAULT_ROUNDS; m_roundKeys.New(DEFAULT_ROUNDS+1); for (unsigned int i=0; i<DEFAULT_ROUNDS; i++) m_roundKeys[i] = cbox[0][i]; m_roundKeys[DEFAULT_ROUNDS] = SHARKTransform(cbox[0][DEFAULT_ROUNDS]); #ifdef IS_LITTLE_ENDIAN m_roundKeys[0] = ByteReverse(m_roundKeys[0]); m_roundKeys[m_rounds] = ByteReverse(m_roundKeys[m_rounds]); #endif }
void SHARKBase::InitEncryptionRoundKeys(const byte *key, unsigned int keyLen, unsigned int rounds, word64 *roundkeys) { // concatenate key enought times to fill a for (unsigned int i=0; i<(rounds+1)*8; i++) ((byte *)roundkeys)[i] = key[i%keyLen]; SHARKEncryption e; byte IV[8] = {0,0,0,0,0,0,0,0}; CFBEncryption cfb(e, IV); cfb.ProcessString((byte *)roundkeys, (rounds+1)*8); #ifdef IS_LITTLE_ENDIAN byteReverse(roundkeys, roundkeys, (rounds+1)*8); #endif roundkeys[rounds] = SHARKTransform(roundkeys[rounds]); }
SHARKDecryption::SHARKDecryption(const byte *key, unsigned int keyLen, unsigned int rounds) : SHARKBase(rounds) { InitEncryptionRoundKeys(key, keyLen, rounds, roundkeys); unsigned int i; // transform encryption round keys into decryption round keys for (i=0; i<rounds/2; i++) std::swap(roundkeys[i], roundkeys[rounds-i]); for (i=1; i<rounds; i++) roundkeys[i] = SHARKTransform(roundkeys[i]); #ifdef IS_LITTLE_ENDIAN roundkeys[0] = byteReverse(roundkeys[0]); roundkeys[rounds] = byteReverse(roundkeys[rounds]); #endif }