This commit adds modular multiplicative inverse to Intel QuickAssist Technology driver. For capabilities or limitations refer to qat.rst or qat_asym_capabilities.h.
Signed-off-by: Arek Kusztal <arkadiuszx.kusz...@intel.com> --- doc/guides/cryptodevs/qat.rst | 1 + drivers/crypto/qat/qat_asym.c | 61 ++++++++++++++++++++++++++++++ drivers/crypto/qat/qat_asym.h | 4 ++ drivers/crypto/qat/qat_asym_capabilities.h | 16 ++++++++ 4 files changed, 82 insertions(+) diff --git a/doc/guides/cryptodevs/qat.rst b/doc/guides/cryptodevs/qat.rst index 9c0196f..d0f3926 100644 --- a/doc/guides/cryptodevs/qat.rst +++ b/doc/guides/cryptodevs/qat.rst @@ -106,6 +106,7 @@ Asymmetric Crypto Service on QAT The QAT Asym PMD has support for: * ``Modular exponentiation`` +* ``Modular multiplicative inverse`` Limitations ~~~~~~~~~~~ diff --git a/drivers/crypto/qat/qat_asym.c b/drivers/crypto/qat/qat_asym.c index 04a35eb..2585ecd 100644 --- a/drivers/crypto/qat/qat_asym.c +++ b/drivers/crypto/qat/qat_asym.c @@ -51,6 +51,9 @@ static void qat_asym_build_req_tmpl(void *sess_private_data, if (xform->xform_type == RTE_CRYPTO_ASYM_XFORM_MODEX) { qat_req->output_param_count = 1; qat_req->input_param_count = 3; + } else if (xform->xform_type == RTE_CRYPTO_ASYM_XFORM_MODINV) { + qat_req->output_param_count = 1; + qat_req->input_param_count = 2; } } @@ -157,6 +160,42 @@ qat_asym_build_request(void *in_op, ctx->sess_alg_params.mod_exp.n.length); cookie->alg_size = alg_size; qat_req->pke_hdr.cd_pars.func_id = func_id; + } else if (ctx->alg == QAT_PKE_MODINV) { + err = qat_asym_check_nonzero(ctx->sess_alg_params.mod_inv.n); + if (err) + goto error; + + alg_size_in_bytes = max_of(3, asym_op->modinv.base.length, + ctx->sess_alg_params.mod_inv.n.length); + alg_size = alg_size_in_bytes << 3; + + if (asym_op->modinv.base.data[asym_op->modinv.base.length - 1] & 0x01) { + if (qat_asym_get_sz_and_func_id(MOD_INV_IDS_ODD, + sizeof(MOD_INV_IDS_ODD)/sizeof(*MOD_INV_IDS_ODD), + &alg_size, &func_id)) { + err = QAT_ASYM_ERROR_INVALID_MODINV_PARAM; + goto error; + } + } else { + if (qat_asym_get_sz_and_func_id(MOD_INV_IDS_EVEN, + sizeof(MOD_INV_IDS_EVEN)/sizeof(*MOD_INV_IDS_EVEN), + &alg_size, &func_id)) { + err = QAT_ASYM_ERROR_INVALID_MODINV_PARAM; + goto error; + } + } + + alg_size_in_bytes = alg_size >> 3; + rte_memcpy(cookie->input_array[0] + alg_size_in_bytes - + asym_op->modinv.base.length + , asym_op->modinv.base.data, + asym_op->modinv.base.length); + rte_memcpy(cookie->input_array[1] + alg_size_in_bytes - + ctx->sess_alg_params.mod_inv.n.length + , ctx->sess_alg_params.mod_inv.n.data, + ctx->sess_alg_params.mod_inv.n.length); + cookie->alg_size = alg_size; + qat_req->pke_hdr.cd_pars.func_id = func_id; } return 0; @@ -217,6 +256,21 @@ qat_asym_process_response(void **op, uint8_t *resp, memset(cookie->input_array[1], 0x0, alg_size_in_bytes); memset(cookie->input_array[2], 0x0, alg_size_in_bytes); memset(cookie->output_array[0], 0x0, alg_size_in_bytes); + } else if (ctx->alg == QAT_PKE_MODINV) { + alg_size = cookie->alg_size; + alg_size_in_bytes = alg_size >> 3; + uint8_t *modinv_result = asym_op->modinv.result.data; + + rte_memcpy(modinv_result + + (asym_op->modinv.result.length - ctx->sess_alg_params.mod_inv.n.length), + cookie->output_array[0] + alg_size_in_bytes + - ctx->sess_alg_params.mod_inv.n.length, + ctx->sess_alg_params.mod_inv.n.length + ); + + memset(cookie->input_array[0], 0x0, alg_size_in_bytes); + memset(cookie->input_array[1], 0x0, alg_size_in_bytes); + memset(cookie->output_array[0], 0x0, alg_size_in_bytes); } } @@ -243,7 +297,14 @@ qat_asym_session_configure(struct rte_cryptodev *dev, if (xform->modex.exponent.length == 0 || xform->modex.modulus.length == 0) return -EINVAL; + } else if (xform->xform_type == RTE_CRYPTO_ASYM_XFORM_MODINV) { + session->sess_alg_params.mod_inv.n = xform->modinv.modulus; + session->alg = QAT_PKE_MODINV; + + if (xform->modinv.modulus.length == 0) + return -EINVAL; } + qat_asym_build_req_tmpl(sess_private_data, xform); set_asym_session_private_data(sess, dev->driver_id, sess_private_data); diff --git a/drivers/crypto/qat/qat_asym.h b/drivers/crypto/qat/qat_asym.h index e6c3ce3..f9edfa9 100644 --- a/drivers/crypto/qat/qat_asym.h +++ b/drivers/crypto/qat/qat_asym.h @@ -19,6 +19,7 @@ typedef uint64_t large_int_ptr; #define QAT_ASYM_ERROR_DIVIDE_BY_ZERO 0x01 #define QAT_ASYM_ERROR_INVALID_MODEXP_PARAM 0x02 +#define QAT_ASYM_ERROR_INVALID_MODINV_PARAM 0x04 struct qat_asym_op_cookie { size_t alg_size; @@ -48,6 +49,9 @@ struct qat_asym_session { rte_crypto_param n; rte_crypto_param e; } mod_exp; + struct { + rte_crypto_param n; + } mod_inv; } sess_alg_params; }; diff --git a/drivers/crypto/qat/qat_asym_capabilities.h b/drivers/crypto/qat/qat_asym_capabilities.h index 1d6323f..f43c025 100644 --- a/drivers/crypto/qat/qat_asym_capabilities.h +++ b/drivers/crypto/qat/qat_asym_capabilities.h @@ -21,6 +21,22 @@ } \ }, \ } \ + }, \ + { /* modinv */ \ + .op = RTE_CRYPTO_OP_TYPE_ASYMMETRIC, \ + {.asym = { \ + .xform_capa = { \ + .xform_type = RTE_CRYPTO_ASYM_XFORM_MODINV, \ + .op_types = 0, \ + { \ + .modlen = { \ + .min = 1, \ + .max = 512, \ + .increment = 1 \ + }, } \ + } \ + }, \ + } \ } \ #endif /* _QAT_ASYM_CAPABILITIES_H_ */ -- 2.1.0