pub async fn gcm_aes_decrypt_async<R, W>(
key: &[u8],
iv: &[u8],
reader: R,
writer: W,
aad: &[u8],
mul_fn: &GcmBlockMulFn,
) -> Result<[u8; 16], AesGcmAsyncError>Expand description
Async version of gcm_aes_decrypt that reads from an AsyncRead source and writes to an AsyncWrite destination.
This function provides authenticated decryption using AES-GCM mode with optimized performance for large data streams. It includes comprehensive error handling and input validation.
§Parameters
key- AES cipher key (16, 24, or 32 bytes for AES-128, AES-192, or AES-256)iv- Initialization Vector (at least 1 byte, longer IVs are hashed to 12 bytes)reader- AsyncRead source for cipher text to decrypt and authenticatewriter- AsyncWrite destination for plain textaad- Additional authenticated data (can be empty)mul_fn- Block multiplication function fromGcmBlockMulEnhancement::to_mul_fn()
§Returns
Result<[u8; 16], AesGcmAsyncError>- Authentication tag on success, error on failure
§Errors
InvalidKeySize- Key size is not 16, 24, or 32 bytesInvalidIvSize- IV size is 0 bytesIoError- I/O error during reading or writingCryptoError- Internal cryptographic errorAuthenticationFailed- Authentication tag verification failed
§Security Note
The returned authentication tag should be compared with the expected tag using constant-time comparison. If the tags don’t match, the message has been tampered with or corrupted.
§Examples
§Basic decryption
use crypto_async_rs::aes_gcm::{GcmBlockMulEnhancement};
use crypto_async_rs::aes_gcm_async::{gcm_aes_decrypt_async, AesGcmAsyncError};
use futures::io::Cursor;
async fn example() -> Result<(), AesGcmAsyncError> {
let cipher_key = [0xfe, 0xff, 0xe9, 0x92, 0x86, 0x65, 0x73, 0x1c, 0x6d, 0x6a, 0x8f, 0x94, 0x67, 0x30, 0x83, 0x08];
let iv = [0xca, 0xfe, 0xba, 0xbe, 0xfa, 0xce, 0xdb, 0xad, 0xde, 0xca, 0xf8, 0x88];
let cipher_text = [0x42, 0x83, 0x1e, 0xc2, 0x21, 0x77, 0x74, 0x24, 0x4b, 0x72, 0x21, 0xb7, 0x84, 0xd0, 0xd4, 0x9c];
let aad = [];
let mul_fn = GcmBlockMulEnhancement::None.to_mul_fn(&cipher_key);
let reader = Cursor::new(&cipher_text);
let mut writer = Cursor::new(Vec::new());
let tag = gcm_aes_decrypt_async(&cipher_key, &iv, reader, &mut writer, &aad, &mul_fn).await?;
println!("Authentication tag: {:?}", tag);
Ok(())
}§Authentication verification
use crypto_async_rs::aes_gcm_async::{gcm_aes_decrypt_async, AesGcmAsyncError};
use crypto_async_rs::aes_gcm::GcmBlockMulEnhancement;
use futures::io::Cursor;
async fn verify_authentication() -> Result<(), AesGcmAsyncError> {
let key = [0u8; 16];
let iv = [0u8; 12];
let expected_tag = [0u8; 16];
let cipher_text = b"encrypted data";
let mul_fn = GcmBlockMulEnhancement::None.to_mul_fn(&key);
let reader = Cursor::new(cipher_text);
let mut writer = Cursor::new(Vec::new());
let computed_tag = gcm_aes_decrypt_async(&key, &iv, reader, &mut writer, &[], &mul_fn).await?;
// Constant-time comparison
if computed_tag == expected_tag {
println!("Authentication successful");
} else {
return Err(AesGcmAsyncError::AuthenticationFailed);
}
Ok(())
}