![]() |
![]()
| ![]() |
![]()
NAME
SYNOPSIS
uint64_t
uint32_t
uint64_t
void
DESCRIPTIONThese functions provide an interface for the ChaCha20 encryption primitive. ChaCha20 is a low-level primitive. Consider using authenticated encryption, implemented by crypto_aead_lock(3monocypher). The arguments are:
The key and nonce buffers may overlap. plain_text and cipher_text must either be the same buffer (for in-place encryption) or non-overlapping.
The
Since XOR is its own inverse, decryption is the same operation as encryption. To decrypt the cipher text, “encrypt” it again with the same key and nonce. You will likely want to wipe the key when you are done with encryption or decryption. Use crypto_wipe(3monocypher) to wipe them. The plain_text pointer is allowed
to be RETURN VALUES
EXAMPLESThe following examples assume the existence of
Simple encryption: uint8_t key [ 32]; /* Secret random key */ uint8_t nonce [ 24]; /* Unique nonce (possibly random) */ uint8_t plain_text [500] = {1}; /* Secret message */ uint8_t cipher_text[500]; /* Encrypted message */ arc4random_buf(key, 32); arc4random_buf(nonce, 24); crypto_chacha20_x(cipher_text, plain_text, 500, key, nonce, 0); /* Wipe secrets if they are no longer needed */ crypto_wipe(key, 32); crypto_wipe(plain_text, 500); To decrypt the above: uint8_t key [ 32]; /* Same key as above */ const uint8_t nonce [ 24]; /* Same nonce as above */ uint8_t plain_text [500]; /* Message to decrypt */ uint8_t cipher_text[500]; /* Secret message */ crypto_chacha20_x(cipher_text, plain_text, 500, key, nonce, 0); /* Wipe secrets if they are no longer needed */ crypto_wipe(key, 32); /* The plaintext likely needs to be processed before you wipe it */ crypto_wipe(plain_text, 12); Incremental encryption (in blocks of 64 bytes): uint8_t key [ 32]; /* Secret random key */ uint8_t nonce [ 24]; /* Unique nonce (possibly random) */ uint8_t plain_text [500]; /* Secret message */ uint8_t cipher_text[500]; /* Encrypted message */ uint64_t ctr = 0; /* Block counter */ unsigned int i; arc4random_buf(key, 32); arc4random_buf(nonce, 24); for(i = 0; i < 500; i += 64) { ctr = crypto_chacha20_x(cipher_text+i, plain_text+i, 64, key, nonce, ctr); } /* Process data that didn't fit into 64-byte pieces */ crypto_chacha20_x(cipher_text+500-(i-64), plain_text+500-(i-64), 500-(i-64), key, nonce, ctr); /* Wipe secrets if they are no longer needed */ crypto_wipe(key, 32); crypto_wipe(plain_text, 500); Encryption by jumping around (do not do this, this is only meant to show how the counter works): uint8_t key [ 32]; /* Secret random key */ uint8_t nonce [ 24]; /* Unique nonce (possibly random) */ uint8_t plain_text [500] = {1}; /* Message to be encrypted */ uint8_t cipher_text[500]; /* Will be the encrypted message */ arc4random_buf(key, 32); arc4random_buf(nonce, 24); /* Encrypt the second part of the message first... */ crypto_chacha20_x(cipher_text + (3 * 64), plain_text + (3 * 64), 500 - (3 * 64), key, nonce, 3); /* ...then encrypt the first part */ crypto_chacha20_x(cipher_text, plain_text, 3 * 64, key, nonce, 0); /* Wipe secrets if they are no longer needed */ crypto_wipe(key, 32); crypto_wipe(plain_text, 500); HCHACHA20
The arguments are:
For instance: uint8_t key[32]; /* Must have enough entropy */ uint8_t in [16]; /* Does not have to be random */ uint8_t out[32]; /* Will be random iff the above holds */ arc4random_buf(key, 32); crypto_chacha20_h(out, key, in); /* Wipe secrets if they are no longer needed */ crypto_wipe(key, 32); crypto_wipe(in , 16); SEE ALSOcrypto_aead_lock(3monocypher), crypto_wipe(3monocypher), intro(3monocypher) STANDARDSThese functions implement ChaCha20, XChaCha20, and HChaCha20. ChaCha20 is described in: Daniel J. Bernstein, ChaCha, a variant of Salsa20, SASC 2008 – The State of the Art of Stream Ciphers, pp. 273–278. The nonce and counter sizes were modified in RFC 8439. XChaCha20 derives from ChaCha20 the same way XSalsa20 derives from Salsa20 and benefits from the same security reduction (proven secure as long as ChaCha20 itself is secure). HISTORY
CAVEATSMonocypher does not perform any input validation. Any deviation from the specified input and output length ranges results in undefined behaviour. Make sure your inputs are correct. SECURITY CONSIDERATIONSEncrypted does not mean secureChaCha20 only protects against eavesdropping, not forgeries. Most applications need protection against forgeries to be properly secure. To ensure the integrity of a message, use BLAKE2b in keyed mode or authenticated encryption; see crypto_blake2b(3monocypher) and crypto_aead_lock(3monocypher). Nonce reuseRepeating a nonce with the same key exposes the XOR of two or more plaintext messages, effectively destroying confidentiality. For the same reason,
do not select small nonces at
random. The Secure random number generationDo not use these functions as a cryptographic random number generator. Always use the operating system's random number generator for cryptographic purposes; see intro(3monocypher). Protection against side channelsSecrets should not dwell in memory longer than needed. Use crypto_wipe(3monocypher) to erase secrets you no longer need. For ChaCha20, this means the key and in some cases the plaintext itself.
|