Description
Hi,
GCM accepts the IV of length 0 and can use it to encrypt data. Quoting Wycheproof tests, this should be rejected with an error:
AES-GCM does not allow an IV of length 0. Encrypting with such an IV leaks the authentication key. Hence using an IV of length 0 is insecure even if the key itself is only used for a single encryption.
Here's a piece of code that demonstrates the issue:
module GCM = Nocrypto.Cipher_block.AES.GCM
let pp_result ppf { GCM.message; tag } =
Format.fprintf ppf "Message:\n%a\nTag:\n%a\n" Cstruct.hexdump_pp message
Cstruct.hexdump_pp tag
let () =
let key =
GCM.of_secret
(Cstruct.of_hex "00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f")
in
let iv = Cstruct.empty in
GCM.encrypt ~key ~iv (Cstruct.of_string "hello")
|> Format.printf "%a\n" pp_result
More background:
AES-GCM allows IVs of bit length 1 .. 2^64-1. See NIST SP 800 38d, Section 5.2.1.1
http://nvlpubs.nist.gov/nistpubs/Legacy/SP/nistspecialpublication800-38d.pdf
Disallowing IVs of length 0 is necessary for the following reason: if an empty IV is used
then the tag is an evaluation of a polynomial with the hash subkey as the value. Since the
polynomial can be derived from the ciphertext it is known to an attacker. Therefore, any
message encrypted with an empty IV leaks the hash subkey. In particular, encrypting an empty
plaintext with an empty IV results in a ciphertext having a tag that is equal to the hash
subkey used in AES-GCM. I.e. both are the same as encrypting an all zero block.
Thanks!
Activity