Commit 3a5a9e1e authored by Horia Geantă's avatar Horia Geantă Committed by Herbert Xu

crypto: caam/qi2 - fix chacha20 data size error

HW generates a Data Size error for chacha20 requests that are not
a multiple of 64B, since algorithm state (AS) does not have
the FINAL bit set.

Since updating req->iv (for chaining) is not required,
modify skcipher descriptors to set the FINAL bit for chacha20.

[Note that for skcipher decryption we know that ctx1_iv_off is 0,
which allows for an optimization by not checking algorithm type,
since append_dec_op1() sets FINAL bit for all algorithms except AES.]

Also drop the descriptor operations that save the IV.
However, in order to keep code logic simple, things like
S/G tables generation etc. are not touched.

Cc: <stable@vger.kernel.org> # v5.3+
Fixes: 334d37c9 ("crypto: caam - update IV using HW support")
Signed-off-by: default avatarHoria Geantă <horia.geanta@nxp.com>
Tested-by: default avatarValentin Ciocoi Radulescu <valentin.ciocoi@nxp.com>
Signed-off-by: default avatarHerbert Xu <herbert@gondor.apana.org.au>
parent a8388006
...@@ -1379,6 +1379,9 @@ void cnstr_shdsc_skcipher_encap(u32 * const desc, struct alginfo *cdata, ...@@ -1379,6 +1379,9 @@ void cnstr_shdsc_skcipher_encap(u32 * const desc, struct alginfo *cdata,
const u32 ctx1_iv_off) const u32 ctx1_iv_off)
{ {
u32 *key_jump_cmd; u32 *key_jump_cmd;
u32 options = cdata->algtype | OP_ALG_AS_INIT | OP_ALG_ENCRYPT;
bool is_chacha20 = ((cdata->algtype & OP_ALG_ALGSEL_MASK) ==
OP_ALG_ALGSEL_CHACHA20);
init_sh_desc(desc, HDR_SHARE_SERIAL | HDR_SAVECTX); init_sh_desc(desc, HDR_SHARE_SERIAL | HDR_SAVECTX);
/* Skip if already shared */ /* Skip if already shared */
...@@ -1417,14 +1420,15 @@ void cnstr_shdsc_skcipher_encap(u32 * const desc, struct alginfo *cdata, ...@@ -1417,14 +1420,15 @@ void cnstr_shdsc_skcipher_encap(u32 * const desc, struct alginfo *cdata,
LDST_OFFSET_SHIFT)); LDST_OFFSET_SHIFT));
/* Load operation */ /* Load operation */
append_operation(desc, cdata->algtype | OP_ALG_AS_INIT | if (is_chacha20)
OP_ALG_ENCRYPT); options |= OP_ALG_AS_FINALIZE;
append_operation(desc, options);
/* Perform operation */ /* Perform operation */
skcipher_append_src_dst(desc); skcipher_append_src_dst(desc);
/* Store IV */ /* Store IV */
if (ivsize) if (!is_chacha20 && ivsize)
append_seq_store(desc, ivsize, LDST_SRCDST_BYTE_CONTEXT | append_seq_store(desc, ivsize, LDST_SRCDST_BYTE_CONTEXT |
LDST_CLASS_1_CCB | (ctx1_iv_off << LDST_CLASS_1_CCB | (ctx1_iv_off <<
LDST_OFFSET_SHIFT)); LDST_OFFSET_SHIFT));
...@@ -1451,6 +1455,8 @@ void cnstr_shdsc_skcipher_decap(u32 * const desc, struct alginfo *cdata, ...@@ -1451,6 +1455,8 @@ void cnstr_shdsc_skcipher_decap(u32 * const desc, struct alginfo *cdata,
const u32 ctx1_iv_off) const u32 ctx1_iv_off)
{ {
u32 *key_jump_cmd; u32 *key_jump_cmd;
bool is_chacha20 = ((cdata->algtype & OP_ALG_ALGSEL_MASK) ==
OP_ALG_ALGSEL_CHACHA20);
init_sh_desc(desc, HDR_SHARE_SERIAL | HDR_SAVECTX); init_sh_desc(desc, HDR_SHARE_SERIAL | HDR_SAVECTX);
/* Skip if already shared */ /* Skip if already shared */
...@@ -1499,7 +1505,7 @@ void cnstr_shdsc_skcipher_decap(u32 * const desc, struct alginfo *cdata, ...@@ -1499,7 +1505,7 @@ void cnstr_shdsc_skcipher_decap(u32 * const desc, struct alginfo *cdata,
skcipher_append_src_dst(desc); skcipher_append_src_dst(desc);
/* Store IV */ /* Store IV */
if (ivsize) if (!is_chacha20 && ivsize)
append_seq_store(desc, ivsize, LDST_SRCDST_BYTE_CONTEXT | append_seq_store(desc, ivsize, LDST_SRCDST_BYTE_CONTEXT |
LDST_CLASS_1_CCB | (ctx1_iv_off << LDST_CLASS_1_CCB | (ctx1_iv_off <<
LDST_OFFSET_SHIFT)); LDST_OFFSET_SHIFT));
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment