1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
|
/* SPDX-License-Identifier: BSD-3-Clause
* Copyright(C) 2019 Marvell International Ltd.
*/
#include <rte_malloc.h>
#include "nitrox_device.h"
#include "nitrox_hal.h"
#include "nitrox_sym.h"
#define PCI_VENDOR_ID_CAVIUM 0x177d
#define NITROX_V_PCI_VF_DEV_ID 0x13
TAILQ_HEAD(ndev_list, nitrox_device);
static struct ndev_list ndev_list = TAILQ_HEAD_INITIALIZER(ndev_list);
static struct nitrox_device *
ndev_allocate(struct rte_pci_device *pdev)
{
struct nitrox_device *ndev;
ndev = rte_zmalloc_socket("nitrox device", sizeof(*ndev),
RTE_CACHE_LINE_SIZE,
pdev->device.numa_node);
if (!ndev)
return NULL;
TAILQ_INSERT_TAIL(&ndev_list, ndev, next);
return ndev;
}
static void
ndev_init(struct nitrox_device *ndev, struct rte_pci_device *pdev)
{
enum nitrox_vf_mode vf_mode;
ndev->pdev = pdev;
ndev->bar_addr = pdev->mem_resource[0].addr;
vf_mode = vf_get_vf_config_mode(ndev->bar_addr);
ndev->nr_queues = vf_config_mode_to_nr_queues(vf_mode);
}
static struct nitrox_device *
find_ndev(struct rte_pci_device *pdev)
{
struct nitrox_device *ndev;
TAILQ_FOREACH(ndev, &ndev_list, next)
if (ndev->pdev == pdev)
return ndev;
return NULL;
}
static void
ndev_release(struct nitrox_device *ndev)
{
if (!ndev)
return;
TAILQ_REMOVE(&ndev_list, ndev, next);
rte_free(ndev);
}
static int
nitrox_pci_probe(struct rte_pci_driver *pci_drv __rte_unused,
struct rte_pci_device *pdev)
{
struct nitrox_device *ndev;
int err;
/* Nitrox CSR space */
if (!pdev->mem_resource[0].addr)
return -EINVAL;
ndev = ndev_allocate(pdev);
if (!ndev)
return -ENOMEM;
ndev_init(ndev, pdev);
err = nitrox_sym_pmd_create(ndev);
if (err) {
ndev_release(ndev);
return err;
}
return 0;
}
static int
nitrox_pci_remove(struct rte_pci_device *pdev)
{
struct nitrox_device *ndev;
int err;
ndev = find_ndev(pdev);
if (!ndev)
return -ENODEV;
err = nitrox_sym_pmd_destroy(ndev);
if (err)
return err;
ndev_release(ndev);
return 0;
}
static struct rte_pci_id pci_id_nitrox_map[] = {
{
/* Nitrox 5 VF */
RTE_PCI_DEVICE(PCI_VENDOR_ID_CAVIUM, NITROX_V_PCI_VF_DEV_ID)
},
{.device_id = 0},
};
static struct rte_pci_driver nitrox_pmd = {
.id_table = pci_id_nitrox_map,
.drv_flags = RTE_PCI_DRV_NEED_MAPPING,
.probe = nitrox_pci_probe,
.remove = nitrox_pci_remove,
};
RTE_PMD_REGISTER_PCI(nitrox, nitrox_pmd);
RTE_PMD_REGISTER_PCI_TABLE(nitrox, pci_id_nitrox_map);
|