RE: [PATCH v2 08/17] crypto/cipher: Add setaad/gettag for AEAD modes
Kane Chen <[email protected]>
| Newsgroups | org.nongnu.qemu-arm,org.nongnu.qemu-devel |
|---|---|
| Message-ID | <SI6PR06MB7631458490FAC1C2AC55E6CBF7DE2@SI6PR06MB7631.apcprd06.prod.outlook.com> |
> -----Original Message----- > From: Jamin Lin <[email protected]> > Sent: Wednesday, July 15, 2026 11:33 AM > To: Daniel P. Berrangé <[email protected]>; Cédric Le Goater > <[email protected]>; Peter Maydell <[email protected]>; Steven Lee > <[email protected]>; Troy Lee <[email protected]>; Kane Chen > <[email protected]>; Andrew Jeffery > <[email protected]>; Joel Stanley <[email protected]>; Eric Blake > <[email protected]>; Markus Armbruster <[email protected]>; Fabiano > Rosas <[email protected]>; Laurent Vivier <[email protected]>; Paolo Bonzini > <[email protected]>; open list:All patches CC here > <[email protected]>; open list:ASPEED BMCs > <[email protected]> > Cc: Jamin Lin <[email protected]>; Troy Lee > <[email protected]> > Subject: [PATCH v2 08/17] crypto/cipher: Add setaad/gettag for AEAD modes > > AEAD modes such as GCM authenticate optional associated data (AAD) and > produce an authentication tag, which the block-cipher encrypt/decrypt > interface cannot express. Add qcrypto_cipher_setaad() and > qcrypto_cipher_gettag() plus the matching backend driver hooks. The generic > front-end reports an error when the selected mode's driver does not > implement them, so calling them on a non-AEAD mode fails cleanly. > > Signed-off-by: Jamin Lin <[email protected]> > Reviewed-by: Daniel P. Berrangé <[email protected]> > --- > crypto/cipherpriv.h | 8 ++++++++ > include/crypto/cipher.h | 36 ++++++++++++++++++++++++++++++++++++ > crypto/cipher.c | 31 +++++++++++++++++++++++++++++++ > 3 files changed, 75 insertions(+) > > diff --git a/crypto/cipherpriv.h b/crypto/cipherpriv.h index > 64737ce961..c4f995f369 100644 > --- a/crypto/cipherpriv.h > +++ b/crypto/cipherpriv.h > @@ -34,6 +34,14 @@ struct QCryptoCipherDriver { > const uint8_t *iv, size_t niv, > Error **errp); > > + int (*cipher_setaad)(QCryptoCipher *cipher, > + const uint8_t *aad, size_t len, > + Error **errp); > + > + int (*cipher_gettag)(QCryptoCipher *cipher, > + uint8_t *tag, size_t len, > + Error **errp); > + > void (*cipher_free)(QCryptoCipher *cipher); }; > > diff --git a/include/crypto/cipher.h b/include/crypto/cipher.h index > 92939310ef..2e361411b9 100644 > --- a/include/crypto/cipher.h > +++ b/include/crypto/cipher.h > @@ -235,4 +235,40 @@ int qcrypto_cipher_setiv(QCryptoCipher *cipher, > const uint8_t *iv, size_t niv, > Error **errp); > > +/** > + * qcrypto_cipher_setaad: > + * @cipher: the cipher object > + * @aad: the associated data to authenticate > + * @len: the length of @aad > + * @errp: pointer to a NULL-initialized error object > + * > + * For AEAD modes such as GCM, feed the associated data (AAD) that is > + * authenticated but not encrypted. It must be called after > + * qcrypto_cipher_setiv() and before the first encrypt/decrypt call. It > +is > + * an error to call this on a mode that is not an AEAD mode. > + * > + * Returns: 0 on success, -1 on error > + */ > +int qcrypto_cipher_setaad(QCryptoCipher *cipher, > + const uint8_t *aad, size_t len, > + Error **errp); > + > +/** > + * qcrypto_cipher_gettag: > + * @cipher: the cipher object > + * @tag: buffer to receive the authentication tag > + * @len: the length of @tag > + * @errp: pointer to a NULL-initialized error object > + * > + * For AEAD modes such as GCM, read back the authentication tag > +computed > + * over the associated data and the message. It must be called after > +the > + * encrypt/decrypt operation. It is an error to call this on a mode > +that is > + * not an AEAD mode. > + * > + * Returns: 0 on success, -1 on error > + */ > +int qcrypto_cipher_gettag(QCryptoCipher *cipher, > + uint8_t *tag, size_t len, > + Error **errp); > + > #endif /* QCRYPTO_CIPHER_H */ > diff --git a/crypto/cipher.c b/crypto/cipher.c index 52d071a90c..67014aad6f > 100644 > --- a/crypto/cipher.c > +++ b/crypto/cipher.c > @@ -205,6 +205,37 @@ int qcrypto_cipher_setiv(QCryptoCipher *cipher, } > > > +int qcrypto_cipher_setaad(QCryptoCipher *cipher, > + const uint8_t *aad, size_t len, > + Error **errp) { > + const QCryptoCipherDriver *drv = cipher->driver; > + > + if (!drv->cipher_setaad) { > + error_setg(errp, "The cipher mode does not support associated > data"); > + return -1; > + } > + > + return drv->cipher_setaad(cipher, aad, len, errp); } > + > + > +int qcrypto_cipher_gettag(QCryptoCipher *cipher, > + uint8_t *tag, size_t len, > + Error **errp) { > + const QCryptoCipherDriver *drv = cipher->driver; > + > + if (!drv->cipher_gettag) { > + error_setg(errp, > + "The cipher mode does not produce an authentication > tag"); > + return -1; > + } > + > + return drv->cipher_gettag(cipher, tag, len, errp); } > + > + > void qcrypto_cipher_free(QCryptoCipher *cipher) { > if (cipher) { > -- > 2.43.0 Reviewed-by: Kane Chen <[email protected]>