Camellia
Documentation |
#include <cryptopp/camellia.h>
|
Camellia is a block cipher developed by Mitsubishi Electric Corporation and Nippon Telegraph and Telephone. The cipher has been approved for use by the ISO/IEC, the European Union's NESSIE project, the Japanese CRYPTREC project, and the Internet Engineering Task Force. The Camellia homepage is located at http://info.isl.ntt.co.jp/crypt/eng/camellia/index.html.
Note: if your project is using encryption alone to secure your data, encryption alone is usually not enough. Please take a moment to read Authenticated Encryption and consider using an algorithm or mode like CCM, GCM, EAX or ChaCha20Poly1305.
Sample Programs
There are three sample programs. The first shows Camellia key and block sizes. The second and third use filters in a pipeline). Pipelining is a high level abstraction and it handles buffering input, buffering output and padding for you.
If you are benchmarking then you may want to visit Benchmarks | Sample Program . It shows you how to use StreamTransformation::ProcessString
method to process blocks at a time. Calling a cipher's ProcessString
or ProcessBlock
eventually call a cipher's ProcessAndXorBlock
or AdvancedProcessBlocks
, and they are the lowest level API you can use.
The first example dumps the minimum, maximum, and default key lengths used by Camellia.
cout << "key length: " << Camellia::DEFAULT_KEYLENGTH << endl; cout << "key length (min): " << Camellia::MIN_KEYLENGTH << endl; cout << "key length (max): " << Camellia::MAX_KEYLENGTH << endl; cout << "block size: " << Camellia::BLOCKSIZE << endl;
Output from the above snippet produces the following. Notice the default key size is 128 bits or 16 bytes.
key length: 16 key length (min): 16 key length (max): 32 block size: 16
The following program shows how to operate Camellia in CBC mode using a pipeline. The key is declared on the stack using a SecByteBlock to ensure the sensitive material is zeroized. Similar could be used for both plain text and recovered text.
AutoSeededRandomPool prng; SecByteBlock key(Camellia::DEFAULT_KEYLENGTH); prng.GenerateBlock(key, key.size()); byte iv[Camellia::BLOCKSIZE]; prng.GenerateBlock(iv, sizeof(iv)); string plain = "CBC Mode Test"; string cipher, encoded, recovered; /*********************************\ \*********************************/ try { cout << "plain text: " << plain << endl; CBC_Mode< Camellia >::Encryption e; e.SetKeyWithIV(key, key.size(), iv); // The StreamTransformationFilter adds padding // as required. ECB and CBC Mode must be padded // to the block size of the cipher. StringSource(plain, true, new StreamTransformationFilter(e, new StringSink(cipher) ) // StreamTransformationFilter ); // StringSource } catch(const CryptoPP::Exception& e) { cerr << e.what() << endl; exit(1); } /*********************************\ \*********************************/ // Pretty print StringSource(cipher, true, new HexEncoder( new StringSink(encoded) ) // HexEncoder ); // StringSource cout << "cipher text: " << encoded << endl; /*********************************\ \*********************************/ try { CBC_Mode< Camellia >::Decryption d; d.SetKeyWithIV(key, key.size(), iv); // The StreamTransformationFilter removes // padding as required. StringSource s(cipher, true, new StreamTransformationFilter(d, new StringSink(recovered) ) // StreamTransformationFilter ); // StringSource cout << "recovered text: " << recovered << endl; } catch(const CryptoPP::Exception& e) { cerr << e.what() << endl; exit(1); }
A typical output is shown below. Note that each run will produce different results because the key and initialization vector are randomly generated.
$ ./Driver.exe key: EF98BD050835282701B4BD705C6C5285 iv: AEF2C9A2ADF0C657BF83145174CB41FD plain text: CBC Mode Test cipher text: 0728F7E36ABE75477749EFAA2B8ADF37 recovered text: CBC Mode Test
By switching to EAX mode, authenticity assurances can placed on the cipher text for nearly no programming costs. Below the StreamTransformationFilter was replaced by AuthenticatedEncryptionFilter and AuthenticatedDecryptionFilter.
EAX< Camellia >::Encryption e; e.SetKeyWithIV(key, key.size(), iv); StringSource(plain, true, new AuthenticatedEncryptionFilter(e, new StringSink(cipher) ) // StreamTransformationFilter ); // StringSource ... EAX< Camellia >::Decryption d; d.SetKeyWithIV(key, key.size(), iv); StringSource s(cipher, true, new AuthenticatedDecryptionFilter(d, new StringSink(recovered) ) // StreamTransformationFilter ); // StringSource
Typical output is as follows. Notice the additional cipher text bytes due to the MAC bytes. See EAX Mode for details.
$ ./Driver.exe key: 11E8A2B52D8D14D5220679B5313F4B2F iv: 98CB3FF05F61170C4E15EEC30DE324B7 plain text: EAX Mode Test cipher text: DA83FBA29CA6E8DD3A15F5795340732CD089CF43F17A5109D22C8B2CA4 recovered text: EAX Mode Test
To manually insert bytes into the filter, perform multiple Put
s. Though Get
is used below, a StringSink
could easily be attached and save the administrivia.
const size_t SIZE = 16 * 4; string plain(SIZE, 0x00); for(size_t i = 0; i < plain.size(); i++) plain[i] = 'A' + (i%26); ... CBC_Mode < Camellia >::Encryption encryption(key, sizeof(key), iv); StreamTransformationFilter encryptor(encryption, NULL); for(size_t j = 0; j < plain.size(); j++) encryptor.Put((byte)plain[j]); encryptor.MessageEnd(); size_t ready = encryptor.MaxRetrievable(); string cipher(ready, 0x00); encryptor.Get((byte*) &cipher[0], cipher.size());
Downloads
Camellia-CBC-Filter.zip - Demonstrates encryption and decryption using Camellia in CBC mode with filters (confidentiality only)
Camellia-CTR-Filter.zip - Demonstrates encryption and decryption using Camellia in CTR mode with filters (confidentiality only)
Camellia-GCM-Filter.zip - Demonstrates encryption and decryption using Camellia in GCM mode with filters (confidentiality and authenticity)
Camellia-EAX-Filter.zip - Demonstrates encryption and decryption using Camellia in EAX mode with filters (confidentiality and authenticity)