1 /* SPDX-License-Identifier: BSD-3-Clause
2 * Copyright(c) 2017 Intel Corporation
13 #include <rte_byteorder.h>
14 #include <rte_common.h>
16 #include <rte_interrupts.h>
17 #include <rte_debug.h>
19 #include <rte_atomic.h>
21 #include <rte_ether.h>
22 #include <rte_ethdev.h>
23 #include <rte_ethdev_pci.h>
24 #include <rte_malloc.h>
25 #include <rte_memzone.h>
29 #include "base/avf_prototype.h"
30 #include "base/avf_adminq_cmd.h"
31 #include "base/avf_type.h"
36 int avf_logtype_driver;
37 static const struct rte_pci_id pci_id_avf_map[] = {
38 { RTE_PCI_DEVICE(AVF_INTEL_VENDOR_ID, AVF_DEV_ID_ADAPTIVE_VF) },
39 { .vendor_id = 0, /* sentinel */ },
42 static const struct eth_dev_ops avf_eth_dev_ops = {
46 avf_check_vf_reset_done(struct avf_hw *hw)
50 for (i = 0; i < AVF_RESET_WAIT_CNT; i++) {
51 reset = AVF_READ_REG(hw, AVFGEN_RSTAT) &
52 AVFGEN_RSTAT_VFR_STATE_MASK;
53 reset = reset >> AVFGEN_RSTAT_VFR_STATE_SHIFT;
54 if (reset == VIRTCHNL_VFR_VFACTIVE ||
55 reset == VIRTCHNL_VFR_COMPLETED)
60 if (i >= AVF_RESET_WAIT_CNT)
67 avf_init_vf(struct rte_eth_dev *dev)
70 struct avf_adapter *adapter =
71 AVF_DEV_PRIVATE_TO_ADAPTER(dev->data->dev_private);
72 struct avf_hw *hw = AVF_DEV_PRIVATE_TO_HW(dev->data->dev_private);
73 struct avf_info *vf = AVF_DEV_PRIVATE_TO_VF(dev->data->dev_private);
75 err = avf_set_mac_type(hw);
77 PMD_INIT_LOG(ERR, "set_mac_type failed: %d", err);
81 err = avf_check_vf_reset_done(hw);
83 PMD_INIT_LOG(ERR, "VF is still resetting");
87 avf_init_adminq_parameter(hw);
88 err = avf_init_adminq(hw);
90 PMD_INIT_LOG(ERR, "init_adminq failed: %d", err);
94 vf->aq_resp = rte_zmalloc("vf_aq_resp", AVF_AQ_BUF_SZ, 0);
96 PMD_INIT_LOG(ERR, "unable to allocate vf_aq_resp memory");
99 if (avf_check_api_version(adapter) != 0) {
100 PMD_INIT_LOG(ERR, "check_api version failed");
104 bufsz = sizeof(struct virtchnl_vf_resource) +
105 (AVF_MAX_VF_VSI * sizeof(struct virtchnl_vsi_resource));
106 vf->vf_res = rte_zmalloc("vf_res", bufsz, 0);
108 PMD_INIT_LOG(ERR, "unable to allocate vf_res memory");
111 if (avf_get_vf_resource(adapter) != 0) {
112 PMD_INIT_LOG(ERR, "avf_get_vf_config failed");
115 /* Allocate memort for RSS info */
116 if (vf->vf_res->vf_cap_flags & VIRTCHNL_VF_OFFLOAD_RSS_PF) {
117 vf->rss_key = rte_zmalloc("rss_key",
118 vf->vf_res->rss_key_size, 0);
120 PMD_INIT_LOG(ERR, "unable to allocate rss_key memory");
123 vf->rss_lut = rte_zmalloc("rss_lut",
124 vf->vf_res->rss_lut_size, 0);
126 PMD_INIT_LOG(ERR, "unable to allocate rss_lut memory");
132 rte_free(vf->rss_key);
133 rte_free(vf->rss_lut);
135 rte_free(vf->vf_res);
138 rte_free(vf->aq_resp);
140 avf_shutdown_adminq(hw);
145 /* Enable default admin queue interrupt setting */
147 avf_enable_irq0(struct avf_hw *hw)
149 /* Enable admin queue interrupt trigger */
150 AVF_WRITE_REG(hw, AVFINT_ICR0_ENA1, AVFINT_ICR0_ENA1_ADMINQ_MASK);
152 AVF_WRITE_REG(hw, AVFINT_DYN_CTL01, AVFINT_DYN_CTL01_INTENA_MASK |
153 AVFINT_DYN_CTL01_ITR_INDX_MASK);
159 avf_disable_irq0(struct avf_hw *hw)
161 /* Disable all interrupt types */
162 AVF_WRITE_REG(hw, AVFINT_ICR0_ENA1, 0);
163 AVF_WRITE_REG(hw, AVFINT_DYN_CTL01,
164 AVFINT_DYN_CTL01_ITR_INDX_MASK);
169 avf_dev_interrupt_handler(void *param)
171 struct rte_eth_dev *dev = (struct rte_eth_dev *)param;
172 struct avf_hw *hw = AVF_DEV_PRIVATE_TO_HW(dev->data->dev_private);
174 avf_disable_irq0(hw);
176 avf_handle_virtchnl_msg(dev);
183 avf_dev_init(struct rte_eth_dev *eth_dev)
185 struct avf_adapter *adapter =
186 AVF_DEV_PRIVATE_TO_ADAPTER(eth_dev->data->dev_private);
187 struct avf_hw *hw = AVF_DEV_PRIVATE_TO_HW(adapter);
188 struct rte_pci_device *pci_dev = RTE_ETH_DEV_TO_PCI(eth_dev);
190 PMD_INIT_FUNC_TRACE();
192 /* assign ops func pointer */
193 eth_dev->dev_ops = &avf_eth_dev_ops;
195 rte_eth_copy_pci_info(eth_dev, pci_dev);
197 hw->vendor_id = pci_dev->id.vendor_id;
198 hw->device_id = pci_dev->id.device_id;
199 hw->subsystem_vendor_id = pci_dev->id.subsystem_vendor_id;
200 hw->subsystem_device_id = pci_dev->id.subsystem_device_id;
201 hw->bus.bus_id = pci_dev->addr.bus;
202 hw->bus.device = pci_dev->addr.devid;
203 hw->bus.func = pci_dev->addr.function;
204 hw->hw_addr = (void *)pci_dev->mem_resource[0].addr;
205 hw->back = AVF_DEV_PRIVATE_TO_ADAPTER(eth_dev->data->dev_private);
206 adapter->eth_dev = eth_dev;
208 if (avf_init_vf(eth_dev) != 0) {
209 PMD_INIT_LOG(ERR, "Init vf failed");
214 eth_dev->data->mac_addrs = rte_zmalloc(
216 ETHER_ADDR_LEN * AVF_NUM_MACADDR_MAX,
218 if (!eth_dev->data->mac_addrs) {
219 PMD_INIT_LOG(ERR, "Failed to allocate %d bytes needed to"
220 " store MAC addresses",
221 ETHER_ADDR_LEN * AVF_NUM_MACADDR_MAX);
224 /* If the MAC address is not configured by host,
225 * generate a random one.
227 if (!is_valid_assigned_ether_addr((struct ether_addr *)hw->mac.addr))
228 eth_random_addr(hw->mac.addr);
229 ether_addr_copy((struct ether_addr *)hw->mac.addr,
230 ð_dev->data->mac_addrs[0]);
232 /* register callback func to eal lib */
233 rte_intr_callback_register(&pci_dev->intr_handle,
234 avf_dev_interrupt_handler,
237 /* enable uio intr after callback register */
238 rte_intr_enable(&pci_dev->intr_handle);
240 /* configure and enable device interrupt */
247 avf_dev_close(struct rte_eth_dev *dev)
249 struct avf_hw *hw = AVF_DEV_PRIVATE_TO_HW(dev->data->dev_private);
250 struct rte_pci_device *pci_dev = RTE_ETH_DEV_TO_PCI(dev);
251 struct rte_intr_handle *intr_handle = &pci_dev->intr_handle;
253 avf_shutdown_adminq(hw);
254 /* disable uio intr before callback unregister */
255 rte_intr_disable(intr_handle);
257 /* unregister callback func from eal lib */
258 rte_intr_callback_unregister(intr_handle,
259 avf_dev_interrupt_handler, dev);
260 avf_disable_irq0(hw);
264 avf_dev_uninit(struct rte_eth_dev *dev)
266 struct avf_info *vf = AVF_DEV_PRIVATE_TO_VF(dev->data->dev_private);
267 struct avf_hw *hw = AVF_DEV_PRIVATE_TO_HW(dev->data->dev_private);
269 if (rte_eal_process_type() != RTE_PROC_PRIMARY)
273 dev->rx_pkt_burst = NULL;
274 dev->tx_pkt_burst = NULL;
275 if (hw->adapter_stopped == 0)
278 rte_free(vf->vf_res);
282 rte_free(vf->aq_resp);
285 rte_free(dev->data->mac_addrs);
286 dev->data->mac_addrs = NULL;
289 rte_free(vf->rss_lut);
293 rte_free(vf->rss_key);
300 static int eth_avf_pci_probe(struct rte_pci_driver *pci_drv __rte_unused,
301 struct rte_pci_device *pci_dev)
303 return rte_eth_dev_pci_generic_probe(pci_dev,
304 sizeof(struct avf_adapter), avf_dev_init);
307 static int eth_avf_pci_remove(struct rte_pci_device *pci_dev)
309 return rte_eth_dev_pci_generic_remove(pci_dev, avf_dev_uninit);
312 /* Adaptive virtual function driver struct */
313 static struct rte_pci_driver rte_avf_pmd = {
314 .id_table = pci_id_avf_map,
315 .drv_flags = RTE_PCI_DRV_NEED_MAPPING | RTE_PCI_DRV_IOVA_AS_VA,
316 .probe = eth_avf_pci_probe,
317 .remove = eth_avf_pci_remove,
320 RTE_PMD_REGISTER_PCI(net_avf, rte_avf_pmd);
321 RTE_PMD_REGISTER_PCI_TABLE(net_avf, pci_id_avf_map);
322 RTE_PMD_REGISTER_KMOD_DEP(net_avf, "* igb_uio | vfio-pci");
323 RTE_INIT(avf_init_log);
327 avf_logtype_init = rte_log_register("pmd.avf.init");
328 if (avf_logtype_init >= 0)
329 rte_log_set_level(avf_logtype_init, RTE_LOG_NOTICE);
330 avf_logtype_driver = rte_log_register("pmd.avf.driver");
331 if (avf_logtype_driver >= 0)
332 rte_log_set_level(avf_logtype_driver, RTE_LOG_NOTICE);
335 /* memory func for base code */
337 avf_allocate_dma_mem_d(__rte_unused struct avf_hw *hw,
338 struct avf_dma_mem *mem,
342 const struct rte_memzone *mz = NULL;
343 char z_name[RTE_MEMZONE_NAMESIZE];
346 return AVF_ERR_PARAM;
348 snprintf(z_name, sizeof(z_name), "avf_dma_%"PRIu64, rte_rand());
349 mz = rte_memzone_reserve_bounded(z_name, size, SOCKET_ID_ANY, 0,
350 alignment, RTE_PGSIZE_2M);
352 return AVF_ERR_NO_MEMORY;
356 mem->pa = mz->phys_addr;
357 mem->zone = (const void *)mz;
359 "memzone %s allocated with physical address: %"PRIu64,
366 avf_free_dma_mem_d(__rte_unused struct avf_hw *hw,
367 struct avf_dma_mem *mem)
370 return AVF_ERR_PARAM;
373 "memzone %s to be freed with physical address: %"PRIu64,
374 ((const struct rte_memzone *)mem->zone)->name, mem->pa);
375 rte_memzone_free((const struct rte_memzone *)mem->zone);
384 avf_allocate_virt_mem_d(__rte_unused struct avf_hw *hw,
385 struct avf_virt_mem *mem,
389 return AVF_ERR_PARAM;
392 mem->va = rte_zmalloc("avf", size, 0);
397 return AVF_ERR_NO_MEMORY;
401 avf_free_virt_mem_d(__rte_unused struct avf_hw *hw,
402 struct avf_virt_mem *mem)
405 return AVF_ERR_PARAM;