xref: /dpdk/drivers/compress/qat/qat_comp_pmd.c (revision d77817d0c4585988ce6bc23aa7590011a61e2a0a)
17a34c215SFiona Trahe /* SPDX-License-Identifier: BSD-3-Clause
2c3352e72SKai Ji  * Copyright(c) 2015-2022 Intel Corporation
37a34c215SFiona Trahe  */
47a34c215SFiona Trahe 
535233274STomasz Jozwiak #include <rte_malloc.h>
635233274STomasz Jozwiak 
7be8343b0SFiona Trahe #include "qat_comp.h"
87a34c215SFiona Trahe #include "qat_comp_pmd.h"
972385564SFiona Trahe 
1035233274STomasz Jozwiak #define QAT_PMD_COMP_SGL_DEF_SEGMENTS 16
1135233274STomasz Jozwiak 
1299ab2806SArkadiusz Kusztal #define COMP_ENQ_THRESHOLD_NAME "qat_comp_enq_threshold"
1399ab2806SArkadiusz Kusztal 
1499ab2806SArkadiusz Kusztal static const char *const arguments[] = {
1599ab2806SArkadiusz Kusztal 	COMP_ENQ_THRESHOLD_NAME,
1699ab2806SArkadiusz Kusztal 	NULL
1799ab2806SArkadiusz Kusztal };
1899ab2806SArkadiusz Kusztal 
194c6912d3SFan Zhang struct qat_comp_gen_dev_ops qat_comp_gen_dev_ops[QAT_N_GENS];
204c6912d3SFan Zhang 
2182822753SAdam Dybkowski struct stream_create_info {
2282822753SAdam Dybkowski 	struct qat_comp_dev_private *comp_dev;
2382822753SAdam Dybkowski 	int socket_id;
2482822753SAdam Dybkowski 	int error;
2582822753SAdam Dybkowski };
2682822753SAdam Dybkowski 
274c6912d3SFan Zhang static struct
qat_comp_get_capa_info(enum qat_device_gen qat_dev_gen,struct qat_pci_device * qat_dev)284c6912d3SFan Zhang qat_comp_capabilities_info qat_comp_get_capa_info(
294c6912d3SFan Zhang 		enum qat_device_gen qat_dev_gen, struct qat_pci_device *qat_dev)
304c6912d3SFan Zhang {
314c6912d3SFan Zhang 	struct qat_comp_capabilities_info ret = { .data = NULL, .size = 0 };
32c0c90bc4SFiona Trahe 
334c6912d3SFan Zhang 	if (qat_dev_gen >= QAT_N_GENS)
344c6912d3SFan Zhang 		return ret;
358f1d23ecSDavid Marchand 	if (qat_comp_gen_dev_ops[qat_dev_gen].qat_comp_get_capabilities == NULL)
368f1d23ecSDavid Marchand 		return ret;
374c6912d3SFan Zhang 	return qat_comp_gen_dev_ops[qat_dev_gen]
384c6912d3SFan Zhang 			.qat_comp_get_capabilities(qat_dev);
394c6912d3SFan Zhang }
404c6912d3SFan Zhang 
414c6912d3SFan Zhang void
qat_comp_stats_get(struct rte_compressdev * dev,struct rte_compressdev_stats * stats)4272385564SFiona Trahe qat_comp_stats_get(struct rte_compressdev *dev,
4372385564SFiona Trahe 		struct rte_compressdev_stats *stats)
4472385564SFiona Trahe {
4572385564SFiona Trahe 	struct qat_common_stats qat_stats = {0};
4672385564SFiona Trahe 	struct qat_comp_dev_private *qat_priv;
4772385564SFiona Trahe 
4872385564SFiona Trahe 	if (stats == NULL || dev == NULL) {
4972385564SFiona Trahe 		QAT_LOG(ERR, "invalid ptr: stats %p, dev %p", stats, dev);
5072385564SFiona Trahe 		return;
5172385564SFiona Trahe 	}
5272385564SFiona Trahe 	qat_priv = dev->data->dev_private;
5372385564SFiona Trahe 
5472385564SFiona Trahe 	qat_stats_get(qat_priv->qat_dev, &qat_stats, QAT_SERVICE_COMPRESSION);
5572385564SFiona Trahe 	stats->enqueued_count = qat_stats.enqueued_count;
5672385564SFiona Trahe 	stats->dequeued_count = qat_stats.dequeued_count;
5772385564SFiona Trahe 	stats->enqueue_err_count = qat_stats.enqueue_err_count;
5872385564SFiona Trahe 	stats->dequeue_err_count = qat_stats.dequeue_err_count;
5972385564SFiona Trahe }
6072385564SFiona Trahe 
614c6912d3SFan Zhang void
qat_comp_stats_reset(struct rte_compressdev * dev)6272385564SFiona Trahe qat_comp_stats_reset(struct rte_compressdev *dev)
6372385564SFiona Trahe {
6472385564SFiona Trahe 	struct qat_comp_dev_private *qat_priv;
6572385564SFiona Trahe 
6672385564SFiona Trahe 	if (dev == NULL) {
6772385564SFiona Trahe 		QAT_LOG(ERR, "invalid compressdev ptr %p", dev);
6872385564SFiona Trahe 		return;
6972385564SFiona Trahe 	}
7072385564SFiona Trahe 	qat_priv = dev->data->dev_private;
7172385564SFiona Trahe 
7272385564SFiona Trahe 	qat_stats_reset(qat_priv->qat_dev, QAT_SERVICE_COMPRESSION);
7372385564SFiona Trahe 
7472385564SFiona Trahe }
75be8343b0SFiona Trahe 
764c6912d3SFan Zhang int
qat_comp_qp_release(struct rte_compressdev * dev,uint16_t queue_pair_id)77be8343b0SFiona Trahe qat_comp_qp_release(struct rte_compressdev *dev, uint16_t queue_pair_id)
78be8343b0SFiona Trahe {
79be8343b0SFiona Trahe 	struct qat_comp_dev_private *qat_private = dev->data->dev_private;
8035233274STomasz Jozwiak 	struct qat_qp **qp_addr =
8135233274STomasz Jozwiak 		(struct qat_qp **)&(dev->data->queue_pairs[queue_pair_id]);
8235233274STomasz Jozwiak 	struct qat_qp *qp = (struct qat_qp *)*qp_addr;
838f393c4fSArek Kusztal 	enum qat_device_gen qat_dev_gen = qat_private->qat_dev->qat_dev_gen;
8435233274STomasz Jozwiak 	uint32_t i;
85be8343b0SFiona Trahe 
86be8343b0SFiona Trahe 	QAT_LOG(DEBUG, "Release comp qp %u on device %d",
87be8343b0SFiona Trahe 				queue_pair_id, dev->data->dev_id);
88be8343b0SFiona Trahe 
89be8343b0SFiona Trahe 	qat_private->qat_dev->qps_in_use[QAT_SERVICE_COMPRESSION][queue_pair_id]
90be8343b0SFiona Trahe 						= NULL;
91be8343b0SFiona Trahe 
92da573c0eSAdam Dybkowski 	if (qp != NULL)
9335233274STomasz Jozwiak 		for (i = 0; i < qp->nb_descriptors; i++) {
9435233274STomasz Jozwiak 			struct qat_comp_op_cookie *cookie = qp->op_cookies[i];
9535233274STomasz Jozwiak 
9635233274STomasz Jozwiak 			rte_free(cookie->qat_sgl_src_d);
9735233274STomasz Jozwiak 			rte_free(cookie->qat_sgl_dst_d);
9835233274STomasz Jozwiak 		}
9935233274STomasz Jozwiak 
1008f393c4fSArek Kusztal 	return qat_qp_release(qat_dev_gen, (struct qat_qp **)
101be8343b0SFiona Trahe 			&(dev->data->queue_pairs[queue_pair_id]));
102be8343b0SFiona Trahe }
103be8343b0SFiona Trahe 
1044c6912d3SFan Zhang int
qat_comp_qp_setup(struct rte_compressdev * dev,uint16_t qp_id,uint32_t max_inflight_ops,int socket_id)105be8343b0SFiona Trahe qat_comp_qp_setup(struct rte_compressdev *dev, uint16_t qp_id,
106be8343b0SFiona Trahe 		uint32_t max_inflight_ops, int socket_id)
107be8343b0SFiona Trahe {
1084c6912d3SFan Zhang 	struct qat_qp_config qat_qp_conf = {0};
109be8343b0SFiona Trahe 	struct qat_qp **qp_addr =
110be8343b0SFiona Trahe 			(struct qat_qp **)&(dev->data->queue_pairs[qp_id]);
111be8343b0SFiona Trahe 	struct qat_comp_dev_private *qat_private = dev->data->dev_private;
1127b976dd0SArek Kusztal 	struct qat_pci_device *qat_dev = qat_private->qat_dev;
1134c6912d3SFan Zhang 	struct qat_qp *qp;
1144c6912d3SFan Zhang 	uint32_t i;
1154c6912d3SFan Zhang 	int ret;
116be8343b0SFiona Trahe 
117be8343b0SFiona Trahe 	/* If qp is already in use free ring memory and qp metadata. */
118be8343b0SFiona Trahe 	if (*qp_addr != NULL) {
119be8343b0SFiona Trahe 		ret = qat_comp_qp_release(dev, qp_id);
120be8343b0SFiona Trahe 		if (ret < 0)
121be8343b0SFiona Trahe 			return ret;
122be8343b0SFiona Trahe 	}
1237b976dd0SArek Kusztal 	if (qp_id >= qat_qps_per_service(qat_dev,
124be8343b0SFiona Trahe 					 QAT_SERVICE_COMPRESSION)) {
125be8343b0SFiona Trahe 		QAT_LOG(ERR, "qp_id %u invalid for this device", qp_id);
126be8343b0SFiona Trahe 		return -EINVAL;
127be8343b0SFiona Trahe 	}
128be8343b0SFiona Trahe 
1294c6912d3SFan Zhang 
1304c6912d3SFan Zhang 	qat_qp_conf.hw = qat_qp_get_hw_data(qat_dev, QAT_SERVICE_COMPRESSION,
1314c6912d3SFan Zhang 			qp_id);
1324c6912d3SFan Zhang 	if (qat_qp_conf.hw == NULL) {
1334c6912d3SFan Zhang 		QAT_LOG(ERR, "qp_id %u invalid for this device", qp_id);
1344c6912d3SFan Zhang 		return -EINVAL;
1354c6912d3SFan Zhang 	}
136be8343b0SFiona Trahe 	qat_qp_conf.cookie_size = sizeof(struct qat_comp_op_cookie);
137be8343b0SFiona Trahe 	qat_qp_conf.nb_descriptors = max_inflight_ops;
138be8343b0SFiona Trahe 	qat_qp_conf.socket_id = socket_id;
139be8343b0SFiona Trahe 	qat_qp_conf.service_str = "comp";
140be8343b0SFiona Trahe 
141be8343b0SFiona Trahe 	ret = qat_qp_setup(qat_private->qat_dev, qp_addr, qp_id, &qat_qp_conf);
142be8343b0SFiona Trahe 	if (ret != 0)
143be8343b0SFiona Trahe 		return ret;
144be8343b0SFiona Trahe 	/* store a link to the qp in the qat_pci_device */
145be8343b0SFiona Trahe 	qat_private->qat_dev->qps_in_use[QAT_SERVICE_COMPRESSION][qp_id]
146be8343b0SFiona Trahe 								= *qp_addr;
147be8343b0SFiona Trahe 
1481947bd18SFiona Trahe 	qp = (struct qat_qp *)*qp_addr;
14947c3f7a4SArek Kusztal 	qp->min_enq_burst_threshold = qat_private->min_enq_burst_threshold;
1501947bd18SFiona Trahe 
1511947bd18SFiona Trahe 	for (i = 0; i < qp->nb_descriptors; i++) {
1521947bd18SFiona Trahe 
1531947bd18SFiona Trahe 		struct qat_comp_op_cookie *cookie =
1541947bd18SFiona Trahe 				qp->op_cookies[i];
1551947bd18SFiona Trahe 
156c13cecf6SAdam Dybkowski 		cookie->qp = qp;
157c13cecf6SAdam Dybkowski 		cookie->cookie_index = i;
158c13cecf6SAdam Dybkowski 
15935233274STomasz Jozwiak 		cookie->qat_sgl_src_d = rte_zmalloc_socket(NULL,
16035233274STomasz Jozwiak 					sizeof(struct qat_sgl) +
16135233274STomasz Jozwiak 					sizeof(struct qat_flat_buf) *
16235233274STomasz Jozwiak 					QAT_PMD_COMP_SGL_DEF_SEGMENTS,
16335233274STomasz Jozwiak 					64, dev->data->socket_id);
16435233274STomasz Jozwiak 
16535233274STomasz Jozwiak 		cookie->qat_sgl_dst_d = rte_zmalloc_socket(NULL,
16635233274STomasz Jozwiak 					sizeof(struct qat_sgl) +
16735233274STomasz Jozwiak 					sizeof(struct qat_flat_buf) *
16835233274STomasz Jozwiak 					QAT_PMD_COMP_SGL_DEF_SEGMENTS,
16935233274STomasz Jozwiak 					64, dev->data->socket_id);
17035233274STomasz Jozwiak 
17135233274STomasz Jozwiak 		if (cookie->qat_sgl_src_d == NULL ||
17235233274STomasz Jozwiak 				cookie->qat_sgl_dst_d == NULL) {
17335233274STomasz Jozwiak 			QAT_LOG(ERR, "Can't allocate SGL"
17435233274STomasz Jozwiak 				     " for device %s",
17535233274STomasz Jozwiak 				     qat_private->qat_dev->name);
17635233274STomasz Jozwiak 			return -ENOMEM;
17735233274STomasz Jozwiak 		}
17835233274STomasz Jozwiak 
1791947bd18SFiona Trahe 		cookie->qat_sgl_src_phys_addr =
18035233274STomasz Jozwiak 				rte_malloc_virt2iova(cookie->qat_sgl_src_d);
1811947bd18SFiona Trahe 
1821947bd18SFiona Trahe 		cookie->qat_sgl_dst_phys_addr =
18335233274STomasz Jozwiak 				rte_malloc_virt2iova(cookie->qat_sgl_dst_d);
18435233274STomasz Jozwiak 
18535233274STomasz Jozwiak 		cookie->dst_nb_elems = cookie->src_nb_elems =
18635233274STomasz Jozwiak 				QAT_PMD_COMP_SGL_DEF_SEGMENTS;
18735233274STomasz Jozwiak 
18835233274STomasz Jozwiak 		cookie->socket_id = dev->data->socket_id;
189b643808fSTomasz Jozwiak 
190b643808fSTomasz Jozwiak 		cookie->error = 0;
1911947bd18SFiona Trahe 	}
1921947bd18SFiona Trahe 
193be8343b0SFiona Trahe 	return ret;
194be8343b0SFiona Trahe }
195a795248dSFiona Trahe 
196a124830aSFiona Trahe 
197a124830aSFiona Trahe #define QAT_IM_BUFFER_DEBUG 0
1984c6912d3SFan Zhang const struct rte_memzone *
qat_comp_setup_inter_buffers(struct qat_comp_dev_private * comp_dev,uint32_t buff_size)199a124830aSFiona Trahe qat_comp_setup_inter_buffers(struct qat_comp_dev_private *comp_dev,
200a124830aSFiona Trahe 			      uint32_t buff_size)
201a124830aSFiona Trahe {
202a124830aSFiona Trahe 	char inter_buff_mz_name[RTE_MEMZONE_NAMESIZE];
203a124830aSFiona Trahe 	const struct rte_memzone *memzone;
204a124830aSFiona Trahe 	uint8_t *mz_start = NULL;
205a124830aSFiona Trahe 	rte_iova_t mz_start_phys = 0;
206a124830aSFiona Trahe 	struct array_of_ptrs *array_of_pointers;
207a124830aSFiona Trahe 	int size_of_ptr_array;
208a124830aSFiona Trahe 	uint32_t full_size;
209da573c0eSAdam Dybkowski 	uint32_t offset_of_flat_buffs;
210a124830aSFiona Trahe 	int i;
2114c6912d3SFan Zhang 	int num_im_sgls = qat_comp_get_num_im_bufs_required(
2124c6912d3SFan Zhang 			comp_dev->qat_dev->qat_dev_gen);
213a124830aSFiona Trahe 
214a124830aSFiona Trahe 	QAT_LOG(DEBUG, "QAT COMP device %s needs %d sgls",
215a124830aSFiona Trahe 				comp_dev->qat_dev->name, num_im_sgls);
216a124830aSFiona Trahe 	snprintf(inter_buff_mz_name, RTE_MEMZONE_NAMESIZE,
217a124830aSFiona Trahe 				"%s_inter_buff", comp_dev->qat_dev->name);
218a124830aSFiona Trahe 	memzone = rte_memzone_lookup(inter_buff_mz_name);
219a124830aSFiona Trahe 	if (memzone != NULL) {
220a124830aSFiona Trahe 		QAT_LOG(DEBUG, "QAT COMP im buffer memzone created already");
221a124830aSFiona Trahe 		return memzone;
222a124830aSFiona Trahe 	}
223a124830aSFiona Trahe 
224da573c0eSAdam Dybkowski 	/* Create multiple memzones to hold intermediate buffers and associated
225da573c0eSAdam Dybkowski 	 * meta-data needed by the firmware.
226da573c0eSAdam Dybkowski 	 * The first memzone contains:
227a124830aSFiona Trahe 	 *  - a list of num_im_sgls physical pointers to sgls
228da573c0eSAdam Dybkowski 	 * All other memzones contain:
229da573c0eSAdam Dybkowski 	 *  - the sgl structure, pointing to QAT_NUM_BUFS_IN_IM_SGL flat buffers
230da573c0eSAdam Dybkowski 	 *  - the flat buffers: QAT_NUM_BUFS_IN_IM_SGL buffers,
231da573c0eSAdam Dybkowski 	 *    each of buff_size
232cea6abe3SFiona Trahe 	 * num_im_sgls depends on the hardware generation of the device
233cea6abe3SFiona Trahe 	 * buff_size comes from the user via the config file
234a124830aSFiona Trahe 	 */
235a124830aSFiona Trahe 
236a124830aSFiona Trahe 	size_of_ptr_array = num_im_sgls * sizeof(phys_addr_t);
237da573c0eSAdam Dybkowski 	offset_of_flat_buffs = sizeof(struct qat_inter_sgl);
238a124830aSFiona Trahe 	full_size = offset_of_flat_buffs +
239da573c0eSAdam Dybkowski 			buff_size * QAT_NUM_BUFS_IN_IM_SGL;
240a124830aSFiona Trahe 
241da573c0eSAdam Dybkowski 	memzone = rte_memzone_reserve_aligned(inter_buff_mz_name,
242da573c0eSAdam Dybkowski 			size_of_ptr_array,
243a124830aSFiona Trahe 			comp_dev->compressdev->data->socket_id,
24425e95179SMarko Kovacevic 			RTE_MEMZONE_IOVA_CONTIG, QAT_64_BYTE_ALIGN);
245a124830aSFiona Trahe 	if (memzone == NULL) {
246da573c0eSAdam Dybkowski 		QAT_LOG(ERR,
247da573c0eSAdam Dybkowski 				"Can't allocate intermediate buffers for device %s",
248da573c0eSAdam Dybkowski 				comp_dev->qat_dev->name);
249a124830aSFiona Trahe 		return NULL;
250a124830aSFiona Trahe 	}
251a124830aSFiona Trahe 
252a124830aSFiona Trahe 	mz_start = (uint8_t *)memzone->addr;
25372f82c43SThomas Monjalon 	mz_start_phys = memzone->iova;
254a124830aSFiona Trahe 	QAT_LOG(DEBUG, "Memzone %s: addr = %p, phys = 0x%"PRIx64
255a124830aSFiona Trahe 			", size required %d, size created %zu",
256a124830aSFiona Trahe 			inter_buff_mz_name, mz_start, mz_start_phys,
257da573c0eSAdam Dybkowski 			size_of_ptr_array, memzone->len);
258a124830aSFiona Trahe 
259a124830aSFiona Trahe 	array_of_pointers = (struct array_of_ptrs *)mz_start;
260a124830aSFiona Trahe 	for (i = 0; i < num_im_sgls; i++) {
261da573c0eSAdam Dybkowski 		const struct rte_memzone *mz;
262da573c0eSAdam Dybkowski 		struct qat_inter_sgl *sgl;
263cea6abe3SFiona Trahe 		int lb;
264a124830aSFiona Trahe 
265da573c0eSAdam Dybkowski 		snprintf(inter_buff_mz_name, RTE_MEMZONE_NAMESIZE,
266da573c0eSAdam Dybkowski 				"%s_inter_buff_%d", comp_dev->qat_dev->name, i);
267da573c0eSAdam Dybkowski 		mz = rte_memzone_lookup(inter_buff_mz_name);
268da573c0eSAdam Dybkowski 		if (mz == NULL) {
269da573c0eSAdam Dybkowski 			mz = rte_memzone_reserve_aligned(inter_buff_mz_name,
270da573c0eSAdam Dybkowski 					full_size,
271da573c0eSAdam Dybkowski 					comp_dev->compressdev->data->socket_id,
272da573c0eSAdam Dybkowski 					RTE_MEMZONE_IOVA_CONTIG,
273da573c0eSAdam Dybkowski 					QAT_64_BYTE_ALIGN);
274da573c0eSAdam Dybkowski 			if (mz == NULL) {
275da573c0eSAdam Dybkowski 				QAT_LOG(ERR,
276da573c0eSAdam Dybkowski 						"Can't allocate intermediate buffers for device %s",
277da573c0eSAdam Dybkowski 						comp_dev->qat_dev->name);
278da573c0eSAdam Dybkowski 				while (--i >= 0) {
279da573c0eSAdam Dybkowski 					snprintf(inter_buff_mz_name,
280da573c0eSAdam Dybkowski 							RTE_MEMZONE_NAMESIZE,
281da573c0eSAdam Dybkowski 							"%s_inter_buff_%d",
282da573c0eSAdam Dybkowski 							comp_dev->qat_dev->name,
283da573c0eSAdam Dybkowski 							i);
284da573c0eSAdam Dybkowski 					rte_memzone_free(
285da573c0eSAdam Dybkowski 							rte_memzone_lookup(
286da573c0eSAdam Dybkowski 							inter_buff_mz_name));
287da573c0eSAdam Dybkowski 				}
288da573c0eSAdam Dybkowski 				rte_memzone_free(memzone);
289da573c0eSAdam Dybkowski 				return NULL;
290da573c0eSAdam Dybkowski 			}
291da573c0eSAdam Dybkowski 		}
292da573c0eSAdam Dybkowski 
293da573c0eSAdam Dybkowski 		QAT_LOG(DEBUG, "Memzone %s: addr = %p, phys = 0x%"PRIx64
294da573c0eSAdam Dybkowski 				", size required %d, size created %zu",
295da573c0eSAdam Dybkowski 				inter_buff_mz_name, mz->addr, mz->iova,
296da573c0eSAdam Dybkowski 				full_size, mz->len);
297da573c0eSAdam Dybkowski 
298da573c0eSAdam Dybkowski 		array_of_pointers->pointer[i] = mz->iova;
299da573c0eSAdam Dybkowski 
300da573c0eSAdam Dybkowski 		sgl = (struct qat_inter_sgl *) mz->addr;
301a124830aSFiona Trahe 		sgl->num_bufs = QAT_NUM_BUFS_IN_IM_SGL;
302a124830aSFiona Trahe 		sgl->num_mapped_bufs = 0;
303a124830aSFiona Trahe 		sgl->resrvd = 0;
304a124830aSFiona Trahe 
305a124830aSFiona Trahe #if QAT_IM_BUFFER_DEBUG
306a124830aSFiona Trahe 		QAT_LOG(DEBUG, "  : phys addr of sgl[%i] in array_of_pointers"
307a124830aSFiona Trahe 			" = 0x%"PRIx64, i, array_of_pointers->pointer[i]);
308a124830aSFiona Trahe 		QAT_LOG(DEBUG, "  : virt address of sgl[%i] = %p", i, sgl);
309a124830aSFiona Trahe #endif
310cea6abe3SFiona Trahe 		for (lb = 0; lb < QAT_NUM_BUFS_IN_IM_SGL; lb++) {
311cea6abe3SFiona Trahe 			sgl->buffers[lb].addr =
312da573c0eSAdam Dybkowski 					mz->iova + offset_of_flat_buffs +
313da573c0eSAdam Dybkowski 					lb * buff_size;
314cea6abe3SFiona Trahe 			sgl->buffers[lb].len = buff_size;
315cea6abe3SFiona Trahe 			sgl->buffers[lb].resrvd = 0;
316cea6abe3SFiona Trahe #if QAT_IM_BUFFER_DEBUG
317cea6abe3SFiona Trahe 			QAT_LOG(DEBUG,
318cea6abe3SFiona Trahe 			  "  : sgl->buffers[%d].addr = 0x%"PRIx64", len=%d",
319cea6abe3SFiona Trahe 			  lb, sgl->buffers[lb].addr, sgl->buffers[lb].len);
320cea6abe3SFiona Trahe #endif
321cea6abe3SFiona Trahe 		}
322a124830aSFiona Trahe 	}
323a124830aSFiona Trahe #if QAT_IM_BUFFER_DEBUG
324a124830aSFiona Trahe 	QAT_DP_HEXDUMP_LOG(DEBUG,  "IM buffer memzone start:",
325da573c0eSAdam Dybkowski 			memzone->addr, size_of_ptr_array);
326a124830aSFiona Trahe #endif
327a124830aSFiona Trahe 	return memzone;
328a124830aSFiona Trahe }
329a124830aSFiona Trahe 
330a795248dSFiona Trahe static struct rte_mempool *
qat_comp_create_xform_pool(struct qat_comp_dev_private * comp_dev,struct rte_compressdev_config * config,uint32_t num_elements)331a795248dSFiona Trahe qat_comp_create_xform_pool(struct qat_comp_dev_private *comp_dev,
3321e796b11STomasz Jozwiak 			   struct rte_compressdev_config *config,
333a795248dSFiona Trahe 			   uint32_t num_elements)
334a795248dSFiona Trahe {
335a795248dSFiona Trahe 	char xform_pool_name[RTE_MEMPOOL_NAMESIZE];
336a795248dSFiona Trahe 	struct rte_mempool *mp;
337a795248dSFiona Trahe 
338a795248dSFiona Trahe 	snprintf(xform_pool_name, RTE_MEMPOOL_NAMESIZE,
339a795248dSFiona Trahe 			"%s_xforms", comp_dev->qat_dev->name);
340a795248dSFiona Trahe 
341a795248dSFiona Trahe 	QAT_LOG(DEBUG, "xformpool: %s", xform_pool_name);
342a795248dSFiona Trahe 	mp = rte_mempool_lookup(xform_pool_name);
343a795248dSFiona Trahe 
344a795248dSFiona Trahe 	if (mp != NULL) {
345a795248dSFiona Trahe 		QAT_LOG(DEBUG, "xformpool already created");
346a795248dSFiona Trahe 		if (mp->size != num_elements) {
347a795248dSFiona Trahe 			QAT_LOG(DEBUG, "xformpool wrong size - delete it");
348a795248dSFiona Trahe 			rte_mempool_free(mp);
349a795248dSFiona Trahe 			mp = NULL;
350a795248dSFiona Trahe 			comp_dev->xformpool = NULL;
351a795248dSFiona Trahe 		}
352a795248dSFiona Trahe 	}
353a795248dSFiona Trahe 
354a795248dSFiona Trahe 	if (mp == NULL)
355a795248dSFiona Trahe 		mp = rte_mempool_create(xform_pool_name,
356a795248dSFiona Trahe 				num_elements,
357a795248dSFiona Trahe 				qat_comp_xform_size(), 0, 0,
3581e796b11STomasz Jozwiak 				NULL, NULL, NULL, NULL, config->socket_id,
359a795248dSFiona Trahe 				0);
360a795248dSFiona Trahe 	if (mp == NULL) {
361a795248dSFiona Trahe 		QAT_LOG(ERR, "Err creating mempool %s w %d elements of size %d",
362a795248dSFiona Trahe 			xform_pool_name, num_elements, qat_comp_xform_size());
363a795248dSFiona Trahe 		return NULL;
364a795248dSFiona Trahe 	}
365a795248dSFiona Trahe 
366a795248dSFiona Trahe 	return mp;
367a795248dSFiona Trahe }
368a795248dSFiona Trahe 
369a795248dSFiona Trahe static void
qat_comp_stream_init(struct rte_mempool * mp __rte_unused,void * opaque,void * obj,unsigned int obj_idx)37082822753SAdam Dybkowski qat_comp_stream_init(struct rte_mempool *mp __rte_unused, void *opaque,
37182822753SAdam Dybkowski 		     void *obj, unsigned int obj_idx)
37282822753SAdam Dybkowski {
37382822753SAdam Dybkowski 	struct stream_create_info *info = opaque;
37482822753SAdam Dybkowski 	struct qat_comp_stream *stream = obj;
37582822753SAdam Dybkowski 	char mz_name[RTE_MEMZONE_NAMESIZE];
37682822753SAdam Dybkowski 	const struct rte_memzone *memzone;
37782822753SAdam Dybkowski 	struct qat_inter_sgl *ram_banks_desc;
37882822753SAdam Dybkowski 
37982822753SAdam Dybkowski 	/* find a memzone for RAM banks */
38082822753SAdam Dybkowski 	snprintf(mz_name, RTE_MEMZONE_NAMESIZE, "%s_%u_rambanks",
38182822753SAdam Dybkowski 		 info->comp_dev->qat_dev->name, obj_idx);
38282822753SAdam Dybkowski 	memzone = rte_memzone_lookup(mz_name);
38382822753SAdam Dybkowski 	if (memzone == NULL) {
38482822753SAdam Dybkowski 		/* allocate a memzone for compression state and RAM banks */
38582822753SAdam Dybkowski 		memzone = rte_memzone_reserve_aligned(mz_name,
38682822753SAdam Dybkowski 			QAT_STATE_REGISTERS_MAX_SIZE
38782822753SAdam Dybkowski 				+ sizeof(struct qat_inter_sgl)
38882822753SAdam Dybkowski 				+ QAT_INFLATE_CONTEXT_SIZE,
38982822753SAdam Dybkowski 			info->socket_id,
39082822753SAdam Dybkowski 			RTE_MEMZONE_IOVA_CONTIG, QAT_64_BYTE_ALIGN);
39182822753SAdam Dybkowski 		if (memzone == NULL) {
39282822753SAdam Dybkowski 			QAT_LOG(ERR,
39382822753SAdam Dybkowski 			    "Can't allocate RAM banks for device %s, object %u",
39482822753SAdam Dybkowski 				info->comp_dev->qat_dev->name, obj_idx);
39582822753SAdam Dybkowski 			info->error = -ENOMEM;
39682822753SAdam Dybkowski 			return;
39782822753SAdam Dybkowski 		}
39882822753SAdam Dybkowski 	}
39982822753SAdam Dybkowski 
40082822753SAdam Dybkowski 	/* prepare the buffer list descriptor for RAM banks */
40182822753SAdam Dybkowski 	ram_banks_desc = (struct qat_inter_sgl *)
40282822753SAdam Dybkowski 		(((uint8_t *) memzone->addr) + QAT_STATE_REGISTERS_MAX_SIZE);
40382822753SAdam Dybkowski 	ram_banks_desc->num_bufs = 1;
40482822753SAdam Dybkowski 	ram_banks_desc->buffers[0].len = QAT_INFLATE_CONTEXT_SIZE;
40582822753SAdam Dybkowski 	ram_banks_desc->buffers[0].addr = memzone->iova
40682822753SAdam Dybkowski 			+ QAT_STATE_REGISTERS_MAX_SIZE
40782822753SAdam Dybkowski 			+ sizeof(struct qat_inter_sgl);
40882822753SAdam Dybkowski 
40982822753SAdam Dybkowski 	memset(stream, 0, qat_comp_stream_size());
41082822753SAdam Dybkowski 	stream->memzone = memzone;
41182822753SAdam Dybkowski 	stream->state_registers_decomp = memzone->addr;
41282822753SAdam Dybkowski 	stream->state_registers_decomp_phys = memzone->iova;
41382822753SAdam Dybkowski 	stream->inflate_context = ((uint8_t *) memzone->addr)
41482822753SAdam Dybkowski 			+ QAT_STATE_REGISTERS_MAX_SIZE;
41582822753SAdam Dybkowski 	stream->inflate_context_phys = memzone->iova
41682822753SAdam Dybkowski 			+ QAT_STATE_REGISTERS_MAX_SIZE;
41782822753SAdam Dybkowski }
41882822753SAdam Dybkowski 
41982822753SAdam Dybkowski static void
qat_comp_stream_destroy(struct rte_mempool * mp __rte_unused,void * opaque __rte_unused,void * obj,unsigned obj_idx __rte_unused)42082822753SAdam Dybkowski qat_comp_stream_destroy(struct rte_mempool *mp __rte_unused,
42182822753SAdam Dybkowski 			void *opaque __rte_unused, void *obj,
42282822753SAdam Dybkowski 			unsigned obj_idx __rte_unused)
42382822753SAdam Dybkowski {
42482822753SAdam Dybkowski 	struct qat_comp_stream *stream = obj;
42582822753SAdam Dybkowski 
42682822753SAdam Dybkowski 	rte_memzone_free(stream->memzone);
42782822753SAdam Dybkowski }
42882822753SAdam Dybkowski 
42982822753SAdam Dybkowski static struct rte_mempool *
qat_comp_create_stream_pool(struct qat_comp_dev_private * comp_dev,int socket_id,uint32_t num_elements)43082822753SAdam Dybkowski qat_comp_create_stream_pool(struct qat_comp_dev_private *comp_dev,
43182822753SAdam Dybkowski 			    int socket_id,
43282822753SAdam Dybkowski 			    uint32_t num_elements)
43382822753SAdam Dybkowski {
43482822753SAdam Dybkowski 	char stream_pool_name[RTE_MEMPOOL_NAMESIZE];
43582822753SAdam Dybkowski 	struct rte_mempool *mp;
43682822753SAdam Dybkowski 
43782822753SAdam Dybkowski 	snprintf(stream_pool_name, RTE_MEMPOOL_NAMESIZE,
43882822753SAdam Dybkowski 		 "%s_streams", comp_dev->qat_dev->name);
43982822753SAdam Dybkowski 
44082822753SAdam Dybkowski 	QAT_LOG(DEBUG, "streampool: %s", stream_pool_name);
44182822753SAdam Dybkowski 	mp = rte_mempool_lookup(stream_pool_name);
44282822753SAdam Dybkowski 
44382822753SAdam Dybkowski 	if (mp != NULL) {
44482822753SAdam Dybkowski 		QAT_LOG(DEBUG, "streampool already created");
44582822753SAdam Dybkowski 		if (mp->size != num_elements) {
44682822753SAdam Dybkowski 			QAT_LOG(DEBUG, "streampool wrong size - delete it");
44782822753SAdam Dybkowski 			rte_mempool_obj_iter(mp, qat_comp_stream_destroy, NULL);
44882822753SAdam Dybkowski 			rte_mempool_free(mp);
44982822753SAdam Dybkowski 			mp = NULL;
45082822753SAdam Dybkowski 			comp_dev->streampool = NULL;
45182822753SAdam Dybkowski 		}
45282822753SAdam Dybkowski 	}
45382822753SAdam Dybkowski 
45482822753SAdam Dybkowski 	if (mp == NULL) {
45582822753SAdam Dybkowski 		struct stream_create_info info = {
45682822753SAdam Dybkowski 			.comp_dev = comp_dev,
45782822753SAdam Dybkowski 			.socket_id = socket_id,
45882822753SAdam Dybkowski 			.error = 0
45982822753SAdam Dybkowski 		};
46082822753SAdam Dybkowski 		mp = rte_mempool_create(stream_pool_name,
46182822753SAdam Dybkowski 				num_elements,
46282822753SAdam Dybkowski 				qat_comp_stream_size(), 0, 0,
46382822753SAdam Dybkowski 				NULL, NULL, qat_comp_stream_init, &info,
46482822753SAdam Dybkowski 				socket_id, 0);
46582822753SAdam Dybkowski 		if (mp == NULL) {
46682822753SAdam Dybkowski 			QAT_LOG(ERR,
46782822753SAdam Dybkowski 			     "Err creating mempool %s w %d elements of size %d",
46882822753SAdam Dybkowski 			     stream_pool_name, num_elements,
46982822753SAdam Dybkowski 			     qat_comp_stream_size());
47082822753SAdam Dybkowski 		} else if (info.error) {
47182822753SAdam Dybkowski 			rte_mempool_obj_iter(mp, qat_comp_stream_destroy, NULL);
47282822753SAdam Dybkowski 			QAT_LOG(ERR,
4737be78d02SJosh Soref 			     "Destroying mempool %s as at least one element failed initialisation",
47482822753SAdam Dybkowski 			     stream_pool_name);
47582822753SAdam Dybkowski 			rte_mempool_free(mp);
47682822753SAdam Dybkowski 			mp = NULL;
47782822753SAdam Dybkowski 		}
47882822753SAdam Dybkowski 	}
47982822753SAdam Dybkowski 
48082822753SAdam Dybkowski 	return mp;
48182822753SAdam Dybkowski }
48282822753SAdam Dybkowski 
48382822753SAdam Dybkowski static void
_qat_comp_dev_config_clear(struct qat_comp_dev_private * comp_dev)484a795248dSFiona Trahe _qat_comp_dev_config_clear(struct qat_comp_dev_private *comp_dev)
485a795248dSFiona Trahe {
486a124830aSFiona Trahe 	/* Free intermediate buffers */
487a124830aSFiona Trahe 	if (comp_dev->interm_buff_mz) {
488da573c0eSAdam Dybkowski 		char mz_name[RTE_MEMZONE_NAMESIZE];
4894c6912d3SFan Zhang 		int i = qat_comp_get_num_im_bufs_required(
4904c6912d3SFan Zhang 				comp_dev->qat_dev->qat_dev_gen);
491da573c0eSAdam Dybkowski 
492da573c0eSAdam Dybkowski 		while (--i >= 0) {
493da573c0eSAdam Dybkowski 			snprintf(mz_name, RTE_MEMZONE_NAMESIZE,
494da573c0eSAdam Dybkowski 					"%s_inter_buff_%d",
495da573c0eSAdam Dybkowski 					comp_dev->qat_dev->name, i);
496da573c0eSAdam Dybkowski 			rte_memzone_free(rte_memzone_lookup(mz_name));
497da573c0eSAdam Dybkowski 		}
498a124830aSFiona Trahe 		rte_memzone_free(comp_dev->interm_buff_mz);
499a124830aSFiona Trahe 		comp_dev->interm_buff_mz = NULL;
500a124830aSFiona Trahe 	}
501a124830aSFiona Trahe 
502a795248dSFiona Trahe 	/* Free private_xform pool */
503a795248dSFiona Trahe 	if (comp_dev->xformpool) {
504a795248dSFiona Trahe 		/* Free internal mempool for private xforms */
505a795248dSFiona Trahe 		rte_mempool_free(comp_dev->xformpool);
506a795248dSFiona Trahe 		comp_dev->xformpool = NULL;
507a795248dSFiona Trahe 	}
50882822753SAdam Dybkowski 
50982822753SAdam Dybkowski 	/* Free stream pool */
51082822753SAdam Dybkowski 	if (comp_dev->streampool) {
51182822753SAdam Dybkowski 		rte_mempool_obj_iter(comp_dev->streampool,
51282822753SAdam Dybkowski 				     qat_comp_stream_destroy, NULL);
51382822753SAdam Dybkowski 		rte_mempool_free(comp_dev->streampool);
51482822753SAdam Dybkowski 		comp_dev->streampool = NULL;
51582822753SAdam Dybkowski 	}
516a795248dSFiona Trahe }
517a795248dSFiona Trahe 
5184c6912d3SFan Zhang int
qat_comp_dev_config(struct rte_compressdev * dev,struct rte_compressdev_config * config)519a795248dSFiona Trahe qat_comp_dev_config(struct rte_compressdev *dev,
520a795248dSFiona Trahe 		struct rte_compressdev_config *config)
521a795248dSFiona Trahe {
522a795248dSFiona Trahe 	struct qat_comp_dev_private *comp_dev = dev->data->dev_private;
523a795248dSFiona Trahe 	int ret = 0;
524a795248dSFiona Trahe 
52582822753SAdam Dybkowski 	if (config->max_nb_priv_xforms) {
52682822753SAdam Dybkowski 		comp_dev->xformpool = qat_comp_create_xform_pool(comp_dev,
52782822753SAdam Dybkowski 					    config, config->max_nb_priv_xforms);
528a795248dSFiona Trahe 		if (comp_dev->xformpool == NULL) {
529a795248dSFiona Trahe 			ret = -ENOMEM;
530a795248dSFiona Trahe 			goto error_out;
531a795248dSFiona Trahe 		}
53282822753SAdam Dybkowski 	} else
53382822753SAdam Dybkowski 		comp_dev->xformpool = NULL;
53482822753SAdam Dybkowski 
53582822753SAdam Dybkowski 	if (config->max_nb_streams) {
53682822753SAdam Dybkowski 		comp_dev->streampool = qat_comp_create_stream_pool(comp_dev,
53782822753SAdam Dybkowski 				     config->socket_id, config->max_nb_streams);
53882822753SAdam Dybkowski 		if (comp_dev->streampool == NULL) {
53982822753SAdam Dybkowski 			ret = -ENOMEM;
54082822753SAdam Dybkowski 			goto error_out;
54182822753SAdam Dybkowski 		}
54282822753SAdam Dybkowski 	} else
54382822753SAdam Dybkowski 		comp_dev->streampool = NULL;
54482822753SAdam Dybkowski 
545a795248dSFiona Trahe 	return 0;
546a795248dSFiona Trahe 
547a795248dSFiona Trahe error_out:
548a795248dSFiona Trahe 	_qat_comp_dev_config_clear(comp_dev);
549a795248dSFiona Trahe 	return ret;
550a795248dSFiona Trahe }
551a795248dSFiona Trahe 
5524c6912d3SFan Zhang int
qat_comp_dev_start(struct rte_compressdev * dev __rte_unused)553d8d380adSFiona Trahe qat_comp_dev_start(struct rte_compressdev *dev __rte_unused)
554d8d380adSFiona Trahe {
555d8d380adSFiona Trahe 	return 0;
556d8d380adSFiona Trahe }
557d8d380adSFiona Trahe 
5584c6912d3SFan Zhang void
qat_comp_dev_stop(struct rte_compressdev * dev __rte_unused)559d8d380adSFiona Trahe qat_comp_dev_stop(struct rte_compressdev *dev __rte_unused)
560d8d380adSFiona Trahe {
561d8d380adSFiona Trahe 
562d8d380adSFiona Trahe }
563a795248dSFiona Trahe 
5644c6912d3SFan Zhang int
qat_comp_dev_close(struct rte_compressdev * dev)565a795248dSFiona Trahe qat_comp_dev_close(struct rte_compressdev *dev)
566a795248dSFiona Trahe {
567a795248dSFiona Trahe 	int i;
568a795248dSFiona Trahe 	int ret = 0;
569a795248dSFiona Trahe 	struct qat_comp_dev_private *comp_dev = dev->data->dev_private;
570a795248dSFiona Trahe 
571a795248dSFiona Trahe 	for (i = 0; i < dev->data->nb_queue_pairs; i++) {
572a795248dSFiona Trahe 		ret = qat_comp_qp_release(dev, i);
573a795248dSFiona Trahe 		if (ret < 0)
574a795248dSFiona Trahe 			return ret;
575a795248dSFiona Trahe 	}
576a795248dSFiona Trahe 
577a795248dSFiona Trahe 	_qat_comp_dev_config_clear(comp_dev);
578a795248dSFiona Trahe 
579a795248dSFiona Trahe 	return ret;
580a795248dSFiona Trahe }
58184aaaf8eSFiona Trahe 
5824c6912d3SFan Zhang void
qat_comp_dev_info_get(struct rte_compressdev * dev,struct rte_compressdev_info * info)58384aaaf8eSFiona Trahe qat_comp_dev_info_get(struct rte_compressdev *dev,
58484aaaf8eSFiona Trahe 			struct rte_compressdev_info *info)
58584aaaf8eSFiona Trahe {
58684aaaf8eSFiona Trahe 	struct qat_comp_dev_private *comp_dev = dev->data->dev_private;
5877b976dd0SArek Kusztal 	struct qat_pci_device *qat_dev = comp_dev->qat_dev;
58884aaaf8eSFiona Trahe 
58984aaaf8eSFiona Trahe 	if (info != NULL) {
59084aaaf8eSFiona Trahe 		info->max_nb_queue_pairs =
5917b976dd0SArek Kusztal 			qat_qps_per_service(qat_dev,
59284aaaf8eSFiona Trahe 					    QAT_SERVICE_COMPRESSION);
59384aaaf8eSFiona Trahe 		info->feature_flags = dev->feature_flags;
59484aaaf8eSFiona Trahe 		info->capabilities = comp_dev->qat_dev_capabilities;
59584aaaf8eSFiona Trahe 	}
59684aaaf8eSFiona Trahe }
597a232ca8bSFiona Trahe 
598c0c90bc4SFiona Trahe static uint16_t
qat_comp_pmd_enq_deq_dummy_op_burst(void * qp __rte_unused,struct rte_comp_op ** ops __rte_unused,uint16_t nb_ops __rte_unused)5992519de89SFiona Trahe qat_comp_pmd_enq_deq_dummy_op_burst(void *qp __rte_unused,
6002519de89SFiona Trahe 				    struct rte_comp_op **ops __rte_unused,
6012519de89SFiona Trahe 				    uint16_t nb_ops __rte_unused)
6022519de89SFiona Trahe {
6032519de89SFiona Trahe 	QAT_DP_LOG(ERR, "QAT PMD detected wrong FW version !");
6042519de89SFiona Trahe 	return 0;
6052519de89SFiona Trahe }
6062519de89SFiona Trahe 
6072519de89SFiona Trahe static struct rte_compressdev_ops compress_qat_dummy_ops = {
6082519de89SFiona Trahe 
6092519de89SFiona Trahe 	/* Device related operations */
6102519de89SFiona Trahe 	.dev_configure		= NULL,
6112519de89SFiona Trahe 	.dev_start		= NULL,
6122519de89SFiona Trahe 	.dev_stop		= qat_comp_dev_stop,
6132519de89SFiona Trahe 	.dev_close		= qat_comp_dev_close,
6142519de89SFiona Trahe 	.dev_infos_get		= NULL,
6152519de89SFiona Trahe 
6162519de89SFiona Trahe 	.stats_get		= NULL,
6172519de89SFiona Trahe 	.stats_reset		= qat_comp_stats_reset,
6182519de89SFiona Trahe 	.queue_pair_setup	= NULL,
6192519de89SFiona Trahe 	.queue_pair_release	= qat_comp_qp_release,
6202519de89SFiona Trahe 
6212519de89SFiona Trahe 	/* Compression related operations */
6222519de89SFiona Trahe 	.private_xform_create	= NULL,
6232519de89SFiona Trahe 	.private_xform_free	= qat_comp_private_xform_free
6242519de89SFiona Trahe };
6252519de89SFiona Trahe 
6262519de89SFiona Trahe static uint16_t
qat_comp_dequeue_burst(void * qp,struct rte_comp_op ** ops,uint16_t nb_ops)62785fec6fdSKai Ji qat_comp_dequeue_burst(void *qp, struct rte_comp_op **ops,  uint16_t nb_ops)
62885fec6fdSKai Ji {
62985fec6fdSKai Ji 	return qat_dequeue_op_burst(qp, (void **)ops, qat_comp_process_response,
63085fec6fdSKai Ji 				nb_ops);
63185fec6fdSKai Ji }
63285fec6fdSKai Ji 
63385fec6fdSKai Ji static uint16_t
qat_comp_pmd_dequeue_first_op_burst(void * qp,struct rte_comp_op ** ops,uint16_t nb_ops)634c13cecf6SAdam Dybkowski qat_comp_pmd_dequeue_first_op_burst(void *qp, struct rte_comp_op **ops,
6352519de89SFiona Trahe 				   uint16_t nb_ops)
6362519de89SFiona Trahe {
63785fec6fdSKai Ji 	uint16_t ret = qat_comp_dequeue_burst(qp, ops, nb_ops);
6382519de89SFiona Trahe 	struct qat_qp *tmp_qp = (struct qat_qp *)qp;
639477d7d05SArkadiusz Kusztal 	struct qat_comp_dev_private *dev =
640477d7d05SArkadiusz Kusztal 		tmp_qp->qat_dev->pmd[QAT_SERVICE_COMPRESSION];
6412519de89SFiona Trahe 
6422519de89SFiona Trahe 	if (ret) {
6432519de89SFiona Trahe 		if ((*ops)->debug_status ==
6442519de89SFiona Trahe 				(uint64_t)ERR_CODE_QAT_COMP_WRONG_FW) {
645477d7d05SArkadiusz Kusztal 			dev->compressdev->enqueue_burst =
6462519de89SFiona Trahe 					qat_comp_pmd_enq_deq_dummy_op_burst;
647477d7d05SArkadiusz Kusztal 			dev->compressdev->dequeue_burst =
6482519de89SFiona Trahe 					qat_comp_pmd_enq_deq_dummy_op_burst;
6492519de89SFiona Trahe 
650477d7d05SArkadiusz Kusztal 			dev->compressdev->dev_ops =
6512519de89SFiona Trahe 					&compress_qat_dummy_ops;
652da573c0eSAdam Dybkowski 			QAT_LOG(ERR,
653da573c0eSAdam Dybkowski 					"This QAT hardware doesn't support compression operation");
6542519de89SFiona Trahe 
6552519de89SFiona Trahe 		} else {
656477d7d05SArkadiusz Kusztal 			dev->compressdev->dequeue_burst =
65785fec6fdSKai Ji 					qat_comp_dequeue_burst;
6582519de89SFiona Trahe 		}
6592519de89SFiona Trahe 	}
6602519de89SFiona Trahe 	return ret;
6612519de89SFiona Trahe }
662edd37ac1SFiona Trahe 
663df8cca46SFiona Trahe /* An rte_driver is needed in the registration of the device with compressdev.
664df8cca46SFiona Trahe  * The actual qat pci's rte_driver can't be used as its name represents
665df8cca46SFiona Trahe  * the whole pci device with all services. Think of this as a holder for a name
666df8cca46SFiona Trahe  * for the compression part of the pci device.
667df8cca46SFiona Trahe  */
668df8cca46SFiona Trahe static const char qat_comp_drv_name[] = RTE_STR(COMPRESSDEV_NAME_QAT_PMD);
669df8cca46SFiona Trahe static const struct rte_driver compdev_qat_driver = {
670df8cca46SFiona Trahe 	.name = qat_comp_drv_name,
671df8cca46SFiona Trahe 	.alias = qat_comp_drv_name
672df8cca46SFiona Trahe };
6734c6912d3SFan Zhang 
674477d7d05SArkadiusz Kusztal static int
qat_comp_dev_create(struct qat_pci_device * qat_pci_dev)67599ab2806SArkadiusz Kusztal qat_comp_dev_create(struct qat_pci_device *qat_pci_dev)
676c0c90bc4SFiona Trahe {
6779904ff68SArek Kusztal 	struct qat_device_info *qat_dev_instance =
6789904ff68SArek Kusztal 			&qat_pci_devs[qat_pci_dev->qat_dev_id];
679c0c90bc4SFiona Trahe 	struct rte_compressdev_pmd_init_params init_params = {
680c0c90bc4SFiona Trahe 		.name = "",
6819904ff68SArek Kusztal 		.socket_id = qat_dev_instance->pci_dev->device.numa_node,
682c0c90bc4SFiona Trahe 	};
683c0c90bc4SFiona Trahe 	char name[RTE_COMPRESSDEV_NAME_MAX_LEN];
6847788dcecSArek Kusztal 	char capa_memz_name[RTE_COMPRESSDEV_NAME_MAX_LEN];
685c0c90bc4SFiona Trahe 	struct rte_compressdev *compressdev;
686c0c90bc4SFiona Trahe 	struct qat_comp_dev_private *comp_dev;
6874c6912d3SFan Zhang 	struct qat_comp_capabilities_info capabilities_info;
6887788dcecSArek Kusztal 	const struct rte_compressdev_capabilities *capabilities;
6894c6912d3SFan Zhang 	const struct qat_comp_gen_dev_ops *qat_comp_gen_ops =
6904c6912d3SFan Zhang 			&qat_comp_gen_dev_ops[qat_pci_dev->qat_dev_gen];
6917788dcecSArek Kusztal 	uint64_t capa_size;
6922e98e808SArkadiusz Kusztal 	uint16_t sub_id = qat_dev_instance->pci_dev->id.subsystem_device_id;
69399ab2806SArkadiusz Kusztal 	char *cmdline = NULL;
694c0c90bc4SFiona Trahe 
695c0c90bc4SFiona Trahe 	snprintf(name, RTE_COMPRESSDEV_NAME_MAX_LEN, "%s_%s",
696c0c90bc4SFiona Trahe 			qat_pci_dev->name, "comp");
697c0c90bc4SFiona Trahe 	QAT_LOG(DEBUG, "Creating QAT COMP device %s", name);
698c0c90bc4SFiona Trahe 
6992e98e808SArkadiusz Kusztal 	if (qat_pci_dev->qat_dev_gen == QAT_VQAT &&
7002e98e808SArkadiusz Kusztal 		sub_id != ADF_VQAT_DC_PCI_SUBSYSTEM_ID) {
7012e98e808SArkadiusz Kusztal 		QAT_LOG(ERR, "Device (vqat instance) %s does not support compression",
7022e98e808SArkadiusz Kusztal 				name);
7032e98e808SArkadiusz Kusztal 		return -EFAULT;
7042e98e808SArkadiusz Kusztal 	}
7054c6912d3SFan Zhang 	if (qat_comp_gen_ops->compressdev_ops == NULL) {
7064c6912d3SFan Zhang 		QAT_LOG(DEBUG, "Device %s does not support compression", name);
7074c6912d3SFan Zhang 		return -ENOTSUP;
7084c6912d3SFan Zhang 	}
7094c6912d3SFan Zhang 
710df8cca46SFiona Trahe 	/* Populate subset device to use in compressdev device creation */
7119904ff68SArek Kusztal 	qat_dev_instance->comp_rte_dev.driver = &compdev_qat_driver;
7129904ff68SArek Kusztal 	qat_dev_instance->comp_rte_dev.numa_node =
7139904ff68SArek Kusztal 			qat_dev_instance->pci_dev->device.numa_node;
7149904ff68SArek Kusztal 	qat_dev_instance->comp_rte_dev.devargs = NULL;
715df8cca46SFiona Trahe 
716c0c90bc4SFiona Trahe 	compressdev = rte_compressdev_pmd_create(name,
7179904ff68SArek Kusztal 			&(qat_dev_instance->comp_rte_dev),
718c0c90bc4SFiona Trahe 			sizeof(struct qat_comp_dev_private),
719c0c90bc4SFiona Trahe 			&init_params);
720c0c90bc4SFiona Trahe 
721c0c90bc4SFiona Trahe 	if (compressdev == NULL)
722c0c90bc4SFiona Trahe 		return -ENODEV;
723c0c90bc4SFiona Trahe 
7244c6912d3SFan Zhang 	compressdev->dev_ops = qat_comp_gen_ops->compressdev_ops;
725c0c90bc4SFiona Trahe 
726c13cecf6SAdam Dybkowski 	compressdev->enqueue_burst = (compressdev_enqueue_pkt_burst_t)
727c13cecf6SAdam Dybkowski 			qat_enqueue_comp_op_burst;
728c13cecf6SAdam Dybkowski 	compressdev->dequeue_burst = qat_comp_pmd_dequeue_first_op_burst;
7294c6912d3SFan Zhang 	compressdev->feature_flags =
7304c6912d3SFan Zhang 			qat_comp_gen_ops->qat_comp_get_feature_flags();
731c0c90bc4SFiona Trahe 
7329904ff68SArek Kusztal 	if (rte_eal_process_type() != RTE_PROC_PRIMARY)
7339904ff68SArek Kusztal 		return 0;
7349904ff68SArek Kusztal 
7357788dcecSArek Kusztal 	snprintf(capa_memz_name, RTE_COMPRESSDEV_NAME_MAX_LEN,
7367788dcecSArek Kusztal 			"QAT_COMP_CAPA_GEN_%d",
7377788dcecSArek Kusztal 			qat_pci_dev->qat_dev_gen);
7387788dcecSArek Kusztal 
739c0c90bc4SFiona Trahe 	comp_dev = compressdev->data->dev_private;
740c0c90bc4SFiona Trahe 	comp_dev->qat_dev = qat_pci_dev;
741c0c90bc4SFiona Trahe 	comp_dev->compressdev = compressdev;
742c0c90bc4SFiona Trahe 
7434c6912d3SFan Zhang 	capabilities_info = qat_comp_get_capa_info(qat_pci_dev->qat_dev_gen,
7444c6912d3SFan Zhang 			qat_pci_dev);
7454c6912d3SFan Zhang 
7464c6912d3SFan Zhang 	if (capabilities_info.data == NULL) {
747c0c90bc4SFiona Trahe 		QAT_LOG(DEBUG,
748c0c90bc4SFiona Trahe 			"QAT gen %d capabilities unknown, default to GEN1",
749c0c90bc4SFiona Trahe 					qat_pci_dev->qat_dev_gen);
7504c6912d3SFan Zhang 		capabilities_info = qat_comp_get_capa_info(QAT_GEN1,
7514c6912d3SFan Zhang 				qat_pci_dev);
752c0c90bc4SFiona Trahe 	}
753c0c90bc4SFiona Trahe 
7544c6912d3SFan Zhang 	capabilities = capabilities_info.data;
7554c6912d3SFan Zhang 	capa_size = capabilities_info.size;
7564c6912d3SFan Zhang 
757dde9cc6fSArek Kusztal 	comp_dev->capa_mz = rte_memzone_lookup(capa_memz_name);
758dde9cc6fSArek Kusztal 	if (comp_dev->capa_mz == NULL) {
7597788dcecSArek Kusztal 		comp_dev->capa_mz = rte_memzone_reserve(capa_memz_name,
7607788dcecSArek Kusztal 			capa_size,
7617788dcecSArek Kusztal 			rte_socket_id(), 0);
762dde9cc6fSArek Kusztal 	}
7637788dcecSArek Kusztal 	if (comp_dev->capa_mz == NULL) {
7647788dcecSArek Kusztal 		QAT_LOG(DEBUG,
7657788dcecSArek Kusztal 			"Error allocating memzone for capabilities, destroying PMD for %s",
7667788dcecSArek Kusztal 			name);
7677788dcecSArek Kusztal 		memset(&qat_dev_instance->comp_rte_dev, 0,
7687788dcecSArek Kusztal 			sizeof(qat_dev_instance->comp_rte_dev));
7697788dcecSArek Kusztal 		rte_compressdev_pmd_destroy(compressdev);
7707788dcecSArek Kusztal 		return -EFAULT;
7717788dcecSArek Kusztal 	}
7727788dcecSArek Kusztal 
7737788dcecSArek Kusztal 	memcpy(comp_dev->capa_mz->addr, capabilities, capa_size);
7747788dcecSArek Kusztal 	comp_dev->qat_dev_capabilities = comp_dev->capa_mz->addr;
7757788dcecSArek Kusztal 
77699ab2806SArkadiusz Kusztal 	cmdline = qat_dev_cmdline_get_val(qat_pci_dev,
77799ab2806SArkadiusz Kusztal 			COMP_ENQ_THRESHOLD_NAME);
77899ab2806SArkadiusz Kusztal 	if (cmdline) {
77947c3f7a4SArek Kusztal 		comp_dev->min_enq_burst_threshold =
78099ab2806SArkadiusz Kusztal 			atoi(cmdline) > MAX_QP_THRESHOLD_SIZE ?
78199ab2806SArkadiusz Kusztal 			MAX_QP_THRESHOLD_SIZE :
78299ab2806SArkadiusz Kusztal 			atoi(cmdline);
78347c3f7a4SArek Kusztal 	}
784477d7d05SArkadiusz Kusztal 	qat_pci_dev->pmd[QAT_SERVICE_COMPRESSION] = comp_dev;
78547c3f7a4SArek Kusztal 
786c0c90bc4SFiona Trahe 	QAT_LOG(DEBUG,
787c0c90bc4SFiona Trahe 		    "Created QAT COMP device %s as compressdev instance %d",
788c0c90bc4SFiona Trahe 			name, compressdev->data->dev_id);
789c0c90bc4SFiona Trahe 	return 0;
790c0c90bc4SFiona Trahe }
791c0c90bc4SFiona Trahe 
792477d7d05SArkadiusz Kusztal static int
qat_comp_dev_destroy(struct qat_pci_device * qat_pci_dev)793c0c90bc4SFiona Trahe qat_comp_dev_destroy(struct qat_pci_device *qat_pci_dev)
794c0c90bc4SFiona Trahe {
795*d77817d0SArkadiusz Kusztal 	struct qat_comp_dev_private *dev;
796c0c90bc4SFiona Trahe 
797c0c90bc4SFiona Trahe 	if (qat_pci_dev == NULL)
798c0c90bc4SFiona Trahe 		return -ENODEV;
799c0c90bc4SFiona Trahe 
800*d77817d0SArkadiusz Kusztal 	dev = qat_pci_dev->pmd[QAT_SERVICE_COMPRESSION];
801*d77817d0SArkadiusz Kusztal 	if (dev == NULL)
802*d77817d0SArkadiusz Kusztal 		return 0;
8037788dcecSArek Kusztal 	if (rte_eal_process_type() == RTE_PROC_PRIMARY)
804477d7d05SArkadiusz Kusztal 		rte_memzone_free(dev->capa_mz);
8057788dcecSArek Kusztal 
806c0c90bc4SFiona Trahe 	/* clean up any resources used by the device */
807477d7d05SArkadiusz Kusztal 	qat_comp_dev_close(dev->compressdev);
808c0c90bc4SFiona Trahe 
809477d7d05SArkadiusz Kusztal 	rte_compressdev_pmd_destroy(dev->compressdev);
810477d7d05SArkadiusz Kusztal 	qat_pci_dev->pmd[QAT_SERVICE_COMPRESSION] = NULL;
811c0c90bc4SFiona Trahe 
812c0c90bc4SFiona Trahe 	return 0;
813c0c90bc4SFiona Trahe }
81499ab2806SArkadiusz Kusztal 
RTE_INIT(qat_sym_init)81599ab2806SArkadiusz Kusztal RTE_INIT(qat_sym_init)
81699ab2806SArkadiusz Kusztal {
81799ab2806SArkadiusz Kusztal 	qat_cmdline_defines[QAT_SERVICE_COMPRESSION] = arguments;
818477d7d05SArkadiusz Kusztal 	qat_service[QAT_SERVICE_COMPRESSION].name = "symmetric crypto";
819477d7d05SArkadiusz Kusztal 	qat_service[QAT_SERVICE_COMPRESSION].dev_create = qat_comp_dev_create;
820477d7d05SArkadiusz Kusztal 	qat_service[QAT_SERVICE_COMPRESSION].dev_destroy = qat_comp_dev_destroy;
82199ab2806SArkadiusz Kusztal }
822