1 /* SPDX-License-Identifier: BSD-3-Clause
2 * Copyright(C) 2019 Marvell International Ltd.
8 #include <rte_bus_pci.h>
10 #include <rte_lcore.h>
11 #include <rte_mempool.h>
14 #include <rte_common.h>
15 #include <rte_rawdev.h>
16 #include <rte_rawdev_pmd.h>
18 #include "otx2_common.h"
19 #include "otx2_ep_rawdev.h"
20 #include "otx2_ep_vf.h"
22 static const struct rte_pci_id pci_sdp_vf_map[] = {
24 RTE_PCI_DEVICE(PCI_VENDOR_ID_CAVIUM,
25 PCI_DEVID_OCTEONTX2_EP_VF)
32 /* SDP_VF default configuration */
33 const struct sdp_config default_sdp_conf = {
36 .max_iqs = SDP_VF_CFG_IO_QUEUES,
37 .instr_type = SDP_VF_64BYTE_INSTR,
38 .pending_list_size = (SDP_VF_MAX_IQ_DESCRIPTORS *
39 SDP_VF_CFG_IO_QUEUES),
44 .max_oqs = SDP_VF_CFG_IO_QUEUES,
45 .info_ptr = SDP_VF_OQ_INFOPTR_MODE,
46 .refill_threshold = SDP_VF_OQ_REFIL_THRESHOLD,
49 .num_iqdef_descs = SDP_VF_MAX_IQ_DESCRIPTORS,
50 .num_oqdef_descs = SDP_VF_MAX_OQ_DESCRIPTORS,
51 .oqdef_buf_size = SDP_VF_OQ_BUF_SIZE,
55 const struct sdp_config*
56 sdp_get_defconf(struct sdp_device *sdp_dev __rte_unused)
58 const struct sdp_config *default_conf = NULL;
60 default_conf = &default_sdp_conf;
66 sdp_chip_specific_setup(struct sdp_device *sdpvf)
68 struct rte_pci_device *pdev = sdpvf->pci_dev;
69 uint32_t dev_id = pdev->id.device_id;
73 case PCI_DEVID_OCTEONTX2_EP_VF:
74 sdpvf->chip_id = PCI_DEVID_OCTEONTX2_EP_VF;
75 ret = sdp_vf_setup_device(sdpvf);
79 otx2_err("Unsupported device");
84 otx2_info("SDP dev_id[%d]", dev_id);
89 /* SDP VF device initialization */
91 sdp_vfdev_init(struct sdp_device *sdpvf)
93 uint32_t rawdev_queues, q;
95 if (sdp_chip_specific_setup(sdpvf)) {
96 otx2_err("Chip specific setup failed");
100 if (sdpvf->fn_list.setup_device_regs(sdpvf)) {
101 otx2_err("Failed to configure device registers");
105 rawdev_queues = (uint32_t)(sdpvf->sriov_info.rings_per_vf);
107 /* Rawdev queues setup for enqueue/dequeue */
108 for (q = 0; q < rawdev_queues; q++) {
109 if (sdp_setup_iqs(sdpvf, q)) {
110 otx2_err("Failed to setup IQs");
114 otx2_info("Total[%d] IQs setup", sdpvf->num_iqs);
116 for (q = 0; q < rawdev_queues; q++) {
117 if (sdp_setup_oqs(sdpvf, q)) {
118 otx2_err("Failed to setup OQs");
122 otx2_info("Total [%d] OQs setup", sdpvf->num_oqs);
124 /* Enable IQ/OQ for this device */
125 sdpvf->fn_list.enable_io_queues(sdpvf);
127 /* Send OQ desc credits for OQs, credits are always
128 * sent after the OQs are enabled.
130 for (q = 0; q < rawdev_queues; q++) {
131 rte_write32(sdpvf->droq[q]->nb_desc,
132 sdpvf->droq[q]->pkts_credit_reg);
135 otx2_info("OQ[%d] dbells [%d]", q,
136 rte_read32(sdpvf->droq[q]->pkts_credit_reg));
141 otx2_info("SDP Device is Ready");
152 sdp_rawdev_configure(const struct rte_rawdev *dev, rte_rawdev_obj_t config)
154 struct sdp_rawdev_info *app_info = (struct sdp_rawdev_info *)config;
155 struct sdp_device *sdpvf;
157 if (app_info == NULL) {
158 otx2_err("Application config info [NULL]");
162 sdpvf = (struct sdp_device *)dev->dev_private;
164 sdpvf->conf = app_info->app_conf;
165 sdpvf->enqdeq_mpool = app_info->enqdeq_mpool;
167 sdp_vfdev_init(sdpvf);
173 /* SDP VF endpoint rawdev ops */
174 static const struct rte_rawdev_ops sdp_rawdev_ops = {
175 .dev_configure = sdp_rawdev_configure,
179 otx2_sdp_rawdev_probe(struct rte_pci_driver *pci_drv __rte_unused,
180 struct rte_pci_device *pci_dev)
182 char name[RTE_RAWDEV_NAME_MAX_LEN];
183 struct sdp_device *sdpvf = NULL;
184 struct rte_rawdev *sdp_rawdev;
187 /* Single process support */
188 if (rte_eal_process_type() != RTE_PROC_PRIMARY)
191 if (pci_dev->mem_resource[0].addr)
192 otx2_info("SDP_EP BAR0 is mapped:");
194 otx2_err("SDP_EP: Failed to map device BARs");
195 otx2_err("BAR0 %p\n BAR2 %p",
196 pci_dev->mem_resource[0].addr,
197 pci_dev->mem_resource[2].addr);
201 memset(name, 0, sizeof(name));
202 snprintf(name, RTE_RAWDEV_NAME_MAX_LEN, "SDPEP:%x:%02x.%x",
203 pci_dev->addr.bus, pci_dev->addr.devid,
204 pci_dev->addr.function);
206 /* Allocate rawdev pmd */
207 sdp_rawdev = rte_rawdev_pmd_allocate(name,
208 sizeof(struct sdp_device),
211 if (sdp_rawdev == NULL) {
212 otx2_err("SDP_EP VF rawdev allocation failed");
216 sdp_rawdev->dev_ops = &sdp_rawdev_ops;
217 sdp_rawdev->device = &pci_dev->device;
218 sdp_rawdev->driver_name = pci_dev->driver->driver.name;
220 sdpvf = (struct sdp_device *)sdp_rawdev->dev_private;
221 sdpvf->hw_addr = pci_dev->mem_resource[0].addr;
222 sdpvf->pci_dev = pci_dev;
224 /* Discover the VF number being probed */
225 vf_id = ((pci_dev->addr.devid & 0x1F) << 3) |
226 (pci_dev->addr.function & 0x7);
229 sdpvf->vf_num = vf_id;
231 otx2_info("SDP_EP VF[%d] probe done", vf_id);
237 otx2_sdp_rawdev_remove(struct rte_pci_device *pci_dev)
239 char name[RTE_RAWDEV_NAME_MAX_LEN];
240 struct rte_rawdev *rawdev;
241 struct sdp_device *sdpvf;
243 /* Single process support */
244 if (rte_eal_process_type() != RTE_PROC_PRIMARY)
247 if (pci_dev == NULL) {
248 otx2_err("SDP_EP:invalid pci_dev!");
253 memset(name, 0, sizeof(name));
254 snprintf(name, RTE_RAWDEV_NAME_MAX_LEN, "SDPEP:%x:%02x.%x",
255 pci_dev->addr.bus, pci_dev->addr.devid,
256 pci_dev->addr.function);
258 rawdev = rte_rawdev_pmd_get_named_dev(name);
259 if (rawdev == NULL) {
260 otx2_err("SDP_EP: invalid device name (%s)", name);
264 sdpvf = (struct sdp_device *)rawdev->dev_private;
265 otx2_info("Removing SDP_EP VF[%d] ", sdpvf->vf_num);
267 /* rte_rawdev_close is called by pmd_release */
268 return rte_rawdev_pmd_release(rawdev);
271 static struct rte_pci_driver rte_sdp_rawdev_pmd = {
272 .id_table = pci_sdp_vf_map,
273 .drv_flags = (RTE_PCI_DRV_NEED_MAPPING | RTE_PCI_DRV_NEED_IOVA_AS_VA),
274 .probe = otx2_sdp_rawdev_probe,
275 .remove = otx2_sdp_rawdev_remove,
278 RTE_PMD_REGISTER_PCI(sdp_rawdev_pci_driver, rte_sdp_rawdev_pmd);
279 RTE_PMD_REGISTER_PCI_TABLE(sdp_rawdev_pci_driver, pci_sdp_vf_map);
280 RTE_PMD_REGISTER_KMOD_DEP(sdp_rawdev_pci_driver, "vfio-pci");