devargs: add common key definition
[dpdk.git] / drivers / common / sfc_efx / sfc_efx.c
1 /* SPDX-License-Identifier: BSD-3-Clause
2  *
3  * Copyright(c) 2019-2021 Xilinx, Inc.
4  * Copyright(c) 2019 Solarflare Communications Inc.
5  *
6  * This software was jointly developed between OKTET Labs (under contract
7  * for Solarflare) and Solarflare Communications, Inc.
8  */
9
10 #include <string.h>
11 #include <rte_log.h>
12 #include <rte_kvargs.h>
13 #include <rte_devargs.h>
14
15 #include "sfc_efx_log.h"
16 #include "sfc_efx.h"
17
18 uint32_t sfc_efx_logtype;
19
20 static int
21 sfc_efx_kvarg_dev_class_handler(__rte_unused const char *key,
22                                 const char *class_str, void *opaque)
23 {
24         enum sfc_efx_dev_class *dev_class = opaque;
25
26         if (class_str == NULL)
27                 return *dev_class;
28
29         if (strcmp(class_str, "vdpa") == 0) {
30                 *dev_class = SFC_EFX_DEV_CLASS_VDPA;
31         } else if (strcmp(class_str, "net") == 0) {
32                 *dev_class = SFC_EFX_DEV_CLASS_NET;
33         } else {
34                 SFC_EFX_LOG(ERR, "Unsupported class %s.", class_str);
35                 *dev_class = SFC_EFX_DEV_CLASS_INVALID;
36         }
37
38         return 0;
39 }
40
41 enum sfc_efx_dev_class
42 sfc_efx_dev_class_get(struct rte_devargs *devargs)
43 {
44         struct rte_kvargs *kvargs;
45         enum sfc_efx_dev_class dev_class = SFC_EFX_DEV_CLASS_NET;
46
47         if (devargs == NULL)
48                 return dev_class;
49
50         kvargs = rte_kvargs_parse(devargs->args, NULL);
51         if (kvargs == NULL)
52                 return dev_class;
53
54         if (rte_kvargs_count(kvargs, RTE_DEVARGS_KEY_CLASS) != 0) {
55                 rte_kvargs_process(kvargs, RTE_DEVARGS_KEY_CLASS,
56                                    sfc_efx_kvarg_dev_class_handler, &dev_class);
57         }
58
59         rte_kvargs_free(kvargs);
60
61         return dev_class;
62 }
63
64 static efx_rc_t
65 sfc_efx_find_mem_bar(efsys_pci_config_t *configp, int bar_index,
66                      efsys_bar_t *barp)
67 {
68         efsys_bar_t result;
69         struct rte_pci_device *dev;
70
71         memset(&result, 0, sizeof(result));
72
73         if (bar_index < 0 || bar_index >= PCI_MAX_RESOURCE)
74                 return -EINVAL;
75
76         dev = configp->espc_dev;
77
78         result.esb_rid = bar_index;
79         result.esb_dev = dev;
80         result.esb_base = dev->mem_resource[bar_index].addr;
81
82         *barp = result;
83
84         return 0;
85 }
86
87 static efx_rc_t
88 sfc_efx_pci_config_readd(efsys_pci_config_t *configp, uint32_t offset,
89                          efx_dword_t *edp)
90 {
91         int rc;
92
93         rc = rte_pci_read_config(configp->espc_dev, edp->ed_u32, sizeof(*edp),
94                                  offset);
95
96         return (rc < 0 || rc != sizeof(*edp)) ? EIO : 0;
97 }
98
99 int
100 sfc_efx_family(struct rte_pci_device *pci_dev,
101                efx_bar_region_t *mem_ebrp, efx_family_t *family)
102 {
103         static const efx_pci_ops_t ops = {
104                 .epo_config_readd = sfc_efx_pci_config_readd,
105                 .epo_find_mem_bar = sfc_efx_find_mem_bar,
106         };
107
108         efsys_pci_config_t espcp;
109         int rc;
110
111         espcp.espc_dev = pci_dev;
112
113         rc = efx_family_probe_bar(pci_dev->id.vendor_id,
114                                   pci_dev->id.device_id,
115                                   &espcp, &ops, family, mem_ebrp);
116
117         return rc;
118 }
119
120 RTE_INIT(sfc_efx_register_logtype)
121 {
122         int ret;
123
124         ret = rte_log_register_type_and_pick_level("pmd.common.sfc_efx",
125                                                    RTE_LOG_NOTICE);
126         sfc_efx_logtype = (ret < 0) ? RTE_LOGTYPE_PMD : ret;
127 }