ica_aes_gcm_intermediate

Purpose

Authenticate data or verify the authenticity of data with an AES key using the Galois/Counter Mode (GCM), as described in NIST Special Publication 800-38D. ica_aes_gcm_intermediate() and ica_aes_gcm_last() can be used when the message to be authenticated or to be verified using GCM is supplied in multiple chunks. ica_aes_gcm_intermediate() is used to process all data chunks. Be aware that all chunks, with the possible exception of the last one, must be a multiple of AES_BLOCK_SIZE (16 bytes). The last data chunk might be any size. In any cases the ica_aes_gcm_last() must be called at the end to calculate the final authentication tag.

When running in FIPS mode, and parameter direction = 1 (ENCRYPT), and the default behavior of only allowing an internally created initialization vector was changed by the application via ica_allow_external_gcm_iv_in_fips_mode(), then the function performs normally, but errno is set to EPERM to indicate that the function is used in a non-approved way.

Format


unsigned int ica_aes_gcm_intermediate(unsigned char *plaintext,
  unsigned long plaintext_length, 
  unsigned char *ciphertext,
  unsigned char *ucb,
  unsigned char *aad, 
  unsigned long aad_length,
  unsigned char *tag, 
  unsigned int tag_length,
  unsigned char *key, 
  unsigned int key_length,
  unsigned char *subkey, 
  unsigned int direction);

Required hardware support

  • KIMD-GHASH
  • KMCTR-AES-128, KMCTR_AES-192 or KMCTR-AES-256

If available, KMA-GCM-AES-128, KMA-GCM-AES-192, and KMA-GCM-AES-256 are used transparently for better performance.

Parameters

unsigned char *plaintext
Pointer to a buffer of size greater than or equal to plaintext_length bytes.

If direction equals 1, the plaintext buffer must be readable and contain a payload message of size plaintext_length that is encrypted. If direction equals 0 the plaintext buffer must be writable.

If the authentication verification succeeds, the decrypted message in the most significant plaintext_length bytes of ciphertext is written to the buffer. Otherwise the contents of the buffer is undefined.

unsigned long plaintext_length
Length in bytes of the message to be encrypted or decrypted. It must be equal or greater than 0 and less than 236-32. With the exception of the call followed by a call to ica_aes_gcm_last(), the value must be a multiple of AES_BLOCK_SIZE. Only in the call followed by ica_aes_gm_last(), the value does not have to be a multiple of AES_BLOCK_SIZE. Padding is done automatically.
unsigned char *ciphertext
Pointer to a buffer of a size which is a multiple of AES_BLOCK_SIZE and which is greater than or equal to plaintext_length bytes.

If direction equals 1, then the buffer must be writable and the encrypted message from plaintext is written to that buffer. If direction equals 0, then the buffer is readable and contains an encrypted message of a length which is equal to the least multiple of AES_BLOCK_SIZE that is greater than or equal to plaintext_length.

unsigned char *ucb
Pointer to the usage counter block, which is a writable buffer that is created during ica_aes_gcm_initialize() and is updated (increased) during the intermediate update operations. The length of this counter block is AES_BLOCK_SIZE (16 bytes). It is assumed that with the call to ica_aes_gcm_intermediate() the contents of the usage counter block was returned in the ucb parameter of a preceding call to ica_aes_gcm_init() or ica_aes_gcm_intermediate().
unsigned char *aad
Pointer to a readable buffer of size greater than or equal to aad_length bytes. The additional authenticated data in the most significant aad_length bytes is subject to the authentication code computation, but is not encrypted.
unsigned long aad_length
Length in bytes of the additional authenticated data in aad. It must be equal to or greater than 0 and less than 261, and the following constraints must apply:
  • If the aad_length is not a multiple of AES_BLOCK_SIZE or 0, then in all subsequent calls to ica_aes_gcm_intermediate() that belong to the same AES GCM computation, the aad_length must be 0 which implies that only the last aad chunk can have a length that is not a multiple of AES_BLOCK_SIZE.
  • If in a preceding call to ica_aes_gcm_intermediate() belonging to the same AES GCM computation, the plaintext_length was greater than 0, then aad_length must be 0, which implies that plaintext or ciphertext can only be supplied when all additional authenticated data is supplied.
unsigned char *tag
Contains the temporary hash/tag value. It is an input/output parameter and must be 16 byte long.
unsigned int tag_length
This parameter is currently not used.
unsigned char *key
Pointer to a valid AES key.
unsigned int key_length
Length in bytes of the AES key. Supported sizes are 16, 24, and 32 for AES-128, AES-192, and AES-256 respectively. Therefore, you can use the macros: AES_KEY_LEN128, AES_KEY_LEN192, and AES_KEY_LEN256.
unsigned char *subkey
Pointer to a writable buffer, generated in ica_aes_gcm_initialize() and used in ica_aes_gcm_intermediate() and ica_aes_gcm_last(). The length of this buffer is AES_BLOCK_SIZE (16 bytes).
unsigned int direction
0
Verify message authentication code and decrypt encrypted payload.
1
Encrypt payload and compute message authentication code for the additional authenticated data and the payload.

Return codes

0
Success
EIO
If the operation fails.
EFAULT
If direction is equal to 0 and the verification of the message authentication code fails.

For return codes indicating exceptions, see Return codes.