xref: /dpdk/drivers/crypto/scheduler/rte_cryptodev_scheduler.c (revision 6723c0fc7207ca4416822b170b1485a78aa47c7c)
15566a3e3SBruce Richardson /* SPDX-License-Identifier: BSD-3-Clause
25566a3e3SBruce Richardson  * Copyright(c) 2017 Intel Corporation
331439ee7SFan Zhang  */
4*6723c0fcSBruce Richardson #include <rte_string_fns.h>
531439ee7SFan Zhang #include <rte_reorder.h>
631439ee7SFan Zhang #include <rte_cryptodev.h>
731439ee7SFan Zhang #include <rte_cryptodev_pmd.h>
831439ee7SFan Zhang #include <rte_malloc.h>
931439ee7SFan Zhang 
10b88161beSBruce Richardson #include "rte_cryptodev_scheduler.h"
1131439ee7SFan Zhang #include "scheduler_pmd_private.h"
1231439ee7SFan Zhang 
1385aa6d34SHari Kumar int scheduler_logtype_driver;
1485aa6d34SHari Kumar 
1531439ee7SFan Zhang /** update the scheduler pmd's capability with attaching device's
1631439ee7SFan Zhang  *  capability.
1731439ee7SFan Zhang  *  For each device to be attached, the scheduler's capability should be
1831439ee7SFan Zhang  *  the common capability set of all slaves
1931439ee7SFan Zhang  **/
2031439ee7SFan Zhang static uint32_t
2131439ee7SFan Zhang sync_caps(struct rte_cryptodev_capabilities *caps,
2231439ee7SFan Zhang 		uint32_t nb_caps,
2331439ee7SFan Zhang 		const struct rte_cryptodev_capabilities *slave_caps)
2431439ee7SFan Zhang {
2531439ee7SFan Zhang 	uint32_t sync_nb_caps = nb_caps, nb_slave_caps = 0;
2631439ee7SFan Zhang 	uint32_t i;
2731439ee7SFan Zhang 
2831439ee7SFan Zhang 	while (slave_caps[nb_slave_caps].op != RTE_CRYPTO_OP_TYPE_UNDEFINED)
2931439ee7SFan Zhang 		nb_slave_caps++;
3031439ee7SFan Zhang 
3131439ee7SFan Zhang 	if (nb_caps == 0) {
3231439ee7SFan Zhang 		rte_memcpy(caps, slave_caps, sizeof(*caps) * nb_slave_caps);
3331439ee7SFan Zhang 		return nb_slave_caps;
3431439ee7SFan Zhang 	}
3531439ee7SFan Zhang 
3631439ee7SFan Zhang 	for (i = 0; i < sync_nb_caps; i++) {
3731439ee7SFan Zhang 		struct rte_cryptodev_capabilities *cap = &caps[i];
3831439ee7SFan Zhang 		uint32_t j;
3931439ee7SFan Zhang 
4031439ee7SFan Zhang 		for (j = 0; j < nb_slave_caps; j++) {
4131439ee7SFan Zhang 			const struct rte_cryptodev_capabilities *s_cap =
427b46f62bSFan Zhang 					&slave_caps[j];
4331439ee7SFan Zhang 
4431439ee7SFan Zhang 			if (s_cap->op != cap->op || s_cap->sym.xform_type !=
4531439ee7SFan Zhang 					cap->sym.xform_type)
4631439ee7SFan Zhang 				continue;
4731439ee7SFan Zhang 
4831439ee7SFan Zhang 			if (s_cap->sym.xform_type ==
4931439ee7SFan Zhang 					RTE_CRYPTO_SYM_XFORM_AUTH) {
5031439ee7SFan Zhang 				if (s_cap->sym.auth.algo !=
5131439ee7SFan Zhang 						cap->sym.auth.algo)
5231439ee7SFan Zhang 					continue;
5331439ee7SFan Zhang 
5431439ee7SFan Zhang 				cap->sym.auth.digest_size.min =
5531439ee7SFan Zhang 					s_cap->sym.auth.digest_size.min <
5631439ee7SFan Zhang 					cap->sym.auth.digest_size.min ?
5731439ee7SFan Zhang 					s_cap->sym.auth.digest_size.min :
5831439ee7SFan Zhang 					cap->sym.auth.digest_size.min;
5931439ee7SFan Zhang 				cap->sym.auth.digest_size.max =
6031439ee7SFan Zhang 					s_cap->sym.auth.digest_size.max <
6131439ee7SFan Zhang 					cap->sym.auth.digest_size.max ?
6231439ee7SFan Zhang 					s_cap->sym.auth.digest_size.max :
6331439ee7SFan Zhang 					cap->sym.auth.digest_size.max;
6431439ee7SFan Zhang 
6531439ee7SFan Zhang 			}
6631439ee7SFan Zhang 
6731439ee7SFan Zhang 			if (s_cap->sym.xform_type ==
6831439ee7SFan Zhang 					RTE_CRYPTO_SYM_XFORM_CIPHER)
6931439ee7SFan Zhang 				if (s_cap->sym.cipher.algo !=
7031439ee7SFan Zhang 						cap->sym.cipher.algo)
7131439ee7SFan Zhang 					continue;
7231439ee7SFan Zhang 
7331439ee7SFan Zhang 			/* no common cap found */
7431439ee7SFan Zhang 			break;
7531439ee7SFan Zhang 		}
7631439ee7SFan Zhang 
7731439ee7SFan Zhang 		if (j < nb_slave_caps)
7831439ee7SFan Zhang 			continue;
7931439ee7SFan Zhang 
8031439ee7SFan Zhang 		/* remove a uncommon cap from the array */
8131439ee7SFan Zhang 		for (j = i; j < sync_nb_caps - 1; j++)
8231439ee7SFan Zhang 			rte_memcpy(&caps[j], &caps[j+1], sizeof(*cap));
8331439ee7SFan Zhang 
8431439ee7SFan Zhang 		memset(&caps[sync_nb_caps - 1], 0, sizeof(*cap));
8531439ee7SFan Zhang 		sync_nb_caps--;
8631439ee7SFan Zhang 	}
8731439ee7SFan Zhang 
8831439ee7SFan Zhang 	return sync_nb_caps;
8931439ee7SFan Zhang }
9031439ee7SFan Zhang 
9131439ee7SFan Zhang static int
9231439ee7SFan Zhang update_scheduler_capability(struct scheduler_ctx *sched_ctx)
9331439ee7SFan Zhang {
9431439ee7SFan Zhang 	struct rte_cryptodev_capabilities tmp_caps[256] = { {0} };
9531439ee7SFan Zhang 	uint32_t nb_caps = 0, i;
9631439ee7SFan Zhang 
9706f0a569SPablo de Lara 	if (sched_ctx->capabilities) {
9831439ee7SFan Zhang 		rte_free(sched_ctx->capabilities);
9906f0a569SPablo de Lara 		sched_ctx->capabilities = NULL;
10006f0a569SPablo de Lara 	}
10131439ee7SFan Zhang 
10231439ee7SFan Zhang 	for (i = 0; i < sched_ctx->nb_slaves; i++) {
10331439ee7SFan Zhang 		struct rte_cryptodev_info dev_info;
10431439ee7SFan Zhang 
10531439ee7SFan Zhang 		rte_cryptodev_info_get(sched_ctx->slaves[i].dev_id, &dev_info);
10631439ee7SFan Zhang 
10731439ee7SFan Zhang 		nb_caps = sync_caps(tmp_caps, nb_caps, dev_info.capabilities);
10831439ee7SFan Zhang 		if (nb_caps == 0)
10931439ee7SFan Zhang 			return -1;
11031439ee7SFan Zhang 	}
11131439ee7SFan Zhang 
11231439ee7SFan Zhang 	sched_ctx->capabilities = rte_zmalloc_socket(NULL,
11331439ee7SFan Zhang 			sizeof(struct rte_cryptodev_capabilities) *
11431439ee7SFan Zhang 			(nb_caps + 1), 0, SOCKET_ID_ANY);
11531439ee7SFan Zhang 	if (!sched_ctx->capabilities)
11631439ee7SFan Zhang 		return -ENOMEM;
11731439ee7SFan Zhang 
11831439ee7SFan Zhang 	rte_memcpy(sched_ctx->capabilities, tmp_caps,
11931439ee7SFan Zhang 			sizeof(struct rte_cryptodev_capabilities) * nb_caps);
12031439ee7SFan Zhang 
12131439ee7SFan Zhang 	return 0;
12231439ee7SFan Zhang }
12331439ee7SFan Zhang 
12431439ee7SFan Zhang static void
12531439ee7SFan Zhang update_scheduler_feature_flag(struct rte_cryptodev *dev)
12631439ee7SFan Zhang {
12731439ee7SFan Zhang 	struct scheduler_ctx *sched_ctx = dev->data->dev_private;
12831439ee7SFan Zhang 	uint32_t i;
12931439ee7SFan Zhang 
13031439ee7SFan Zhang 	dev->feature_flags = 0;
13131439ee7SFan Zhang 
13231439ee7SFan Zhang 	for (i = 0; i < sched_ctx->nb_slaves; i++) {
13331439ee7SFan Zhang 		struct rte_cryptodev_info dev_info;
13431439ee7SFan Zhang 
13531439ee7SFan Zhang 		rte_cryptodev_info_get(sched_ctx->slaves[i].dev_id, &dev_info);
13631439ee7SFan Zhang 
13731439ee7SFan Zhang 		dev->feature_flags |= dev_info.feature_flags;
13831439ee7SFan Zhang 	}
13931439ee7SFan Zhang }
14031439ee7SFan Zhang 
14131439ee7SFan Zhang static void
14231439ee7SFan Zhang update_max_nb_qp(struct scheduler_ctx *sched_ctx)
14331439ee7SFan Zhang {
14431439ee7SFan Zhang 	uint32_t i;
14531439ee7SFan Zhang 	uint32_t max_nb_qp;
14631439ee7SFan Zhang 
14731439ee7SFan Zhang 	if (!sched_ctx->nb_slaves)
14831439ee7SFan Zhang 		return;
14931439ee7SFan Zhang 
15031439ee7SFan Zhang 	max_nb_qp = sched_ctx->nb_slaves ? UINT32_MAX : 0;
15131439ee7SFan Zhang 
15231439ee7SFan Zhang 	for (i = 0; i < sched_ctx->nb_slaves; i++) {
15331439ee7SFan Zhang 		struct rte_cryptodev_info dev_info;
15431439ee7SFan Zhang 
15531439ee7SFan Zhang 		rte_cryptodev_info_get(sched_ctx->slaves[i].dev_id, &dev_info);
15631439ee7SFan Zhang 		max_nb_qp = dev_info.max_nb_queue_pairs < max_nb_qp ?
15731439ee7SFan Zhang 				dev_info.max_nb_queue_pairs : max_nb_qp;
15831439ee7SFan Zhang 	}
15931439ee7SFan Zhang 
16031439ee7SFan Zhang 	sched_ctx->max_nb_queue_pairs = max_nb_qp;
16131439ee7SFan Zhang }
16231439ee7SFan Zhang 
16331439ee7SFan Zhang /** Attach a device to the scheduler. */
16431439ee7SFan Zhang int
16531439ee7SFan Zhang rte_cryptodev_scheduler_slave_attach(uint8_t scheduler_id, uint8_t slave_id)
16631439ee7SFan Zhang {
16731439ee7SFan Zhang 	struct rte_cryptodev *dev = rte_cryptodev_pmd_get_dev(scheduler_id);
16831439ee7SFan Zhang 	struct scheduler_ctx *sched_ctx;
16931439ee7SFan Zhang 	struct scheduler_slave *slave;
17031439ee7SFan Zhang 	struct rte_cryptodev_info dev_info;
17131439ee7SFan Zhang 	uint32_t i;
17231439ee7SFan Zhang 
17331439ee7SFan Zhang 	if (!dev) {
17485aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Operation not supported");
17531439ee7SFan Zhang 		return -ENOTSUP;
17631439ee7SFan Zhang 	}
17731439ee7SFan Zhang 
178520dd992SFerruh Yigit 	if (dev->driver_id != cryptodev_scheduler_driver_id) {
17985aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Operation not supported");
18031439ee7SFan Zhang 		return -ENOTSUP;
18131439ee7SFan Zhang 	}
18231439ee7SFan Zhang 
18331439ee7SFan Zhang 	if (dev->data->dev_started) {
18485aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Illegal operation");
18531439ee7SFan Zhang 		return -EBUSY;
18631439ee7SFan Zhang 	}
18731439ee7SFan Zhang 
18831439ee7SFan Zhang 	sched_ctx = dev->data->dev_private;
189029bb907SFan Zhang 	if (sched_ctx->nb_slaves >=
190029bb907SFan Zhang 			RTE_CRYPTODEV_SCHEDULER_MAX_NB_SLAVES) {
19185aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Too many slaves attached");
19231439ee7SFan Zhang 		return -ENOMEM;
19331439ee7SFan Zhang 	}
19431439ee7SFan Zhang 
19531439ee7SFan Zhang 	for (i = 0; i < sched_ctx->nb_slaves; i++)
19631439ee7SFan Zhang 		if (sched_ctx->slaves[i].dev_id == slave_id) {
19785aa6d34SHari Kumar 			CR_SCHED_LOG(ERR, "Slave already added");
19831439ee7SFan Zhang 			return -ENOTSUP;
19931439ee7SFan Zhang 		}
20031439ee7SFan Zhang 
20131439ee7SFan Zhang 	slave = &sched_ctx->slaves[sched_ctx->nb_slaves];
20231439ee7SFan Zhang 
20331439ee7SFan Zhang 	rte_cryptodev_info_get(slave_id, &dev_info);
20431439ee7SFan Zhang 
20531439ee7SFan Zhang 	slave->dev_id = slave_id;
2067a364faeSSlawomir Mrozowicz 	slave->driver_id = dev_info.driver_id;
20731439ee7SFan Zhang 	sched_ctx->nb_slaves++;
20831439ee7SFan Zhang 
20931439ee7SFan Zhang 	if (update_scheduler_capability(sched_ctx) < 0) {
21031439ee7SFan Zhang 		slave->dev_id = 0;
2117a364faeSSlawomir Mrozowicz 		slave->driver_id = 0;
21231439ee7SFan Zhang 		sched_ctx->nb_slaves--;
21331439ee7SFan Zhang 
21485aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "capabilities update failed");
21531439ee7SFan Zhang 		return -ENOTSUP;
21631439ee7SFan Zhang 	}
21731439ee7SFan Zhang 
21831439ee7SFan Zhang 	update_scheduler_feature_flag(dev);
21931439ee7SFan Zhang 
22031439ee7SFan Zhang 	update_max_nb_qp(sched_ctx);
22131439ee7SFan Zhang 
22231439ee7SFan Zhang 	return 0;
22331439ee7SFan Zhang }
22431439ee7SFan Zhang 
22531439ee7SFan Zhang int
22631439ee7SFan Zhang rte_cryptodev_scheduler_slave_detach(uint8_t scheduler_id, uint8_t slave_id)
22731439ee7SFan Zhang {
22831439ee7SFan Zhang 	struct rte_cryptodev *dev = rte_cryptodev_pmd_get_dev(scheduler_id);
22931439ee7SFan Zhang 	struct scheduler_ctx *sched_ctx;
23031439ee7SFan Zhang 	uint32_t i, slave_pos;
23131439ee7SFan Zhang 
23231439ee7SFan Zhang 	if (!dev) {
23385aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Operation not supported");
23431439ee7SFan Zhang 		return -ENOTSUP;
23531439ee7SFan Zhang 	}
23631439ee7SFan Zhang 
237520dd992SFerruh Yigit 	if (dev->driver_id != cryptodev_scheduler_driver_id) {
23885aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Operation not supported");
23931439ee7SFan Zhang 		return -ENOTSUP;
24031439ee7SFan Zhang 	}
24131439ee7SFan Zhang 
24231439ee7SFan Zhang 	if (dev->data->dev_started) {
24385aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Illegal operation");
24431439ee7SFan Zhang 		return -EBUSY;
24531439ee7SFan Zhang 	}
24631439ee7SFan Zhang 
24731439ee7SFan Zhang 	sched_ctx = dev->data->dev_private;
24831439ee7SFan Zhang 
24931439ee7SFan Zhang 	for (slave_pos = 0; slave_pos < sched_ctx->nb_slaves; slave_pos++)
25031439ee7SFan Zhang 		if (sched_ctx->slaves[slave_pos].dev_id == slave_id)
25131439ee7SFan Zhang 			break;
25231439ee7SFan Zhang 	if (slave_pos == sched_ctx->nb_slaves) {
25385aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Cannot find slave");
25431439ee7SFan Zhang 		return -ENOTSUP;
25531439ee7SFan Zhang 	}
25631439ee7SFan Zhang 
25731439ee7SFan Zhang 	if (sched_ctx->ops.slave_detach(dev, slave_id) < 0) {
25885aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Failed to detach slave");
25931439ee7SFan Zhang 		return -ENOTSUP;
26031439ee7SFan Zhang 	}
26131439ee7SFan Zhang 
26231439ee7SFan Zhang 	for (i = slave_pos; i < sched_ctx->nb_slaves - 1; i++) {
26331439ee7SFan Zhang 		memcpy(&sched_ctx->slaves[i], &sched_ctx->slaves[i+1],
26431439ee7SFan Zhang 				sizeof(struct scheduler_slave));
26531439ee7SFan Zhang 	}
26631439ee7SFan Zhang 	memset(&sched_ctx->slaves[sched_ctx->nb_slaves - 1], 0,
26731439ee7SFan Zhang 			sizeof(struct scheduler_slave));
26831439ee7SFan Zhang 	sched_ctx->nb_slaves--;
26931439ee7SFan Zhang 
27031439ee7SFan Zhang 	if (update_scheduler_capability(sched_ctx) < 0) {
27185aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "capabilities update failed");
27231439ee7SFan Zhang 		return -ENOTSUP;
27331439ee7SFan Zhang 	}
27431439ee7SFan Zhang 
27531439ee7SFan Zhang 	update_scheduler_feature_flag(dev);
27631439ee7SFan Zhang 
27731439ee7SFan Zhang 	update_max_nb_qp(sched_ctx);
27831439ee7SFan Zhang 
27931439ee7SFan Zhang 	return 0;
28031439ee7SFan Zhang }
28131439ee7SFan Zhang 
28231439ee7SFan Zhang int
2833fb45fdbSFan Zhang rte_cryptodev_scheduler_mode_set(uint8_t scheduler_id,
28431439ee7SFan Zhang 		enum rte_cryptodev_scheduler_mode mode)
28531439ee7SFan Zhang {
28631439ee7SFan Zhang 	struct rte_cryptodev *dev = rte_cryptodev_pmd_get_dev(scheduler_id);
28731439ee7SFan Zhang 	struct scheduler_ctx *sched_ctx;
28831439ee7SFan Zhang 
28931439ee7SFan Zhang 	if (!dev) {
29085aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Operation not supported");
29131439ee7SFan Zhang 		return -ENOTSUP;
29231439ee7SFan Zhang 	}
29331439ee7SFan Zhang 
294520dd992SFerruh Yigit 	if (dev->driver_id != cryptodev_scheduler_driver_id) {
29585aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Operation not supported");
29631439ee7SFan Zhang 		return -ENOTSUP;
29731439ee7SFan Zhang 	}
29831439ee7SFan Zhang 
29931439ee7SFan Zhang 	if (dev->data->dev_started) {
30085aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Illegal operation");
30131439ee7SFan Zhang 		return -EBUSY;
30231439ee7SFan Zhang 	}
30331439ee7SFan Zhang 
30431439ee7SFan Zhang 	sched_ctx = dev->data->dev_private;
30531439ee7SFan Zhang 
30631439ee7SFan Zhang 	if (mode == sched_ctx->mode)
30731439ee7SFan Zhang 		return 0;
30831439ee7SFan Zhang 
30931439ee7SFan Zhang 	switch (mode) {
310100e4f7eSFan Zhang 	case CDEV_SCHED_MODE_ROUNDROBIN:
311100e4f7eSFan Zhang 		if (rte_cryptodev_scheduler_load_user_scheduler(scheduler_id,
312520dd992SFerruh Yigit 				crypto_scheduler_roundrobin) < 0) {
31385aa6d34SHari Kumar 			CR_SCHED_LOG(ERR, "Failed to load scheduler");
314100e4f7eSFan Zhang 			return -1;
315100e4f7eSFan Zhang 		}
316100e4f7eSFan Zhang 		break;
317a783aa63SFan Zhang 	case CDEV_SCHED_MODE_PKT_SIZE_DISTR:
318a783aa63SFan Zhang 		if (rte_cryptodev_scheduler_load_user_scheduler(scheduler_id,
319520dd992SFerruh Yigit 				crypto_scheduler_pkt_size_based_distr) < 0) {
32085aa6d34SHari Kumar 			CR_SCHED_LOG(ERR, "Failed to load scheduler");
321a783aa63SFan Zhang 			return -1;
322a783aa63SFan Zhang 		}
323a783aa63SFan Zhang 		break;
32437f075daSFan Zhang 	case CDEV_SCHED_MODE_FAILOVER:
32537f075daSFan Zhang 		if (rte_cryptodev_scheduler_load_user_scheduler(scheduler_id,
326520dd992SFerruh Yigit 				crypto_scheduler_failover) < 0) {
32785aa6d34SHari Kumar 			CR_SCHED_LOG(ERR, "Failed to load scheduler");
32837f075daSFan Zhang 			return -1;
32937f075daSFan Zhang 		}
33037f075daSFan Zhang 		break;
3314c07e055SKirill Rybalchenko 	case CDEV_SCHED_MODE_MULTICORE:
3324c07e055SKirill Rybalchenko 		if (rte_cryptodev_scheduler_load_user_scheduler(scheduler_id,
333520dd992SFerruh Yigit 				crypto_scheduler_multicore) < 0) {
33485aa6d34SHari Kumar 			CR_SCHED_LOG(ERR, "Failed to load scheduler");
3354c07e055SKirill Rybalchenko 			return -1;
3364c07e055SKirill Rybalchenko 		}
3374c07e055SKirill Rybalchenko 		break;
33831439ee7SFan Zhang 	default:
33985aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Not yet supported");
34031439ee7SFan Zhang 		return -ENOTSUP;
34131439ee7SFan Zhang 	}
34231439ee7SFan Zhang 
34331439ee7SFan Zhang 	return 0;
34431439ee7SFan Zhang }
34531439ee7SFan Zhang 
34631439ee7SFan Zhang enum rte_cryptodev_scheduler_mode
3473fb45fdbSFan Zhang rte_cryptodev_scheduler_mode_get(uint8_t scheduler_id)
34831439ee7SFan Zhang {
34931439ee7SFan Zhang 	struct rte_cryptodev *dev = rte_cryptodev_pmd_get_dev(scheduler_id);
35031439ee7SFan Zhang 	struct scheduler_ctx *sched_ctx;
35131439ee7SFan Zhang 
35231439ee7SFan Zhang 	if (!dev) {
35385aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Operation not supported");
35431439ee7SFan Zhang 		return -ENOTSUP;
35531439ee7SFan Zhang 	}
35631439ee7SFan Zhang 
357520dd992SFerruh Yigit 	if (dev->driver_id != cryptodev_scheduler_driver_id) {
35885aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Operation not supported");
35931439ee7SFan Zhang 		return -ENOTSUP;
36031439ee7SFan Zhang 	}
36131439ee7SFan Zhang 
36231439ee7SFan Zhang 	sched_ctx = dev->data->dev_private;
36331439ee7SFan Zhang 
36431439ee7SFan Zhang 	return sched_ctx->mode;
36531439ee7SFan Zhang }
36631439ee7SFan Zhang 
36731439ee7SFan Zhang int
36831439ee7SFan Zhang rte_cryptodev_scheduler_ordering_set(uint8_t scheduler_id,
36931439ee7SFan Zhang 		uint32_t enable_reorder)
37031439ee7SFan Zhang {
37131439ee7SFan Zhang 	struct rte_cryptodev *dev = rte_cryptodev_pmd_get_dev(scheduler_id);
37231439ee7SFan Zhang 	struct scheduler_ctx *sched_ctx;
37331439ee7SFan Zhang 
37431439ee7SFan Zhang 	if (!dev) {
37585aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Operation not supported");
37631439ee7SFan Zhang 		return -ENOTSUP;
37731439ee7SFan Zhang 	}
37831439ee7SFan Zhang 
379520dd992SFerruh Yigit 	if (dev->driver_id != cryptodev_scheduler_driver_id) {
38085aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Operation not supported");
38131439ee7SFan Zhang 		return -ENOTSUP;
38231439ee7SFan Zhang 	}
38331439ee7SFan Zhang 
38431439ee7SFan Zhang 	if (dev->data->dev_started) {
38585aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Illegal operation");
38631439ee7SFan Zhang 		return -EBUSY;
38731439ee7SFan Zhang 	}
38831439ee7SFan Zhang 
38931439ee7SFan Zhang 	sched_ctx = dev->data->dev_private;
39031439ee7SFan Zhang 
39131439ee7SFan Zhang 	sched_ctx->reordering_enabled = enable_reorder;
39231439ee7SFan Zhang 
39331439ee7SFan Zhang 	return 0;
39431439ee7SFan Zhang }
39531439ee7SFan Zhang 
39631439ee7SFan Zhang int
39731439ee7SFan Zhang rte_cryptodev_scheduler_ordering_get(uint8_t scheduler_id)
39831439ee7SFan Zhang {
39931439ee7SFan Zhang 	struct rte_cryptodev *dev = rte_cryptodev_pmd_get_dev(scheduler_id);
40031439ee7SFan Zhang 	struct scheduler_ctx *sched_ctx;
40131439ee7SFan Zhang 
40231439ee7SFan Zhang 	if (!dev) {
40385aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Operation not supported");
40431439ee7SFan Zhang 		return -ENOTSUP;
40531439ee7SFan Zhang 	}
40631439ee7SFan Zhang 
407520dd992SFerruh Yigit 	if (dev->driver_id != cryptodev_scheduler_driver_id) {
40885aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Operation not supported");
40931439ee7SFan Zhang 		return -ENOTSUP;
41031439ee7SFan Zhang 	}
41131439ee7SFan Zhang 
41231439ee7SFan Zhang 	sched_ctx = dev->data->dev_private;
41331439ee7SFan Zhang 
41431439ee7SFan Zhang 	return (int)sched_ctx->reordering_enabled;
41531439ee7SFan Zhang }
41631439ee7SFan Zhang 
41731439ee7SFan Zhang int
41831439ee7SFan Zhang rte_cryptodev_scheduler_load_user_scheduler(uint8_t scheduler_id,
41931439ee7SFan Zhang 		struct rte_cryptodev_scheduler *scheduler) {
42031439ee7SFan Zhang 
42131439ee7SFan Zhang 	struct rte_cryptodev *dev = rte_cryptodev_pmd_get_dev(scheduler_id);
42231439ee7SFan Zhang 	struct scheduler_ctx *sched_ctx;
42331439ee7SFan Zhang 
42431439ee7SFan Zhang 	if (!dev) {
42585aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Operation not supported");
42631439ee7SFan Zhang 		return -ENOTSUP;
42731439ee7SFan Zhang 	}
42831439ee7SFan Zhang 
429520dd992SFerruh Yigit 	if (dev->driver_id != cryptodev_scheduler_driver_id) {
43085aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Operation not supported");
43131439ee7SFan Zhang 		return -ENOTSUP;
43231439ee7SFan Zhang 	}
43331439ee7SFan Zhang 
43431439ee7SFan Zhang 	if (dev->data->dev_started) {
43585aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Illegal operation");
43631439ee7SFan Zhang 		return -EBUSY;
43731439ee7SFan Zhang 	}
43831439ee7SFan Zhang 
43931439ee7SFan Zhang 	sched_ctx = dev->data->dev_private;
44031439ee7SFan Zhang 
441d040aca6SPablo de Lara 	if (strlen(scheduler->name) > RTE_CRYPTODEV_NAME_MAX_LEN - 1) {
44285aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Invalid name %s, should be less than "
44385aa6d34SHari Kumar 				"%u bytes.", scheduler->name,
444d040aca6SPablo de Lara 				RTE_CRYPTODEV_NAME_MAX_LEN);
445d040aca6SPablo de Lara 		return -EINVAL;
446d040aca6SPablo de Lara 	}
447*6723c0fcSBruce Richardson 	strlcpy(sched_ctx->name, scheduler->name, sizeof(sched_ctx->name));
448d040aca6SPablo de Lara 
449d040aca6SPablo de Lara 	if (strlen(scheduler->description) >
450d040aca6SPablo de Lara 			RTE_CRYPTODEV_SCHEDULER_DESC_MAX_LEN - 1) {
45185aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Invalid description %s, should be less than "
45285aa6d34SHari Kumar 				"%u bytes.", scheduler->description,
453d040aca6SPablo de Lara 				RTE_CRYPTODEV_SCHEDULER_DESC_MAX_LEN - 1);
454d040aca6SPablo de Lara 		return -EINVAL;
455d040aca6SPablo de Lara 	}
456*6723c0fcSBruce Richardson 	strlcpy(sched_ctx->description, scheduler->description,
457*6723c0fcSBruce Richardson 		sizeof(sched_ctx->description));
45831439ee7SFan Zhang 
45931439ee7SFan Zhang 	/* load scheduler instance operations functions */
46031439ee7SFan Zhang 	sched_ctx->ops.config_queue_pair = scheduler->ops->config_queue_pair;
46131439ee7SFan Zhang 	sched_ctx->ops.create_private_ctx = scheduler->ops->create_private_ctx;
46231439ee7SFan Zhang 	sched_ctx->ops.scheduler_start = scheduler->ops->scheduler_start;
46331439ee7SFan Zhang 	sched_ctx->ops.scheduler_stop = scheduler->ops->scheduler_stop;
46431439ee7SFan Zhang 	sched_ctx->ops.slave_attach = scheduler->ops->slave_attach;
46531439ee7SFan Zhang 	sched_ctx->ops.slave_detach = scheduler->ops->slave_detach;
4664e30ead5SFan Zhang 	sched_ctx->ops.option_set = scheduler->ops->option_set;
4674e30ead5SFan Zhang 	sched_ctx->ops.option_get = scheduler->ops->option_get;
46831439ee7SFan Zhang 
46906f0a569SPablo de Lara 	if (sched_ctx->private_ctx) {
47031439ee7SFan Zhang 		rte_free(sched_ctx->private_ctx);
47106f0a569SPablo de Lara 		sched_ctx->private_ctx = NULL;
47206f0a569SPablo de Lara 	}
47331439ee7SFan Zhang 
47431439ee7SFan Zhang 	if (sched_ctx->ops.create_private_ctx) {
47531439ee7SFan Zhang 		int ret = (*sched_ctx->ops.create_private_ctx)(dev);
47631439ee7SFan Zhang 
47731439ee7SFan Zhang 		if (ret < 0) {
47885aa6d34SHari Kumar 			CR_SCHED_LOG(ERR, "Unable to create scheduler private "
47931439ee7SFan Zhang 					"context");
48031439ee7SFan Zhang 			return ret;
48131439ee7SFan Zhang 		}
48231439ee7SFan Zhang 	}
48331439ee7SFan Zhang 
48431439ee7SFan Zhang 	sched_ctx->mode = scheduler->mode;
48531439ee7SFan Zhang 
48631439ee7SFan Zhang 	return 0;
48731439ee7SFan Zhang }
488029bb907SFan Zhang 
489029bb907SFan Zhang int
490029bb907SFan Zhang rte_cryptodev_scheduler_slaves_get(uint8_t scheduler_id, uint8_t *slaves)
491029bb907SFan Zhang {
492029bb907SFan Zhang 	struct rte_cryptodev *dev = rte_cryptodev_pmd_get_dev(scheduler_id);
493029bb907SFan Zhang 	struct scheduler_ctx *sched_ctx;
494029bb907SFan Zhang 	uint32_t nb_slaves = 0;
495029bb907SFan Zhang 
496029bb907SFan Zhang 	if (!dev) {
49785aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Operation not supported");
498029bb907SFan Zhang 		return -ENOTSUP;
499029bb907SFan Zhang 	}
500029bb907SFan Zhang 
501520dd992SFerruh Yigit 	if (dev->driver_id != cryptodev_scheduler_driver_id) {
50285aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Operation not supported");
503029bb907SFan Zhang 		return -ENOTSUP;
504029bb907SFan Zhang 	}
505029bb907SFan Zhang 
506029bb907SFan Zhang 	sched_ctx = dev->data->dev_private;
507029bb907SFan Zhang 
508029bb907SFan Zhang 	nb_slaves = sched_ctx->nb_slaves;
509029bb907SFan Zhang 
510029bb907SFan Zhang 	if (slaves && nb_slaves) {
511029bb907SFan Zhang 		uint32_t i;
512029bb907SFan Zhang 
513029bb907SFan Zhang 		for (i = 0; i < nb_slaves; i++)
514029bb907SFan Zhang 			slaves[i] = sched_ctx->slaves[i].dev_id;
515029bb907SFan Zhang 	}
516029bb907SFan Zhang 
517029bb907SFan Zhang 	return (int)nb_slaves;
518029bb907SFan Zhang }
5194e30ead5SFan Zhang 
5204e30ead5SFan Zhang int
5214e30ead5SFan Zhang rte_cryptodev_scheduler_option_set(uint8_t scheduler_id,
5224e30ead5SFan Zhang 		enum rte_cryptodev_schedule_option_type option_type,
5234e30ead5SFan Zhang 		void *option)
5244e30ead5SFan Zhang {
5254e30ead5SFan Zhang 	struct rte_cryptodev *dev = rte_cryptodev_pmd_get_dev(scheduler_id);
5264e30ead5SFan Zhang 	struct scheduler_ctx *sched_ctx;
5274e30ead5SFan Zhang 
5284e30ead5SFan Zhang 	if (option_type == CDEV_SCHED_OPTION_NOT_SET ||
5294e30ead5SFan Zhang 			option_type >= CDEV_SCHED_OPTION_COUNT) {
53085aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Invalid option parameter");
5314e30ead5SFan Zhang 		return -EINVAL;
5324e30ead5SFan Zhang 	}
5334e30ead5SFan Zhang 
5344e30ead5SFan Zhang 	if (!option) {
53585aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Invalid option parameter");
5364e30ead5SFan Zhang 		return -EINVAL;
5374e30ead5SFan Zhang 	}
5384e30ead5SFan Zhang 
5394e30ead5SFan Zhang 	if (dev->data->dev_started) {
54085aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Illegal operation");
5414e30ead5SFan Zhang 		return -EBUSY;
5424e30ead5SFan Zhang 	}
5434e30ead5SFan Zhang 
5444e30ead5SFan Zhang 	sched_ctx = dev->data->dev_private;
5454e30ead5SFan Zhang 
5464e30ead5SFan Zhang 	RTE_FUNC_PTR_OR_ERR_RET(*sched_ctx->ops.option_set, -ENOTSUP);
5474e30ead5SFan Zhang 
5484e30ead5SFan Zhang 	return (*sched_ctx->ops.option_set)(dev, option_type, option);
5494e30ead5SFan Zhang }
5504e30ead5SFan Zhang 
5514e30ead5SFan Zhang int
5524e30ead5SFan Zhang rte_cryptodev_scheduler_option_get(uint8_t scheduler_id,
5534e30ead5SFan Zhang 		enum rte_cryptodev_schedule_option_type option_type,
5544e30ead5SFan Zhang 		void *option)
5554e30ead5SFan Zhang {
5564e30ead5SFan Zhang 	struct rte_cryptodev *dev = rte_cryptodev_pmd_get_dev(scheduler_id);
5574e30ead5SFan Zhang 	struct scheduler_ctx *sched_ctx;
5584e30ead5SFan Zhang 
5594e30ead5SFan Zhang 	if (!dev) {
56085aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Operation not supported");
5614e30ead5SFan Zhang 		return -ENOTSUP;
5624e30ead5SFan Zhang 	}
5634e30ead5SFan Zhang 
5644e30ead5SFan Zhang 	if (!option) {
56585aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Invalid option parameter");
5664e30ead5SFan Zhang 		return -EINVAL;
5674e30ead5SFan Zhang 	}
5684e30ead5SFan Zhang 
569520dd992SFerruh Yigit 	if (dev->driver_id != cryptodev_scheduler_driver_id) {
57085aa6d34SHari Kumar 		CR_SCHED_LOG(ERR, "Operation not supported");
5714e30ead5SFan Zhang 		return -ENOTSUP;
5724e30ead5SFan Zhang 	}
5734e30ead5SFan Zhang 
5744e30ead5SFan Zhang 	sched_ctx = dev->data->dev_private;
5754e30ead5SFan Zhang 
5764e30ead5SFan Zhang 	RTE_FUNC_PTR_OR_ERR_RET(*sched_ctx->ops.option_get, -ENOTSUP);
5774e30ead5SFan Zhang 
5784e30ead5SFan Zhang 	return (*sched_ctx->ops.option_get)(dev, option_type, option);
5794e30ead5SFan Zhang }
58085aa6d34SHari Kumar 
581f8e99896SThomas Monjalon RTE_INIT(scheduler_init_log)
58285aa6d34SHari Kumar {
58385aa6d34SHari Kumar 	scheduler_logtype_driver = rte_log_register("pmd.crypto.scheduler");
58485aa6d34SHari Kumar }
585