1 /* SPDX-License-Identifier: BSD-3-Clause
2 * Copyright(C) 2021 Marvell.
4 #include <cnxk_rte_flow.h>
6 const struct cnxk_rte_flow_term_info term[] = {
7 [RTE_FLOW_ITEM_TYPE_ETH] = {ROC_NPC_ITEM_TYPE_ETH,
8 sizeof(struct rte_flow_item_eth)},
9 [RTE_FLOW_ITEM_TYPE_VLAN] = {ROC_NPC_ITEM_TYPE_VLAN,
10 sizeof(struct rte_flow_item_vlan)},
11 [RTE_FLOW_ITEM_TYPE_E_TAG] = {ROC_NPC_ITEM_TYPE_E_TAG,
12 sizeof(struct rte_flow_item_e_tag)},
13 [RTE_FLOW_ITEM_TYPE_IPV4] = {ROC_NPC_ITEM_TYPE_IPV4,
14 sizeof(struct rte_flow_item_ipv4)},
15 [RTE_FLOW_ITEM_TYPE_IPV6] = {ROC_NPC_ITEM_TYPE_IPV6,
16 sizeof(struct rte_flow_item_ipv6)},
17 [RTE_FLOW_ITEM_TYPE_ARP_ETH_IPV4] = {
18 ROC_NPC_ITEM_TYPE_ARP_ETH_IPV4,
19 sizeof(struct rte_flow_item_arp_eth_ipv4)},
20 [RTE_FLOW_ITEM_TYPE_MPLS] = {ROC_NPC_ITEM_TYPE_MPLS,
21 sizeof(struct rte_flow_item_mpls)},
22 [RTE_FLOW_ITEM_TYPE_ICMP] = {ROC_NPC_ITEM_TYPE_ICMP,
23 sizeof(struct rte_flow_item_icmp)},
24 [RTE_FLOW_ITEM_TYPE_UDP] = {ROC_NPC_ITEM_TYPE_UDP,
25 sizeof(struct rte_flow_item_udp)},
26 [RTE_FLOW_ITEM_TYPE_TCP] = {ROC_NPC_ITEM_TYPE_TCP,
27 sizeof(struct rte_flow_item_tcp)},
28 [RTE_FLOW_ITEM_TYPE_SCTP] = {ROC_NPC_ITEM_TYPE_SCTP,
29 sizeof(struct rte_flow_item_sctp)},
30 [RTE_FLOW_ITEM_TYPE_ESP] = {ROC_NPC_ITEM_TYPE_ESP,
31 sizeof(struct rte_flow_item_esp)},
32 [RTE_FLOW_ITEM_TYPE_GRE] = {ROC_NPC_ITEM_TYPE_GRE,
33 sizeof(struct rte_flow_item_gre)},
34 [RTE_FLOW_ITEM_TYPE_NVGRE] = {ROC_NPC_ITEM_TYPE_NVGRE,
35 sizeof(struct rte_flow_item_nvgre)},
36 [RTE_FLOW_ITEM_TYPE_VXLAN] = {ROC_NPC_ITEM_TYPE_VXLAN,
37 sizeof(struct rte_flow_item_vxlan)},
38 [RTE_FLOW_ITEM_TYPE_GTPC] = {ROC_NPC_ITEM_TYPE_GTPC,
39 sizeof(struct rte_flow_item_gtp)},
40 [RTE_FLOW_ITEM_TYPE_GTPU] = {ROC_NPC_ITEM_TYPE_GTPU,
41 sizeof(struct rte_flow_item_gtp)},
42 [RTE_FLOW_ITEM_TYPE_GENEVE] = {ROC_NPC_ITEM_TYPE_GENEVE,
43 sizeof(struct rte_flow_item_geneve)},
44 [RTE_FLOW_ITEM_TYPE_VXLAN_GPE] = {
45 ROC_NPC_ITEM_TYPE_VXLAN_GPE,
46 sizeof(struct rte_flow_item_vxlan_gpe)},
47 [RTE_FLOW_ITEM_TYPE_IPV6_EXT] = {ROC_NPC_ITEM_TYPE_IPV6_EXT,
48 sizeof(struct rte_flow_item_ipv6_ext)},
49 [RTE_FLOW_ITEM_TYPE_VOID] = {ROC_NPC_ITEM_TYPE_VOID, 0},
50 [RTE_FLOW_ITEM_TYPE_ANY] = {ROC_NPC_ITEM_TYPE_ANY, 0},
51 [RTE_FLOW_ITEM_TYPE_GRE_KEY] = {ROC_NPC_ITEM_TYPE_GRE_KEY,
53 [RTE_FLOW_ITEM_TYPE_HIGIG2] = {
54 ROC_NPC_ITEM_TYPE_HIGIG2,
55 sizeof(struct rte_flow_item_higig2_hdr)}
59 cnxk_map_actions(struct rte_eth_dev *eth_dev,
60 const struct rte_flow_action actions[],
61 struct roc_npc_action in_actions[])
63 const struct rte_flow_action_count *act_count;
64 const struct rte_flow_action_queue *act_q;
68 for (; actions->type != RTE_FLOW_ACTION_TYPE_END; actions++) {
69 switch (actions->type) {
70 case RTE_FLOW_ACTION_TYPE_VOID:
71 in_actions[i].type = ROC_NPC_ACTION_TYPE_VOID;
74 case RTE_FLOW_ACTION_TYPE_MARK:
75 in_actions[i].type = ROC_NPC_ACTION_TYPE_MARK;
76 in_actions[i].conf = actions->conf;
79 case RTE_FLOW_ACTION_TYPE_FLAG:
80 in_actions[i].type = ROC_NPC_ACTION_TYPE_FLAG;
83 case RTE_FLOW_ACTION_TYPE_COUNT:
84 act_count = (const struct rte_flow_action_count *)
87 if (act_count->shared == 1) {
88 plt_npc_dbg("Shared counter is not supported");
91 in_actions[i].type = ROC_NPC_ACTION_TYPE_COUNT;
94 case RTE_FLOW_ACTION_TYPE_DROP:
95 in_actions[i].type = ROC_NPC_ACTION_TYPE_DROP;
98 case RTE_FLOW_ACTION_TYPE_PF:
99 in_actions[i].type = ROC_NPC_ACTION_TYPE_PF;
102 case RTE_FLOW_ACTION_TYPE_VF:
103 in_actions[i].type = ROC_NPC_ACTION_TYPE_VF;
104 in_actions[i].conf = actions->conf;
107 case RTE_FLOW_ACTION_TYPE_QUEUE:
108 act_q = (const struct rte_flow_action_queue *)
111 if (rq >= eth_dev->data->nb_rx_queues) {
112 plt_npc_dbg("Invalid queue index");
115 in_actions[i].type = ROC_NPC_ACTION_TYPE_QUEUE;
116 in_actions[i].conf = actions->conf;
119 case RTE_FLOW_ACTION_TYPE_RSS:
120 in_actions[i].type = ROC_NPC_ACTION_TYPE_RSS;
123 case RTE_FLOW_ACTION_TYPE_SECURITY:
124 in_actions[i].type = ROC_NPC_ACTION_TYPE_SEC;
127 plt_npc_dbg("Action is not supported = %d",
133 in_actions[i].type = ROC_NPC_ACTION_TYPE_END;
141 cnxk_map_flow_data(struct rte_eth_dev *eth_dev,
142 const struct rte_flow_attr *attr,
143 const struct rte_flow_item pattern[],
144 const struct rte_flow_action actions[],
145 struct roc_npc_attr *in_attr,
146 struct roc_npc_item_info in_pattern[],
147 struct roc_npc_action in_actions[])
151 in_attr->priority = attr->priority;
152 in_attr->ingress = attr->ingress;
153 in_attr->egress = attr->egress;
155 while (pattern->type != RTE_FLOW_ITEM_TYPE_END) {
156 in_pattern[i].spec = pattern->spec;
157 in_pattern[i].last = pattern->last;
158 in_pattern[i].mask = pattern->mask;
159 in_pattern[i].type = term[pattern->type].item_type;
160 in_pattern[i].size = term[pattern->type].item_size;
164 in_pattern[i].type = ROC_NPC_ITEM_TYPE_END;
166 return cnxk_map_actions(eth_dev, actions, in_actions);
170 cnxk_flow_validate(struct rte_eth_dev *eth_dev,
171 const struct rte_flow_attr *attr,
172 const struct rte_flow_item pattern[],
173 const struct rte_flow_action actions[],
174 struct rte_flow_error *error)
176 struct roc_npc_item_info in_pattern[ROC_NPC_ITEM_TYPE_END + 1];
177 struct roc_npc_action in_actions[ROC_NPC_MAX_ACTION_COUNT];
178 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
179 struct roc_npc *npc = &dev->npc;
180 struct roc_npc_attr in_attr;
181 struct roc_npc_flow flow;
184 memset(&flow, 0, sizeof(flow));
186 rc = cnxk_map_flow_data(eth_dev, attr, pattern, actions, &in_attr,
187 in_pattern, in_actions);
189 rte_flow_error_set(error, 0, RTE_FLOW_ERROR_TYPE_ACTION_NUM,
190 NULL, "Failed to map flow data");
194 return roc_npc_flow_parse(npc, &in_attr, in_pattern, in_actions, &flow);
197 struct roc_npc_flow *
198 cnxk_flow_create(struct rte_eth_dev *eth_dev, const struct rte_flow_attr *attr,
199 const struct rte_flow_item pattern[],
200 const struct rte_flow_action actions[],
201 struct rte_flow_error *error)
203 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
204 struct roc_npc_item_info in_pattern[ROC_NPC_ITEM_TYPE_END + 1];
205 struct roc_npc_action in_actions[ROC_NPC_MAX_ACTION_COUNT];
206 struct roc_npc *npc = &dev->npc;
207 struct roc_npc_attr in_attr;
208 struct roc_npc_flow *flow;
212 rc = cnxk_map_flow_data(eth_dev, attr, pattern, actions, &in_attr,
213 in_pattern, in_actions);
215 rte_flow_error_set(error, 0, RTE_FLOW_ERROR_TYPE_ACTION_NUM,
216 NULL, "Failed to map flow data");
220 flow = roc_npc_flow_create(npc, &in_attr, in_pattern, in_actions,
223 rte_flow_error_set(error, errcode, errcode, NULL,
224 roc_error_msg_get(errcode));
232 cnxk_flow_destroy(struct rte_eth_dev *eth_dev, struct roc_npc_flow *flow,
233 struct rte_flow_error *error)
235 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
236 struct roc_npc *npc = &dev->npc;
239 rc = roc_npc_flow_destroy(npc, flow);
241 rte_flow_error_set(error, rc, RTE_FLOW_ERROR_TYPE_UNSPECIFIED,
242 NULL, "Flow Destroy failed");
247 cnxk_flow_flush(struct rte_eth_dev *eth_dev, struct rte_flow_error *error)
249 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
250 struct roc_npc *npc = &dev->npc;
253 rc = roc_npc_mcam_free_all_resources(npc);
255 rte_flow_error_set(error, EIO, RTE_FLOW_ERROR_TYPE_UNSPECIFIED,
256 NULL, "Failed to flush filter");
264 cnxk_flow_query(struct rte_eth_dev *eth_dev, struct rte_flow *flow,
265 const struct rte_flow_action *action, void *data,
266 struct rte_flow_error *error)
268 struct roc_npc_flow *in_flow = (struct roc_npc_flow *)flow;
269 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
270 struct roc_npc *npc = &dev->npc;
271 struct rte_flow_query_count *query = data;
272 const char *errmsg = NULL;
273 int errcode = ENOTSUP;
276 if (action->type != RTE_FLOW_ACTION_TYPE_COUNT) {
277 errmsg = "Only COUNT is supported in query";
281 if (in_flow->ctr_id == NPC_COUNTER_NONE) {
282 errmsg = "Counter is not available";
286 rc = roc_npc_mcam_read_counter(npc, in_flow->ctr_id, &query->hits);
289 errmsg = "Error reading flow counter";
293 query->bytes_set = 0;
296 rc = roc_npc_mcam_clear_counter(npc, in_flow->ctr_id);
299 errmsg = "Error clearing flow counter";
306 rte_flow_error_set(error, errcode, RTE_FLOW_ERROR_TYPE_UNSPECIFIED,
312 cnxk_flow_isolate(struct rte_eth_dev *eth_dev __rte_unused,
313 int enable __rte_unused, struct rte_flow_error *error)
315 /* If we support, we need to un-install the default mcam
316 * entry for this port.
319 rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_UNSPECIFIED,
320 NULL, "Flow isolation not supported");
326 cnxk_flow_dev_dump(struct rte_eth_dev *eth_dev, struct rte_flow *flow,
327 FILE *file, struct rte_flow_error *error)
329 struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
330 struct roc_npc *npc = &dev->npc;
333 rte_flow_error_set(error, EINVAL,
334 RTE_FLOW_ERROR_TYPE_UNSPECIFIED, NULL,
340 rte_flow_error_set(error, EINVAL,
341 RTE_FLOW_ERROR_TYPE_HANDLE,
347 roc_npc_flow_dump(file, npc);
352 struct rte_flow_ops cnxk_flow_ops = {
353 .validate = cnxk_flow_validate,
354 .flush = cnxk_flow_flush,
355 .query = cnxk_flow_query,
356 .isolate = cnxk_flow_isolate,
357 .dev_dump = cnxk_flow_dev_dump,