void aesCfbDecrypt(uint8_t *key, int32_t keyLength, uint8_t* IV, uint8_t *data, int32_t dataLength) { AESencrypt *saAes = new AESencrypt(); if (keyLength == 16) saAes->key128(key); else if (keyLength == 32) saAes->key256(key); else return; // Note: maybe copy IV to an internal array if we encounter strange things. // the cfb encrypt modify the IV on return. Same for output data (inplace encryption) saAes->cfb_decrypt(data, data, dataLength, IV); delete saAes; }
int32_t zina::aesCbcEncrypt(const string& key, const string& IV, const string& plainText, string* cryptText) { LOGGER(DEBUGGING, __func__, " -->"); if (IV.size() != AES_BLOCK_SIZE) { LOGGER(ERROR, __func__, " <-- IV wrong block size."); return WRONG_BLK_SIZE; } size_t padlen = (AES_BLOCK_SIZE - plainText.size() % AES_BLOCK_SIZE); // data.append(padlen, padlen); uint8_t* outBuffer = new uint8_t[plainText.size() + padlen]; memcpy(outBuffer, plainText.data(), plainText.size()); memset(outBuffer + plainText.size(), static_cast<int>(padlen&0xff), padlen); // pad to full blocksize uint8_t ivTemp[AES_BLOCK_SIZE]; // copy IV, AES code modifies IV buffer memcpy(ivTemp, IV.data(), AES_BLOCK_SIZE); AESencrypt aes; if (key.size() == 16) aes.key128((const uint8_t*)key.data()); else if (key.size() == 32) aes.key256((const uint8_t*)key.data()); else { LOGGER(ERROR, __func__, " <-- Unsupported key size: ", key.size()); delete[] outBuffer; return UNSUPPORTED_KEY_SIZE; } // Encrypt in place aes.cbc_encrypt(outBuffer, outBuffer, static_cast<int>(plainText.size() + padlen), ivTemp); cryptText->assign((const char*)outBuffer, plainText.size() + padlen); delete[] outBuffer; LOGGER(DEBUGGING, __func__, " <--"); return SUCCESS; }
void Sekrit::DoEncrypt(const Plaintext& plaintext) { const size_t roundedsize = util::roundup(plaintext.size(), aes_blocksize); assert(plaintext.size() <= std::numeric_limits<unsigned>::max()); assert(roundedsize <= std::numeric_limits<unsigned>::max()); m_impl->header.realsize = static_cast<unsigned>( plaintext.size() ); m_impl->header.size = static_cast<unsigned>( roundedsize ); m_impl->data.resize( m_impl->header.size ); // Fill CBC-mode InitializationVector with random bytes. Notice that we use // a "tempiv" and don't just work on header.iv, since cbc_encrypt works directly // on the buffer (which would leave us with a modified IV in the header - bad.) unsigned char tempiv[sizeof(m_impl->header.iv)]; util::fill_random( m_impl->header.iv, sizeof(m_impl->header.iv) ); memcpy(tempiv, m_impl->header.iv, sizeof(tempiv) ); AESencrypt crypt; crypt.key256(m_impl->key); crypt.cbc_encrypt(static_cast<unsigned char*>(plaintext.data()), &m_impl->data[0], m_impl->header.size, tempiv); }