xref: /dpdk/examples/l2fwd-event/l2fwd_event.c (revision 1f41deac447d7938198a2acdd1b7862161feef91)
11b2143aaSPavan Nikhilesh /* SPDX-License-Identifier: BSD-3-Clause
21b2143aaSPavan Nikhilesh  * Copyright(C) 2019 Marvell International Ltd.
31b2143aaSPavan Nikhilesh  */
41b2143aaSPavan Nikhilesh 
51b2143aaSPavan Nikhilesh #include <stdbool.h>
61b2143aaSPavan Nikhilesh #include <getopt.h>
71b2143aaSPavan Nikhilesh 
81b2143aaSPavan Nikhilesh #include <rte_cycles.h>
91b2143aaSPavan Nikhilesh #include <rte_ethdev.h>
101b2143aaSPavan Nikhilesh #include <rte_eventdev.h>
111b2143aaSPavan Nikhilesh #include <rte_event_eth_rx_adapter.h>
121b2143aaSPavan Nikhilesh #include <rte_event_eth_tx_adapter.h>
131b2143aaSPavan Nikhilesh #include <rte_lcore.h>
141b2143aaSPavan Nikhilesh #include <rte_malloc.h>
151b2143aaSPavan Nikhilesh #include <rte_spinlock.h>
161b2143aaSPavan Nikhilesh 
171b2143aaSPavan Nikhilesh #include "l2fwd_event.h"
181b2143aaSPavan Nikhilesh 
19080f57bcSPavan Nikhilesh #define L2FWD_EVENT_SINGLE	0x1
20080f57bcSPavan Nikhilesh #define L2FWD_EVENT_BURST	0x2
21080f57bcSPavan Nikhilesh #define L2FWD_EVENT_TX_DIRECT	0x4
22080f57bcSPavan Nikhilesh #define L2FWD_EVENT_TX_ENQ	0x8
23080f57bcSPavan Nikhilesh #define L2FWD_EVENT_UPDT_MAC	0x10
24080f57bcSPavan Nikhilesh 
25bcb6f841SPavan Nikhilesh static inline int
26bcb6f841SPavan Nikhilesh l2fwd_event_service_enable(uint32_t service_id)
27bcb6f841SPavan Nikhilesh {
28bcb6f841SPavan Nikhilesh 	uint8_t min_service_count = UINT8_MAX;
29bcb6f841SPavan Nikhilesh 	uint32_t slcore_array[RTE_MAX_LCORE];
30bcb6f841SPavan Nikhilesh 	unsigned int slcore = 0;
31bcb6f841SPavan Nikhilesh 	uint8_t service_count;
32bcb6f841SPavan Nikhilesh 	int32_t slcore_count;
33bcb6f841SPavan Nikhilesh 
34bcb6f841SPavan Nikhilesh 	if (!rte_service_lcore_count())
35bcb6f841SPavan Nikhilesh 		return -ENOENT;
36bcb6f841SPavan Nikhilesh 
37bcb6f841SPavan Nikhilesh 	slcore_count = rte_service_lcore_list(slcore_array, RTE_MAX_LCORE);
38bcb6f841SPavan Nikhilesh 	if (slcore_count < 0)
39bcb6f841SPavan Nikhilesh 		return -ENOENT;
40bcb6f841SPavan Nikhilesh 	/* Get the core which has least number of services running. */
41bcb6f841SPavan Nikhilesh 	while (slcore_count--) {
42bcb6f841SPavan Nikhilesh 		/* Reset default mapping */
438b33aa7eSPavan Nikhilesh 		if (rte_service_map_lcore_set(service_id,
448b33aa7eSPavan Nikhilesh 					slcore_array[slcore_count], 0) != 0)
458b33aa7eSPavan Nikhilesh 			return -ENOENT;
46bcb6f841SPavan Nikhilesh 		service_count = rte_service_lcore_count_services(
47bcb6f841SPavan Nikhilesh 				slcore_array[slcore_count]);
48bcb6f841SPavan Nikhilesh 		if (service_count < min_service_count) {
49bcb6f841SPavan Nikhilesh 			slcore = slcore_array[slcore_count];
50bcb6f841SPavan Nikhilesh 			min_service_count = service_count;
51bcb6f841SPavan Nikhilesh 		}
52bcb6f841SPavan Nikhilesh 	}
538b33aa7eSPavan Nikhilesh 	if (rte_service_map_lcore_set(service_id, slcore, 1) != 0)
54bcb6f841SPavan Nikhilesh 		return -ENOENT;
55bcb6f841SPavan Nikhilesh 	rte_service_lcore_start(slcore);
56bcb6f841SPavan Nikhilesh 
57bcb6f841SPavan Nikhilesh 	return 0;
58bcb6f841SPavan Nikhilesh }
59bcb6f841SPavan Nikhilesh 
60bcb6f841SPavan Nikhilesh void
61bcb6f841SPavan Nikhilesh l2fwd_event_service_setup(struct l2fwd_resources *rsrc)
62bcb6f841SPavan Nikhilesh {
63bcb6f841SPavan Nikhilesh 	struct l2fwd_event_resources *evt_rsrc = rsrc->evt_rsrc;
64bcb6f841SPavan Nikhilesh 	struct rte_event_dev_info evdev_info;
65bcb6f841SPavan Nikhilesh 	uint32_t service_id, caps;
66bcb6f841SPavan Nikhilesh 	int ret, i;
67bcb6f841SPavan Nikhilesh 
689a212dc0SConor Fogarty 	/* Running eventdev scheduler service on service core. 8< */
69bcb6f841SPavan Nikhilesh 	rte_event_dev_info_get(evt_rsrc->event_d_id, &evdev_info);
70345a22d5SPavan Nikhilesh 	if (!(evdev_info.event_dev_cap & RTE_EVENT_DEV_CAP_DISTRIBUTED_SCHED)) {
71bcb6f841SPavan Nikhilesh 		ret = rte_event_dev_service_id_get(evt_rsrc->event_d_id,
72bcb6f841SPavan Nikhilesh 				&service_id);
73bcb6f841SPavan Nikhilesh 		if (ret != -ESRCH && ret != 0)
74bcb6f841SPavan Nikhilesh 			rte_panic("Error in starting eventdev service\n");
75bcb6f841SPavan Nikhilesh 		l2fwd_event_service_enable(service_id);
76bcb6f841SPavan Nikhilesh 	}
779a212dc0SConor Fogarty 	/* >8 End of running eventdev scheduler service on service core. */
78bcb6f841SPavan Nikhilesh 
799a212dc0SConor Fogarty 	/* Gets service ID for RX/TX adapters. 8< */
80bcb6f841SPavan Nikhilesh 	for (i = 0; i < evt_rsrc->rx_adptr.nb_rx_adptr; i++) {
81bcb6f841SPavan Nikhilesh 		ret = rte_event_eth_rx_adapter_caps_get(evt_rsrc->event_d_id,
82bcb6f841SPavan Nikhilesh 				evt_rsrc->rx_adptr.rx_adptr[i], &caps);
83bcb6f841SPavan Nikhilesh 		if (ret < 0)
84bcb6f841SPavan Nikhilesh 			rte_panic("Failed to get Rx adapter[%d] caps\n",
85bcb6f841SPavan Nikhilesh 				  evt_rsrc->rx_adptr.rx_adptr[i]);
86bcb6f841SPavan Nikhilesh 		ret = rte_event_eth_rx_adapter_service_id_get(
87bcb6f841SPavan Nikhilesh 				evt_rsrc->event_d_id,
88bcb6f841SPavan Nikhilesh 				&service_id);
89bcb6f841SPavan Nikhilesh 		if (ret != -ESRCH && ret != 0)
90bcb6f841SPavan Nikhilesh 			rte_panic("Error in starting Rx adapter[%d] service\n",
91bcb6f841SPavan Nikhilesh 				  evt_rsrc->rx_adptr.rx_adptr[i]);
92bcb6f841SPavan Nikhilesh 		l2fwd_event_service_enable(service_id);
93bcb6f841SPavan Nikhilesh 	}
94bcb6f841SPavan Nikhilesh 
95bcb6f841SPavan Nikhilesh 	for (i = 0; i < evt_rsrc->tx_adptr.nb_tx_adptr; i++) {
96bcb6f841SPavan Nikhilesh 		ret = rte_event_eth_tx_adapter_caps_get(evt_rsrc->event_d_id,
97bcb6f841SPavan Nikhilesh 				evt_rsrc->tx_adptr.tx_adptr[i], &caps);
98bcb6f841SPavan Nikhilesh 		if (ret < 0)
99bcb6f841SPavan Nikhilesh 			rte_panic("Failed to get Rx adapter[%d] caps\n",
100bcb6f841SPavan Nikhilesh 				  evt_rsrc->tx_adptr.tx_adptr[i]);
101bcb6f841SPavan Nikhilesh 		ret = rte_event_eth_tx_adapter_service_id_get(
102bcb6f841SPavan Nikhilesh 				evt_rsrc->event_d_id,
103bcb6f841SPavan Nikhilesh 				&service_id);
104bcb6f841SPavan Nikhilesh 		if (ret != -ESRCH && ret != 0)
105bcb6f841SPavan Nikhilesh 			rte_panic("Error in starting Rx adapter[%d] service\n",
106bcb6f841SPavan Nikhilesh 				  evt_rsrc->tx_adptr.tx_adptr[i]);
107bcb6f841SPavan Nikhilesh 		l2fwd_event_service_enable(service_id);
108bcb6f841SPavan Nikhilesh 	}
1099a212dc0SConor Fogarty 	/* >8 End of get service ID for RX/TX adapters. */
110bcb6f841SPavan Nikhilesh }
111bcb6f841SPavan Nikhilesh 
11269de9488SSunil Kumar Kori static void
11369de9488SSunil Kumar Kori l2fwd_event_capability_setup(struct l2fwd_event_resources *evt_rsrc)
11469de9488SSunil Kumar Kori {
11569de9488SSunil Kumar Kori 	uint32_t caps = 0;
11669de9488SSunil Kumar Kori 	uint16_t i;
11769de9488SSunil Kumar Kori 	int ret;
11869de9488SSunil Kumar Kori 
11969de9488SSunil Kumar Kori 	RTE_ETH_FOREACH_DEV(i) {
12069de9488SSunil Kumar Kori 		ret = rte_event_eth_tx_adapter_caps_get(0, i, &caps);
12169de9488SSunil Kumar Kori 		if (ret)
12269de9488SSunil Kumar Kori 			rte_panic("Invalid capability for Tx adptr port %d\n",
12369de9488SSunil Kumar Kori 				  i);
12469de9488SSunil Kumar Kori 
12569de9488SSunil Kumar Kori 		evt_rsrc->tx_mode_q |= !(caps &
12669de9488SSunil Kumar Kori 				   RTE_EVENT_ETH_TX_ADAPTER_CAP_INTERNAL_PORT);
12769de9488SSunil Kumar Kori 	}
12869de9488SSunil Kumar Kori 
12969de9488SSunil Kumar Kori 	if (evt_rsrc->tx_mode_q)
13069de9488SSunil Kumar Kori 		l2fwd_event_set_generic_ops(&evt_rsrc->ops);
13169de9488SSunil Kumar Kori 	else
13269de9488SSunil Kumar Kori 		l2fwd_event_set_internal_port_ops(&evt_rsrc->ops);
13369de9488SSunil Kumar Kori }
13469de9488SSunil Kumar Kori 
135080f57bcSPavan Nikhilesh static __rte_noinline int
136080f57bcSPavan Nikhilesh l2fwd_get_free_event_port(struct l2fwd_event_resources *evt_rsrc)
137080f57bcSPavan Nikhilesh {
138080f57bcSPavan Nikhilesh 	static int index;
139080f57bcSPavan Nikhilesh 	int port_id;
140080f57bcSPavan Nikhilesh 
141080f57bcSPavan Nikhilesh 	rte_spinlock_lock(&evt_rsrc->evp.lock);
142080f57bcSPavan Nikhilesh 	if (index >= evt_rsrc->evp.nb_ports) {
143080f57bcSPavan Nikhilesh 		printf("No free event port is available\n");
144*1f41deacSHemant Agrawal 		rte_spinlock_unlock(&evt_rsrc->evp.lock);
145080f57bcSPavan Nikhilesh 		return -1;
146080f57bcSPavan Nikhilesh 	}
147080f57bcSPavan Nikhilesh 
148080f57bcSPavan Nikhilesh 	port_id = evt_rsrc->evp.event_p_id[index];
149080f57bcSPavan Nikhilesh 	index++;
150080f57bcSPavan Nikhilesh 	rte_spinlock_unlock(&evt_rsrc->evp.lock);
151080f57bcSPavan Nikhilesh 
152080f57bcSPavan Nikhilesh 	return port_id;
153080f57bcSPavan Nikhilesh }
154080f57bcSPavan Nikhilesh 
155080f57bcSPavan Nikhilesh static  __rte_always_inline void
156080f57bcSPavan Nikhilesh l2fwd_event_fwd(struct l2fwd_resources *rsrc, struct rte_event *ev,
157080f57bcSPavan Nikhilesh 		const uint8_t tx_q_id, const uint64_t timer_period,
158080f57bcSPavan Nikhilesh 		const uint32_t flags)
159080f57bcSPavan Nikhilesh {
160080f57bcSPavan Nikhilesh 	struct rte_mbuf *mbuf = ev->mbuf;
161080f57bcSPavan Nikhilesh 	uint16_t dst_port;
162080f57bcSPavan Nikhilesh 
163080f57bcSPavan Nikhilesh 	rte_prefetch0(rte_pktmbuf_mtod(mbuf, void *));
164080f57bcSPavan Nikhilesh 	dst_port = rsrc->dst_ports[mbuf->port];
165080f57bcSPavan Nikhilesh 
166080f57bcSPavan Nikhilesh 	if (timer_period > 0)
16792e68d9cSTyler Retzlaff 		rte_atomic_fetch_add_explicit(&rsrc->port_stats[mbuf->port].rx,
16892e68d9cSTyler Retzlaff 				1, rte_memory_order_relaxed);
169080f57bcSPavan Nikhilesh 	mbuf->port = dst_port;
170080f57bcSPavan Nikhilesh 
171080f57bcSPavan Nikhilesh 	if (flags & L2FWD_EVENT_UPDT_MAC)
172080f57bcSPavan Nikhilesh 		l2fwd_mac_updating(mbuf, dst_port, &rsrc->eth_addr[dst_port]);
173080f57bcSPavan Nikhilesh 
174080f57bcSPavan Nikhilesh 	if (flags & L2FWD_EVENT_TX_ENQ) {
175080f57bcSPavan Nikhilesh 		ev->queue_id = tx_q_id;
176080f57bcSPavan Nikhilesh 		ev->op = RTE_EVENT_OP_FORWARD;
177080f57bcSPavan Nikhilesh 	}
178080f57bcSPavan Nikhilesh 
179080f57bcSPavan Nikhilesh 	if (flags & L2FWD_EVENT_TX_DIRECT)
180080f57bcSPavan Nikhilesh 		rte_event_eth_tx_adapter_txq_set(mbuf, 0);
181080f57bcSPavan Nikhilesh 
182080f57bcSPavan Nikhilesh 	if (timer_period > 0)
18392e68d9cSTyler Retzlaff 		rte_atomic_fetch_add_explicit(&rsrc->port_stats[mbuf->port].tx,
18492e68d9cSTyler Retzlaff 				1, rte_memory_order_relaxed);
185080f57bcSPavan Nikhilesh }
186080f57bcSPavan Nikhilesh 
187080f57bcSPavan Nikhilesh static __rte_always_inline void
188080f57bcSPavan Nikhilesh l2fwd_event_loop_single(struct l2fwd_resources *rsrc,
189080f57bcSPavan Nikhilesh 			const uint32_t flags)
190080f57bcSPavan Nikhilesh {
191080f57bcSPavan Nikhilesh 	struct l2fwd_event_resources *evt_rsrc = rsrc->evt_rsrc;
192080f57bcSPavan Nikhilesh 	const int port_id = l2fwd_get_free_event_port(evt_rsrc);
193080f57bcSPavan Nikhilesh 	const uint8_t tx_q_id = evt_rsrc->evq.event_q_id[
194080f57bcSPavan Nikhilesh 					evt_rsrc->evq.nb_queues - 1];
195080f57bcSPavan Nikhilesh 	const uint64_t timer_period = rsrc->timer_period;
196080f57bcSPavan Nikhilesh 	const uint8_t event_d_id = evt_rsrc->event_d_id;
197622ebb6bSPavan Nikhilesh 	uint8_t enq = 0, deq = 0;
198080f57bcSPavan Nikhilesh 	struct rte_event ev;
199080f57bcSPavan Nikhilesh 
200080f57bcSPavan Nikhilesh 	if (port_id < 0)
201080f57bcSPavan Nikhilesh 		return;
202080f57bcSPavan Nikhilesh 
203080f57bcSPavan Nikhilesh 	printf("%s(): entering eventdev main loop on lcore %u\n", __func__,
204080f57bcSPavan Nikhilesh 		rte_lcore_id());
205080f57bcSPavan Nikhilesh 
206080f57bcSPavan Nikhilesh 	while (!rsrc->force_quit) {
207080f57bcSPavan Nikhilesh 		/* Read packet from eventdev */
208622ebb6bSPavan Nikhilesh 		deq = rte_event_dequeue_burst(event_d_id, port_id, &ev, 1, 0);
209622ebb6bSPavan Nikhilesh 		if (!deq)
210080f57bcSPavan Nikhilesh 			continue;
211080f57bcSPavan Nikhilesh 
212080f57bcSPavan Nikhilesh 		l2fwd_event_fwd(rsrc, &ev, tx_q_id, timer_period, flags);
213080f57bcSPavan Nikhilesh 
214080f57bcSPavan Nikhilesh 		if (flags & L2FWD_EVENT_TX_ENQ) {
215622ebb6bSPavan Nikhilesh 			do {
216622ebb6bSPavan Nikhilesh 				enq = rte_event_enqueue_burst(event_d_id,
217622ebb6bSPavan Nikhilesh 							      port_id, &ev, 1);
218622ebb6bSPavan Nikhilesh 			} while (!enq && !rsrc->force_quit);
219080f57bcSPavan Nikhilesh 		}
220080f57bcSPavan Nikhilesh 
221080f57bcSPavan Nikhilesh 		if (flags & L2FWD_EVENT_TX_DIRECT) {
222622ebb6bSPavan Nikhilesh 			do {
223622ebb6bSPavan Nikhilesh 				enq = rte_event_eth_tx_adapter_enqueue(
224622ebb6bSPavan Nikhilesh 					event_d_id, port_id, &ev, 1, 0);
225622ebb6bSPavan Nikhilesh 			} while (!enq && !rsrc->force_quit);
226080f57bcSPavan Nikhilesh 		}
227080f57bcSPavan Nikhilesh 	}
228622ebb6bSPavan Nikhilesh 
229622ebb6bSPavan Nikhilesh 	l2fwd_event_worker_cleanup(event_d_id, port_id, &ev, enq, deq, 0);
230080f57bcSPavan Nikhilesh }
231080f57bcSPavan Nikhilesh 
232080f57bcSPavan Nikhilesh static __rte_always_inline void
233080f57bcSPavan Nikhilesh l2fwd_event_loop_burst(struct l2fwd_resources *rsrc,
234080f57bcSPavan Nikhilesh 		       const uint32_t flags)
235080f57bcSPavan Nikhilesh {
236080f57bcSPavan Nikhilesh 	struct l2fwd_event_resources *evt_rsrc = rsrc->evt_rsrc;
237080f57bcSPavan Nikhilesh 	const int port_id = l2fwd_get_free_event_port(evt_rsrc);
238080f57bcSPavan Nikhilesh 	const uint8_t tx_q_id = evt_rsrc->evq.event_q_id[
239080f57bcSPavan Nikhilesh 					evt_rsrc->evq.nb_queues - 1];
240080f57bcSPavan Nikhilesh 	const uint64_t timer_period = rsrc->timer_period;
241080f57bcSPavan Nikhilesh 	const uint8_t event_d_id = evt_rsrc->event_d_id;
242080f57bcSPavan Nikhilesh 	const uint8_t deq_len = evt_rsrc->deq_depth;
243080f57bcSPavan Nikhilesh 	struct rte_event ev[MAX_PKT_BURST];
244622ebb6bSPavan Nikhilesh 	uint16_t nb_rx = 0, nb_tx = 0;
245080f57bcSPavan Nikhilesh 	uint8_t i;
246080f57bcSPavan Nikhilesh 
247080f57bcSPavan Nikhilesh 	if (port_id < 0)
248080f57bcSPavan Nikhilesh 		return;
249080f57bcSPavan Nikhilesh 
250080f57bcSPavan Nikhilesh 	printf("%s(): entering eventdev main loop on lcore %u\n", __func__,
251080f57bcSPavan Nikhilesh 		rte_lcore_id());
252080f57bcSPavan Nikhilesh 
253080f57bcSPavan Nikhilesh 	while (!rsrc->force_quit) {
2549a212dc0SConor Fogarty 		/* Read packet from eventdev. 8< */
255080f57bcSPavan Nikhilesh 		nb_rx = rte_event_dequeue_burst(event_d_id, port_id, ev,
256080f57bcSPavan Nikhilesh 						deq_len, 0);
257080f57bcSPavan Nikhilesh 		if (nb_rx == 0)
258080f57bcSPavan Nikhilesh 			continue;
259080f57bcSPavan Nikhilesh 
260080f57bcSPavan Nikhilesh 		for (i = 0; i < nb_rx; i++) {
261080f57bcSPavan Nikhilesh 			l2fwd_event_fwd(rsrc, &ev[i], tx_q_id, timer_period,
262080f57bcSPavan Nikhilesh 					flags);
263080f57bcSPavan Nikhilesh 		}
2649a212dc0SConor Fogarty 		/* >8 End of reading packets from eventdev. */
265080f57bcSPavan Nikhilesh 
266080f57bcSPavan Nikhilesh 		if (flags & L2FWD_EVENT_TX_ENQ) {
2679a212dc0SConor Fogarty 			/* Forwarding to destination ports. 8< */
268080f57bcSPavan Nikhilesh 			nb_tx = rte_event_enqueue_burst(event_d_id, port_id,
269080f57bcSPavan Nikhilesh 							ev, nb_rx);
270080f57bcSPavan Nikhilesh 			while (nb_tx < nb_rx && !rsrc->force_quit)
271080f57bcSPavan Nikhilesh 				nb_tx += rte_event_enqueue_burst(event_d_id,
272080f57bcSPavan Nikhilesh 						port_id, ev + nb_tx,
273080f57bcSPavan Nikhilesh 						nb_rx - nb_tx);
2749a212dc0SConor Fogarty 			/* >8 End of forwarding to destination ports. */
275080f57bcSPavan Nikhilesh 		}
276080f57bcSPavan Nikhilesh 
277080f57bcSPavan Nikhilesh 		if (flags & L2FWD_EVENT_TX_DIRECT) {
278080f57bcSPavan Nikhilesh 			nb_tx = rte_event_eth_tx_adapter_enqueue(event_d_id,
279080f57bcSPavan Nikhilesh 								 port_id, ev,
280080f57bcSPavan Nikhilesh 								 nb_rx, 0);
281080f57bcSPavan Nikhilesh 			while (nb_tx < nb_rx && !rsrc->force_quit)
282080f57bcSPavan Nikhilesh 				nb_tx += rte_event_eth_tx_adapter_enqueue(
283080f57bcSPavan Nikhilesh 						event_d_id, port_id,
284080f57bcSPavan Nikhilesh 						ev + nb_tx, nb_rx - nb_tx, 0);
285080f57bcSPavan Nikhilesh 		}
286080f57bcSPavan Nikhilesh 	}
287622ebb6bSPavan Nikhilesh 
2887af8167aSShijith Thotton 	l2fwd_event_worker_cleanup(event_d_id, port_id, ev, nb_tx, nb_rx, 0);
289080f57bcSPavan Nikhilesh }
290080f57bcSPavan Nikhilesh 
291080f57bcSPavan Nikhilesh static __rte_always_inline void
292080f57bcSPavan Nikhilesh l2fwd_event_loop(struct l2fwd_resources *rsrc,
293080f57bcSPavan Nikhilesh 			const uint32_t flags)
294080f57bcSPavan Nikhilesh {
295080f57bcSPavan Nikhilesh 	if (flags & L2FWD_EVENT_SINGLE)
296080f57bcSPavan Nikhilesh 		l2fwd_event_loop_single(rsrc, flags);
297080f57bcSPavan Nikhilesh 	if (flags & L2FWD_EVENT_BURST)
298080f57bcSPavan Nikhilesh 		l2fwd_event_loop_burst(rsrc, flags);
299080f57bcSPavan Nikhilesh }
300080f57bcSPavan Nikhilesh 
301080f57bcSPavan Nikhilesh static void __rte_noinline
302080f57bcSPavan Nikhilesh l2fwd_event_main_loop_tx_d(struct l2fwd_resources *rsrc)
303080f57bcSPavan Nikhilesh {
304080f57bcSPavan Nikhilesh 	l2fwd_event_loop(rsrc,
305080f57bcSPavan Nikhilesh 			 L2FWD_EVENT_TX_DIRECT | L2FWD_EVENT_SINGLE);
306080f57bcSPavan Nikhilesh }
307080f57bcSPavan Nikhilesh 
308080f57bcSPavan Nikhilesh static void __rte_noinline
309080f57bcSPavan Nikhilesh l2fwd_event_main_loop_tx_d_brst(struct l2fwd_resources *rsrc)
310080f57bcSPavan Nikhilesh {
311080f57bcSPavan Nikhilesh 	l2fwd_event_loop(rsrc, L2FWD_EVENT_TX_DIRECT | L2FWD_EVENT_BURST);
312080f57bcSPavan Nikhilesh }
313080f57bcSPavan Nikhilesh 
314080f57bcSPavan Nikhilesh static void __rte_noinline
315080f57bcSPavan Nikhilesh l2fwd_event_main_loop_tx_q(struct l2fwd_resources *rsrc)
316080f57bcSPavan Nikhilesh {
317080f57bcSPavan Nikhilesh 	l2fwd_event_loop(rsrc, L2FWD_EVENT_TX_ENQ | L2FWD_EVENT_SINGLE);
318080f57bcSPavan Nikhilesh }
319080f57bcSPavan Nikhilesh 
320080f57bcSPavan Nikhilesh static void __rte_noinline
321080f57bcSPavan Nikhilesh l2fwd_event_main_loop_tx_q_brst(struct l2fwd_resources *rsrc)
322080f57bcSPavan Nikhilesh {
323080f57bcSPavan Nikhilesh 	l2fwd_event_loop(rsrc, L2FWD_EVENT_TX_ENQ | L2FWD_EVENT_BURST);
324080f57bcSPavan Nikhilesh }
325080f57bcSPavan Nikhilesh 
326080f57bcSPavan Nikhilesh static void __rte_noinline
327080f57bcSPavan Nikhilesh l2fwd_event_main_loop_tx_d_mac(struct l2fwd_resources *rsrc)
328080f57bcSPavan Nikhilesh {
329080f57bcSPavan Nikhilesh 	l2fwd_event_loop(rsrc, L2FWD_EVENT_UPDT_MAC |
330080f57bcSPavan Nikhilesh 			L2FWD_EVENT_TX_DIRECT | L2FWD_EVENT_SINGLE);
331080f57bcSPavan Nikhilesh }
332080f57bcSPavan Nikhilesh 
333080f57bcSPavan Nikhilesh static void __rte_noinline
334080f57bcSPavan Nikhilesh l2fwd_event_main_loop_tx_d_brst_mac(struct l2fwd_resources *rsrc)
335080f57bcSPavan Nikhilesh {
336080f57bcSPavan Nikhilesh 	l2fwd_event_loop(rsrc, L2FWD_EVENT_UPDT_MAC |
337080f57bcSPavan Nikhilesh 			L2FWD_EVENT_TX_DIRECT | L2FWD_EVENT_BURST);
338080f57bcSPavan Nikhilesh }
339080f57bcSPavan Nikhilesh 
340080f57bcSPavan Nikhilesh static void __rte_noinline
341080f57bcSPavan Nikhilesh l2fwd_event_main_loop_tx_q_mac(struct l2fwd_resources *rsrc)
342080f57bcSPavan Nikhilesh {
343080f57bcSPavan Nikhilesh 	l2fwd_event_loop(rsrc, L2FWD_EVENT_UPDT_MAC |
344080f57bcSPavan Nikhilesh 			L2FWD_EVENT_TX_ENQ | L2FWD_EVENT_SINGLE);
345080f57bcSPavan Nikhilesh }
346080f57bcSPavan Nikhilesh 
347080f57bcSPavan Nikhilesh static void __rte_noinline
348080f57bcSPavan Nikhilesh l2fwd_event_main_loop_tx_q_brst_mac(struct l2fwd_resources *rsrc)
349080f57bcSPavan Nikhilesh {
350080f57bcSPavan Nikhilesh 	l2fwd_event_loop(rsrc, L2FWD_EVENT_UPDT_MAC |
351080f57bcSPavan Nikhilesh 			L2FWD_EVENT_TX_ENQ | L2FWD_EVENT_BURST);
352080f57bcSPavan Nikhilesh }
353080f57bcSPavan Nikhilesh 
354796b07e9SShijith Thotton static __rte_always_inline void
355796b07e9SShijith Thotton l2fwd_event_vector_fwd(struct l2fwd_resources *rsrc,
356796b07e9SShijith Thotton 		       struct rte_event_vector *vec,
357796b07e9SShijith Thotton 		       const uint64_t timer_period, const uint32_t flags)
358796b07e9SShijith Thotton {
359796b07e9SShijith Thotton 	struct rte_mbuf **mbufs = vec->mbufs;
360796b07e9SShijith Thotton 	uint16_t i, j;
361796b07e9SShijith Thotton 
362796b07e9SShijith Thotton 	rte_prefetch0(rte_pktmbuf_mtod(mbufs[0], void *));
363796b07e9SShijith Thotton 
364796b07e9SShijith Thotton 	/* If vector attribute is valid, mbufs will be from same port/queue */
365796b07e9SShijith Thotton 	if (vec->attr_valid) {
366796b07e9SShijith Thotton 		vec->port = rsrc->dst_ports[mbufs[0]->port];
367796b07e9SShijith Thotton 		if (flags & L2FWD_EVENT_TX_DIRECT)
368796b07e9SShijith Thotton 			vec->queue = 0;
369796b07e9SShijith Thotton 
370796b07e9SShijith Thotton 		if (timer_period > 0)
37192e68d9cSTyler Retzlaff 			rte_atomic_fetch_add_explicit(&rsrc->port_stats[mbufs[0]->port].rx,
37292e68d9cSTyler Retzlaff 					   vec->nb_elem, rte_memory_order_relaxed);
373796b07e9SShijith Thotton 
374796b07e9SShijith Thotton 		for (i = 0, j = 1; i < vec->nb_elem; i++, j++) {
375796b07e9SShijith Thotton 			if (j < vec->nb_elem)
376796b07e9SShijith Thotton 				rte_prefetch0(
377796b07e9SShijith Thotton 					rte_pktmbuf_mtod(mbufs[j], void *));
378796b07e9SShijith Thotton 
379796b07e9SShijith Thotton 			if (flags & L2FWD_EVENT_UPDT_MAC)
380796b07e9SShijith Thotton 				l2fwd_mac_updating(
381796b07e9SShijith Thotton 					mbufs[i], vec->port,
382796b07e9SShijith Thotton 					&rsrc->eth_addr[vec->port]);
383796b07e9SShijith Thotton 		}
384796b07e9SShijith Thotton 
385796b07e9SShijith Thotton 		if (timer_period > 0)
38692e68d9cSTyler Retzlaff 			rte_atomic_fetch_add_explicit(&rsrc->port_stats[vec->port].tx,
38792e68d9cSTyler Retzlaff 					   vec->nb_elem, rte_memory_order_relaxed);
388796b07e9SShijith Thotton 	} else {
389796b07e9SShijith Thotton 		for (i = 0, j = 1; i < vec->nb_elem; i++, j++) {
390796b07e9SShijith Thotton 			if (timer_period > 0)
39192e68d9cSTyler Retzlaff 				rte_atomic_fetch_add_explicit(
392796b07e9SShijith Thotton 					&rsrc->port_stats[mbufs[i]->port].rx, 1,
39392e68d9cSTyler Retzlaff 					rte_memory_order_relaxed);
394796b07e9SShijith Thotton 
395796b07e9SShijith Thotton 			if (j < vec->nb_elem)
396796b07e9SShijith Thotton 				rte_prefetch0(
397796b07e9SShijith Thotton 					rte_pktmbuf_mtod(mbufs[j], void *));
398796b07e9SShijith Thotton 
399796b07e9SShijith Thotton 			mbufs[i]->port = rsrc->dst_ports[mbufs[i]->port];
400796b07e9SShijith Thotton 
401796b07e9SShijith Thotton 			if (flags & L2FWD_EVENT_UPDT_MAC)
402796b07e9SShijith Thotton 				l2fwd_mac_updating(
403796b07e9SShijith Thotton 					mbufs[i], mbufs[i]->port,
404796b07e9SShijith Thotton 					&rsrc->eth_addr[mbufs[i]->port]);
405796b07e9SShijith Thotton 
406796b07e9SShijith Thotton 			if (flags & L2FWD_EVENT_TX_DIRECT)
407796b07e9SShijith Thotton 				rte_event_eth_tx_adapter_txq_set(mbufs[i], 0);
408796b07e9SShijith Thotton 
409796b07e9SShijith Thotton 			if (timer_period > 0)
41092e68d9cSTyler Retzlaff 				rte_atomic_fetch_add_explicit(
411796b07e9SShijith Thotton 					&rsrc->port_stats[mbufs[i]->port].tx, 1,
41292e68d9cSTyler Retzlaff 					rte_memory_order_relaxed);
413796b07e9SShijith Thotton 		}
414796b07e9SShijith Thotton 	}
415796b07e9SShijith Thotton }
416796b07e9SShijith Thotton 
417796b07e9SShijith Thotton static __rte_always_inline void
418796b07e9SShijith Thotton l2fwd_event_loop_vector(struct l2fwd_resources *rsrc, const uint32_t flags)
419796b07e9SShijith Thotton {
420796b07e9SShijith Thotton 	struct l2fwd_event_resources *evt_rsrc = rsrc->evt_rsrc;
421796b07e9SShijith Thotton 	const int port_id = l2fwd_get_free_event_port(evt_rsrc);
422796b07e9SShijith Thotton 	const uint8_t tx_q_id =
423796b07e9SShijith Thotton 		evt_rsrc->evq.event_q_id[evt_rsrc->evq.nb_queues - 1];
424796b07e9SShijith Thotton 	const uint64_t timer_period = rsrc->timer_period;
425796b07e9SShijith Thotton 	const uint8_t event_d_id = evt_rsrc->event_d_id;
426796b07e9SShijith Thotton 	const uint8_t deq_len = evt_rsrc->deq_depth;
427796b07e9SShijith Thotton 	struct rte_event ev[MAX_PKT_BURST];
428622ebb6bSPavan Nikhilesh 	uint16_t nb_rx = 0, nb_tx = 0;
429796b07e9SShijith Thotton 	uint8_t i;
430796b07e9SShijith Thotton 
431796b07e9SShijith Thotton 	if (port_id < 0)
432796b07e9SShijith Thotton 		return;
433796b07e9SShijith Thotton 
434796b07e9SShijith Thotton 	printf("%s(): entering eventdev main loop on lcore %u\n", __func__,
435796b07e9SShijith Thotton 	       rte_lcore_id());
436796b07e9SShijith Thotton 
437796b07e9SShijith Thotton 	while (!rsrc->force_quit) {
438796b07e9SShijith Thotton 		nb_rx = rte_event_dequeue_burst(event_d_id, port_id, ev,
439796b07e9SShijith Thotton 						deq_len, 0);
440796b07e9SShijith Thotton 		if (nb_rx == 0)
441796b07e9SShijith Thotton 			continue;
442796b07e9SShijith Thotton 
443796b07e9SShijith Thotton 		for (i = 0; i < nb_rx; i++) {
444796b07e9SShijith Thotton 			if (flags & L2FWD_EVENT_TX_ENQ) {
445796b07e9SShijith Thotton 				ev[i].queue_id = tx_q_id;
446796b07e9SShijith Thotton 				ev[i].op = RTE_EVENT_OP_FORWARD;
447796b07e9SShijith Thotton 			}
448796b07e9SShijith Thotton 
449796b07e9SShijith Thotton 			l2fwd_event_vector_fwd(rsrc, ev[i].vec, timer_period,
450796b07e9SShijith Thotton 					       flags);
451796b07e9SShijith Thotton 		}
452796b07e9SShijith Thotton 
453796b07e9SShijith Thotton 		if (flags & L2FWD_EVENT_TX_ENQ) {
454796b07e9SShijith Thotton 			nb_tx = rte_event_enqueue_burst(event_d_id, port_id, ev,
455796b07e9SShijith Thotton 							nb_rx);
456796b07e9SShijith Thotton 			while (nb_tx < nb_rx && !rsrc->force_quit)
457796b07e9SShijith Thotton 				nb_tx += rte_event_enqueue_burst(
458796b07e9SShijith Thotton 					event_d_id, port_id, ev + nb_tx,
459796b07e9SShijith Thotton 					nb_rx - nb_tx);
460796b07e9SShijith Thotton 		}
461796b07e9SShijith Thotton 
462796b07e9SShijith Thotton 		if (flags & L2FWD_EVENT_TX_DIRECT) {
463796b07e9SShijith Thotton 			nb_tx = rte_event_eth_tx_adapter_enqueue(
464796b07e9SShijith Thotton 				event_d_id, port_id, ev, nb_rx, 0);
465796b07e9SShijith Thotton 			while (nb_tx < nb_rx && !rsrc->force_quit)
466796b07e9SShijith Thotton 				nb_tx += rte_event_eth_tx_adapter_enqueue(
467796b07e9SShijith Thotton 					event_d_id, port_id, ev + nb_tx,
468796b07e9SShijith Thotton 					nb_rx - nb_tx, 0);
469796b07e9SShijith Thotton 		}
470796b07e9SShijith Thotton 	}
471622ebb6bSPavan Nikhilesh 
4727af8167aSShijith Thotton 	l2fwd_event_worker_cleanup(event_d_id, port_id, ev, nb_tx, nb_rx, 1);
473796b07e9SShijith Thotton }
474796b07e9SShijith Thotton 
475796b07e9SShijith Thotton static void __rte_noinline
476796b07e9SShijith Thotton l2fwd_event_main_loop_tx_d_vec(struct l2fwd_resources *rsrc)
477796b07e9SShijith Thotton {
478796b07e9SShijith Thotton 	l2fwd_event_loop_vector(rsrc, L2FWD_EVENT_TX_DIRECT);
479796b07e9SShijith Thotton }
480796b07e9SShijith Thotton 
481796b07e9SShijith Thotton static void __rte_noinline
482796b07e9SShijith Thotton l2fwd_event_main_loop_tx_d_brst_vec(struct l2fwd_resources *rsrc)
483796b07e9SShijith Thotton {
484796b07e9SShijith Thotton 	l2fwd_event_loop_vector(rsrc, L2FWD_EVENT_TX_DIRECT);
485796b07e9SShijith Thotton }
486796b07e9SShijith Thotton 
487796b07e9SShijith Thotton static void __rte_noinline
488796b07e9SShijith Thotton l2fwd_event_main_loop_tx_q_vec(struct l2fwd_resources *rsrc)
489796b07e9SShijith Thotton {
490796b07e9SShijith Thotton 	l2fwd_event_loop_vector(rsrc, L2FWD_EVENT_TX_ENQ);
491796b07e9SShijith Thotton }
492796b07e9SShijith Thotton 
493796b07e9SShijith Thotton static void __rte_noinline
494796b07e9SShijith Thotton l2fwd_event_main_loop_tx_q_brst_vec(struct l2fwd_resources *rsrc)
495796b07e9SShijith Thotton {
496796b07e9SShijith Thotton 	l2fwd_event_loop_vector(rsrc, L2FWD_EVENT_TX_ENQ);
497796b07e9SShijith Thotton }
498796b07e9SShijith Thotton 
499796b07e9SShijith Thotton static void __rte_noinline
500796b07e9SShijith Thotton l2fwd_event_main_loop_tx_d_mac_vec(struct l2fwd_resources *rsrc)
501796b07e9SShijith Thotton {
502796b07e9SShijith Thotton 	l2fwd_event_loop_vector(rsrc,
503796b07e9SShijith Thotton 				L2FWD_EVENT_UPDT_MAC | L2FWD_EVENT_TX_DIRECT);
504796b07e9SShijith Thotton }
505796b07e9SShijith Thotton 
506796b07e9SShijith Thotton static void __rte_noinline
507796b07e9SShijith Thotton l2fwd_event_main_loop_tx_d_brst_mac_vec(struct l2fwd_resources *rsrc)
508796b07e9SShijith Thotton {
509796b07e9SShijith Thotton 	l2fwd_event_loop_vector(rsrc,
510796b07e9SShijith Thotton 				L2FWD_EVENT_UPDT_MAC | L2FWD_EVENT_TX_DIRECT);
511796b07e9SShijith Thotton }
512796b07e9SShijith Thotton 
513796b07e9SShijith Thotton static void __rte_noinline
514796b07e9SShijith Thotton l2fwd_event_main_loop_tx_q_mac_vec(struct l2fwd_resources *rsrc)
515796b07e9SShijith Thotton {
516796b07e9SShijith Thotton 	l2fwd_event_loop_vector(rsrc,
517796b07e9SShijith Thotton 				L2FWD_EVENT_UPDT_MAC | L2FWD_EVENT_TX_ENQ);
518796b07e9SShijith Thotton }
519796b07e9SShijith Thotton 
520796b07e9SShijith Thotton static void __rte_noinline
521796b07e9SShijith Thotton l2fwd_event_main_loop_tx_q_brst_mac_vec(struct l2fwd_resources *rsrc)
522796b07e9SShijith Thotton {
523796b07e9SShijith Thotton 	l2fwd_event_loop_vector(rsrc,
524796b07e9SShijith Thotton 				L2FWD_EVENT_UPDT_MAC | L2FWD_EVENT_TX_ENQ);
525796b07e9SShijith Thotton }
526796b07e9SShijith Thotton 
5271b2143aaSPavan Nikhilesh void
5281b2143aaSPavan Nikhilesh l2fwd_event_resource_setup(struct l2fwd_resources *rsrc)
5291b2143aaSPavan Nikhilesh {
530080f57bcSPavan Nikhilesh 	/* [MAC_UPDT][TX_MODE][BURST] */
531796b07e9SShijith Thotton 	const event_loop_cb event_loop[2][2][2][2] = {
532796b07e9SShijith Thotton 		[0][0][0][0] = l2fwd_event_main_loop_tx_d,
533796b07e9SShijith Thotton 		[0][0][0][1] = l2fwd_event_main_loop_tx_d_brst,
534796b07e9SShijith Thotton 		[0][0][1][0] = l2fwd_event_main_loop_tx_q,
535796b07e9SShijith Thotton 		[0][0][1][1] = l2fwd_event_main_loop_tx_q_brst,
536796b07e9SShijith Thotton 		[0][1][0][0] = l2fwd_event_main_loop_tx_d_mac,
537796b07e9SShijith Thotton 		[0][1][0][1] = l2fwd_event_main_loop_tx_d_brst_mac,
538796b07e9SShijith Thotton 		[0][1][1][0] = l2fwd_event_main_loop_tx_q_mac,
539796b07e9SShijith Thotton 		[0][1][1][1] = l2fwd_event_main_loop_tx_q_brst_mac,
540796b07e9SShijith Thotton 		[1][0][0][0] = l2fwd_event_main_loop_tx_d_vec,
541796b07e9SShijith Thotton 		[1][0][0][1] = l2fwd_event_main_loop_tx_d_brst_vec,
542796b07e9SShijith Thotton 		[1][0][1][0] = l2fwd_event_main_loop_tx_q_vec,
543796b07e9SShijith Thotton 		[1][0][1][1] = l2fwd_event_main_loop_tx_q_brst_vec,
544796b07e9SShijith Thotton 		[1][1][0][0] = l2fwd_event_main_loop_tx_d_mac_vec,
545796b07e9SShijith Thotton 		[1][1][0][1] = l2fwd_event_main_loop_tx_d_brst_mac_vec,
546796b07e9SShijith Thotton 		[1][1][1][0] = l2fwd_event_main_loop_tx_q_mac_vec,
547796b07e9SShijith Thotton 		[1][1][1][1] = l2fwd_event_main_loop_tx_q_brst_mac_vec,
548080f57bcSPavan Nikhilesh 	};
5491b2143aaSPavan Nikhilesh 	struct l2fwd_event_resources *evt_rsrc;
5503b5476dbSSunil Kumar Kori 	uint32_t event_queue_cfg;
551080f57bcSPavan Nikhilesh 	int ret;
5521b2143aaSPavan Nikhilesh 
5531b2143aaSPavan Nikhilesh 	if (!rte_event_dev_count())
5541b2143aaSPavan Nikhilesh 		rte_panic("No Eventdev found\n");
5551b2143aaSPavan Nikhilesh 
5561b2143aaSPavan Nikhilesh 	evt_rsrc = rte_zmalloc("l2fwd_event",
5571b2143aaSPavan Nikhilesh 				 sizeof(struct l2fwd_event_resources), 0);
5581b2143aaSPavan Nikhilesh 	if (evt_rsrc == NULL)
5591b2143aaSPavan Nikhilesh 		rte_panic("Failed to allocate memory\n");
5601b2143aaSPavan Nikhilesh 
5611b2143aaSPavan Nikhilesh 	rsrc->evt_rsrc = evt_rsrc;
56269de9488SSunil Kumar Kori 
56369de9488SSunil Kumar Kori 	/* Setup eventdev capability callbacks */
56469de9488SSunil Kumar Kori 	l2fwd_event_capability_setup(evt_rsrc);
5656ab87600SSunil Kumar Kori 
5666ab87600SSunil Kumar Kori 	/* Event device configuration */
5673b5476dbSSunil Kumar Kori 	event_queue_cfg = evt_rsrc->ops.event_device_setup(rsrc);
5683b5476dbSSunil Kumar Kori 
5693b5476dbSSunil Kumar Kori 	/* Event queue configuration */
5703b5476dbSSunil Kumar Kori 	evt_rsrc->ops.event_queue_setup(rsrc, event_queue_cfg);
5713b5476dbSSunil Kumar Kori 
5723b5476dbSSunil Kumar Kori 	/* Event port configuration */
5733b5476dbSSunil Kumar Kori 	evt_rsrc->ops.event_port_setup(rsrc);
57450f05aa6SSunil Kumar Kori 
57550f05aa6SSunil Kumar Kori 	/* Rx/Tx adapters configuration */
57650f05aa6SSunil Kumar Kori 	evt_rsrc->ops.adapter_setup(rsrc);
577080f57bcSPavan Nikhilesh 
578080f57bcSPavan Nikhilesh 	/* Start event device */
579080f57bcSPavan Nikhilesh 	ret = rte_event_dev_start(evt_rsrc->event_d_id);
580080f57bcSPavan Nikhilesh 	if (ret < 0)
581080f57bcSPavan Nikhilesh 		rte_panic("Error in starting eventdev\n");
582080f57bcSPavan Nikhilesh 
583796b07e9SShijith Thotton 	evt_rsrc->ops.l2fwd_event_loop =
584796b07e9SShijith Thotton 		event_loop[rsrc->evt_vec.enabled][rsrc->mac_updating]
585796b07e9SShijith Thotton 			  [evt_rsrc->tx_mode_q][evt_rsrc->has_burst];
5861b2143aaSPavan Nikhilesh }
587