xref: /dpdk/drivers/net/cnxk/cnxk_flow.c (revision 0981a22ec3359793e7515decb07adc5a13d772c0)
1795ac238SJerin Jacob /* SPDX-License-Identifier: BSD-3-Clause
2795ac238SJerin Jacob  * Copyright(C) 2021 Marvell.
3795ac238SJerin Jacob  */
4795ac238SJerin Jacob #include <cnxk_flow.h>
5c1ae225eSHarman Kalra #include <cnxk_rep.h>
6795ac238SJerin Jacob 
7d11278e3SHarman Kalra #define IS_REP_BIT 7
8c2f3e9e7SHarman Kalra 
9c2f3e9e7SHarman Kalra #define TNL_DCP_MATCH_ID 5
10c2f3e9e7SHarman Kalra #define NRML_MATCH_ID	 1
11795ac238SJerin Jacob const struct cnxk_rte_flow_term_info term[] = {
1200701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_ETH] = {ROC_NPC_ITEM_TYPE_ETH, sizeof(struct rte_flow_item_eth)},
1300701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_VLAN] = {ROC_NPC_ITEM_TYPE_VLAN, sizeof(struct rte_flow_item_vlan)},
1400701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_E_TAG] = {ROC_NPC_ITEM_TYPE_E_TAG, sizeof(struct rte_flow_item_e_tag)},
1500701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_IPV4] = {ROC_NPC_ITEM_TYPE_IPV4, sizeof(struct rte_flow_item_ipv4)},
1600701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_IPV6] = {ROC_NPC_ITEM_TYPE_IPV6, sizeof(struct rte_flow_item_ipv6)},
1700701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_IPV6_FRAG_EXT] = {ROC_NPC_ITEM_TYPE_IPV6_FRAG_EXT,
18a800675bSSatheesh Paul 					      sizeof(struct rte_flow_item_ipv6_frag_ext)},
1900701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_ARP_ETH_IPV4] = {ROC_NPC_ITEM_TYPE_ARP_ETH_IPV4,
20795ac238SJerin Jacob 					     sizeof(struct rte_flow_item_arp_eth_ipv4)},
2100701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_MPLS] = {ROC_NPC_ITEM_TYPE_MPLS, sizeof(struct rte_flow_item_mpls)},
2200701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_ICMP] = {ROC_NPC_ITEM_TYPE_ICMP, sizeof(struct rte_flow_item_icmp)},
2300701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_UDP] = {ROC_NPC_ITEM_TYPE_UDP, sizeof(struct rte_flow_item_udp)},
2400701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_TCP] = {ROC_NPC_ITEM_TYPE_TCP, sizeof(struct rte_flow_item_tcp)},
2500701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_SCTP] = {ROC_NPC_ITEM_TYPE_SCTP, sizeof(struct rte_flow_item_sctp)},
2600701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_ESP] = {ROC_NPC_ITEM_TYPE_ESP, sizeof(struct rte_flow_item_esp)},
2700701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_GRE] = {ROC_NPC_ITEM_TYPE_GRE, sizeof(struct rte_flow_item_gre)},
2800701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_NVGRE] = {ROC_NPC_ITEM_TYPE_NVGRE, sizeof(struct rte_flow_item_nvgre)},
2900701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_VXLAN] = {ROC_NPC_ITEM_TYPE_VXLAN, sizeof(struct rte_flow_item_vxlan)},
3000701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_GTPC] = {ROC_NPC_ITEM_TYPE_GTPC, sizeof(struct rte_flow_item_gtp)},
3100701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_GTPU] = {ROC_NPC_ITEM_TYPE_GTPU, sizeof(struct rte_flow_item_gtp)},
32795ac238SJerin Jacob 	[RTE_FLOW_ITEM_TYPE_GENEVE] = {ROC_NPC_ITEM_TYPE_GENEVE,
33795ac238SJerin Jacob 				       sizeof(struct rte_flow_item_geneve)},
3400701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_VXLAN_GPE] = {ROC_NPC_ITEM_TYPE_VXLAN_GPE,
35795ac238SJerin Jacob 					  sizeof(struct rte_flow_item_vxlan_gpe)},
36795ac238SJerin Jacob 	[RTE_FLOW_ITEM_TYPE_IPV6_EXT] = {ROC_NPC_ITEM_TYPE_IPV6_EXT,
37795ac238SJerin Jacob 					 sizeof(struct rte_flow_item_ipv6_ext)},
38795ac238SJerin Jacob 	[RTE_FLOW_ITEM_TYPE_VOID] = {ROC_NPC_ITEM_TYPE_VOID, 0},
39795ac238SJerin Jacob 	[RTE_FLOW_ITEM_TYPE_ANY] = {ROC_NPC_ITEM_TYPE_ANY, 0},
4000701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_GRE_KEY] = {ROC_NPC_ITEM_TYPE_GRE_KEY, sizeof(uint32_t)},
41795ac238SJerin Jacob 	[RTE_FLOW_ITEM_TYPE_HIGIG2] = {ROC_NPC_ITEM_TYPE_HIGIG2,
42795ac238SJerin Jacob 				       sizeof(struct rte_flow_item_higig2_hdr)},
4300701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_RAW] = {ROC_NPC_ITEM_TYPE_RAW, sizeof(struct rte_flow_item_raw)},
4400701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_MARK] = {ROC_NPC_ITEM_TYPE_MARK, sizeof(struct rte_flow_item_mark)},
45986739d9SSatheesh Paul 	[RTE_FLOW_ITEM_TYPE_IPV6_ROUTING_EXT] = {ROC_NPC_ITEM_TYPE_IPV6_ROUTING_EXT,
46986739d9SSatheesh Paul 						 sizeof(struct rte_flow_item_ipv6_routing_ext)},
4728896009SSatheesh Paul 	[RTE_FLOW_ITEM_TYPE_TX_QUEUE] = {ROC_NPC_ITEM_TYPE_TX_QUEUE,
48db715b94SSatheesh Paul 					 sizeof(struct rte_flow_item_tx_queue)},
4900701e71SKiran Kumar K 	[RTE_FLOW_ITEM_TYPE_REPRESENTED_PORT] = {ROC_NPC_ITEM_TYPE_REPRESENTED_PORT,
5000701e71SKiran Kumar K 						 sizeof(struct rte_flow_item_ethdev)},
51db715b94SSatheesh Paul 	[RTE_FLOW_ITEM_TYPE_PPPOES] = {ROC_NPC_ITEM_TYPE_PPPOES,
5200701e71SKiran Kumar K 				       sizeof(struct rte_flow_item_pppoe)}
5300701e71SKiran Kumar K };
54795ac238SJerin Jacob 
55795ac238SJerin Jacob static int
56db715b94SSatheesh Paul npc_rss_action_validate(struct rte_eth_dev *eth_dev, const struct rte_flow_attr *attr,
57795ac238SJerin Jacob 			const struct rte_flow_action *act)
58795ac238SJerin Jacob {
59795ac238SJerin Jacob 	const struct rte_flow_action_rss *rss;
60795ac238SJerin Jacob 
61795ac238SJerin Jacob 	rss = (const struct rte_flow_action_rss *)act->conf;
62795ac238SJerin Jacob 
63795ac238SJerin Jacob 	if (attr->egress) {
64795ac238SJerin Jacob 		plt_err("No support of RSS in egress");
65795ac238SJerin Jacob 		return -EINVAL;
66795ac238SJerin Jacob 	}
67795ac238SJerin Jacob 
68795ac238SJerin Jacob 	if (eth_dev->data->dev_conf.rxmode.mq_mode != RTE_ETH_MQ_RX_RSS) {
69795ac238SJerin Jacob 		plt_err("multi-queue mode is disabled");
70795ac238SJerin Jacob 		return -ENOTSUP;
71795ac238SJerin Jacob 	}
72795ac238SJerin Jacob 
73795ac238SJerin Jacob 	if (!rss || !rss->queue_num) {
74795ac238SJerin Jacob 		plt_err("no valid queues");
75795ac238SJerin Jacob 		return -EINVAL;
76795ac238SJerin Jacob 	}
77795ac238SJerin Jacob 
78795ac238SJerin Jacob 	if (rss->func != RTE_ETH_HASH_FUNCTION_DEFAULT) {
79795ac238SJerin Jacob 		plt_err("non-default RSS hash functions are not supported");
80795ac238SJerin Jacob 		return -ENOTSUP;
81795ac238SJerin Jacob 	}
82795ac238SJerin Jacob 
83795ac238SJerin Jacob 	if (rss->key_len && rss->key_len > ROC_NIX_RSS_KEY_LEN) {
84795ac238SJerin Jacob 		plt_err("RSS hash key too large");
85795ac238SJerin Jacob 		return -ENOTSUP;
86795ac238SJerin Jacob 	}
87795ac238SJerin Jacob 
88795ac238SJerin Jacob 	return 0;
89795ac238SJerin Jacob }
90795ac238SJerin Jacob 
91795ac238SJerin Jacob static void
92752ce2f3SKiran Kumar K npc_rss_flowkey_get(struct cnxk_eth_dev *eth_dev, const struct roc_npc_action *rss_action,
93752ce2f3SKiran Kumar K 		    uint32_t *flowkey_cfg, uint64_t default_rss_types)
94795ac238SJerin Jacob {
95795ac238SJerin Jacob 	const struct roc_npc_action_rss *rss;
96752ce2f3SKiran Kumar K 	uint64_t rss_types;
97795ac238SJerin Jacob 
98795ac238SJerin Jacob 	rss = (const struct roc_npc_action_rss *)rss_action->conf;
99752ce2f3SKiran Kumar K 	rss_types = rss->types;
100752ce2f3SKiran Kumar K 	/* If no RSS types are specified, use default one */
101752ce2f3SKiran Kumar K 	if (rss_types == 0)
102752ce2f3SKiran Kumar K 		rss_types = default_rss_types;
103795ac238SJerin Jacob 
104752ce2f3SKiran Kumar K 	*flowkey_cfg = cnxk_rss_ethdev_to_nix(eth_dev, rss_types, rss->level);
105795ac238SJerin Jacob }
106795ac238SJerin Jacob 
107795ac238SJerin Jacob static int
108dd23ff70SSatheesh Paul npc_parse_port_id_action(struct rte_eth_dev *eth_dev, const struct rte_flow_action *action,
109dd23ff70SSatheesh Paul 			 uint16_t *dst_pf_func, uint16_t *dst_channel)
110dd23ff70SSatheesh Paul {
111dd23ff70SSatheesh Paul 	const struct rte_flow_action_port_id *port_act;
112dd23ff70SSatheesh Paul 	struct rte_eth_dev *portid_eth_dev;
113dd23ff70SSatheesh Paul 	char if_name[RTE_ETH_NAME_MAX_LEN];
114dd23ff70SSatheesh Paul 	struct cnxk_eth_dev *hw_dst;
115dd23ff70SSatheesh Paul 	struct roc_npc *roc_npc_dst;
116dd23ff70SSatheesh Paul 	int rc = 0;
117dd23ff70SSatheesh Paul 
118dd23ff70SSatheesh Paul 	port_act = (const struct rte_flow_action_port_id *)action->conf;
119dd23ff70SSatheesh Paul 
120dd23ff70SSatheesh Paul 	rc = rte_eth_dev_get_name_by_port(port_act->id, if_name);
121dd23ff70SSatheesh Paul 	if (rc) {
122dd23ff70SSatheesh Paul 		plt_err("Name not found for output port id");
123dd23ff70SSatheesh Paul 		goto err_exit;
124dd23ff70SSatheesh Paul 	}
125dd23ff70SSatheesh Paul 	portid_eth_dev = rte_eth_dev_allocated(if_name);
126dd23ff70SSatheesh Paul 	if (!portid_eth_dev) {
127dd23ff70SSatheesh Paul 		plt_err("eth_dev not found for output port id");
128dd23ff70SSatheesh Paul 		goto err_exit;
129dd23ff70SSatheesh Paul 	}
130dd23ff70SSatheesh Paul 	if (strcmp(portid_eth_dev->device->driver->name, eth_dev->device->driver->name) != 0) {
131dd23ff70SSatheesh Paul 		plt_err("Output port not under same driver");
132dd23ff70SSatheesh Paul 		goto err_exit;
133dd23ff70SSatheesh Paul 	}
134dd23ff70SSatheesh Paul 	hw_dst = portid_eth_dev->data->dev_private;
135dd23ff70SSatheesh Paul 	roc_npc_dst = &hw_dst->npc;
136dd23ff70SSatheesh Paul 	*dst_pf_func = roc_npc_dst->pf_func;
137dd23ff70SSatheesh Paul 	*dst_channel = hw_dst->npc.channel;
138dd23ff70SSatheesh Paul 
139dd23ff70SSatheesh Paul 	return 0;
140dd23ff70SSatheesh Paul 
141dd23ff70SSatheesh Paul err_exit:
142dd23ff70SSatheesh Paul 	return -EINVAL;
143dd23ff70SSatheesh Paul }
144dd23ff70SSatheesh Paul 
145dd23ff70SSatheesh Paul static int
146dd23ff70SSatheesh Paul roc_npc_parse_sample_subaction(struct rte_eth_dev *eth_dev, const struct rte_flow_action actions[],
147dd23ff70SSatheesh Paul 			       struct roc_npc_action_sample *sample_action)
148dd23ff70SSatheesh Paul {
149dd23ff70SSatheesh Paul 	uint16_t dst_pf_func = 0, dst_channel = 0;
150dd23ff70SSatheesh Paul 	const struct roc_npc_action_vf *vf_act;
151dd23ff70SSatheesh Paul 	int rc = 0, count = 0;
152dd23ff70SSatheesh Paul 	bool is_empty = true;
153dd23ff70SSatheesh Paul 
154dd23ff70SSatheesh Paul 	if (sample_action->ratio != 1) {
155dd23ff70SSatheesh Paul 		plt_err("Sample ratio must be 1");
156dd23ff70SSatheesh Paul 		return -EINVAL;
157dd23ff70SSatheesh Paul 	}
158dd23ff70SSatheesh Paul 
159dd23ff70SSatheesh Paul 	for (; actions->type != RTE_FLOW_ACTION_TYPE_END; actions++) {
160dd23ff70SSatheesh Paul 		is_empty = false;
161dd23ff70SSatheesh Paul 		switch (actions->type) {
162dd23ff70SSatheesh Paul 		case RTE_FLOW_ACTION_TYPE_PF:
163dd23ff70SSatheesh Paul 			count++;
164dd23ff70SSatheesh Paul 			sample_action->action_type |= ROC_NPC_ACTION_TYPE_PF;
165dd23ff70SSatheesh Paul 			break;
166dd23ff70SSatheesh Paul 		case RTE_FLOW_ACTION_TYPE_VF:
167dd23ff70SSatheesh Paul 			count++;
168dd23ff70SSatheesh Paul 			vf_act = (const struct roc_npc_action_vf *)actions->conf;
169dd23ff70SSatheesh Paul 			sample_action->action_type |= ROC_NPC_ACTION_TYPE_VF;
170dd23ff70SSatheesh Paul 			sample_action->pf_func = vf_act->id & NPC_PFVF_FUNC_MASK;
171dd23ff70SSatheesh Paul 			break;
172dd23ff70SSatheesh Paul 		case RTE_FLOW_ACTION_TYPE_PORT_ID:
173dd23ff70SSatheesh Paul 			rc = npc_parse_port_id_action(eth_dev, actions, &dst_pf_func, &dst_channel);
174dd23ff70SSatheesh Paul 			if (rc)
175dd23ff70SSatheesh Paul 				return -EINVAL;
176dd23ff70SSatheesh Paul 
177dd23ff70SSatheesh Paul 			count++;
178dd23ff70SSatheesh Paul 			sample_action->action_type |= ROC_NPC_ACTION_TYPE_PORT_ID;
179dd23ff70SSatheesh Paul 			sample_action->pf_func = dst_pf_func;
180dd23ff70SSatheesh Paul 			sample_action->channel = dst_channel;
181dd23ff70SSatheesh Paul 			break;
182dd23ff70SSatheesh Paul 		default:
183dd23ff70SSatheesh Paul 			continue;
184dd23ff70SSatheesh Paul 		}
185dd23ff70SSatheesh Paul 	}
186dd23ff70SSatheesh Paul 
187dd23ff70SSatheesh Paul 	if (count > 1 || is_empty)
188dd23ff70SSatheesh Paul 		return -EINVAL;
189dd23ff70SSatheesh Paul 
190dd23ff70SSatheesh Paul 	return 0;
191dd23ff70SSatheesh Paul }
192dd23ff70SSatheesh Paul 
193dd23ff70SSatheesh Paul static int
194c2f3e9e7SHarman Kalra append_mark_action(struct roc_npc_action *in_actions, uint8_t has_tunnel_pattern,
195c2f3e9e7SHarman Kalra 		   uint64_t *free_allocs, int *act_cnt)
196c2f3e9e7SHarman Kalra {
197c2f3e9e7SHarman Kalra 	struct rte_flow_action_mark *act_mark;
198c2f3e9e7SHarman Kalra 	int i = *act_cnt, j = 0;
199c2f3e9e7SHarman Kalra 
200c2f3e9e7SHarman Kalra 	/* Add Mark action */
201c2f3e9e7SHarman Kalra 	i++;
202c2f3e9e7SHarman Kalra 	act_mark = plt_zmalloc(sizeof(struct rte_flow_action_mark), 0);
203c2f3e9e7SHarman Kalra 	if (!act_mark) {
204c2f3e9e7SHarman Kalra 		plt_err("Error allocation memory");
205c2f3e9e7SHarman Kalra 		return -ENOMEM;
206c2f3e9e7SHarman Kalra 	}
207c2f3e9e7SHarman Kalra 
208c2f3e9e7SHarman Kalra 	while (free_allocs[j] != 0)
209c2f3e9e7SHarman Kalra 		j++;
210c2f3e9e7SHarman Kalra 	free_allocs[j] = (uint64_t)act_mark;
211c2f3e9e7SHarman Kalra 	/* Mark ID format: (tunnel type - VxLAN, Geneve << 6) | Tunnel decap */
212c2f3e9e7SHarman Kalra 	act_mark->id =
213c2f3e9e7SHarman Kalra 		has_tunnel_pattern ? ((has_tunnel_pattern << 6) | TNL_DCP_MATCH_ID) : NRML_MATCH_ID;
214c2f3e9e7SHarman Kalra 	in_actions[i].type = ROC_NPC_ACTION_TYPE_MARK;
215c2f3e9e7SHarman Kalra 	in_actions[i].conf = (struct rte_flow_action_mark *)act_mark;
216c2f3e9e7SHarman Kalra 
217c2f3e9e7SHarman Kalra 	plt_rep_dbg("Assigned mark ID %x", act_mark->id);
218c2f3e9e7SHarman Kalra 
219c2f3e9e7SHarman Kalra 	*act_cnt = i;
220c2f3e9e7SHarman Kalra 
221c2f3e9e7SHarman Kalra 	return 0;
222c2f3e9e7SHarman Kalra }
223c2f3e9e7SHarman Kalra 
224c2f3e9e7SHarman Kalra static int
225*0981a22eSHarman Kalra append_rss_action(struct cnxk_eth_dev *dev, struct roc_npc_action *in_actions, uint16_t nb_rxq,
226*0981a22eSHarman Kalra 		  uint32_t *flowkey_cfg, uint64_t *free_allocs, uint16_t rss_repte_pf_func,
227*0981a22eSHarman Kalra 		  int *act_cnt)
228*0981a22eSHarman Kalra {
229*0981a22eSHarman Kalra 	struct roc_npc_action_rss *rss_conf;
230*0981a22eSHarman Kalra 	int i = *act_cnt, j = 0, l, rc = 0;
231*0981a22eSHarman Kalra 	uint16_t *queue_arr;
232*0981a22eSHarman Kalra 
233*0981a22eSHarman Kalra 	rss_conf = plt_zmalloc(sizeof(struct roc_npc_action_rss), 0);
234*0981a22eSHarman Kalra 	if (!rss_conf) {
235*0981a22eSHarman Kalra 		plt_err("Failed to allocate memory for rss conf");
236*0981a22eSHarman Kalra 		rc = -ENOMEM;
237*0981a22eSHarman Kalra 		goto fail;
238*0981a22eSHarman Kalra 	}
239*0981a22eSHarman Kalra 
240*0981a22eSHarman Kalra 	/* Add RSS action */
241*0981a22eSHarman Kalra 	rss_conf->queue_num = nb_rxq;
242*0981a22eSHarman Kalra 	queue_arr = calloc(1, rss_conf->queue_num * sizeof(uint16_t));
243*0981a22eSHarman Kalra 	if (!queue_arr) {
244*0981a22eSHarman Kalra 		plt_err("Failed to allocate memory for rss queue");
245*0981a22eSHarman Kalra 		rc = -ENOMEM;
246*0981a22eSHarman Kalra 		goto free_rss;
247*0981a22eSHarman Kalra 	}
248*0981a22eSHarman Kalra 
249*0981a22eSHarman Kalra 	for (l = 0; l < nb_rxq; l++)
250*0981a22eSHarman Kalra 		queue_arr[l] = l;
251*0981a22eSHarman Kalra 	rss_conf->queue = queue_arr;
252*0981a22eSHarman Kalra 	rss_conf->key = NULL;
253*0981a22eSHarman Kalra 	rss_conf->types = RTE_ETH_RSS_IP | RTE_ETH_RSS_UDP | RTE_ETH_RSS_TCP;
254*0981a22eSHarman Kalra 
255*0981a22eSHarman Kalra 	i++;
256*0981a22eSHarman Kalra 
257*0981a22eSHarman Kalra 	in_actions[i].type = ROC_NPC_ACTION_TYPE_RSS;
258*0981a22eSHarman Kalra 	in_actions[i].conf = (struct roc_npc_action_rss *)rss_conf;
259*0981a22eSHarman Kalra 	in_actions[i].rss_repte_pf_func = rss_repte_pf_func;
260*0981a22eSHarman Kalra 
261*0981a22eSHarman Kalra 	npc_rss_flowkey_get(dev, &in_actions[i], flowkey_cfg,
262*0981a22eSHarman Kalra 			    RTE_ETH_RSS_IP | RTE_ETH_RSS_UDP | RTE_ETH_RSS_TCP);
263*0981a22eSHarman Kalra 
264*0981a22eSHarman Kalra 	*act_cnt = i;
265*0981a22eSHarman Kalra 
266*0981a22eSHarman Kalra 	while (free_allocs[j] != 0)
267*0981a22eSHarman Kalra 		j++;
268*0981a22eSHarman Kalra 	free_allocs[j] = (uint64_t)rss_conf;
269*0981a22eSHarman Kalra 
270*0981a22eSHarman Kalra 	return 0;
271*0981a22eSHarman Kalra free_rss:
272*0981a22eSHarman Kalra 	rte_free(rss_conf);
273*0981a22eSHarman Kalra fail:
274*0981a22eSHarman Kalra 	return rc;
275*0981a22eSHarman Kalra }
276*0981a22eSHarman Kalra 
277*0981a22eSHarman Kalra static int
278d11278e3SHarman Kalra representor_rep_portid_action(struct roc_npc_action *in_actions, struct rte_eth_dev *eth_dev,
279d11278e3SHarman Kalra 			      struct rte_eth_dev *portid_eth_dev,
280d11278e3SHarman Kalra 			      enum rte_flow_action_type act_type, uint8_t rep_pattern,
281c2f3e9e7SHarman Kalra 			      uint16_t *dst_pf_func, bool is_rep, uint8_t has_tunnel_pattern,
282*0981a22eSHarman Kalra 			      uint64_t *free_allocs, int *act_cnt, uint32_t *flowkey_cfg)
283d11278e3SHarman Kalra {
284d11278e3SHarman Kalra 	struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
285d11278e3SHarman Kalra 	struct rte_eth_dev *rep_eth_dev = portid_eth_dev;
286d11278e3SHarman Kalra 	struct rte_flow_action_of_set_vlan_vid *vlan_vid;
287d11278e3SHarman Kalra 	struct rte_flow_action_of_set_vlan_pcp *vlan_pcp;
288d11278e3SHarman Kalra 	struct rte_flow_action_of_push_vlan *push_vlan;
289d11278e3SHarman Kalra 	struct rte_flow_action_queue *act_q = NULL;
290d11278e3SHarman Kalra 	struct cnxk_rep_dev *rep_dev;
291d11278e3SHarman Kalra 	struct roc_npc *npc;
292d11278e3SHarman Kalra 	uint16_t vlan_tci;
293c2f3e9e7SHarman Kalra 	int j = 0, rc;
294d11278e3SHarman Kalra 
295d11278e3SHarman Kalra 	/* For inserting an action in the list */
296d11278e3SHarman Kalra 	int i = *act_cnt;
297d11278e3SHarman Kalra 
298d11278e3SHarman Kalra 	rep_dev = cnxk_rep_pmd_priv(rep_eth_dev);
299d11278e3SHarman Kalra 	if (!is_rep) {
300d11278e3SHarman Kalra 		dev = cnxk_eth_pmd_priv(eth_dev);
301d11278e3SHarman Kalra 		npc = &dev->npc;
302d11278e3SHarman Kalra 	} else {
303d11278e3SHarman Kalra 		npc = &rep_dev->parent_dev->npc;
304d11278e3SHarman Kalra 	}
305d11278e3SHarman Kalra 	if (rep_pattern >> IS_REP_BIT) { /* Check for normal/representor port as action */
306d11278e3SHarman Kalra 		if ((rep_pattern & 0x7f) == RTE_FLOW_ITEM_TYPE_PORT_REPRESENTOR) {
307d11278e3SHarman Kalra 			/* Case: Repr port pattern -> Default TX rule -> LBK ->
308d11278e3SHarman Kalra 			 *  Pattern RX LBK rule hit -> Action: send to new pf_func
309d11278e3SHarman Kalra 			 */
310d11278e3SHarman Kalra 			if (act_type == RTE_FLOW_ACTION_TYPE_PORT_REPRESENTOR) {
311d11278e3SHarman Kalra 				/* New pf_func corresponds to ESW + queue corresponding to rep_id */
312d11278e3SHarman Kalra 				act_q = plt_zmalloc(sizeof(struct rte_flow_action_queue), 0);
313d11278e3SHarman Kalra 				if (!act_q) {
314d11278e3SHarman Kalra 					plt_err("Error allocation memory");
315d11278e3SHarman Kalra 					return -ENOMEM;
316d11278e3SHarman Kalra 				}
317d11278e3SHarman Kalra 				act_q->index = rep_dev->rep_id;
318d11278e3SHarman Kalra 
319d11278e3SHarman Kalra 				while (free_allocs[j] != 0)
320d11278e3SHarman Kalra 					j++;
321d11278e3SHarman Kalra 				free_allocs[j] = (uint64_t)act_q;
322d11278e3SHarman Kalra 				in_actions[i].type = ROC_NPC_ACTION_TYPE_QUEUE;
323d11278e3SHarman Kalra 				in_actions[i].conf = (struct rte_flow_action_queue *)act_q;
324d11278e3SHarman Kalra 				npc->rep_act_pf_func = rep_dev->parent_dev->npc.pf_func;
325d11278e3SHarman Kalra 			} else {
326d11278e3SHarman Kalra 				/* New pf_func corresponds to hw_func of representee */
327d11278e3SHarman Kalra 				in_actions[i].type = ROC_NPC_ACTION_TYPE_PORT_ID;
328d11278e3SHarman Kalra 				npc->rep_act_pf_func = rep_dev->hw_func;
329d11278e3SHarman Kalra 				*dst_pf_func = rep_dev->hw_func;
330d11278e3SHarman Kalra 			}
331d11278e3SHarman Kalra 			/* Additional action to strip the VLAN from packets received by LBK */
332d11278e3SHarman Kalra 			i++;
333d11278e3SHarman Kalra 			in_actions[i].type = ROC_NPC_ACTION_TYPE_VLAN_STRIP;
334d11278e3SHarman Kalra 			goto done;
335d11278e3SHarman Kalra 		}
336d11278e3SHarman Kalra 		/* Case: Repd port pattern -> TX Rule with VLAN -> LBK -> Default RX LBK rule hit
337d11278e3SHarman Kalra 		 * base on vlan, if packet goes to ESW or actual pf_func -> Action :
338d11278e3SHarman Kalra 		 *    act port_representor: send to ESW respective using 1<<8 | rep_id as tci value
339d11278e3SHarman Kalra 		 *    act represented_port: send to actual port using rep_id as tci value.
340d11278e3SHarman Kalra 		 */
341d11278e3SHarman Kalra 		/* Add RTE_FLOW_ACTION_TYPE_OF_PUSH_VLAN action */
342d11278e3SHarman Kalra 		push_vlan = plt_zmalloc(sizeof(struct rte_flow_action_of_push_vlan), 0);
343d11278e3SHarman Kalra 		if (!push_vlan) {
344d11278e3SHarman Kalra 			plt_err("Error allocation memory");
345d11278e3SHarman Kalra 			return -ENOMEM;
346d11278e3SHarman Kalra 		}
347d11278e3SHarman Kalra 
348d11278e3SHarman Kalra 		while (free_allocs[j] != 0)
349d11278e3SHarman Kalra 			j++;
350d11278e3SHarman Kalra 		free_allocs[j] = (uint64_t)push_vlan;
351d11278e3SHarman Kalra 		push_vlan->ethertype = ntohs(ROC_ESWITCH_VLAN_TPID);
352d11278e3SHarman Kalra 		in_actions[i].type = ROC_NPC_ACTION_TYPE_VLAN_ETHTYPE_INSERT;
353d11278e3SHarman Kalra 		in_actions[i].conf = (struct rte_flow_action_of_push_vlan *)push_vlan;
354d11278e3SHarman Kalra 		i++;
355d11278e3SHarman Kalra 
356d11278e3SHarman Kalra 		/* Add RTE_FLOW_ACTION_TYPE_OF_SET_VLAN_PCP action */
357d11278e3SHarman Kalra 		vlan_pcp = plt_zmalloc(sizeof(struct rte_flow_action_of_set_vlan_pcp), 0);
358d11278e3SHarman Kalra 		if (!vlan_pcp) {
359d11278e3SHarman Kalra 			plt_err("Error allocation memory");
360d11278e3SHarman Kalra 			return -ENOMEM;
361d11278e3SHarman Kalra 		}
362d11278e3SHarman Kalra 
363d11278e3SHarman Kalra 		free_allocs[j + 1] = (uint64_t)vlan_pcp;
364d11278e3SHarman Kalra 		vlan_pcp->vlan_pcp = 0;
365d11278e3SHarman Kalra 		in_actions[i].type = ROC_NPC_ACTION_TYPE_VLAN_PCP_INSERT;
366d11278e3SHarman Kalra 		in_actions[i].conf = (struct rte_flow_action_of_set_vlan_pcp *)vlan_pcp;
367d11278e3SHarman Kalra 		i++;
368d11278e3SHarman Kalra 
369d11278e3SHarman Kalra 		/* Add RTE_FLOW_ACTION_TYPE_OF_SET_VLAN_VID action */
370d11278e3SHarman Kalra 		vlan_vid = plt_zmalloc(sizeof(struct rte_flow_action_of_set_vlan_vid), 0);
371d11278e3SHarman Kalra 		if (!vlan_vid) {
372d11278e3SHarman Kalra 			plt_err("Error allocation memory");
373d11278e3SHarman Kalra 			return -ENOMEM;
374d11278e3SHarman Kalra 		}
375d11278e3SHarman Kalra 
376d11278e3SHarman Kalra 		free_allocs[j + 2] = (uint64_t)vlan_vid;
377d11278e3SHarman Kalra 		if (act_type == RTE_FLOW_ACTION_TYPE_PORT_REPRESENTOR)
378d11278e3SHarman Kalra 			vlan_tci = rep_dev->rep_id | (1ULL << CNXK_ESWITCH_VFPF_SHIFT);
379d11278e3SHarman Kalra 		else
380d11278e3SHarman Kalra 			vlan_tci = rep_dev->rep_id;
381d11278e3SHarman Kalra 		vlan_vid->vlan_vid = ntohs(vlan_tci);
382d11278e3SHarman Kalra 		in_actions[i].type = ROC_NPC_ACTION_TYPE_VLAN_INSERT;
383d11278e3SHarman Kalra 		in_actions[i].conf = (struct rte_flow_action_of_set_vlan_vid *)vlan_vid;
384d11278e3SHarman Kalra 
385d11278e3SHarman Kalra 		/* Change default channel to UCAST_CHAN (63) while sending */
386d11278e3SHarman Kalra 		npc->rep_act_rep = true;
387d11278e3SHarman Kalra 	} else {
388d11278e3SHarman Kalra 		if (act_type == RTE_FLOW_ACTION_TYPE_PORT_REPRESENTOR) {
389d11278e3SHarman Kalra 			/* Case: Pattern wire port ->  Pattern RX rule->
390d11278e3SHarman Kalra 			 * Action: pf_func = ESW. queue = rep_id
391d11278e3SHarman Kalra 			 */
392d11278e3SHarman Kalra 			act_q = plt_zmalloc(sizeof(struct rte_flow_action_queue), 0);
393d11278e3SHarman Kalra 			if (!act_q) {
394d11278e3SHarman Kalra 				plt_err("Error allocation memory");
395d11278e3SHarman Kalra 				return -ENOMEM;
396d11278e3SHarman Kalra 			}
397d11278e3SHarman Kalra 			while (free_allocs[j] != 0)
398d11278e3SHarman Kalra 				j++;
399d11278e3SHarman Kalra 			free_allocs[j] = (uint64_t)act_q;
400d11278e3SHarman Kalra 			act_q->index = rep_dev->rep_id;
401d11278e3SHarman Kalra 
402d11278e3SHarman Kalra 			in_actions[i].type = ROC_NPC_ACTION_TYPE_QUEUE;
403d11278e3SHarman Kalra 			in_actions[i].conf = (struct rte_flow_action_queue *)act_q;
404d11278e3SHarman Kalra 			npc->rep_act_pf_func = rep_dev->parent_dev->npc.pf_func;
405d11278e3SHarman Kalra 		} else {
406d11278e3SHarman Kalra 			/* Case: Pattern wire port -> Pattern RX rule->
407d11278e3SHarman Kalra 			 * Action: Receive at actual hw_func
408d11278e3SHarman Kalra 			 */
409d11278e3SHarman Kalra 			in_actions[i].type = ROC_NPC_ACTION_TYPE_PORT_ID;
410d11278e3SHarman Kalra 			npc->rep_act_pf_func = rep_dev->hw_func;
411d11278e3SHarman Kalra 			*dst_pf_func = rep_dev->hw_func;
412c2f3e9e7SHarman Kalra 
413c2f3e9e7SHarman Kalra 			/* Append a mark action - needed to identify the flow */
414c2f3e9e7SHarman Kalra 			rc = append_mark_action(in_actions, has_tunnel_pattern, free_allocs, &i);
415c2f3e9e7SHarman Kalra 			if (rc)
416c2f3e9e7SHarman Kalra 				return rc;
417*0981a22eSHarman Kalra 			/* Append RSS action if representee has RSS enabled */
418*0981a22eSHarman Kalra 			if (rep_dev->nb_rxq > 1) {
419*0981a22eSHarman Kalra 				/* PF can install rule for only its VF acting as representee */
420*0981a22eSHarman Kalra 				if (rep_dev->hw_func &&
421*0981a22eSHarman Kalra 				    roc_eswitch_is_repte_pfs_vf(rep_dev->hw_func,
422*0981a22eSHarman Kalra 							roc_nix_get_pf_func(npc->roc_nix))) {
423*0981a22eSHarman Kalra 					rc = append_rss_action(dev, in_actions, rep_dev->nb_rxq,
424*0981a22eSHarman Kalra 							       flowkey_cfg, free_allocs,
425*0981a22eSHarman Kalra 							       rep_dev->hw_func, &i);
426*0981a22eSHarman Kalra 					if (rc)
427*0981a22eSHarman Kalra 						return rc;
428*0981a22eSHarman Kalra 				}
429*0981a22eSHarman Kalra 			}
430d11278e3SHarman Kalra 		}
431d11278e3SHarman Kalra 	}
432d11278e3SHarman Kalra done:
433d11278e3SHarman Kalra 	*act_cnt = i;
434d11278e3SHarman Kalra 
435d11278e3SHarman Kalra 	return 0;
436d11278e3SHarman Kalra }
437d11278e3SHarman Kalra 
438d11278e3SHarman Kalra static int
439c1ae225eSHarman Kalra representor_portid_action(struct roc_npc_action *in_actions, struct rte_eth_dev *portid_eth_dev,
440d11278e3SHarman Kalra 			  uint16_t *dst_pf_func, uint8_t has_tunnel_pattern, uint64_t *free_allocs,
441d11278e3SHarman Kalra 			  int *act_cnt)
442c1ae225eSHarman Kalra {
443c1ae225eSHarman Kalra 	struct rte_eth_dev *rep_eth_dev = portid_eth_dev;
444c1ae225eSHarman Kalra 	struct cnxk_rep_dev *rep_dev;
445c1ae225eSHarman Kalra 	/* For inserting an action in the list */
446c2f3e9e7SHarman Kalra 	int i = *act_cnt, rc;
447c1ae225eSHarman Kalra 
448c1ae225eSHarman Kalra 	rep_dev = cnxk_rep_pmd_priv(rep_eth_dev);
449d11278e3SHarman Kalra 
450c1ae225eSHarman Kalra 	*dst_pf_func = rep_dev->hw_func;
451c1ae225eSHarman Kalra 
452c2f3e9e7SHarman Kalra 	rc = append_mark_action(in_actions, has_tunnel_pattern, free_allocs, &i);
453c2f3e9e7SHarman Kalra 	if (rc)
454c2f3e9e7SHarman Kalra 		return rc;
455c1ae225eSHarman Kalra 
456c1ae225eSHarman Kalra 	*act_cnt = i;
457c2f3e9e7SHarman Kalra 	plt_rep_dbg("Rep port %d ID %d rep_dev->hw_func 0x%x", rep_dev->port_id, rep_dev->rep_id,
458c2f3e9e7SHarman Kalra 		    rep_dev->hw_func);
459c1ae225eSHarman Kalra 
460c1ae225eSHarman Kalra 	return 0;
461c1ae225eSHarman Kalra }
462c1ae225eSHarman Kalra 
463c1ae225eSHarman Kalra static int
464795ac238SJerin Jacob cnxk_map_actions(struct rte_eth_dev *eth_dev, const struct rte_flow_attr *attr,
465b7eb0e0cSSatheesh Paul 		 const struct rte_flow_action actions[], struct roc_npc_action in_actions[],
466dd23ff70SSatheesh Paul 		 struct roc_npc_action_sample *in_sample_actions, uint32_t *flowkey_cfg,
467d11278e3SHarman Kalra 		 uint16_t *dst_pf_func, uint8_t has_tunnel_pattern, bool is_rep,
468d11278e3SHarman Kalra 		 uint8_t rep_pattern, uint64_t *free_allocs)
469795ac238SJerin Jacob {
470795ac238SJerin Jacob 	struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
47147f40516SSatheesh Paul 	const struct rte_flow_action_queue *act_q = NULL;
472a05a8e40SIvan Malov 	const struct rte_flow_action_ethdev *act_ethdev;
473dd23ff70SSatheesh Paul 	const struct rte_flow_action_sample *act_sample;
474795ac238SJerin Jacob 	const struct rte_flow_action_port_id *port_act;
475795ac238SJerin Jacob 	struct rte_eth_dev *portid_eth_dev;
476795ac238SJerin Jacob 	char if_name[RTE_ETH_NAME_MAX_LEN];
477795ac238SJerin Jacob 	struct cnxk_eth_dev *hw_dst;
478795ac238SJerin Jacob 	struct roc_npc *roc_npc_dst;
47947f40516SSatheesh Paul 	bool is_vf_action = false;
480795ac238SJerin Jacob 	int i = 0, rc = 0;
481795ac238SJerin Jacob 	int rq;
482795ac238SJerin Jacob 
483795ac238SJerin Jacob 	for (; actions->type != RTE_FLOW_ACTION_TYPE_END; actions++) {
484795ac238SJerin Jacob 		switch (actions->type) {
485795ac238SJerin Jacob 		case RTE_FLOW_ACTION_TYPE_VOID:
486795ac238SJerin Jacob 			in_actions[i].type = ROC_NPC_ACTION_TYPE_VOID;
487795ac238SJerin Jacob 			break;
488795ac238SJerin Jacob 
489795ac238SJerin Jacob 		case RTE_FLOW_ACTION_TYPE_MARK:
490795ac238SJerin Jacob 			in_actions[i].type = ROC_NPC_ACTION_TYPE_MARK;
491795ac238SJerin Jacob 			in_actions[i].conf = actions->conf;
492795ac238SJerin Jacob 			break;
493795ac238SJerin Jacob 
494795ac238SJerin Jacob 		case RTE_FLOW_ACTION_TYPE_FLAG:
495795ac238SJerin Jacob 			in_actions[i].type = ROC_NPC_ACTION_TYPE_FLAG;
496795ac238SJerin Jacob 			break;
497795ac238SJerin Jacob 
498795ac238SJerin Jacob 		case RTE_FLOW_ACTION_TYPE_COUNT:
499795ac238SJerin Jacob 			in_actions[i].type = ROC_NPC_ACTION_TYPE_COUNT;
500795ac238SJerin Jacob 			break;
501795ac238SJerin Jacob 
502795ac238SJerin Jacob 		case RTE_FLOW_ACTION_TYPE_DROP:
503795ac238SJerin Jacob 			in_actions[i].type = ROC_NPC_ACTION_TYPE_DROP;
504795ac238SJerin Jacob 			break;
505795ac238SJerin Jacob 
506795ac238SJerin Jacob 		case RTE_FLOW_ACTION_TYPE_PF:
507795ac238SJerin Jacob 			in_actions[i].type = ROC_NPC_ACTION_TYPE_PF;
508795ac238SJerin Jacob 			break;
509795ac238SJerin Jacob 
510795ac238SJerin Jacob 		case RTE_FLOW_ACTION_TYPE_VF:
511795ac238SJerin Jacob 			in_actions[i].type = ROC_NPC_ACTION_TYPE_VF;
512795ac238SJerin Jacob 			in_actions[i].conf = actions->conf;
51347f40516SSatheesh Paul 			is_vf_action = true;
514795ac238SJerin Jacob 			break;
515795ac238SJerin Jacob 
516a05a8e40SIvan Malov 		case RTE_FLOW_ACTION_TYPE_REPRESENTED_PORT:
517c1ae225eSHarman Kalra 		case RTE_FLOW_ACTION_TYPE_PORT_REPRESENTOR:
518d11278e3SHarman Kalra 			in_actions[i].conf = actions->conf;
519d11278e3SHarman Kalra 			act_ethdev = (const struct rte_flow_action_ethdev *)actions->conf;
520d11278e3SHarman Kalra 			if (rte_eth_dev_get_name_by_port(act_ethdev->port_id, if_name)) {
521d11278e3SHarman Kalra 				plt_err("Name not found for output port id");
522d11278e3SHarman Kalra 				goto err_exit;
523d11278e3SHarman Kalra 			}
524d11278e3SHarman Kalra 			portid_eth_dev = rte_eth_dev_allocated(if_name);
525d11278e3SHarman Kalra 			if (!portid_eth_dev) {
526d11278e3SHarman Kalra 				plt_err("eth_dev not found for output port id");
527d11278e3SHarman Kalra 				goto err_exit;
528d11278e3SHarman Kalra 			}
529d11278e3SHarman Kalra 
530d11278e3SHarman Kalra 			plt_rep_dbg("Rule installed by port %d if_name %s act_ethdev->port_id %d",
531d11278e3SHarman Kalra 				    eth_dev->data->port_id, if_name, act_ethdev->port_id);
532d11278e3SHarman Kalra 			if (cnxk_ethdev_is_representor(if_name)) {
533d11278e3SHarman Kalra 				if (representor_rep_portid_action(in_actions, eth_dev,
534*0981a22eSHarman Kalra 					    portid_eth_dev, actions->type, rep_pattern,
535*0981a22eSHarman Kalra 					    dst_pf_func, is_rep, has_tunnel_pattern,
536*0981a22eSHarman Kalra 					    free_allocs, &i, flowkey_cfg)) {
537d11278e3SHarman Kalra 					plt_err("Representor port action set failed");
538d11278e3SHarman Kalra 					goto err_exit;
539d11278e3SHarman Kalra 				}
540d11278e3SHarman Kalra 			} else {
541d11278e3SHarman Kalra 				if (actions->type == RTE_FLOW_ACTION_TYPE_REPRESENTED_PORT)
542d11278e3SHarman Kalra 					continue;
543d11278e3SHarman Kalra 				/* Normal port as represented_port as action not supported*/
544d11278e3SHarman Kalra 				return -ENOTSUP;
545d11278e3SHarman Kalra 			}
546d11278e3SHarman Kalra 			break;
547795ac238SJerin Jacob 		case RTE_FLOW_ACTION_TYPE_PORT_ID:
548d11278e3SHarman Kalra 			/* No port ID action on representor ethdevs */
549d11278e3SHarman Kalra 			if (is_rep)
550d11278e3SHarman Kalra 				continue;
551795ac238SJerin Jacob 			in_actions[i].type = ROC_NPC_ACTION_TYPE_PORT_ID;
552795ac238SJerin Jacob 			in_actions[i].conf = actions->conf;
553d11278e3SHarman Kalra 			act_ethdev = (const struct rte_flow_action_ethdev *)actions->conf;
554d11278e3SHarman Kalra 			port_act = (const struct rte_flow_action_port_id *)actions->conf;
555a05a8e40SIvan Malov 			if (rte_eth_dev_get_name_by_port(
556a05a8e40SIvan Malov 				    actions->type != RTE_FLOW_ACTION_TYPE_PORT_ID ?
557d11278e3SHarman Kalra 					    act_ethdev->port_id :
558d11278e3SHarman Kalra 					    port_act->id,
559d11278e3SHarman Kalra 				    if_name)) {
560795ac238SJerin Jacob 				plt_err("Name not found for output port id");
561795ac238SJerin Jacob 				goto err_exit;
562795ac238SJerin Jacob 			}
563795ac238SJerin Jacob 			portid_eth_dev = rte_eth_dev_allocated(if_name);
564795ac238SJerin Jacob 			if (!portid_eth_dev) {
565795ac238SJerin Jacob 				plt_err("eth_dev not found for output port id");
566795ac238SJerin Jacob 				goto err_exit;
567795ac238SJerin Jacob 			}
568c1ae225eSHarman Kalra 
569c1ae225eSHarman Kalra 			if (cnxk_ethdev_is_representor(if_name)) {
570c1ae225eSHarman Kalra 				plt_rep_dbg("Representor port %d act port %d", port_act->id,
571c1ae225eSHarman Kalra 					    act_ethdev->port_id);
572c1ae225eSHarman Kalra 				if (representor_portid_action(in_actions, portid_eth_dev,
573c1ae225eSHarman Kalra 							      dst_pf_func, has_tunnel_pattern,
574d11278e3SHarman Kalra 							      free_allocs, &i)) {
575c1ae225eSHarman Kalra 					plt_err("Representor port action set failed");
576c1ae225eSHarman Kalra 					goto err_exit;
577c1ae225eSHarman Kalra 				}
578c1ae225eSHarman Kalra 			} else {
579795ac238SJerin Jacob 				if (strcmp(portid_eth_dev->device->driver->name,
580795ac238SJerin Jacob 					   eth_dev->device->driver->name) != 0) {
581795ac238SJerin Jacob 					plt_err("Output port not under same driver");
582795ac238SJerin Jacob 					goto err_exit;
583795ac238SJerin Jacob 				}
584c1ae225eSHarman Kalra 
585795ac238SJerin Jacob 				hw_dst = portid_eth_dev->data->dev_private;
586795ac238SJerin Jacob 				roc_npc_dst = &hw_dst->npc;
587b7eb0e0cSSatheesh Paul 				*dst_pf_func = roc_npc_dst->pf_func;
588c1ae225eSHarman Kalra 			}
589795ac238SJerin Jacob 			break;
590795ac238SJerin Jacob 
591795ac238SJerin Jacob 		case RTE_FLOW_ACTION_TYPE_QUEUE:
59247f40516SSatheesh Paul 			act_q = (const struct rte_flow_action_queue *)actions->conf;
593795ac238SJerin Jacob 			in_actions[i].type = ROC_NPC_ACTION_TYPE_QUEUE;
594795ac238SJerin Jacob 			in_actions[i].conf = actions->conf;
595795ac238SJerin Jacob 			break;
596795ac238SJerin Jacob 
597795ac238SJerin Jacob 		case RTE_FLOW_ACTION_TYPE_RSS:
598d11278e3SHarman Kalra 			/* No RSS action on representor ethdevs */
599d11278e3SHarman Kalra 			if (is_rep)
600d11278e3SHarman Kalra 				continue;
601795ac238SJerin Jacob 			rc = npc_rss_action_validate(eth_dev, attr, actions);
602795ac238SJerin Jacob 			if (rc)
603795ac238SJerin Jacob 				goto err_exit;
604*0981a22eSHarman Kalra 
605795ac238SJerin Jacob 			in_actions[i].type = ROC_NPC_ACTION_TYPE_RSS;
606795ac238SJerin Jacob 			in_actions[i].conf = actions->conf;
607752ce2f3SKiran Kumar K 			npc_rss_flowkey_get(dev, &in_actions[i], flowkey_cfg,
608752ce2f3SKiran Kumar K 					    eth_dev->data->dev_conf.rx_adv_conf.rss_conf.rss_hf);
609795ac238SJerin Jacob 			break;
610795ac238SJerin Jacob 
611795ac238SJerin Jacob 		case RTE_FLOW_ACTION_TYPE_SECURITY:
612795ac238SJerin Jacob 			in_actions[i].type = ROC_NPC_ACTION_TYPE_SEC;
6138efa348eSKiran Kumar K 			in_actions[i].conf = actions->conf;
614795ac238SJerin Jacob 			break;
615795ac238SJerin Jacob 		case RTE_FLOW_ACTION_TYPE_OF_POP_VLAN:
616795ac238SJerin Jacob 			in_actions[i].type = ROC_NPC_ACTION_TYPE_VLAN_STRIP;
617795ac238SJerin Jacob 			break;
618795ac238SJerin Jacob 		case RTE_FLOW_ACTION_TYPE_OF_SET_VLAN_VID:
619795ac238SJerin Jacob 			in_actions[i].type = ROC_NPC_ACTION_TYPE_VLAN_INSERT;
620795ac238SJerin Jacob 			in_actions[i].conf = actions->conf;
621795ac238SJerin Jacob 			break;
622795ac238SJerin Jacob 		case RTE_FLOW_ACTION_TYPE_OF_PUSH_VLAN:
623795ac238SJerin Jacob 			in_actions[i].type =
624795ac238SJerin Jacob 				ROC_NPC_ACTION_TYPE_VLAN_ETHTYPE_INSERT;
625795ac238SJerin Jacob 			in_actions[i].conf = actions->conf;
626795ac238SJerin Jacob 			break;
627795ac238SJerin Jacob 		case RTE_FLOW_ACTION_TYPE_OF_SET_VLAN_PCP:
628795ac238SJerin Jacob 			in_actions[i].type =
629795ac238SJerin Jacob 				ROC_NPC_ACTION_TYPE_VLAN_PCP_INSERT;
630795ac238SJerin Jacob 			in_actions[i].conf = actions->conf;
631795ac238SJerin Jacob 			break;
632795ac238SJerin Jacob 		case RTE_FLOW_ACTION_TYPE_METER:
633795ac238SJerin Jacob 			in_actions[i].type = ROC_NPC_ACTION_TYPE_METER;
634795ac238SJerin Jacob 			in_actions[i].conf = actions->conf;
635795ac238SJerin Jacob 			break;
636a4477550SAnkur Dwivedi 		case RTE_FLOW_ACTION_TYPE_AGE:
637a4477550SAnkur Dwivedi 			in_actions[i].type = ROC_NPC_ACTION_TYPE_AGE;
638a4477550SAnkur Dwivedi 			in_actions[i].conf = actions->conf;
639a4477550SAnkur Dwivedi 			break;
640dd23ff70SSatheesh Paul 		case RTE_FLOW_ACTION_TYPE_SAMPLE:
641dd23ff70SSatheesh Paul 			act_sample = actions->conf;
642dd23ff70SSatheesh Paul 			in_sample_actions->ratio = act_sample->ratio;
643dd23ff70SSatheesh Paul 			rc = roc_npc_parse_sample_subaction(eth_dev, act_sample->actions,
644dd23ff70SSatheesh Paul 							    in_sample_actions);
645dd23ff70SSatheesh Paul 			if (rc) {
646dd23ff70SSatheesh Paul 				plt_err("Sample subaction parsing failed.");
647dd23ff70SSatheesh Paul 				goto err_exit;
648dd23ff70SSatheesh Paul 			}
649dd23ff70SSatheesh Paul 
650dd23ff70SSatheesh Paul 			in_actions[i].type = ROC_NPC_ACTION_TYPE_SAMPLE;
651dd23ff70SSatheesh Paul 			in_actions[i].conf = in_sample_actions;
652dd23ff70SSatheesh Paul 			break;
653c1ae225eSHarman Kalra 		case RTE_FLOW_ACTION_TYPE_VXLAN_DECAP:
654c1ae225eSHarman Kalra 			continue;
655795ac238SJerin Jacob 		default:
656dd23ff70SSatheesh Paul 			plt_npc_dbg("Action is not supported = %d", actions->type);
657795ac238SJerin Jacob 			goto err_exit;
658795ac238SJerin Jacob 		}
659795ac238SJerin Jacob 		i++;
660795ac238SJerin Jacob 	}
66147f40516SSatheesh Paul 
66247f40516SSatheesh Paul 	if (!is_vf_action && act_q) {
66347f40516SSatheesh Paul 		rq = act_q->index;
66447f40516SSatheesh Paul 		if (rq >= eth_dev->data->nb_rx_queues) {
66547f40516SSatheesh Paul 			plt_npc_dbg("Invalid queue index");
66647f40516SSatheesh Paul 			goto err_exit;
66747f40516SSatheesh Paul 		}
66847f40516SSatheesh Paul 	}
669795ac238SJerin Jacob 	in_actions[i].type = ROC_NPC_ACTION_TYPE_END;
670795ac238SJerin Jacob 	return 0;
671795ac238SJerin Jacob 
672795ac238SJerin Jacob err_exit:
673795ac238SJerin Jacob 	return -EINVAL;
674795ac238SJerin Jacob }
675795ac238SJerin Jacob 
676795ac238SJerin Jacob static int
677c1ae225eSHarman Kalra cnxk_map_pattern(struct rte_eth_dev *eth_dev, const struct rte_flow_item pattern[],
678d11278e3SHarman Kalra 		 struct roc_npc_item_info in_pattern[], uint8_t *has_tunnel_pattern, bool is_rep,
679d11278e3SHarman Kalra 		 uint8_t *rep_pattern, uint64_t *free_allocs)
680795ac238SJerin Jacob {
68100701e71SKiran Kumar K 	const struct rte_flow_item_ethdev *rep_eth_dev;
68200701e71SKiran Kumar K 	struct rte_eth_dev *portid_eth_dev;
68300701e71SKiran Kumar K 	char if_name[RTE_ETH_NAME_MAX_LEN];
68400701e71SKiran Kumar K 	struct cnxk_eth_dev *hw_dst;
685d11278e3SHarman Kalra 	struct cnxk_rep_dev *rdev;
686d11278e3SHarman Kalra 	struct cnxk_eth_dev *dev;
687d11278e3SHarman Kalra 	struct roc_npc *npc;
688d11278e3SHarman Kalra 	int i = 0, j = 0;
689d11278e3SHarman Kalra 
690d11278e3SHarman Kalra 	if (!is_rep) {
691d11278e3SHarman Kalra 		dev = cnxk_eth_pmd_priv(eth_dev);
692d11278e3SHarman Kalra 		npc = &dev->npc;
693d11278e3SHarman Kalra 	} else {
694d11278e3SHarman Kalra 		rdev = cnxk_rep_pmd_priv(eth_dev);
695d11278e3SHarman Kalra 		npc = &rdev->parent_dev->npc;
696d11278e3SHarman Kalra 
697d11278e3SHarman Kalra 		npc->rep_npc = npc;
698d11278e3SHarman Kalra 		npc->rep_port_id = rdev->port_id;
699d11278e3SHarman Kalra 		npc->rep_pf_func = rdev->hw_func;
700d11278e3SHarman Kalra 	}
701795ac238SJerin Jacob 
702795ac238SJerin Jacob 	while (pattern->type != RTE_FLOW_ITEM_TYPE_END) {
703795ac238SJerin Jacob 		in_pattern[i].spec = pattern->spec;
704795ac238SJerin Jacob 		in_pattern[i].last = pattern->last;
705795ac238SJerin Jacob 		in_pattern[i].mask = pattern->mask;
706795ac238SJerin Jacob 		in_pattern[i].type = term[pattern->type].item_type;
707795ac238SJerin Jacob 		in_pattern[i].size = term[pattern->type].item_size;
708d11278e3SHarman Kalra 		if (pattern->type == RTE_FLOW_ITEM_TYPE_REPRESENTED_PORT ||
709d11278e3SHarman Kalra 		    pattern->type == RTE_FLOW_ITEM_TYPE_PORT_REPRESENTOR) {
71000701e71SKiran Kumar K 			rep_eth_dev = (const struct rte_flow_item_ethdev *)pattern->spec;
71100701e71SKiran Kumar K 			if (rte_eth_dev_get_name_by_port(rep_eth_dev->port_id, if_name)) {
71200701e71SKiran Kumar K 				plt_err("Name not found for output port id");
713c1ae225eSHarman Kalra 				goto fail;
71400701e71SKiran Kumar K 			}
71500701e71SKiran Kumar K 			portid_eth_dev = rte_eth_dev_allocated(if_name);
71600701e71SKiran Kumar K 			if (!portid_eth_dev) {
71700701e71SKiran Kumar K 				plt_err("eth_dev not found for output port id");
718c1ae225eSHarman Kalra 				goto fail;
71900701e71SKiran Kumar K 			}
720d11278e3SHarman Kalra 			*rep_pattern = pattern->type;
721c1ae225eSHarman Kalra 			if (cnxk_ethdev_is_representor(if_name)) {
722c1ae225eSHarman Kalra 				/* Case where represented port not part of same
723c1ae225eSHarman Kalra 				 * app and represented by a representor port.
724c1ae225eSHarman Kalra 				 */
725c1ae225eSHarman Kalra 				struct cnxk_rep_dev *rep_dev;
726c1ae225eSHarman Kalra 				struct cnxk_eswitch_dev *eswitch_dev;
727c1ae225eSHarman Kalra 
728c1ae225eSHarman Kalra 				rep_dev = cnxk_rep_pmd_priv(portid_eth_dev);
729c1ae225eSHarman Kalra 				eswitch_dev = rep_dev->parent_dev;
730d11278e3SHarman Kalra 				npc->rep_npc = &eswitch_dev->npc;
731d11278e3SHarman Kalra 				npc->rep_port_id = rep_eth_dev->port_id;
732d11278e3SHarman Kalra 				npc->rep_pf_func = rep_dev->hw_func;
733d11278e3SHarman Kalra 
734d11278e3SHarman Kalra 				if (pattern->type == RTE_FLOW_ITEM_TYPE_PORT_REPRESENTOR) {
735d11278e3SHarman Kalra 					struct rte_flow_item_vlan *vlan;
736d11278e3SHarman Kalra 
737d11278e3SHarman Kalra 					npc->rep_pf_func = eswitch_dev->npc.pf_func;
738d11278e3SHarman Kalra 					/* Add VLAN pattern corresponding to rep_id */
739d11278e3SHarman Kalra 					i++;
740d11278e3SHarman Kalra 					vlan = plt_zmalloc(sizeof(struct rte_flow_item_vlan), 0);
741d11278e3SHarman Kalra 					if (!vlan) {
742d11278e3SHarman Kalra 						plt_err("error allocation memory");
743d11278e3SHarman Kalra 						return -ENOMEM;
744d11278e3SHarman Kalra 					}
745d11278e3SHarman Kalra 
746d11278e3SHarman Kalra 					while (free_allocs[j] != 0)
747d11278e3SHarman Kalra 						j++;
748d11278e3SHarman Kalra 					free_allocs[j] = (uint64_t)vlan;
749d11278e3SHarman Kalra 
750d11278e3SHarman Kalra 					npc->rep_rx_channel = ROC_ESWITCH_LBK_CHAN;
751d11278e3SHarman Kalra 					vlan->hdr.vlan_tci = RTE_BE16(rep_dev->rep_id);
752d11278e3SHarman Kalra 					in_pattern[i].spec = (struct rte_flow_item_vlan *)vlan;
753d11278e3SHarman Kalra 					in_pattern[i].last = NULL;
754d11278e3SHarman Kalra 					in_pattern[i].mask = &rte_flow_item_vlan_mask;
755d11278e3SHarman Kalra 					in_pattern[i].type =
756d11278e3SHarman Kalra 						term[RTE_FLOW_ITEM_TYPE_VLAN].item_type;
757d11278e3SHarman Kalra 					in_pattern[i].size =
758d11278e3SHarman Kalra 						term[RTE_FLOW_ITEM_TYPE_VLAN].item_size;
759d11278e3SHarman Kalra 				}
760d11278e3SHarman Kalra 				*rep_pattern |= 1 << IS_REP_BIT;
761c1ae225eSHarman Kalra 				plt_rep_dbg("Represented port %d act port %d rep_dev->hw_func 0x%x",
762c1ae225eSHarman Kalra 					    rep_eth_dev->port_id, eth_dev->data->port_id,
763c1ae225eSHarman Kalra 					    rep_dev->hw_func);
764c1ae225eSHarman Kalra 			} else {
765d11278e3SHarman Kalra 				if (strcmp(portid_eth_dev->device->driver->name,
766d11278e3SHarman Kalra 					   eth_dev->device->driver->name) != 0) {
767d11278e3SHarman Kalra 					plt_err("Output port not under same driver");
768d11278e3SHarman Kalra 					goto fail;
769d11278e3SHarman Kalra 				}
770d11278e3SHarman Kalra 				/* Normal port as port_representor pattern can't be supported */
771d11278e3SHarman Kalra 				if (pattern->type == RTE_FLOW_ITEM_TYPE_PORT_REPRESENTOR)
772d11278e3SHarman Kalra 					return -ENOTSUP;
773c1ae225eSHarman Kalra 				/* Case where represented port part of same app
774c1ae225eSHarman Kalra 				 * as PF.
775c1ae225eSHarman Kalra 				 */
77600701e71SKiran Kumar K 				hw_dst = portid_eth_dev->data->dev_private;
777d11278e3SHarman Kalra 				npc->rep_npc = &hw_dst->npc;
778d11278e3SHarman Kalra 				npc->rep_port_id = rep_eth_dev->port_id;
779d11278e3SHarman Kalra 				npc->rep_pf_func = hw_dst->npc.pf_func;
78000701e71SKiran Kumar K 			}
781c1ae225eSHarman Kalra 		}
782c1ae225eSHarman Kalra 
783c1ae225eSHarman Kalra 		if (pattern->type == RTE_FLOW_ITEM_TYPE_VXLAN ||
784c1ae225eSHarman Kalra 		    pattern->type == RTE_FLOW_ITEM_TYPE_VXLAN_GPE ||
785c1ae225eSHarman Kalra 		    pattern->type == RTE_FLOW_ITEM_TYPE_GRE)
786c1ae225eSHarman Kalra 			*has_tunnel_pattern = pattern->type;
787c1ae225eSHarman Kalra 
788795ac238SJerin Jacob 		pattern++;
789795ac238SJerin Jacob 		i++;
790795ac238SJerin Jacob 	}
791795ac238SJerin Jacob 	in_pattern[i].type = ROC_NPC_ITEM_TYPE_END;
792c1ae225eSHarman Kalra 	return 0;
793c1ae225eSHarman Kalra fail:
794c1ae225eSHarman Kalra 	return -EINVAL;
795c1ae225eSHarman Kalra }
796c1ae225eSHarman Kalra 
797c1ae225eSHarman Kalra static int
798c1ae225eSHarman Kalra cnxk_map_flow_data(struct rte_eth_dev *eth_dev, const struct rte_flow_attr *attr,
799c1ae225eSHarman Kalra 		   const struct rte_flow_item pattern[], const struct rte_flow_action actions[],
800c1ae225eSHarman Kalra 		   struct roc_npc_attr *in_attr, struct roc_npc_item_info in_pattern[],
801c1ae225eSHarman Kalra 		   struct roc_npc_action in_actions[],
802c1ae225eSHarman Kalra 		   struct roc_npc_action_sample *in_sample_actions, uint32_t *flowkey_cfg,
803d11278e3SHarman Kalra 		   uint16_t *dst_pf_func, bool is_rep, uint64_t *free_allocs)
804c1ae225eSHarman Kalra {
805d11278e3SHarman Kalra 	uint8_t has_tunnel_pattern = 0, rep_pattern = 0;
806c1ae225eSHarman Kalra 	int rc;
807c1ae225eSHarman Kalra 
808c1ae225eSHarman Kalra 	in_attr->priority = attr->priority;
809c1ae225eSHarman Kalra 	in_attr->ingress = attr->ingress;
810c1ae225eSHarman Kalra 	in_attr->egress = attr->egress;
811c1ae225eSHarman Kalra 
812d11278e3SHarman Kalra 	rc = cnxk_map_pattern(eth_dev, pattern, in_pattern, &has_tunnel_pattern, is_rep,
813d11278e3SHarman Kalra 			      &rep_pattern, free_allocs);
814c1ae225eSHarman Kalra 	if (rc) {
815c1ae225eSHarman Kalra 		plt_err("Failed to map pattern list");
816c1ae225eSHarman Kalra 		return rc;
817c1ae225eSHarman Kalra 	}
818795ac238SJerin Jacob 
819d11278e3SHarman Kalra 	if (attr->transfer) {
820d11278e3SHarman Kalra 		/* rep_pattern is used to identify if RTE_FLOW_ITEM_TYPE_REPRESENTED_PORT
821d11278e3SHarman Kalra 		 * OR RTE_FLOW_ITEM_TYPE_PORT_REPRESENTOR is defined + if pattern's portid is
822d11278e3SHarman Kalra 		 * normal port or representor port.
823d11278e3SHarman Kalra 		 * For normal port_id, rep_pattern = pattern-> type
824d11278e3SHarman Kalra 		 * For representor port, rep_pattern = pattern-> type | 1 << IS_REP_BIT
825d11278e3SHarman Kalra 		 */
826d11278e3SHarman Kalra 		if (is_rep || rep_pattern) {
827d11278e3SHarman Kalra 			if (rep_pattern == RTE_FLOW_ITEM_TYPE_REPRESENTED_PORT ||
828d11278e3SHarman Kalra 			    ((rep_pattern & 0x7f) == RTE_FLOW_ITEM_TYPE_PORT_REPRESENTOR))
829d11278e3SHarman Kalra 				/* If pattern is port_representor or pattern has normal port as
830d11278e3SHarman Kalra 				 * represented port, install ingress rule.
831d11278e3SHarman Kalra 				 */
832d11278e3SHarman Kalra 				in_attr->ingress = attr->transfer;
833d11278e3SHarman Kalra 			else
834d11278e3SHarman Kalra 				in_attr->egress = attr->transfer;
835d11278e3SHarman Kalra 		} else {
836d11278e3SHarman Kalra 			in_attr->ingress = attr->transfer;
837d11278e3SHarman Kalra 		}
838795ac238SJerin Jacob 	}
839795ac238SJerin Jacob 
840d11278e3SHarman Kalra 	return cnxk_map_actions(eth_dev, attr, actions, in_actions, in_sample_actions, flowkey_cfg,
841d11278e3SHarman Kalra 				dst_pf_func, has_tunnel_pattern, is_rep, rep_pattern, free_allocs);
842d11278e3SHarman Kalra }
843d11278e3SHarman Kalra 
844d11278e3SHarman Kalra int
845d11278e3SHarman Kalra cnxk_flow_validate_common(struct rte_eth_dev *eth_dev, const struct rte_flow_attr *attr,
846d11278e3SHarman Kalra 			  const struct rte_flow_item pattern[],
847d11278e3SHarman Kalra 			  const struct rte_flow_action actions[], struct rte_flow_error *error,
848d11278e3SHarman Kalra 			  bool is_rep)
849795ac238SJerin Jacob {
850795ac238SJerin Jacob 	struct roc_npc_item_info in_pattern[ROC_NPC_ITEM_TYPE_END + 1];
851795ac238SJerin Jacob 	struct roc_npc_action in_actions[ROC_NPC_MAX_ACTION_COUNT];
852dd23ff70SSatheesh Paul 	struct roc_npc_action_sample in_sample_action;
853d11278e3SHarman Kalra 	struct cnxk_rep_dev *rep_dev;
854795ac238SJerin Jacob 	struct roc_npc_attr in_attr;
855d11278e3SHarman Kalra 	uint64_t *free_allocs, sz;
856d11278e3SHarman Kalra 	struct cnxk_eth_dev *dev;
857795ac238SJerin Jacob 	struct roc_npc_flow flow;
858795ac238SJerin Jacob 	uint32_t flowkey_cfg = 0;
859b7eb0e0cSSatheesh Paul 	uint16_t dst_pf_func = 0;
860d11278e3SHarman Kalra 	struct roc_npc *npc;
861d11278e3SHarman Kalra 	int rc, j;
862795ac238SJerin Jacob 
863d11278e3SHarman Kalra 	/* is_rep set for operation performed via representor ports */
864d11278e3SHarman Kalra 	if (!is_rep) {
865d11278e3SHarman Kalra 		dev = cnxk_eth_pmd_priv(eth_dev);
866d11278e3SHarman Kalra 		npc = &dev->npc;
86714598b31SAkhil Goyal 		/* Skip flow validation for MACsec. */
86814598b31SAkhil Goyal 		if (actions[0].type == RTE_FLOW_ACTION_TYPE_SECURITY &&
86914598b31SAkhil Goyal 		    cnxk_eth_macsec_sess_get_by_sess(dev, actions[0].conf) != NULL)
87014598b31SAkhil Goyal 			return 0;
871d11278e3SHarman Kalra 	} else {
872d11278e3SHarman Kalra 		rep_dev = cnxk_rep_pmd_priv(eth_dev);
873d11278e3SHarman Kalra 		npc = &rep_dev->parent_dev->npc;
874d11278e3SHarman Kalra 	}
87514598b31SAkhil Goyal 
876795ac238SJerin Jacob 	memset(&flow, 0, sizeof(flow));
877dd23ff70SSatheesh Paul 	memset(&in_sample_action, 0, sizeof(in_sample_action));
878b7f7e748SKiran Kumar K 	flow.is_validate = true;
879795ac238SJerin Jacob 
880d11278e3SHarman Kalra 	sz = ROC_NPC_MAX_ACTION_COUNT + ROC_NPC_ITEM_TYPE_END + 1;
881d11278e3SHarman Kalra 	free_allocs = plt_zmalloc(sz * sizeof(uint64_t), 0);
882d11278e3SHarman Kalra 	if (!free_allocs) {
883d11278e3SHarman Kalra 		rte_flow_error_set(error, -ENOMEM, RTE_FLOW_ERROR_TYPE_ACTION_NUM, NULL,
884d11278e3SHarman Kalra 				   "Failed to map flow data");
885d11278e3SHarman Kalra 		return -ENOMEM;
886d11278e3SHarman Kalra 	}
887b7f7e748SKiran Kumar K 	rc = cnxk_map_flow_data(eth_dev, attr, pattern, actions, &in_attr, in_pattern, in_actions,
888d11278e3SHarman Kalra 				&in_sample_action, &flowkey_cfg, &dst_pf_func, is_rep, free_allocs);
889795ac238SJerin Jacob 	if (rc) {
890b7f7e748SKiran Kumar K 		rte_flow_error_set(error, 0, RTE_FLOW_ERROR_TYPE_ACTION_NUM, NULL,
891b7f7e748SKiran Kumar K 				   "Failed to map flow data");
892d11278e3SHarman Kalra 		goto clean;
893795ac238SJerin Jacob 	}
894795ac238SJerin Jacob 
895c8647cd7SSatheesh Paul 	rc = roc_npc_flow_parse(npc, &in_attr, in_pattern, in_actions, &flow);
896c8647cd7SSatheesh Paul 
897c8647cd7SSatheesh Paul 	if (rc) {
898c8647cd7SSatheesh Paul 		rte_flow_error_set(error, 0, rc, NULL,
899c8647cd7SSatheesh Paul 				   "Flow validation failed");
900d11278e3SHarman Kalra 		goto clean;
901d11278e3SHarman Kalra 	}
902d11278e3SHarman Kalra clean:
903d11278e3SHarman Kalra 	/* Freeing the allocations done for additional patterns/actions */
904d11278e3SHarman Kalra 	for (j = 0; (j < (int)sz) && free_allocs[j]; j++)
905d11278e3SHarman Kalra 		plt_free((void *)free_allocs[j]);
906d11278e3SHarman Kalra 	plt_free(free_allocs);
907d11278e3SHarman Kalra 
908c8647cd7SSatheesh Paul 	return rc;
909c8647cd7SSatheesh Paul }
910d11278e3SHarman Kalra 
911d11278e3SHarman Kalra static int
912d11278e3SHarman Kalra cnxk_flow_validate(struct rte_eth_dev *eth_dev, const struct rte_flow_attr *attr,
913d11278e3SHarman Kalra 		   const struct rte_flow_item pattern[], const struct rte_flow_action actions[],
914d11278e3SHarman Kalra 		   struct rte_flow_error *error)
915d11278e3SHarman Kalra {
916d11278e3SHarman Kalra 	return cnxk_flow_validate_common(eth_dev, attr, pattern, actions, error, false);
917795ac238SJerin Jacob }
918795ac238SJerin Jacob 
919795ac238SJerin Jacob struct roc_npc_flow *
920d11278e3SHarman Kalra cnxk_flow_create_common(struct rte_eth_dev *eth_dev, const struct rte_flow_attr *attr,
921795ac238SJerin Jacob 			const struct rte_flow_item pattern[],
922d11278e3SHarman Kalra 			const struct rte_flow_action actions[], struct rte_flow_error *error,
923d11278e3SHarman Kalra 			bool is_rep)
924795ac238SJerin Jacob {
925*0981a22eSHarman Kalra 	struct roc_npc_item_info in_pattern[ROC_NPC_ITEM_TYPE_END + 1] = {0};
926*0981a22eSHarman Kalra 	struct roc_npc_action in_actions[ROC_NPC_MAX_ACTION_COUNT] = {0};
927dd23ff70SSatheesh Paul 	struct roc_npc_action_sample in_sample_action;
928d11278e3SHarman Kalra 	struct cnxk_rep_dev *rep_dev = NULL;
929d11278e3SHarman Kalra 	struct roc_npc_flow *flow = NULL;
930d11278e3SHarman Kalra 	struct cnxk_eth_dev *dev = NULL;
931795ac238SJerin Jacob 	struct roc_npc_attr in_attr;
932d11278e3SHarman Kalra 	uint64_t *free_allocs, sz;
933b7eb0e0cSSatheesh Paul 	uint16_t dst_pf_func = 0;
934d11278e3SHarman Kalra 	struct roc_npc *npc;
935795ac238SJerin Jacob 	int errcode = 0;
936d11278e3SHarman Kalra 	int rc, j;
937795ac238SJerin Jacob 
938d11278e3SHarman Kalra 	/* is_rep set for operation performed via representor ports */
939d11278e3SHarman Kalra 	if (!is_rep) {
940d11278e3SHarman Kalra 		dev = cnxk_eth_pmd_priv(eth_dev);
941d11278e3SHarman Kalra 		npc = &dev->npc;
942d11278e3SHarman Kalra 	} else {
943d11278e3SHarman Kalra 		rep_dev = cnxk_rep_pmd_priv(eth_dev);
944d11278e3SHarman Kalra 		npc = &rep_dev->parent_dev->npc;
945d11278e3SHarman Kalra 	}
946d11278e3SHarman Kalra 
947d11278e3SHarman Kalra 	sz = ROC_NPC_MAX_ACTION_COUNT + ROC_NPC_ITEM_TYPE_END + 1;
948d11278e3SHarman Kalra 	free_allocs = plt_zmalloc(sz * sizeof(uint64_t), 0);
949d11278e3SHarman Kalra 	if (!free_allocs) {
950d11278e3SHarman Kalra 		rte_flow_error_set(error, -ENOMEM, RTE_FLOW_ERROR_TYPE_ACTION_NUM, NULL,
951d11278e3SHarman Kalra 				   "Failed to map flow data");
952d11278e3SHarman Kalra 		return NULL;
953d11278e3SHarman Kalra 	}
954dd23ff70SSatheesh Paul 	memset(&in_sample_action, 0, sizeof(in_sample_action));
955c1ae225eSHarman Kalra 	memset(&in_attr, 0, sizeof(struct roc_npc_attr));
956b7eb0e0cSSatheesh Paul 	rc = cnxk_map_flow_data(eth_dev, attr, pattern, actions, &in_attr, in_pattern, in_actions,
957d11278e3SHarman Kalra 				&in_sample_action, &npc->flowkey_cfg_state, &dst_pf_func, is_rep,
958d11278e3SHarman Kalra 				free_allocs);
959795ac238SJerin Jacob 	if (rc) {
960d11278e3SHarman Kalra 		rte_flow_error_set(error, rc, RTE_FLOW_ERROR_TYPE_ACTION_NUM, NULL,
961b7eb0e0cSSatheesh Paul 				   "Failed to map flow data");
962d11278e3SHarman Kalra 		goto clean;
963795ac238SJerin Jacob 	}
964795ac238SJerin Jacob 
965b7eb0e0cSSatheesh Paul 	flow = roc_npc_flow_create(npc, &in_attr, in_pattern, in_actions, dst_pf_func, &errcode);
966795ac238SJerin Jacob 	if (errcode != 0) {
967b7eb0e0cSSatheesh Paul 		rte_flow_error_set(error, errcode, errcode, NULL, roc_error_msg_get(errcode));
968d11278e3SHarman Kalra 		goto clean;
969795ac238SJerin Jacob 	}
970795ac238SJerin Jacob 
971d11278e3SHarman Kalra clean:
972d11278e3SHarman Kalra 	/* Freeing the allocations done for additional patterns/actions */
973d11278e3SHarman Kalra 	for (j = 0; (j < (int)sz) && free_allocs[j]; j++)
974d11278e3SHarman Kalra 		plt_free((void *)free_allocs[j]);
975d11278e3SHarman Kalra 	plt_free(free_allocs);
976d11278e3SHarman Kalra 
977795ac238SJerin Jacob 	return flow;
978795ac238SJerin Jacob }
979795ac238SJerin Jacob 
980d11278e3SHarman Kalra struct roc_npc_flow *
981d11278e3SHarman Kalra cnxk_flow_create(struct rte_eth_dev *eth_dev, const struct rte_flow_attr *attr,
982d11278e3SHarman Kalra 		 const struct rte_flow_item pattern[], const struct rte_flow_action actions[],
983d11278e3SHarman Kalra 		 struct rte_flow_error *error)
984d11278e3SHarman Kalra {
985d11278e3SHarman Kalra 	return cnxk_flow_create_common(eth_dev, attr, pattern, actions, error, false);
986d11278e3SHarman Kalra }
987d11278e3SHarman Kalra 
988d11278e3SHarman Kalra int
989d11278e3SHarman Kalra cnxk_flow_destroy_common(struct rte_eth_dev *eth_dev, struct roc_npc_flow *flow,
990d11278e3SHarman Kalra 			 struct rte_flow_error *error, bool is_rep)
991d11278e3SHarman Kalra {
992d11278e3SHarman Kalra 	struct cnxk_rep_dev *rep_dev;
993d11278e3SHarman Kalra 	struct cnxk_eth_dev *dev;
994d11278e3SHarman Kalra 	struct roc_npc *npc;
995d11278e3SHarman Kalra 	int rc;
996d11278e3SHarman Kalra 
997d11278e3SHarman Kalra 	/* is_rep set for operation performed via representor ports */
998d11278e3SHarman Kalra 	if (!is_rep) {
999d11278e3SHarman Kalra 		dev = cnxk_eth_pmd_priv(eth_dev);
1000d11278e3SHarman Kalra 		npc = &dev->npc;
1001d11278e3SHarman Kalra 	} else {
1002d11278e3SHarman Kalra 		rep_dev = cnxk_rep_pmd_priv(eth_dev);
1003d11278e3SHarman Kalra 		npc = &rep_dev->parent_dev->npc;
1004d11278e3SHarman Kalra 	}
1005d11278e3SHarman Kalra 
1006d11278e3SHarman Kalra 	rc = roc_npc_flow_destroy(npc, flow);
1007d11278e3SHarman Kalra 	if (rc)
1008d11278e3SHarman Kalra 		rte_flow_error_set(error, rc, RTE_FLOW_ERROR_TYPE_UNSPECIFIED, NULL,
1009d11278e3SHarman Kalra 				   "Flow Destroy failed");
1010d11278e3SHarman Kalra 	return rc;
1011d11278e3SHarman Kalra }
1012d11278e3SHarman Kalra 
1013795ac238SJerin Jacob int
1014795ac238SJerin Jacob cnxk_flow_destroy(struct rte_eth_dev *eth_dev, struct roc_npc_flow *flow,
1015795ac238SJerin Jacob 		  struct rte_flow_error *error)
1016795ac238SJerin Jacob {
1017d11278e3SHarman Kalra 	return cnxk_flow_destroy_common(eth_dev, flow, error, false);
1018795ac238SJerin Jacob }
1019795ac238SJerin Jacob 
1020d11278e3SHarman Kalra int
1021d11278e3SHarman Kalra cnxk_flow_flush_common(struct rte_eth_dev *eth_dev, struct rte_flow_error *error, bool is_rep)
1022795ac238SJerin Jacob {
1023d11278e3SHarman Kalra 	struct cnxk_rep_dev *rep_dev;
1024d11278e3SHarman Kalra 	struct cnxk_eth_dev *dev;
1025d11278e3SHarman Kalra 	struct roc_npc *npc;
1026795ac238SJerin Jacob 	int rc;
1027795ac238SJerin Jacob 
1028d11278e3SHarman Kalra 	/* is_rep set for operation performed via representor ports */
1029d11278e3SHarman Kalra 	if (!is_rep) {
1030d11278e3SHarman Kalra 		dev = cnxk_eth_pmd_priv(eth_dev);
1031d11278e3SHarman Kalra 		npc = &dev->npc;
1032d11278e3SHarman Kalra 	} else {
1033d11278e3SHarman Kalra 		rep_dev = cnxk_rep_pmd_priv(eth_dev);
1034d11278e3SHarman Kalra 		npc = &rep_dev->parent_dev->npc;
1035d11278e3SHarman Kalra 	}
1036d11278e3SHarman Kalra 
1037795ac238SJerin Jacob 	rc = roc_npc_mcam_free_all_resources(npc);
1038795ac238SJerin Jacob 	if (rc) {
1039d11278e3SHarman Kalra 		rte_flow_error_set(error, EIO, RTE_FLOW_ERROR_TYPE_UNSPECIFIED, NULL,
1040d11278e3SHarman Kalra 				   "Failed to flush filter");
1041795ac238SJerin Jacob 		return -rte_errno;
1042795ac238SJerin Jacob 	}
1043795ac238SJerin Jacob 
1044795ac238SJerin Jacob 	return 0;
1045795ac238SJerin Jacob }
1046795ac238SJerin Jacob 
1047795ac238SJerin Jacob static int
1048d11278e3SHarman Kalra cnxk_flow_flush(struct rte_eth_dev *eth_dev, struct rte_flow_error *error)
1049d11278e3SHarman Kalra {
1050d11278e3SHarman Kalra 	return cnxk_flow_flush_common(eth_dev, error, false);
1051d11278e3SHarman Kalra }
1052d11278e3SHarman Kalra 
1053d11278e3SHarman Kalra int
1054d11278e3SHarman Kalra cnxk_flow_query_common(struct rte_eth_dev *eth_dev, struct rte_flow *flow,
1055795ac238SJerin Jacob 		       const struct rte_flow_action *action, void *data,
1056d11278e3SHarman Kalra 		       struct rte_flow_error *error, bool is_rep)
1057795ac238SJerin Jacob {
1058795ac238SJerin Jacob 	struct roc_npc_flow *in_flow = (struct roc_npc_flow *)flow;
1059795ac238SJerin Jacob 	struct rte_flow_query_count *query = data;
1060d11278e3SHarman Kalra 	struct cnxk_rep_dev *rep_dev;
1061d11278e3SHarman Kalra 	struct cnxk_eth_dev *dev;
1062d11278e3SHarman Kalra 	struct roc_npc *npc;
1063795ac238SJerin Jacob 	const char *errmsg = NULL;
1064795ac238SJerin Jacob 	int errcode = ENOTSUP;
1065795ac238SJerin Jacob 	int rc;
1066795ac238SJerin Jacob 
1067795ac238SJerin Jacob 	if (action->type != RTE_FLOW_ACTION_TYPE_COUNT) {
1068795ac238SJerin Jacob 		errmsg = "Only COUNT is supported in query";
1069795ac238SJerin Jacob 		goto err_exit;
1070795ac238SJerin Jacob 	}
1071795ac238SJerin Jacob 
1072795ac238SJerin Jacob 	if (in_flow->ctr_id == NPC_COUNTER_NONE) {
1073795ac238SJerin Jacob 		errmsg = "Counter is not available";
1074795ac238SJerin Jacob 		goto err_exit;
1075795ac238SJerin Jacob 	}
1076795ac238SJerin Jacob 
1077d11278e3SHarman Kalra 	/* is_rep set for operation performed via representor ports */
1078d11278e3SHarman Kalra 	if (!is_rep) {
1079d11278e3SHarman Kalra 		dev = cnxk_eth_pmd_priv(eth_dev);
1080d11278e3SHarman Kalra 		npc = &dev->npc;
1081d11278e3SHarman Kalra 	} else {
1082d11278e3SHarman Kalra 		rep_dev = cnxk_rep_pmd_priv(eth_dev);
1083d11278e3SHarman Kalra 		npc = &rep_dev->parent_dev->npc;
1084d11278e3SHarman Kalra 	}
1085d11278e3SHarman Kalra 
1086df5cf15fSKiran Kumar K 	if (in_flow->use_pre_alloc)
1087df5cf15fSKiran Kumar K 		rc = roc_npc_inl_mcam_read_counter(in_flow->ctr_id, &query->hits);
1088df5cf15fSKiran Kumar K 	else
1089795ac238SJerin Jacob 		rc = roc_npc_mcam_read_counter(npc, in_flow->ctr_id, &query->hits);
1090795ac238SJerin Jacob 	if (rc != 0) {
1091795ac238SJerin Jacob 		errcode = EIO;
1092795ac238SJerin Jacob 		errmsg = "Error reading flow counter";
1093795ac238SJerin Jacob 		goto err_exit;
1094795ac238SJerin Jacob 	}
1095795ac238SJerin Jacob 	query->hits_set = 1;
1096795ac238SJerin Jacob 	query->bytes_set = 0;
1097795ac238SJerin Jacob 
1098df5cf15fSKiran Kumar K 	if (query->reset) {
1099df5cf15fSKiran Kumar K 		if (in_flow->use_pre_alloc)
1100df5cf15fSKiran Kumar K 			rc = roc_npc_inl_mcam_clear_counter(in_flow->ctr_id);
1101df5cf15fSKiran Kumar K 		else
1102795ac238SJerin Jacob 			rc = roc_npc_mcam_clear_counter(npc, in_flow->ctr_id);
1103df5cf15fSKiran Kumar K 	}
1104795ac238SJerin Jacob 	if (rc != 0) {
1105795ac238SJerin Jacob 		errcode = EIO;
1106795ac238SJerin Jacob 		errmsg = "Error clearing flow counter";
1107795ac238SJerin Jacob 		goto err_exit;
1108795ac238SJerin Jacob 	}
1109795ac238SJerin Jacob 
1110795ac238SJerin Jacob 	return 0;
1111795ac238SJerin Jacob 
1112795ac238SJerin Jacob err_exit:
1113795ac238SJerin Jacob 	rte_flow_error_set(error, errcode, RTE_FLOW_ERROR_TYPE_UNSPECIFIED,
1114795ac238SJerin Jacob 			   NULL, errmsg);
1115795ac238SJerin Jacob 	return -rte_errno;
1116795ac238SJerin Jacob }
1117795ac238SJerin Jacob 
1118795ac238SJerin Jacob static int
1119d11278e3SHarman Kalra cnxk_flow_query(struct rte_eth_dev *eth_dev, struct rte_flow *flow,
1120d11278e3SHarman Kalra 		const struct rte_flow_action *action, void *data, struct rte_flow_error *error)
1121d11278e3SHarman Kalra {
1122d11278e3SHarman Kalra 	return cnxk_flow_query_common(eth_dev, flow, action, data, error, false);
1123d11278e3SHarman Kalra }
1124d11278e3SHarman Kalra 
1125d11278e3SHarman Kalra static int
1126d11278e3SHarman Kalra cnxk_flow_isolate(struct rte_eth_dev *eth_dev __rte_unused, int enable __rte_unused,
1127d11278e3SHarman Kalra 		  struct rte_flow_error *error)
1128795ac238SJerin Jacob {
1129795ac238SJerin Jacob 	/* If we support, we need to un-install the default mcam
1130795ac238SJerin Jacob 	 * entry for this port.
1131795ac238SJerin Jacob 	 */
1132795ac238SJerin Jacob 
1133795ac238SJerin Jacob 	rte_flow_error_set(error, ENOTSUP, RTE_FLOW_ERROR_TYPE_UNSPECIFIED,
1134795ac238SJerin Jacob 			   NULL, "Flow isolation not supported");
1135795ac238SJerin Jacob 
1136795ac238SJerin Jacob 	return -rte_errno;
1137795ac238SJerin Jacob }
1138795ac238SJerin Jacob 
1139d11278e3SHarman Kalra int
1140d11278e3SHarman Kalra cnxk_flow_dev_dump_common(struct rte_eth_dev *eth_dev, struct rte_flow *flow, FILE *file,
1141d11278e3SHarman Kalra 			  struct rte_flow_error *error, bool is_rep)
1142795ac238SJerin Jacob {
1143d11278e3SHarman Kalra 	struct cnxk_rep_dev *rep_dev;
1144d11278e3SHarman Kalra 	struct cnxk_eth_dev *dev;
1145d11278e3SHarman Kalra 	struct roc_npc *npc;
1146d11278e3SHarman Kalra 
1147d11278e3SHarman Kalra 	/* is_rep set for operation performed via representor ports */
1148d11278e3SHarman Kalra 	if (!is_rep) {
1149d11278e3SHarman Kalra 		dev = cnxk_eth_pmd_priv(eth_dev);
1150d11278e3SHarman Kalra 		npc = &dev->npc;
1151d11278e3SHarman Kalra 	} else {
1152d11278e3SHarman Kalra 		rep_dev = cnxk_rep_pmd_priv(eth_dev);
1153d11278e3SHarman Kalra 		npc = &rep_dev->parent_dev->npc;
1154d11278e3SHarman Kalra 	}
1155795ac238SJerin Jacob 
1156795ac238SJerin Jacob 	if (file == NULL) {
1157d11278e3SHarman Kalra 		rte_flow_error_set(error, EINVAL, RTE_FLOW_ERROR_TYPE_UNSPECIFIED, NULL,
1158795ac238SJerin Jacob 				   "Invalid file");
1159795ac238SJerin Jacob 		return -rte_errno;
1160795ac238SJerin Jacob 	}
1161795ac238SJerin Jacob 
1162795ac238SJerin Jacob 	if (flow != NULL) {
1163abdd7a9dSHarman Kalra 		roc_npc_flow_mcam_dump(file, npc, (struct roc_npc_flow *)flow);
1164abdd7a9dSHarman Kalra 		return 0;
1165795ac238SJerin Jacob 	}
1166795ac238SJerin Jacob 
1167296e9040SKiran Kumar K 	roc_npc_flow_dump(file, npc, -1);
1168795ac238SJerin Jacob 
1169795ac238SJerin Jacob 	return 0;
1170795ac238SJerin Jacob }
1171795ac238SJerin Jacob 
1172a4477550SAnkur Dwivedi static int
1173d11278e3SHarman Kalra cnxk_flow_dev_dump(struct rte_eth_dev *eth_dev, struct rte_flow *flow, FILE *file,
1174d11278e3SHarman Kalra 		   struct rte_flow_error *error)
1175d11278e3SHarman Kalra {
1176d11278e3SHarman Kalra 	return cnxk_flow_dev_dump_common(eth_dev, flow, file, error, false);
1177d11278e3SHarman Kalra }
1178d11278e3SHarman Kalra 
1179d11278e3SHarman Kalra static int
1180d11278e3SHarman Kalra cnxk_flow_get_aged_flows(struct rte_eth_dev *eth_dev, void **context, uint32_t nb_contexts,
1181d11278e3SHarman Kalra 			 struct rte_flow_error *err)
1182a4477550SAnkur Dwivedi {
1183a4477550SAnkur Dwivedi 	struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
1184a4477550SAnkur Dwivedi 	struct roc_npc *roc_npc = &dev->npc;
1185a4477550SAnkur Dwivedi 	struct roc_npc_flow_age *flow_age;
1186a4477550SAnkur Dwivedi 	uint32_t start_id;
1187a4477550SAnkur Dwivedi 	uint32_t end_id;
1188a4477550SAnkur Dwivedi 	int cnt = 0;
1189a4477550SAnkur Dwivedi 	uint32_t sn;
1190a4477550SAnkur Dwivedi 	uint32_t i;
1191a4477550SAnkur Dwivedi 
1192a4477550SAnkur Dwivedi 	RTE_SET_USED(err);
1193a4477550SAnkur Dwivedi 
1194a4477550SAnkur Dwivedi 	flow_age = &roc_npc->flow_age;
1195a4477550SAnkur Dwivedi 
11964ebef525SSatheesh Paul 	if (!flow_age->age_flow_refcnt)
11974ebef525SSatheesh Paul 		return 0;
11984ebef525SSatheesh Paul 
1199a4477550SAnkur Dwivedi 	do {
1200a4477550SAnkur Dwivedi 		sn = plt_seqcount_read_begin(&flow_age->seq_cnt);
1201a4477550SAnkur Dwivedi 
1202a4477550SAnkur Dwivedi 		if (nb_contexts == 0) {
1203a4477550SAnkur Dwivedi 			cnt = flow_age->aged_flows_cnt;
1204a4477550SAnkur Dwivedi 		} else {
1205a4477550SAnkur Dwivedi 			start_id = flow_age->start_id;
1206a4477550SAnkur Dwivedi 			end_id = flow_age->end_id;
1207a4477550SAnkur Dwivedi 			for (i = start_id; i <= end_id; i++) {
1208a4477550SAnkur Dwivedi 				if ((int)nb_contexts == cnt)
1209a4477550SAnkur Dwivedi 					break;
1210a4477550SAnkur Dwivedi 				if (plt_bitmap_get(flow_age->aged_flows, i)) {
1211a4477550SAnkur Dwivedi 					context[cnt] =
1212a4477550SAnkur Dwivedi 						roc_npc_aged_flow_ctx_get(roc_npc, i);
1213a4477550SAnkur Dwivedi 					cnt++;
1214a4477550SAnkur Dwivedi 				}
1215a4477550SAnkur Dwivedi 			}
1216a4477550SAnkur Dwivedi 		}
1217a4477550SAnkur Dwivedi 	} while (plt_seqcount_read_retry(&flow_age->seq_cnt, sn));
1218a4477550SAnkur Dwivedi 
1219a4477550SAnkur Dwivedi 	return cnt;
1220a4477550SAnkur Dwivedi }
1221a4477550SAnkur Dwivedi 
1222c1ae225eSHarman Kalra static int
1223c1ae225eSHarman Kalra cnxk_flow_tunnel_decap_set(__rte_unused struct rte_eth_dev *dev, struct rte_flow_tunnel *tunnel,
1224c1ae225eSHarman Kalra 			   struct rte_flow_action **pmd_actions, uint32_t *num_of_actions,
1225c1ae225eSHarman Kalra 			   __rte_unused struct rte_flow_error *err)
1226c1ae225eSHarman Kalra {
1227c1ae225eSHarman Kalra 	struct rte_flow_action *nfp_action;
1228c1ae225eSHarman Kalra 
1229c1ae225eSHarman Kalra 	nfp_action = rte_zmalloc("nfp_tun_action", sizeof(struct rte_flow_action), 0);
1230c1ae225eSHarman Kalra 	if (nfp_action == NULL) {
1231c1ae225eSHarman Kalra 		plt_err("Alloc memory for nfp tunnel action failed.");
1232c1ae225eSHarman Kalra 		return -ENOMEM;
1233c1ae225eSHarman Kalra 	}
1234c1ae225eSHarman Kalra 
1235c1ae225eSHarman Kalra 	if (tunnel->is_ipv6)
1236c1ae225eSHarman Kalra 		nfp_action->conf = (void *)~0;
1237c1ae225eSHarman Kalra 
1238c1ae225eSHarman Kalra 	switch (tunnel->type) {
1239c1ae225eSHarman Kalra 	case RTE_FLOW_ITEM_TYPE_VXLAN:
1240c1ae225eSHarman Kalra 		nfp_action->type = RTE_FLOW_ACTION_TYPE_VXLAN_DECAP;
1241c1ae225eSHarman Kalra 		*pmd_actions = nfp_action;
1242c1ae225eSHarman Kalra 		*num_of_actions = 1;
1243c1ae225eSHarman Kalra 		break;
1244c1ae225eSHarman Kalra 	default:
1245c1ae225eSHarman Kalra 		*pmd_actions = NULL;
1246c1ae225eSHarman Kalra 		*num_of_actions = 0;
1247c1ae225eSHarman Kalra 		rte_free(nfp_action);
1248c1ae225eSHarman Kalra 		break;
1249c1ae225eSHarman Kalra 	}
1250c1ae225eSHarman Kalra 
1251c1ae225eSHarman Kalra 	return 0;
1252c1ae225eSHarman Kalra }
1253c1ae225eSHarman Kalra 
1254c1ae225eSHarman Kalra static int
1255c1ae225eSHarman Kalra cnxk_flow_tunnel_action_decap_release(__rte_unused struct rte_eth_dev *dev,
1256c1ae225eSHarman Kalra 				      struct rte_flow_action *pmd_actions, uint32_t num_of_actions,
1257c1ae225eSHarman Kalra 				      __rte_unused struct rte_flow_error *err)
1258c1ae225eSHarman Kalra {
1259c1ae225eSHarman Kalra 	uint32_t i;
1260c1ae225eSHarman Kalra 	struct rte_flow_action *nfp_action;
1261c1ae225eSHarman Kalra 
1262c1ae225eSHarman Kalra 	for (i = 0; i < num_of_actions; i++) {
1263c1ae225eSHarman Kalra 		nfp_action = &pmd_actions[i];
1264c1ae225eSHarman Kalra 		nfp_action->conf = NULL;
1265c1ae225eSHarman Kalra 		rte_free(nfp_action);
1266c1ae225eSHarman Kalra 	}
1267c1ae225eSHarman Kalra 
1268c1ae225eSHarman Kalra 	return 0;
1269c1ae225eSHarman Kalra }
1270c1ae225eSHarman Kalra 
1271c1ae225eSHarman Kalra static int
1272c1ae225eSHarman Kalra cnxk_flow_tunnel_match(__rte_unused struct rte_eth_dev *dev,
1273c1ae225eSHarman Kalra 		       __rte_unused struct rte_flow_tunnel *tunnel,
1274c1ae225eSHarman Kalra 		       __rte_unused struct rte_flow_item **pmd_items, uint32_t *num_of_items,
1275c1ae225eSHarman Kalra 		       __rte_unused struct rte_flow_error *err)
1276c1ae225eSHarman Kalra {
1277c1ae225eSHarman Kalra 	*num_of_items = 0;
1278c1ae225eSHarman Kalra 
1279c1ae225eSHarman Kalra 	return 0;
1280c1ae225eSHarman Kalra }
1281c1ae225eSHarman Kalra 
1282c1ae225eSHarman Kalra static int
1283c1ae225eSHarman Kalra cnxk_flow_tunnel_item_release(__rte_unused struct rte_eth_dev *dev,
1284c1ae225eSHarman Kalra 			      __rte_unused struct rte_flow_item *pmd_items,
1285c1ae225eSHarman Kalra 			      __rte_unused uint32_t num_of_items,
1286c1ae225eSHarman Kalra 			      __rte_unused struct rte_flow_error *err)
1287c1ae225eSHarman Kalra {
1288c1ae225eSHarman Kalra 	return 0;
1289c1ae225eSHarman Kalra }
1290c1ae225eSHarman Kalra 
1291795ac238SJerin Jacob struct rte_flow_ops cnxk_flow_ops = {
1292795ac238SJerin Jacob 	.validate = cnxk_flow_validate,
1293795ac238SJerin Jacob 	.flush = cnxk_flow_flush,
1294795ac238SJerin Jacob 	.query = cnxk_flow_query,
1295795ac238SJerin Jacob 	.isolate = cnxk_flow_isolate,
1296795ac238SJerin Jacob 	.dev_dump = cnxk_flow_dev_dump,
1297a4477550SAnkur Dwivedi 	.get_aged_flows = cnxk_flow_get_aged_flows,
1298c1ae225eSHarman Kalra 	.tunnel_match = cnxk_flow_tunnel_match,
1299c1ae225eSHarman Kalra 	.tunnel_item_release = cnxk_flow_tunnel_item_release,
1300c1ae225eSHarman Kalra 	.tunnel_decap_set = cnxk_flow_tunnel_decap_set,
1301c1ae225eSHarman Kalra 	.tunnel_action_decap_release = cnxk_flow_tunnel_action_decap_release,
1302795ac238SJerin Jacob };
1303