xref: /freebsd/sys/dev/netmap/netmap_vale.c (revision ab40f58ccfe6c07ebefddc72f4661a52fe746353)
1 /*-
2  * SPDX-License-Identifier: BSD-2-Clause-FreeBSD
3  *
4  * Copyright (C) 2013-2016 Universita` di Pisa
5  * All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  *   1. Redistributions of source code must retain the above copyright
11  *      notice, this list of conditions and the following disclaimer.
12  *   2. Redistributions in binary form must reproduce the above copyright
13  *      notice, this list of conditions and the following disclaimer in the
14  *      documentation and/or other materials provided with the distribution.
15  *
16  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
17  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
20  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
21  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
22  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
23  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
24  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
25  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
26  * SUCH DAMAGE.
27  */
28 
29 
30 /*
31  * This module implements the VALE switch for netmap
32 
33 --- VALE SWITCH ---
34 
35 NMG_LOCK() serializes all modifications to switches and ports.
36 A switch cannot be deleted until all ports are gone.
37 
38 For each switch, an SX lock (RWlock on linux) protects
39 deletion of ports. When configuring or deleting a new port, the
40 lock is acquired in exclusive mode (after holding NMG_LOCK).
41 When forwarding, the lock is acquired in shared mode (without NMG_LOCK).
42 The lock is held throughout the entire forwarding cycle,
43 during which the thread may incur in a page fault.
44 Hence it is important that sleepable shared locks are used.
45 
46 On the rx ring, the per-port lock is grabbed initially to reserve
47 a number of slot in the ring, then the lock is released,
48 packets are copied from source to destination, and then
49 the lock is acquired again and the receive ring is updated.
50 (A similar thing is done on the tx ring for NIC and host stack
51 ports attached to the switch)
52 
53  */
54 
55 /*
56  * OS-specific code that is used only within this file.
57  * Other OS-specific code that must be accessed by drivers
58  * is present in netmap_kern.h
59  */
60 
61 #if defined(__FreeBSD__)
62 #include <sys/cdefs.h> /* prerequisite */
63 __FBSDID("$FreeBSD$");
64 
65 #include <sys/types.h>
66 #include <sys/errno.h>
67 #include <sys/param.h>	/* defines used in kernel.h */
68 #include <sys/kernel.h>	/* types used in module initialization */
69 #include <sys/conf.h>	/* cdevsw struct, UID, GID */
70 #include <sys/sockio.h>
71 #include <sys/socketvar.h>	/* struct socket */
72 #include <sys/malloc.h>
73 #include <sys/poll.h>
74 #include <sys/rwlock.h>
75 #include <sys/socket.h> /* sockaddrs */
76 #include <sys/selinfo.h>
77 #include <sys/sysctl.h>
78 #include <net/if.h>
79 #include <net/if_var.h>
80 #include <net/bpf.h>		/* BIOCIMMEDIATE */
81 #include <machine/bus.h>	/* bus_dmamap_* */
82 #include <sys/endian.h>
83 #include <sys/refcount.h>
84 
85 
86 #define BDG_RWLOCK_T		struct rwlock // struct rwlock
87 
88 #define	BDG_RWINIT(b)		\
89 	rw_init_flags(&(b)->bdg_lock, "bdg lock", RW_NOWITNESS)
90 #define BDG_WLOCK(b)		rw_wlock(&(b)->bdg_lock)
91 #define BDG_WUNLOCK(b)		rw_wunlock(&(b)->bdg_lock)
92 #define BDG_RLOCK(b)		rw_rlock(&(b)->bdg_lock)
93 #define BDG_RTRYLOCK(b)		rw_try_rlock(&(b)->bdg_lock)
94 #define BDG_RUNLOCK(b)		rw_runlock(&(b)->bdg_lock)
95 #define BDG_RWDESTROY(b)	rw_destroy(&(b)->bdg_lock)
96 
97 
98 #elif defined(linux)
99 
100 #include "bsd_glue.h"
101 
102 #elif defined(__APPLE__)
103 
104 #warning OSX support is only partial
105 #include "osx_glue.h"
106 
107 #elif defined(_WIN32)
108 #include "win_glue.h"
109 
110 #else
111 
112 #error	Unsupported platform
113 
114 #endif /* unsupported */
115 
116 /*
117  * common headers
118  */
119 
120 #include <net/netmap.h>
121 #include <dev/netmap/netmap_kern.h>
122 #include <dev/netmap/netmap_mem2.h>
123 
124 #ifdef WITH_VALE
125 
126 /*
127  * system parameters (most of them in netmap_kern.h)
128  * NM_BDG_NAME	prefix for switch port names, default "vale"
129  * NM_BDG_MAXPORTS	number of ports
130  * NM_BRIDGES	max number of switches in the system.
131  *	XXX should become a sysctl or tunable
132  *
133  * Switch ports are named valeX:Y where X is the switch name and Y
134  * is the port. If Y matches a physical interface name, the port is
135  * connected to a physical device.
136  *
137  * Unlike physical interfaces, switch ports use their own memory region
138  * for rings and buffers.
139  * The virtual interfaces use per-queue lock instead of core lock.
140  * In the tx loop, we aggregate traffic in batches to make all operations
141  * faster. The batch size is bridge_batch.
142  */
143 #define NM_BDG_MAXRINGS		16	/* XXX unclear how many. */
144 #define NM_BDG_MAXSLOTS		4096	/* XXX same as above */
145 #define NM_BRIDGE_RINGSIZE	1024	/* in the device */
146 #define NM_BDG_HASH		1024	/* forwarding table entries */
147 #define NM_BDG_BATCH		1024	/* entries in the forwarding buffer */
148 #define NM_MULTISEG		64	/* max size of a chain of bufs */
149 /* actual size of the tables */
150 #define NM_BDG_BATCH_MAX	(NM_BDG_BATCH + NM_MULTISEG)
151 /* NM_FT_NULL terminates a list of slots in the ft */
152 #define NM_FT_NULL		NM_BDG_BATCH_MAX
153 /* Default size for the Maximum Frame Size. */
154 #define NM_BDG_MFS_DEFAULT	1514
155 
156 
157 /*
158  * bridge_batch is set via sysctl to the max batch size to be
159  * used in the bridge. The actual value may be larger as the
160  * last packet in the block may overflow the size.
161  */
162 static int bridge_batch = NM_BDG_BATCH; /* bridge batch size */
163 SYSBEGIN(vars_vale);
164 SYSCTL_DECL(_dev_netmap);
165 SYSCTL_INT(_dev_netmap, OID_AUTO, bridge_batch, CTLFLAG_RW, &bridge_batch, 0,
166 		"Max batch size to be used in the bridge");
167 SYSEND;
168 
169 static int netmap_vp_create(struct nmreq_header *hdr, struct ifnet *,
170 		struct netmap_mem_d *nmd, struct netmap_vp_adapter **);
171 static int netmap_vp_reg(struct netmap_adapter *na, int onoff);
172 static int netmap_bwrap_reg(struct netmap_adapter *, int onoff);
173 
174 /*
175  * For each output interface, nm_bdg_q is used to construct a list.
176  * bq_len is the number of output buffers (we can have coalescing
177  * during the copy).
178  */
179 struct nm_bdg_q {
180 	uint16_t bq_head;
181 	uint16_t bq_tail;
182 	uint32_t bq_len;	/* number of buffers */
183 };
184 
185 /* XXX revise this */
186 struct nm_hash_ent {
187 	uint64_t	mac;	/* the top 2 bytes are the epoch */
188 	uint64_t	ports;
189 };
190 
191 /* Holds the default callbacks */
192 static struct netmap_bdg_ops default_bdg_ops = {netmap_bdg_learning, NULL, NULL};
193 
194 /*
195  * nm_bridge is a descriptor for a VALE switch.
196  * Interfaces for a bridge are all in bdg_ports[].
197  * The array has fixed size, an empty entry does not terminate
198  * the search, but lookups only occur on attach/detach so we
199  * don't mind if they are slow.
200  *
201  * The bridge is non blocking on the transmit ports: excess
202  * packets are dropped if there is no room on the output port.
203  *
204  * bdg_lock protects accesses to the bdg_ports array.
205  * This is a rw lock (or equivalent).
206  */
207 #define NM_BDG_IFNAMSIZ IFNAMSIZ
208 struct nm_bridge {
209 	/* XXX what is the proper alignment/layout ? */
210 	BDG_RWLOCK_T	bdg_lock;	/* protects bdg_ports */
211 	int		bdg_namelen;
212 	uint32_t	bdg_active_ports;
213 	char		bdg_basename[NM_BDG_IFNAMSIZ];
214 
215 	/* Indexes of active ports (up to active_ports)
216 	 * and all other remaining ports.
217 	 */
218 	uint32_t	bdg_port_index[NM_BDG_MAXPORTS];
219 	/* used by netmap_bdg_detach_common() */
220 	uint32_t	tmp_bdg_port_index[NM_BDG_MAXPORTS];
221 
222 	struct netmap_vp_adapter *bdg_ports[NM_BDG_MAXPORTS];
223 
224 	/*
225 	 * Programmable lookup functions to figure out the destination port.
226 	 * It returns either of an index of the destination port,
227 	 * NM_BDG_BROADCAST to broadcast this packet, or NM_BDG_NOPORT not to
228 	 * forward this packet.  ring_nr is the source ring index, and the
229 	 * function may overwrite this value to forward this packet to a
230 	 * different ring index.
231 	 * The function is set by netmap_bdg_regops().
232 	 */
233 	struct netmap_bdg_ops *bdg_ops;
234 
235 	/*
236 	 * Contains the data structure used by the bdg_ops.lookup function.
237 	 * By default points to *ht which is allocated on attach and used by the default lookup
238 	 * otherwise will point to the data structure received by netmap_bdg_regops().
239 	 */
240 	void *private_data;
241 	struct nm_hash_ent *ht;
242 
243 	/* Currently used to specify if the bridge is still in use while empty and
244 	 * if it has been put in exclusive mode by an external module, see netmap_bdg_regops()
245 	 * and netmap_bdg_create().
246 	 */
247 #define NM_BDG_ACTIVE		1
248 #define NM_BDG_EXCLUSIVE	2
249 	uint8_t			bdg_flags;
250 
251 
252 #ifdef CONFIG_NET_NS
253 	struct net *ns;
254 #endif /* CONFIG_NET_NS */
255 };
256 
257 const char*
258 netmap_bdg_name(struct netmap_vp_adapter *vp)
259 {
260 	struct nm_bridge *b = vp->na_bdg;
261 	if (b == NULL)
262 		return NULL;
263 	return b->bdg_basename;
264 }
265 
266 
267 #ifndef CONFIG_NET_NS
268 /*
269  * XXX in principle nm_bridges could be created dynamically
270  * Right now we have a static array and deletions are protected
271  * by an exclusive lock.
272  */
273 static struct nm_bridge *nm_bridges;
274 #endif /* !CONFIG_NET_NS */
275 
276 
277 /*
278  * this is a slightly optimized copy routine which rounds
279  * to multiple of 64 bytes and is often faster than dealing
280  * with other odd sizes. We assume there is enough room
281  * in the source and destination buffers.
282  *
283  * XXX only for multiples of 64 bytes, non overlapped.
284  */
285 static inline void
286 pkt_copy(void *_src, void *_dst, int l)
287 {
288 	uint64_t *src = _src;
289 	uint64_t *dst = _dst;
290 	if (unlikely(l >= 1024)) {
291 		memcpy(dst, src, l);
292 		return;
293 	}
294 	for (; likely(l > 0); l-=64) {
295 		*dst++ = *src++;
296 		*dst++ = *src++;
297 		*dst++ = *src++;
298 		*dst++ = *src++;
299 		*dst++ = *src++;
300 		*dst++ = *src++;
301 		*dst++ = *src++;
302 		*dst++ = *src++;
303 	}
304 }
305 
306 
307 static int
308 nm_is_id_char(const char c)
309 {
310 	return (c >= 'a' && c <= 'z') ||
311 	       (c >= 'A' && c <= 'Z') ||
312 	       (c >= '0' && c <= '9') ||
313 	       (c == '_');
314 }
315 
316 /* Validate the name of a VALE bridge port and return the
317  * position of the ":" character. */
318 static int
319 nm_vale_name_validate(const char *name)
320 {
321 	int colon_pos = -1;
322 	int i;
323 
324 	if (!name || strlen(name) < strlen(NM_BDG_NAME)) {
325 		return -1;
326 	}
327 
328 	for (i = 0; i < NM_BDG_IFNAMSIZ && name[i]; i++) {
329 		if (name[i] == ':') {
330 			colon_pos = i;
331 			break;
332 		} else if (!nm_is_id_char(name[i])) {
333 			return -1;
334 		}
335 	}
336 
337 	if (strlen(name) - colon_pos > IFNAMSIZ) {
338 		/* interface name too long */
339 		return -1;
340 	}
341 
342 	return colon_pos;
343 }
344 
345 /*
346  * locate a bridge among the existing ones.
347  * MUST BE CALLED WITH NMG_LOCK()
348  *
349  * a ':' in the name terminates the bridge name. Otherwise, just NM_NAME.
350  * We assume that this is called with a name of at least NM_NAME chars.
351  */
352 static struct nm_bridge *
353 nm_find_bridge(const char *name, int create)
354 {
355 	int i, namelen;
356 	struct nm_bridge *b = NULL, *bridges;
357 	u_int num_bridges;
358 
359 	NMG_LOCK_ASSERT();
360 
361 	netmap_bns_getbridges(&bridges, &num_bridges);
362 
363 	namelen = nm_vale_name_validate(name);
364 	if (namelen < 0) {
365 		D("invalid bridge name %s", name ? name : NULL);
366 		return NULL;
367 	}
368 
369 	/* lookup the name, remember empty slot if there is one */
370 	for (i = 0; i < num_bridges; i++) {
371 		struct nm_bridge *x = bridges + i;
372 
373 		if ((x->bdg_flags & NM_BDG_ACTIVE) + x->bdg_active_ports == 0) {
374 			if (create && b == NULL)
375 				b = x;	/* record empty slot */
376 		} else if (x->bdg_namelen != namelen) {
377 			continue;
378 		} else if (strncmp(name, x->bdg_basename, namelen) == 0) {
379 			ND("found '%.*s' at %d", namelen, name, i);
380 			b = x;
381 			break;
382 		}
383 	}
384 	if (i == num_bridges && b) { /* name not found, can create entry */
385 		/* initialize the bridge */
386 		ND("create new bridge %s with ports %d", b->bdg_basename,
387 			b->bdg_active_ports);
388 		b->ht = nm_os_malloc(sizeof(struct nm_hash_ent) * NM_BDG_HASH);
389 		if (b->ht == NULL) {
390 			D("failed to allocate hash table");
391 			return NULL;
392 		}
393 		strncpy(b->bdg_basename, name, namelen);
394 		b->bdg_namelen = namelen;
395 		b->bdg_active_ports = 0;
396 		for (i = 0; i < NM_BDG_MAXPORTS; i++)
397 			b->bdg_port_index[i] = i;
398 		/* set the default function */
399 		b->bdg_ops = &default_bdg_ops;
400 		b->private_data = b->ht;
401 		b->bdg_flags = 0;
402 		NM_BNS_GET(b);
403 	}
404 	return b;
405 }
406 
407 
408 /*
409  * Free the forwarding tables for rings attached to switch ports.
410  */
411 static void
412 nm_free_bdgfwd(struct netmap_adapter *na)
413 {
414 	int nrings, i;
415 	struct netmap_kring **kring;
416 
417 	NMG_LOCK_ASSERT();
418 	nrings = na->num_tx_rings;
419 	kring = na->tx_rings;
420 	for (i = 0; i < nrings; i++) {
421 		if (kring[i]->nkr_ft) {
422 			nm_os_free(kring[i]->nkr_ft);
423 			kring[i]->nkr_ft = NULL; /* protect from freeing twice */
424 		}
425 	}
426 }
427 
428 
429 /*
430  * Allocate the forwarding tables for the rings attached to the bridge ports.
431  */
432 static int
433 nm_alloc_bdgfwd(struct netmap_adapter *na)
434 {
435 	int nrings, l, i, num_dstq;
436 	struct netmap_kring **kring;
437 
438 	NMG_LOCK_ASSERT();
439 	/* all port:rings + broadcast */
440 	num_dstq = NM_BDG_MAXPORTS * NM_BDG_MAXRINGS + 1;
441 	l = sizeof(struct nm_bdg_fwd) * NM_BDG_BATCH_MAX;
442 	l += sizeof(struct nm_bdg_q) * num_dstq;
443 	l += sizeof(uint16_t) * NM_BDG_BATCH_MAX;
444 
445 	nrings = netmap_real_rings(na, NR_TX);
446 	kring = na->tx_rings;
447 	for (i = 0; i < nrings; i++) {
448 		struct nm_bdg_fwd *ft;
449 		struct nm_bdg_q *dstq;
450 		int j;
451 
452 		ft = nm_os_malloc(l);
453 		if (!ft) {
454 			nm_free_bdgfwd(na);
455 			return ENOMEM;
456 		}
457 		dstq = (struct nm_bdg_q *)(ft + NM_BDG_BATCH_MAX);
458 		for (j = 0; j < num_dstq; j++) {
459 			dstq[j].bq_head = dstq[j].bq_tail = NM_FT_NULL;
460 			dstq[j].bq_len = 0;
461 		}
462 		kring[i]->nkr_ft = ft;
463 	}
464 	return 0;
465 }
466 
467 static int
468 netmap_bdg_free(struct nm_bridge *b)
469 {
470 	if ((b->bdg_flags & NM_BDG_ACTIVE) + b->bdg_active_ports != 0) {
471 		return EBUSY;
472 	}
473 
474 	ND("marking bridge %s as free", b->bdg_basename);
475 	nm_os_free(b->ht);
476 	b->bdg_ops = NULL;
477 	b->bdg_flags = 0;
478 	NM_BNS_PUT(b);
479 	return 0;
480 }
481 
482 
483 /* remove from bridge b the ports in slots hw and sw
484  * (sw can be -1 if not needed)
485  */
486 static void
487 netmap_bdg_detach_common(struct nm_bridge *b, int hw, int sw)
488 {
489 	int s_hw = hw, s_sw = sw;
490 	int i, lim =b->bdg_active_ports;
491 	uint32_t *tmp = b->tmp_bdg_port_index;
492 
493 	/*
494 	New algorithm:
495 	make a copy of bdg_port_index;
496 	lookup NA(ifp)->bdg_port and SWNA(ifp)->bdg_port
497 	in the array of bdg_port_index, replacing them with
498 	entries from the bottom of the array;
499 	decrement bdg_active_ports;
500 	acquire BDG_WLOCK() and copy back the array.
501 	 */
502 
503 	if (netmap_verbose)
504 		D("detach %d and %d (lim %d)", hw, sw, lim);
505 	/* make a copy of the list of active ports, update it,
506 	 * and then copy back within BDG_WLOCK().
507 	 */
508 	memcpy(b->tmp_bdg_port_index, b->bdg_port_index, sizeof(b->tmp_bdg_port_index));
509 	for (i = 0; (hw >= 0 || sw >= 0) && i < lim; ) {
510 		if (hw >= 0 && tmp[i] == hw) {
511 			ND("detach hw %d at %d", hw, i);
512 			lim--; /* point to last active port */
513 			tmp[i] = tmp[lim]; /* swap with i */
514 			tmp[lim] = hw;	/* now this is inactive */
515 			hw = -1;
516 		} else if (sw >= 0 && tmp[i] == sw) {
517 			ND("detach sw %d at %d", sw, i);
518 			lim--;
519 			tmp[i] = tmp[lim];
520 			tmp[lim] = sw;
521 			sw = -1;
522 		} else {
523 			i++;
524 		}
525 	}
526 	if (hw >= 0 || sw >= 0) {
527 		D("XXX delete failed hw %d sw %d, should panic...", hw, sw);
528 	}
529 
530 	BDG_WLOCK(b);
531 	if (b->bdg_ops->dtor)
532 		b->bdg_ops->dtor(b->bdg_ports[s_hw]);
533 	b->bdg_ports[s_hw] = NULL;
534 	if (s_sw >= 0) {
535 		b->bdg_ports[s_sw] = NULL;
536 	}
537 	memcpy(b->bdg_port_index, b->tmp_bdg_port_index, sizeof(b->tmp_bdg_port_index));
538 	b->bdg_active_ports = lim;
539 	BDG_WUNLOCK(b);
540 
541 	ND("now %d active ports", lim);
542 	netmap_bdg_free(b);
543 }
544 
545 static inline void *
546 nm_bdg_get_auth_token(struct nm_bridge *b)
547 {
548 	return b->ht;
549 }
550 
551 /* bridge not in exclusive mode ==> always valid
552  * bridge in exclusive mode (created through netmap_bdg_create()) ==> check authentication token
553  */
554 static inline int
555 nm_bdg_valid_auth_token(struct nm_bridge *b, void *auth_token)
556 {
557 	return !(b->bdg_flags & NM_BDG_EXCLUSIVE) || b->ht == auth_token;
558 }
559 
560 /* Allows external modules to create bridges in exclusive mode,
561  * returns an authentication token that the external module will need
562  * to provide during nm_bdg_ctl_{attach, detach}(), netmap_bdg_regops(),
563  * and nm_bdg_update_private_data() operations.
564  * Successfully executed if ret != NULL and *return_status == 0.
565  */
566 void *
567 netmap_bdg_create(const char *bdg_name, int *return_status)
568 {
569 	struct nm_bridge *b = NULL;
570 	void *ret = NULL;
571 
572 	NMG_LOCK();
573 	b = nm_find_bridge(bdg_name, 0 /* don't create */);
574 	if (b) {
575 		*return_status = EEXIST;
576 		goto unlock_bdg_create;
577 	}
578 
579 	b = nm_find_bridge(bdg_name, 1 /* create */);
580 	if (!b) {
581 		*return_status = ENOMEM;
582 		goto unlock_bdg_create;
583 	}
584 
585 	b->bdg_flags |= NM_BDG_ACTIVE | NM_BDG_EXCLUSIVE;
586 	ret = nm_bdg_get_auth_token(b);
587 	*return_status = 0;
588 
589 unlock_bdg_create:
590 	NMG_UNLOCK();
591 	return ret;
592 }
593 
594 /* Allows external modules to destroy a bridge created through
595  * netmap_bdg_create(), the bridge must be empty.
596  */
597 int
598 netmap_bdg_destroy(const char *bdg_name, void *auth_token)
599 {
600 	struct nm_bridge *b = NULL;
601 	int ret = 0;
602 
603 	NMG_LOCK();
604 	b = nm_find_bridge(bdg_name, 0 /* don't create */);
605 	if (!b) {
606 		ret = ENXIO;
607 		goto unlock_bdg_free;
608 	}
609 
610 	if (!nm_bdg_valid_auth_token(b, auth_token)) {
611 		ret = EACCES;
612 		goto unlock_bdg_free;
613 	}
614 	if (!(b->bdg_flags & NM_BDG_EXCLUSIVE)) {
615 		ret = EINVAL;
616 		goto unlock_bdg_free;
617 	}
618 
619 	b->bdg_flags &= ~(NM_BDG_EXCLUSIVE | NM_BDG_ACTIVE);
620 	ret = netmap_bdg_free(b);
621 	if (ret) {
622 		b->bdg_flags |= NM_BDG_EXCLUSIVE | NM_BDG_ACTIVE;
623 	}
624 
625 unlock_bdg_free:
626 	NMG_UNLOCK();
627 	return ret;
628 }
629 
630 
631 
632 /* nm_bdg_ctl callback for VALE ports */
633 static int
634 netmap_vp_bdg_ctl(struct nmreq_header *hdr, struct netmap_adapter *na)
635 {
636 	struct netmap_vp_adapter *vpna = (struct netmap_vp_adapter *)na;
637 	struct nm_bridge *b = vpna->na_bdg;
638 
639 	if (hdr->nr_reqtype == NETMAP_REQ_VALE_ATTACH) {
640 		return 0; /* nothing to do */
641 	}
642 	if (b) {
643 		netmap_set_all_rings(na, 0 /* disable */);
644 		netmap_bdg_detach_common(b, vpna->bdg_port, -1);
645 		vpna->na_bdg = NULL;
646 		netmap_set_all_rings(na, 1 /* enable */);
647 	}
648 	/* I have took reference just for attach */
649 	netmap_adapter_put(na);
650 	return 0;
651 }
652 
653 /* nm_dtor callback for ephemeral VALE ports */
654 static void
655 netmap_vp_dtor(struct netmap_adapter *na)
656 {
657 	struct netmap_vp_adapter *vpna = (struct netmap_vp_adapter*)na;
658 	struct nm_bridge *b = vpna->na_bdg;
659 
660 	ND("%s has %d references", na->name, na->na_refcount);
661 
662 	if (b) {
663 		netmap_bdg_detach_common(b, vpna->bdg_port, -1);
664 	}
665 
666 	if (na->ifp != NULL && !nm_iszombie(na)) {
667 		WNA(na->ifp) = NULL;
668 		if (vpna->autodelete) {
669 			ND("releasing %s", na->ifp->if_xname);
670 			NMG_UNLOCK();
671 			nm_os_vi_detach(na->ifp);
672 			NMG_LOCK();
673 		}
674 	}
675 }
676 
677 /* creates a persistent VALE port */
678 int
679 nm_vi_create(struct nmreq_header *hdr)
680 {
681 	struct nmreq_vale_newif *req =
682 		(struct nmreq_vale_newif *)(uintptr_t)hdr->nr_body;
683 	int error = 0;
684 	/* Build a nmreq_register out of the nmreq_vale_newif,
685 	 * so that we can call netmap_get_bdg_na(). */
686 	struct nmreq_register regreq;
687 	bzero(&regreq, sizeof(regreq));
688 	regreq.nr_tx_slots = req->nr_tx_slots;
689 	regreq.nr_rx_slots = req->nr_rx_slots;
690 	regreq.nr_tx_rings = req->nr_tx_rings;
691 	regreq.nr_rx_rings = req->nr_rx_rings;
692 	regreq.nr_mem_id = req->nr_mem_id;
693 	hdr->nr_reqtype = NETMAP_REQ_REGISTER;
694 	hdr->nr_body = (uintptr_t)&regreq;
695 	error = netmap_vi_create(hdr, 0 /* no autodelete */);
696 	hdr->nr_reqtype = NETMAP_REQ_VALE_NEWIF;
697 	hdr->nr_body = (uintptr_t)req;
698 	/* Write back to the original struct. */
699 	req->nr_tx_slots = regreq.nr_tx_slots;
700 	req->nr_rx_slots = regreq.nr_rx_slots;
701 	req->nr_tx_rings = regreq.nr_tx_rings;
702 	req->nr_rx_rings = regreq.nr_rx_rings;
703 	req->nr_mem_id = regreq.nr_mem_id;
704 	return error;
705 }
706 
707 /* remove a persistent VALE port from the system */
708 int
709 nm_vi_destroy(const char *name)
710 {
711 	struct ifnet *ifp;
712 	struct netmap_vp_adapter *vpna;
713 	int error;
714 
715 	ifp = ifunit_ref(name);
716 	if (!ifp)
717 		return ENXIO;
718 	NMG_LOCK();
719 	/* make sure this is actually a VALE port */
720 	if (!NM_NA_VALID(ifp) || NA(ifp)->nm_register != netmap_vp_reg) {
721 		error = EINVAL;
722 		goto err;
723 	}
724 
725 	vpna = (struct netmap_vp_adapter *)NA(ifp);
726 
727 	/* we can only destroy ports that were created via NETMAP_BDG_NEWIF */
728 	if (vpna->autodelete) {
729 		error = EINVAL;
730 		goto err;
731 	}
732 
733 	/* also make sure that nobody is using the inferface */
734 	if (NETMAP_OWNED_BY_ANY(&vpna->up) ||
735 	    vpna->up.na_refcount > 1 /* any ref besides the one in nm_vi_create()? */) {
736 		error = EBUSY;
737 		goto err;
738 	}
739 
740 	NMG_UNLOCK();
741 
742 	D("destroying a persistent vale interface %s", ifp->if_xname);
743 	/* Linux requires all the references are released
744 	 * before unregister
745 	 */
746 	netmap_detach(ifp);
747 	if_rele(ifp);
748 	nm_os_vi_detach(ifp);
749 	return 0;
750 
751 err:
752 	NMG_UNLOCK();
753 	if_rele(ifp);
754 	return error;
755 }
756 
757 static int
758 nm_update_info(struct nmreq_register *req, struct netmap_adapter *na)
759 {
760 	req->nr_rx_rings = na->num_rx_rings;
761 	req->nr_tx_rings = na->num_tx_rings;
762 	req->nr_rx_slots = na->num_rx_desc;
763 	req->nr_tx_slots = na->num_tx_desc;
764 	return netmap_mem_get_info(na->nm_mem, &req->nr_memsize, NULL,
765 					&req->nr_mem_id);
766 }
767 
768 /*
769  * Create a virtual interface registered to the system.
770  * The interface will be attached to a bridge later.
771  */
772 int
773 netmap_vi_create(struct nmreq_header *hdr, int autodelete)
774 {
775 	struct nmreq_register *req = (struct nmreq_register *)(uintptr_t)hdr->nr_body;
776 	struct ifnet *ifp;
777 	struct netmap_vp_adapter *vpna;
778 	struct netmap_mem_d *nmd = NULL;
779 	int error;
780 
781 	if (hdr->nr_reqtype != NETMAP_REQ_REGISTER) {
782 		return EINVAL;
783 	}
784 
785 	/* don't include VALE prefix */
786 	if (!strncmp(hdr->nr_name, NM_BDG_NAME, strlen(NM_BDG_NAME)))
787 		return EINVAL;
788 	if (strlen(hdr->nr_name) >= IFNAMSIZ) {
789 		return EINVAL;
790 	}
791 	ifp = ifunit_ref(hdr->nr_name);
792 	if (ifp) { /* already exist, cannot create new one */
793 		error = EEXIST;
794 		NMG_LOCK();
795 		if (NM_NA_VALID(ifp)) {
796 			int update_err = nm_update_info(req, NA(ifp));
797 			if (update_err)
798 				error = update_err;
799 		}
800 		NMG_UNLOCK();
801 		if_rele(ifp);
802 		return error;
803 	}
804 	error = nm_os_vi_persist(hdr->nr_name, &ifp);
805 	if (error)
806 		return error;
807 
808 	NMG_LOCK();
809 	if (req->nr_mem_id) {
810 		nmd = netmap_mem_find(req->nr_mem_id);
811 		if (nmd == NULL) {
812 			error = EINVAL;
813 			goto err_1;
814 		}
815 	}
816 	/* netmap_vp_create creates a struct netmap_vp_adapter */
817 	error = netmap_vp_create(hdr, ifp, nmd, &vpna);
818 	if (error) {
819 		D("error %d", error);
820 		goto err_1;
821 	}
822 	/* persist-specific routines */
823 	vpna->up.nm_bdg_ctl = netmap_vp_bdg_ctl;
824 	if (!autodelete) {
825 		netmap_adapter_get(&vpna->up);
826 	} else {
827 		vpna->autodelete = 1;
828 	}
829 	NM_ATTACH_NA(ifp, &vpna->up);
830 	/* return the updated info */
831 	error = nm_update_info(req, &vpna->up);
832 	if (error) {
833 		goto err_2;
834 	}
835 	ND("returning nr_mem_id %d", req->nr_mem_id);
836 	if (nmd)
837 		netmap_mem_put(nmd);
838 	NMG_UNLOCK();
839 	ND("created %s", ifp->if_xname);
840 	return 0;
841 
842 err_2:
843 	netmap_detach(ifp);
844 err_1:
845 	if (nmd)
846 		netmap_mem_put(nmd);
847 	NMG_UNLOCK();
848 	nm_os_vi_detach(ifp);
849 
850 	return error;
851 }
852 
853 /* Try to get a reference to a netmap adapter attached to a VALE switch.
854  * If the adapter is found (or is created), this function returns 0, a
855  * non NULL pointer is returned into *na, and the caller holds a
856  * reference to the adapter.
857  * If an adapter is not found, then no reference is grabbed and the
858  * function returns an error code, or 0 if there is just a VALE prefix
859  * mismatch. Therefore the caller holds a reference when
860  * (*na != NULL && return == 0).
861  */
862 int
863 netmap_get_bdg_na(struct nmreq_header *hdr, struct netmap_adapter **na,
864 		struct netmap_mem_d *nmd, int create)
865 {
866 	char *nr_name = hdr->nr_name;
867 	const char *ifname;
868 	struct ifnet *ifp = NULL;
869 	int error = 0;
870 	struct netmap_vp_adapter *vpna, *hostna = NULL;
871 	struct nm_bridge *b;
872 	uint32_t i, j;
873 	uint32_t cand = NM_BDG_NOPORT, cand2 = NM_BDG_NOPORT;
874 	int needed;
875 
876 	*na = NULL;     /* default return value */
877 
878 	/* first try to see if this is a bridge port. */
879 	NMG_LOCK_ASSERT();
880 	if (strncmp(nr_name, NM_BDG_NAME, sizeof(NM_BDG_NAME) - 1)) {
881 		return 0;  /* no error, but no VALE prefix */
882 	}
883 
884 	b = nm_find_bridge(nr_name, create);
885 	if (b == NULL) {
886 		ND("no bridges available for '%s'", nr_name);
887 		return (create ? ENOMEM : ENXIO);
888 	}
889 	if (strlen(nr_name) < b->bdg_namelen) /* impossible */
890 		panic("x");
891 
892 	/* Now we are sure that name starts with the bridge's name,
893 	 * lookup the port in the bridge. We need to scan the entire
894 	 * list. It is not important to hold a WLOCK on the bridge
895 	 * during the search because NMG_LOCK already guarantees
896 	 * that there are no other possible writers.
897 	 */
898 
899 	/* lookup in the local list of ports */
900 	for (j = 0; j < b->bdg_active_ports; j++) {
901 		i = b->bdg_port_index[j];
902 		vpna = b->bdg_ports[i];
903 		ND("checking %s", vpna->up.name);
904 		if (!strcmp(vpna->up.name, nr_name)) {
905 			netmap_adapter_get(&vpna->up);
906 			ND("found existing if %s refs %d", nr_name)
907 			*na = &vpna->up;
908 			return 0;
909 		}
910 	}
911 	/* not found, should we create it? */
912 	if (!create)
913 		return ENXIO;
914 	/* yes we should, see if we have space to attach entries */
915 	needed = 2; /* in some cases we only need 1 */
916 	if (b->bdg_active_ports + needed >= NM_BDG_MAXPORTS) {
917 		D("bridge full %d, cannot create new port", b->bdg_active_ports);
918 		return ENOMEM;
919 	}
920 	/* record the next two ports available, but do not allocate yet */
921 	cand = b->bdg_port_index[b->bdg_active_ports];
922 	cand2 = b->bdg_port_index[b->bdg_active_ports + 1];
923 	ND("+++ bridge %s port %s used %d avail %d %d",
924 		b->bdg_basename, ifname, b->bdg_active_ports, cand, cand2);
925 
926 	/*
927 	 * try see if there is a matching NIC with this name
928 	 * (after the bridge's name)
929 	 */
930 	ifname = nr_name + b->bdg_namelen + 1;
931 	ifp = ifunit_ref(ifname);
932 	if (!ifp) {
933 		/* Create an ephemeral virtual port.
934 		 * This block contains all the ephemeral-specific logic.
935 		 */
936 
937 		if (hdr->nr_reqtype != NETMAP_REQ_REGISTER) {
938 			error = EINVAL;
939 			goto out;
940 		}
941 
942 		/* bdg_netmap_attach creates a struct netmap_adapter */
943 		error = netmap_vp_create(hdr, NULL, nmd, &vpna);
944 		if (error) {
945 			D("error %d", error);
946 			goto out;
947 		}
948 		/* shortcut - we can skip get_hw_na(),
949 		 * ownership check and nm_bdg_attach()
950 		 */
951 
952 	} else {
953 		struct netmap_adapter *hw;
954 
955 		/* the vale:nic syntax is only valid for some commands */
956 		switch (hdr->nr_reqtype) {
957 		case NETMAP_REQ_VALE_ATTACH:
958 		case NETMAP_REQ_VALE_DETACH:
959 		case NETMAP_REQ_VALE_POLLING_ENABLE:
960 		case NETMAP_REQ_VALE_POLLING_DISABLE:
961 			break; /* ok */
962 		default:
963 			error = EINVAL;
964 			goto out;
965 		}
966 
967 		error = netmap_get_hw_na(ifp, nmd, &hw);
968 		if (error || hw == NULL)
969 			goto out;
970 
971 		/* host adapter might not be created */
972 		error = hw->nm_bdg_attach(nr_name, hw);
973 		if (error)
974 			goto out;
975 		vpna = hw->na_vp;
976 		hostna = hw->na_hostvp;
977 		if (hdr->nr_reqtype == NETMAP_REQ_VALE_ATTACH) {
978 			/* Check if we need to skip the host rings. */
979 			struct nmreq_vale_attach *areq =
980 				(struct nmreq_vale_attach *)(uintptr_t)hdr->nr_body;
981 			if (areq->reg.nr_mode != NR_REG_NIC_SW) {
982 				hostna = NULL;
983 			}
984 		}
985 	}
986 
987 	BDG_WLOCK(b);
988 	vpna->bdg_port = cand;
989 	ND("NIC  %p to bridge port %d", vpna, cand);
990 	/* bind the port to the bridge (virtual ports are not active) */
991 	b->bdg_ports[cand] = vpna;
992 	vpna->na_bdg = b;
993 	b->bdg_active_ports++;
994 	if (hostna != NULL) {
995 		/* also bind the host stack to the bridge */
996 		b->bdg_ports[cand2] = hostna;
997 		hostna->bdg_port = cand2;
998 		hostna->na_bdg = b;
999 		b->bdg_active_ports++;
1000 		ND("host %p to bridge port %d", hostna, cand2);
1001 	}
1002 	ND("if %s refs %d", ifname, vpna->up.na_refcount);
1003 	BDG_WUNLOCK(b);
1004 	*na = &vpna->up;
1005 	netmap_adapter_get(*na);
1006 
1007 out:
1008 	if (ifp)
1009 		if_rele(ifp);
1010 
1011 	return error;
1012 }
1013 
1014 /* Process NETMAP_REQ_VALE_ATTACH.
1015  */
1016 int
1017 nm_bdg_ctl_attach(struct nmreq_header *hdr, void *auth_token)
1018 {
1019 	struct nmreq_vale_attach *req =
1020 		(struct nmreq_vale_attach *)(uintptr_t)hdr->nr_body;
1021 	struct netmap_vp_adapter * vpna;
1022 	struct netmap_adapter *na;
1023 	struct netmap_mem_d *nmd = NULL;
1024 	struct nm_bridge *b = NULL;
1025 	int error;
1026 
1027 	NMG_LOCK();
1028 	/* permission check for modified bridges */
1029 	b = nm_find_bridge(hdr->nr_name, 0 /* don't create */);
1030 	if (b && !nm_bdg_valid_auth_token(b, auth_token)) {
1031 		error = EACCES;
1032 		goto unlock_exit;
1033 	}
1034 
1035 	if (req->reg.nr_mem_id) {
1036 		nmd = netmap_mem_find(req->reg.nr_mem_id);
1037 		if (nmd == NULL) {
1038 			error = EINVAL;
1039 			goto unlock_exit;
1040 		}
1041 	}
1042 
1043 	/* check for existing one */
1044 	error = netmap_get_bdg_na(hdr, &na, nmd, 0);
1045 	if (!error) {
1046 		error = EBUSY;
1047 		goto unref_exit;
1048 	}
1049 	error = netmap_get_bdg_na(hdr, &na,
1050 				nmd, 1 /* create if not exists */);
1051 	if (error) { /* no device */
1052 		goto unlock_exit;
1053 	}
1054 
1055 	if (na == NULL) { /* VALE prefix missing */
1056 		error = EINVAL;
1057 		goto unlock_exit;
1058 	}
1059 
1060 	if (NETMAP_OWNED_BY_ANY(na)) {
1061 		error = EBUSY;
1062 		goto unref_exit;
1063 	}
1064 
1065 	if (na->nm_bdg_ctl) {
1066 		/* nop for VALE ports. The bwrap needs to put the hwna
1067 		 * in netmap mode (see netmap_bwrap_bdg_ctl)
1068 		 */
1069 		error = na->nm_bdg_ctl(hdr, na);
1070 		if (error)
1071 			goto unref_exit;
1072 		ND("registered %s to netmap-mode", na->name);
1073 	}
1074 	vpna = (struct netmap_vp_adapter *)na;
1075 	req->port_index = vpna->bdg_port;
1076 	NMG_UNLOCK();
1077 	return 0;
1078 
1079 unref_exit:
1080 	netmap_adapter_put(na);
1081 unlock_exit:
1082 	NMG_UNLOCK();
1083 	return error;
1084 }
1085 
1086 static inline int
1087 nm_is_bwrap(struct netmap_adapter *na)
1088 {
1089 	return na->nm_register == netmap_bwrap_reg;
1090 }
1091 
1092 /* Process NETMAP_REQ_VALE_DETACH.
1093  */
1094 int
1095 nm_bdg_ctl_detach(struct nmreq_header *hdr, void *auth_token)
1096 {
1097 	struct nmreq_vale_detach *nmreq_det = (void *)(uintptr_t)hdr->nr_body;
1098 	struct netmap_vp_adapter *vpna;
1099 	struct netmap_adapter *na;
1100 	struct nm_bridge *b = NULL;
1101 	int error;
1102 
1103 	NMG_LOCK();
1104 	/* permission check for modified bridges */
1105 	b = nm_find_bridge(hdr->nr_name, 0 /* don't create */);
1106 	if (b && !nm_bdg_valid_auth_token(b, auth_token)) {
1107 		error = EACCES;
1108 		goto unlock_exit;
1109 	}
1110 
1111 	error = netmap_get_bdg_na(hdr, &na, NULL, 0 /* don't create */);
1112 	if (error) { /* no device, or another bridge or user owns the device */
1113 		goto unlock_exit;
1114 	}
1115 
1116 	if (na == NULL) { /* VALE prefix missing */
1117 		error = EINVAL;
1118 		goto unlock_exit;
1119 	} else if (nm_is_bwrap(na) &&
1120 		   ((struct netmap_bwrap_adapter *)na)->na_polling_state) {
1121 		/* Don't detach a NIC with polling */
1122 		error = EBUSY;
1123 		goto unref_exit;
1124 	}
1125 
1126 	vpna = (struct netmap_vp_adapter *)na;
1127 	if (na->na_vp != vpna) {
1128 		/* trying to detach first attach of VALE persistent port attached
1129 		 * to 2 bridges
1130 		 */
1131 		error = EBUSY;
1132 		goto unref_exit;
1133 	}
1134 	nmreq_det->port_index = vpna->bdg_port;
1135 
1136 	if (na->nm_bdg_ctl) {
1137 		/* remove the port from bridge. The bwrap
1138 		 * also needs to put the hwna in normal mode
1139 		 */
1140 		error = na->nm_bdg_ctl(hdr, na);
1141 	}
1142 
1143 unref_exit:
1144 	netmap_adapter_put(na);
1145 unlock_exit:
1146 	NMG_UNLOCK();
1147 	return error;
1148 
1149 }
1150 
1151 struct nm_bdg_polling_state;
1152 struct
1153 nm_bdg_kthread {
1154 	struct nm_kctx *nmk;
1155 	u_int qfirst;
1156 	u_int qlast;
1157 	struct nm_bdg_polling_state *bps;
1158 };
1159 
1160 struct nm_bdg_polling_state {
1161 	bool configured;
1162 	bool stopped;
1163 	struct netmap_bwrap_adapter *bna;
1164 	uint32_t mode;
1165 	u_int qfirst;
1166 	u_int qlast;
1167 	u_int cpu_from;
1168 	u_int ncpus;
1169 	struct nm_bdg_kthread *kthreads;
1170 };
1171 
1172 static void
1173 netmap_bwrap_polling(void *data, int is_kthread)
1174 {
1175 	struct nm_bdg_kthread *nbk = data;
1176 	struct netmap_bwrap_adapter *bna;
1177 	u_int qfirst, qlast, i;
1178 	struct netmap_kring **kring0, *kring;
1179 
1180 	if (!nbk)
1181 		return;
1182 	qfirst = nbk->qfirst;
1183 	qlast = nbk->qlast;
1184 	bna = nbk->bps->bna;
1185 	kring0 = NMR(bna->hwna, NR_RX);
1186 
1187 	for (i = qfirst; i < qlast; i++) {
1188 		kring = kring0[i];
1189 		kring->nm_notify(kring, 0);
1190 	}
1191 }
1192 
1193 static int
1194 nm_bdg_create_kthreads(struct nm_bdg_polling_state *bps)
1195 {
1196 	struct nm_kctx_cfg kcfg;
1197 	int i, j;
1198 
1199 	bps->kthreads = nm_os_malloc(sizeof(struct nm_bdg_kthread) * bps->ncpus);
1200 	if (bps->kthreads == NULL)
1201 		return ENOMEM;
1202 
1203 	bzero(&kcfg, sizeof(kcfg));
1204 	kcfg.worker_fn = netmap_bwrap_polling;
1205 	kcfg.use_kthread = 1;
1206 	for (i = 0; i < bps->ncpus; i++) {
1207 		struct nm_bdg_kthread *t = bps->kthreads + i;
1208 		int all = (bps->ncpus == 1 &&
1209 			bps->mode == NETMAP_POLLING_MODE_SINGLE_CPU);
1210 		int affinity = bps->cpu_from + i;
1211 
1212 		t->bps = bps;
1213 		t->qfirst = all ? bps->qfirst /* must be 0 */: affinity;
1214 		t->qlast = all ? bps->qlast : t->qfirst + 1;
1215 		D("kthread %d a:%u qf:%u ql:%u", i, affinity, t->qfirst,
1216 			t->qlast);
1217 
1218 		kcfg.type = i;
1219 		kcfg.worker_private = t;
1220 		t->nmk = nm_os_kctx_create(&kcfg, NULL);
1221 		if (t->nmk == NULL) {
1222 			goto cleanup;
1223 		}
1224 		nm_os_kctx_worker_setaff(t->nmk, affinity);
1225 	}
1226 	return 0;
1227 
1228 cleanup:
1229 	for (j = 0; j < i; j++) {
1230 		struct nm_bdg_kthread *t = bps->kthreads + i;
1231 		nm_os_kctx_destroy(t->nmk);
1232 	}
1233 	nm_os_free(bps->kthreads);
1234 	return EFAULT;
1235 }
1236 
1237 /* A variant of ptnetmap_start_kthreads() */
1238 static int
1239 nm_bdg_polling_start_kthreads(struct nm_bdg_polling_state *bps)
1240 {
1241 	int error, i, j;
1242 
1243 	if (!bps) {
1244 		D("polling is not configured");
1245 		return EFAULT;
1246 	}
1247 	bps->stopped = false;
1248 
1249 	for (i = 0; i < bps->ncpus; i++) {
1250 		struct nm_bdg_kthread *t = bps->kthreads + i;
1251 		error = nm_os_kctx_worker_start(t->nmk);
1252 		if (error) {
1253 			D("error in nm_kthread_start()");
1254 			goto cleanup;
1255 		}
1256 	}
1257 	return 0;
1258 
1259 cleanup:
1260 	for (j = 0; j < i; j++) {
1261 		struct nm_bdg_kthread *t = bps->kthreads + i;
1262 		nm_os_kctx_worker_stop(t->nmk);
1263 	}
1264 	bps->stopped = true;
1265 	return error;
1266 }
1267 
1268 static void
1269 nm_bdg_polling_stop_delete_kthreads(struct nm_bdg_polling_state *bps)
1270 {
1271 	int i;
1272 
1273 	if (!bps)
1274 		return;
1275 
1276 	for (i = 0; i < bps->ncpus; i++) {
1277 		struct nm_bdg_kthread *t = bps->kthreads + i;
1278 		nm_os_kctx_worker_stop(t->nmk);
1279 		nm_os_kctx_destroy(t->nmk);
1280 	}
1281 	bps->stopped = true;
1282 }
1283 
1284 static int
1285 get_polling_cfg(struct nmreq_vale_polling *req, struct netmap_adapter *na,
1286 		struct nm_bdg_polling_state *bps)
1287 {
1288 	unsigned int avail_cpus, core_from;
1289 	unsigned int qfirst, qlast;
1290 	uint32_t i = req->nr_first_cpu_id;
1291 	uint32_t req_cpus = req->nr_num_polling_cpus;
1292 
1293 	avail_cpus = nm_os_ncpus();
1294 
1295 	if (req_cpus == 0) {
1296 		D("req_cpus must be > 0");
1297 		return EINVAL;
1298 	} else if (req_cpus >= avail_cpus) {
1299 		D("Cannot use all the CPUs in the system");
1300 		return EINVAL;
1301 	}
1302 
1303 	if (req->nr_mode == NETMAP_POLLING_MODE_MULTI_CPU) {
1304 		/* Use a separate core for each ring. If nr_num_polling_cpus>1
1305 		 * more consecutive rings are polled.
1306 		 * For example, if nr_first_cpu_id=2 and nr_num_polling_cpus=2,
1307 		 * ring 2 and 3 are polled by core 2 and 3, respectively. */
1308 		if (i + req_cpus > nma_get_nrings(na, NR_RX)) {
1309 			D("Rings %u-%u not in range (have %d rings)",
1310 				i, i + req_cpus, nma_get_nrings(na, NR_RX));
1311 			return EINVAL;
1312 		}
1313 		qfirst = i;
1314 		qlast = qfirst + req_cpus;
1315 		core_from = qfirst;
1316 
1317 	} else if (req->nr_mode == NETMAP_POLLING_MODE_SINGLE_CPU) {
1318 		/* Poll all the rings using a core specified by nr_first_cpu_id.
1319 		 * the number of cores must be 1. */
1320 		if (req_cpus != 1) {
1321 			D("ncpus must be 1 for NETMAP_POLLING_MODE_SINGLE_CPU "
1322 				"(was %d)", req_cpus);
1323 			return EINVAL;
1324 		}
1325 		qfirst = 0;
1326 		qlast = nma_get_nrings(na, NR_RX);
1327 		core_from = i;
1328 	} else {
1329 		D("Invalid polling mode");
1330 		return EINVAL;
1331 	}
1332 
1333 	bps->mode = req->nr_mode;
1334 	bps->qfirst = qfirst;
1335 	bps->qlast = qlast;
1336 	bps->cpu_from = core_from;
1337 	bps->ncpus = req_cpus;
1338 	D("%s qfirst %u qlast %u cpu_from %u ncpus %u",
1339 		req->nr_mode == NETMAP_POLLING_MODE_MULTI_CPU ?
1340 		"MULTI" : "SINGLE",
1341 		qfirst, qlast, core_from, req_cpus);
1342 	return 0;
1343 }
1344 
1345 static int
1346 nm_bdg_ctl_polling_start(struct nmreq_vale_polling *req, struct netmap_adapter *na)
1347 {
1348 	struct nm_bdg_polling_state *bps;
1349 	struct netmap_bwrap_adapter *bna;
1350 	int error;
1351 
1352 	bna = (struct netmap_bwrap_adapter *)na;
1353 	if (bna->na_polling_state) {
1354 		D("ERROR adapter already in polling mode");
1355 		return EFAULT;
1356 	}
1357 
1358 	bps = nm_os_malloc(sizeof(*bps));
1359 	if (!bps)
1360 		return ENOMEM;
1361 	bps->configured = false;
1362 	bps->stopped = true;
1363 
1364 	if (get_polling_cfg(req, na, bps)) {
1365 		nm_os_free(bps);
1366 		return EINVAL;
1367 	}
1368 
1369 	if (nm_bdg_create_kthreads(bps)) {
1370 		nm_os_free(bps);
1371 		return EFAULT;
1372 	}
1373 
1374 	bps->configured = true;
1375 	bna->na_polling_state = bps;
1376 	bps->bna = bna;
1377 
1378 	/* disable interrupts if possible */
1379 	nma_intr_enable(bna->hwna, 0);
1380 	/* start kthread now */
1381 	error = nm_bdg_polling_start_kthreads(bps);
1382 	if (error) {
1383 		D("ERROR nm_bdg_polling_start_kthread()");
1384 		nm_os_free(bps->kthreads);
1385 		nm_os_free(bps);
1386 		bna->na_polling_state = NULL;
1387 		nma_intr_enable(bna->hwna, 1);
1388 	}
1389 	return error;
1390 }
1391 
1392 static int
1393 nm_bdg_ctl_polling_stop(struct netmap_adapter *na)
1394 {
1395 	struct netmap_bwrap_adapter *bna = (struct netmap_bwrap_adapter *)na;
1396 	struct nm_bdg_polling_state *bps;
1397 
1398 	if (!bna->na_polling_state) {
1399 		D("ERROR adapter is not in polling mode");
1400 		return EFAULT;
1401 	}
1402 	bps = bna->na_polling_state;
1403 	nm_bdg_polling_stop_delete_kthreads(bna->na_polling_state);
1404 	bps->configured = false;
1405 	nm_os_free(bps);
1406 	bna->na_polling_state = NULL;
1407 	/* reenable interrupts */
1408 	nma_intr_enable(bna->hwna, 1);
1409 	return 0;
1410 }
1411 
1412 int
1413 nm_bdg_polling(struct nmreq_header *hdr)
1414 {
1415 	struct nmreq_vale_polling *req =
1416 		(struct nmreq_vale_polling *)(uintptr_t)hdr->nr_body;
1417 	struct netmap_adapter *na = NULL;
1418 	int error = 0;
1419 
1420 	NMG_LOCK();
1421 	error = netmap_get_bdg_na(hdr, &na, NULL, /*create=*/0);
1422 	if (na && !error) {
1423 		if (!nm_is_bwrap(na)) {
1424 			error = EOPNOTSUPP;
1425 		} else if (hdr->nr_reqtype == NETMAP_BDG_POLLING_ON) {
1426 			error = nm_bdg_ctl_polling_start(req, na);
1427 			if (!error)
1428 				netmap_adapter_get(na);
1429 		} else {
1430 			error = nm_bdg_ctl_polling_stop(na);
1431 			if (!error)
1432 				netmap_adapter_put(na);
1433 		}
1434 		netmap_adapter_put(na);
1435 	} else if (!na && !error) {
1436 		/* Not VALE port. */
1437 		error = EINVAL;
1438 	}
1439 	NMG_UNLOCK();
1440 
1441 	return error;
1442 }
1443 
1444 /* Process NETMAP_REQ_VALE_LIST. */
1445 int
1446 netmap_bdg_list(struct nmreq_header *hdr)
1447 {
1448 	struct nmreq_vale_list *req =
1449 		(struct nmreq_vale_list *)(uintptr_t)hdr->nr_body;
1450 	int namelen = strlen(hdr->nr_name);
1451 	struct nm_bridge *b, *bridges;
1452 	struct netmap_vp_adapter *vpna;
1453 	int error = 0, i, j;
1454 	u_int num_bridges;
1455 
1456 	netmap_bns_getbridges(&bridges, &num_bridges);
1457 
1458 	/* this is used to enumerate bridges and ports */
1459 	if (namelen) { /* look up indexes of bridge and port */
1460 		if (strncmp(hdr->nr_name, NM_BDG_NAME,
1461 					strlen(NM_BDG_NAME))) {
1462 			return EINVAL;
1463 		}
1464 		NMG_LOCK();
1465 		b = nm_find_bridge(hdr->nr_name, 0 /* don't create */);
1466 		if (!b) {
1467 			NMG_UNLOCK();
1468 			return ENOENT;
1469 		}
1470 
1471 		req->nr_bridge_idx = b - bridges; /* bridge index */
1472 		req->nr_port_idx = NM_BDG_NOPORT;
1473 		for (j = 0; j < b->bdg_active_ports; j++) {
1474 			i = b->bdg_port_index[j];
1475 			vpna = b->bdg_ports[i];
1476 			if (vpna == NULL) {
1477 				D("This should not happen");
1478 				continue;
1479 			}
1480 			/* the former and the latter identify a
1481 			 * virtual port and a NIC, respectively
1482 			 */
1483 			if (!strcmp(vpna->up.name, hdr->nr_name)) {
1484 				req->nr_port_idx = i; /* port index */
1485 				break;
1486 			}
1487 		}
1488 		NMG_UNLOCK();
1489 	} else {
1490 		/* return the first non-empty entry starting from
1491 		 * bridge nr_arg1 and port nr_arg2.
1492 		 *
1493 		 * Users can detect the end of the same bridge by
1494 		 * seeing the new and old value of nr_arg1, and can
1495 		 * detect the end of all the bridge by error != 0
1496 		 */
1497 		i = req->nr_bridge_idx;
1498 		j = req->nr_port_idx;
1499 
1500 		NMG_LOCK();
1501 		for (error = ENOENT; i < NM_BRIDGES; i++) {
1502 			b = bridges + i;
1503 			for ( ; j < NM_BDG_MAXPORTS; j++) {
1504 				if (b->bdg_ports[j] == NULL)
1505 					continue;
1506 				vpna = b->bdg_ports[j];
1507 				/* write back the VALE switch name */
1508 				strncpy(hdr->nr_name, vpna->up.name,
1509 					(size_t)IFNAMSIZ);
1510 				error = 0;
1511 				goto out;
1512 			}
1513 			j = 0; /* following bridges scan from 0 */
1514 		}
1515 	out:
1516 		req->nr_bridge_idx = i;
1517 		req->nr_port_idx = j;
1518 		NMG_UNLOCK();
1519 	}
1520 
1521 	return error;
1522 }
1523 
1524 /* Called by external kernel modules (e.g., Openvswitch).
1525  * to set configure/lookup/dtor functions of a VALE instance.
1526  * Register callbacks to the given bridge. 'name' may be just
1527  * bridge's name (including ':' if it is not just NM_BDG_NAME).
1528  *
1529  * Called without NMG_LOCK.
1530  */
1531 
1532 int
1533 netmap_bdg_regops(const char *name, struct netmap_bdg_ops *bdg_ops, void *private_data, void *auth_token)
1534 {
1535 	struct nm_bridge *b;
1536 	int error = 0;
1537 
1538 	NMG_LOCK();
1539 	b = nm_find_bridge(name, 0 /* don't create */);
1540 	if (!b) {
1541 		error = ENXIO;
1542 		goto unlock_regops;
1543 	}
1544 	if (!nm_bdg_valid_auth_token(b, auth_token)) {
1545 		error = EACCES;
1546 		goto unlock_regops;
1547 	}
1548 
1549 	BDG_WLOCK(b);
1550 	if (!bdg_ops) {
1551 		/* resetting the bridge */
1552 		bzero(b->ht, sizeof(struct nm_hash_ent) * NM_BDG_HASH);
1553 		b->bdg_ops = &default_bdg_ops;
1554 		b->private_data = b->ht;
1555 	} else {
1556 		/* modifying the bridge */
1557 		b->private_data = private_data;
1558 		b->bdg_ops = bdg_ops;
1559 	}
1560 	BDG_WUNLOCK(b);
1561 
1562 unlock_regops:
1563 	NMG_UNLOCK();
1564 	return error;
1565 }
1566 
1567 /* Called by external kernel modules (e.g., Openvswitch).
1568  * to modify the private data previously given to regops().
1569  * 'name' may be just bridge's name (including ':' if it
1570  * is not just NM_BDG_NAME).
1571  * Called without NMG_LOCK.
1572  */
1573 int
1574 nm_bdg_update_private_data(const char *name, bdg_update_private_data_fn_t callback,
1575 	void *callback_data, void *auth_token)
1576 {
1577 	void *private_data = NULL;
1578 	struct nm_bridge *b;
1579 	int error = 0;
1580 
1581 	NMG_LOCK();
1582 	b = nm_find_bridge(name, 0 /* don't create */);
1583 	if (!b) {
1584 		error = EINVAL;
1585 		goto unlock_update_priv;
1586 	}
1587 	if (!nm_bdg_valid_auth_token(b, auth_token)) {
1588 		error = EACCES;
1589 		goto unlock_update_priv;
1590 	}
1591 	BDG_WLOCK(b);
1592 	private_data = callback(b->private_data, callback_data, &error);
1593 	b->private_data = private_data;
1594 	BDG_WUNLOCK(b);
1595 
1596 unlock_update_priv:
1597 	NMG_UNLOCK();
1598 	return error;
1599 }
1600 
1601 int
1602 netmap_bdg_config(struct nm_ifreq *nr)
1603 {
1604 	struct nm_bridge *b;
1605 	int error = EINVAL;
1606 
1607 	NMG_LOCK();
1608 	b = nm_find_bridge(nr->nifr_name, 0);
1609 	if (!b) {
1610 		NMG_UNLOCK();
1611 		return error;
1612 	}
1613 	NMG_UNLOCK();
1614 	/* Don't call config() with NMG_LOCK() held */
1615 	BDG_RLOCK(b);
1616 	if (b->bdg_ops->config != NULL)
1617 		error = b->bdg_ops->config(nr);
1618 	BDG_RUNLOCK(b);
1619 	return error;
1620 }
1621 
1622 
1623 /* nm_krings_create callback for VALE ports.
1624  * Calls the standard netmap_krings_create, then adds leases on rx
1625  * rings and bdgfwd on tx rings.
1626  */
1627 static int
1628 netmap_vp_krings_create(struct netmap_adapter *na)
1629 {
1630 	u_int tailroom;
1631 	int error, i;
1632 	uint32_t *leases;
1633 	u_int nrx = netmap_real_rings(na, NR_RX);
1634 
1635 	/*
1636 	 * Leases are attached to RX rings on vale ports
1637 	 */
1638 	tailroom = sizeof(uint32_t) * na->num_rx_desc * nrx;
1639 
1640 	error = netmap_krings_create(na, tailroom);
1641 	if (error)
1642 		return error;
1643 
1644 	leases = na->tailroom;
1645 
1646 	for (i = 0; i < nrx; i++) { /* Receive rings */
1647 		na->rx_rings[i]->nkr_leases = leases;
1648 		leases += na->num_rx_desc;
1649 	}
1650 
1651 	error = nm_alloc_bdgfwd(na);
1652 	if (error) {
1653 		netmap_krings_delete(na);
1654 		return error;
1655 	}
1656 
1657 	return 0;
1658 }
1659 
1660 
1661 /* nm_krings_delete callback for VALE ports. */
1662 static void
1663 netmap_vp_krings_delete(struct netmap_adapter *na)
1664 {
1665 	nm_free_bdgfwd(na);
1666 	netmap_krings_delete(na);
1667 }
1668 
1669 
1670 static int
1671 nm_bdg_flush(struct nm_bdg_fwd *ft, u_int n,
1672 	struct netmap_vp_adapter *na, u_int ring_nr);
1673 
1674 
1675 /*
1676  * main dispatch routine for the bridge.
1677  * Grab packets from a kring, move them into the ft structure
1678  * associated to the tx (input) port. Max one instance per port,
1679  * filtered on input (ioctl, poll or XXX).
1680  * Returns the next position in the ring.
1681  */
1682 static int
1683 nm_bdg_preflush(struct netmap_kring *kring, u_int end)
1684 {
1685 	struct netmap_vp_adapter *na =
1686 		(struct netmap_vp_adapter*)kring->na;
1687 	struct netmap_ring *ring = kring->ring;
1688 	struct nm_bdg_fwd *ft;
1689 	u_int ring_nr = kring->ring_id;
1690 	u_int j = kring->nr_hwcur, lim = kring->nkr_num_slots - 1;
1691 	u_int ft_i = 0;	/* start from 0 */
1692 	u_int frags = 1; /* how many frags ? */
1693 	struct nm_bridge *b = na->na_bdg;
1694 
1695 	/* To protect against modifications to the bridge we acquire a
1696 	 * shared lock, waiting if we can sleep (if the source port is
1697 	 * attached to a user process) or with a trylock otherwise (NICs).
1698 	 */
1699 	ND("wait rlock for %d packets", ((j > end ? lim+1 : 0) + end) - j);
1700 	if (na->up.na_flags & NAF_BDG_MAYSLEEP)
1701 		BDG_RLOCK(b);
1702 	else if (!BDG_RTRYLOCK(b))
1703 		return j;
1704 	ND(5, "rlock acquired for %d packets", ((j > end ? lim+1 : 0) + end) - j);
1705 	ft = kring->nkr_ft;
1706 
1707 	for (; likely(j != end); j = nm_next(j, lim)) {
1708 		struct netmap_slot *slot = &ring->slot[j];
1709 		char *buf;
1710 
1711 		ft[ft_i].ft_len = slot->len;
1712 		ft[ft_i].ft_flags = slot->flags;
1713 		ft[ft_i].ft_offset = 0;
1714 
1715 		ND("flags is 0x%x", slot->flags);
1716 		/* we do not use the buf changed flag, but we still need to reset it */
1717 		slot->flags &= ~NS_BUF_CHANGED;
1718 
1719 		/* this slot goes into a list so initialize the link field */
1720 		ft[ft_i].ft_next = NM_FT_NULL;
1721 		buf = ft[ft_i].ft_buf = (slot->flags & NS_INDIRECT) ?
1722 			(void *)(uintptr_t)slot->ptr : NMB(&na->up, slot);
1723 		if (unlikely(buf == NULL)) {
1724 			RD(5, "NULL %s buffer pointer from %s slot %d len %d",
1725 				(slot->flags & NS_INDIRECT) ? "INDIRECT" : "DIRECT",
1726 				kring->name, j, ft[ft_i].ft_len);
1727 			buf = ft[ft_i].ft_buf = NETMAP_BUF_BASE(&na->up);
1728 			ft[ft_i].ft_len = 0;
1729 			ft[ft_i].ft_flags = 0;
1730 		}
1731 		__builtin_prefetch(buf);
1732 		++ft_i;
1733 		if (slot->flags & NS_MOREFRAG) {
1734 			frags++;
1735 			continue;
1736 		}
1737 		if (unlikely(netmap_verbose && frags > 1))
1738 			RD(5, "%d frags at %d", frags, ft_i - frags);
1739 		ft[ft_i - frags].ft_frags = frags;
1740 		frags = 1;
1741 		if (unlikely((int)ft_i >= bridge_batch))
1742 			ft_i = nm_bdg_flush(ft, ft_i, na, ring_nr);
1743 	}
1744 	if (frags > 1) {
1745 		/* Here ft_i > 0, ft[ft_i-1].flags has NS_MOREFRAG, and we
1746 		 * have to fix frags count. */
1747 		frags--;
1748 		ft[ft_i - 1].ft_flags &= ~NS_MOREFRAG;
1749 		ft[ft_i - frags].ft_frags = frags;
1750 		D("Truncate incomplete fragment at %d (%d frags)", ft_i, frags);
1751 	}
1752 	if (ft_i)
1753 		ft_i = nm_bdg_flush(ft, ft_i, na, ring_nr);
1754 	BDG_RUNLOCK(b);
1755 	return j;
1756 }
1757 
1758 
1759 /* ----- FreeBSD if_bridge hash function ------- */
1760 
1761 /*
1762  * The following hash function is adapted from "Hash Functions" by Bob Jenkins
1763  * ("Algorithm Alley", Dr. Dobbs Journal, September 1997).
1764  *
1765  * http://www.burtleburtle.net/bob/hash/spooky.html
1766  */
1767 #define mix(a, b, c)                                                    \
1768 do {                                                                    \
1769 	a -= b; a -= c; a ^= (c >> 13);                                 \
1770 	b -= c; b -= a; b ^= (a << 8);                                  \
1771 	c -= a; c -= b; c ^= (b >> 13);                                 \
1772 	a -= b; a -= c; a ^= (c >> 12);                                 \
1773 	b -= c; b -= a; b ^= (a << 16);                                 \
1774 	c -= a; c -= b; c ^= (b >> 5);                                  \
1775 	a -= b; a -= c; a ^= (c >> 3);                                  \
1776 	b -= c; b -= a; b ^= (a << 10);                                 \
1777 	c -= a; c -= b; c ^= (b >> 15);                                 \
1778 } while (/*CONSTCOND*/0)
1779 
1780 
1781 static __inline uint32_t
1782 nm_bridge_rthash(const uint8_t *addr)
1783 {
1784 	uint32_t a = 0x9e3779b9, b = 0x9e3779b9, c = 0; // hask key
1785 
1786 	b += addr[5] << 8;
1787 	b += addr[4];
1788 	a += addr[3] << 24;
1789 	a += addr[2] << 16;
1790 	a += addr[1] << 8;
1791 	a += addr[0];
1792 
1793 	mix(a, b, c);
1794 #define BRIDGE_RTHASH_MASK	(NM_BDG_HASH-1)
1795 	return (c & BRIDGE_RTHASH_MASK);
1796 }
1797 
1798 #undef mix
1799 
1800 
1801 /* nm_register callback for VALE ports */
1802 static int
1803 netmap_vp_reg(struct netmap_adapter *na, int onoff)
1804 {
1805 	struct netmap_vp_adapter *vpna =
1806 		(struct netmap_vp_adapter*)na;
1807 	enum txrx t;
1808 	int i;
1809 
1810 	/* persistent ports may be put in netmap mode
1811 	 * before being attached to a bridge
1812 	 */
1813 	if (vpna->na_bdg)
1814 		BDG_WLOCK(vpna->na_bdg);
1815 	if (onoff) {
1816 		for_rx_tx(t) {
1817 			for (i = 0; i < netmap_real_rings(na, t); i++) {
1818 				struct netmap_kring *kring = NMR(na, t)[i];
1819 
1820 				if (nm_kring_pending_on(kring))
1821 					kring->nr_mode = NKR_NETMAP_ON;
1822 			}
1823 		}
1824 		if (na->active_fds == 0)
1825 			na->na_flags |= NAF_NETMAP_ON;
1826 		 /* XXX on FreeBSD, persistent VALE ports should also
1827 		 * toggle IFCAP_NETMAP in na->ifp (2014-03-16)
1828 		 */
1829 	} else {
1830 		if (na->active_fds == 0)
1831 			na->na_flags &= ~NAF_NETMAP_ON;
1832 		for_rx_tx(t) {
1833 			for (i = 0; i < netmap_real_rings(na, t); i++) {
1834 				struct netmap_kring *kring = NMR(na, t)[i];
1835 
1836 				if (nm_kring_pending_off(kring))
1837 					kring->nr_mode = NKR_NETMAP_OFF;
1838 			}
1839 		}
1840 	}
1841 	if (vpna->na_bdg)
1842 		BDG_WUNLOCK(vpna->na_bdg);
1843 	return 0;
1844 }
1845 
1846 
1847 /*
1848  * Lookup function for a learning bridge.
1849  * Update the hash table with the source address,
1850  * and then returns the destination port index, and the
1851  * ring in *dst_ring (at the moment, always use ring 0)
1852  */
1853 uint32_t
1854 netmap_bdg_learning(struct nm_bdg_fwd *ft, uint8_t *dst_ring,
1855 		struct netmap_vp_adapter *na, void *private_data)
1856 {
1857 	uint8_t *buf = ((uint8_t *)ft->ft_buf) + ft->ft_offset;
1858 	u_int buf_len = ft->ft_len - ft->ft_offset;
1859 	struct nm_hash_ent *ht = private_data;
1860 	uint32_t sh, dh;
1861 	u_int dst, mysrc = na->bdg_port;
1862 	uint64_t smac, dmac;
1863 	uint8_t indbuf[12];
1864 
1865 	if (buf_len < 14) {
1866 		return NM_BDG_NOPORT;
1867 	}
1868 
1869 	if (ft->ft_flags & NS_INDIRECT) {
1870 		if (copyin(buf, indbuf, sizeof(indbuf))) {
1871 			return NM_BDG_NOPORT;
1872 		}
1873 		buf = indbuf;
1874 	}
1875 
1876 	dmac = le64toh(*(uint64_t *)(buf)) & 0xffffffffffff;
1877 	smac = le64toh(*(uint64_t *)(buf + 4));
1878 	smac >>= 16;
1879 
1880 	/*
1881 	 * The hash is somewhat expensive, there might be some
1882 	 * worthwhile optimizations here.
1883 	 */
1884 	if (((buf[6] & 1) == 0) && (na->last_smac != smac)) { /* valid src */
1885 		uint8_t *s = buf+6;
1886 		sh = nm_bridge_rthash(s); /* hash of source */
1887 		/* update source port forwarding entry */
1888 		na->last_smac = ht[sh].mac = smac;	/* XXX expire ? */
1889 		ht[sh].ports = mysrc;
1890 		if (netmap_verbose)
1891 		    D("src %02x:%02x:%02x:%02x:%02x:%02x on port %d",
1892 			s[0], s[1], s[2], s[3], s[4], s[5], mysrc);
1893 	}
1894 	dst = NM_BDG_BROADCAST;
1895 	if ((buf[0] & 1) == 0) { /* unicast */
1896 		dh = nm_bridge_rthash(buf); /* hash of dst */
1897 		if (ht[dh].mac == dmac) {	/* found dst */
1898 			dst = ht[dh].ports;
1899 		}
1900 	}
1901 	return dst;
1902 }
1903 
1904 
1905 /*
1906  * Available space in the ring. Only used in VALE code
1907  * and only with is_rx = 1
1908  */
1909 static inline uint32_t
1910 nm_kr_space(struct netmap_kring *k, int is_rx)
1911 {
1912 	int space;
1913 
1914 	if (is_rx) {
1915 		int busy = k->nkr_hwlease - k->nr_hwcur;
1916 		if (busy < 0)
1917 			busy += k->nkr_num_slots;
1918 		space = k->nkr_num_slots - 1 - busy;
1919 	} else {
1920 		/* XXX never used in this branch */
1921 		space = k->nr_hwtail - k->nkr_hwlease;
1922 		if (space < 0)
1923 			space += k->nkr_num_slots;
1924 	}
1925 #if 0
1926 	// sanity check
1927 	if (k->nkr_hwlease >= k->nkr_num_slots ||
1928 		k->nr_hwcur >= k->nkr_num_slots ||
1929 		k->nr_tail >= k->nkr_num_slots ||
1930 		busy < 0 ||
1931 		busy >= k->nkr_num_slots) {
1932 		D("invalid kring, cur %d tail %d lease %d lease_idx %d lim %d",			k->nr_hwcur, k->nr_hwtail, k->nkr_hwlease,
1933 			k->nkr_lease_idx, k->nkr_num_slots);
1934 	}
1935 #endif
1936 	return space;
1937 }
1938 
1939 
1940 
1941 
1942 /* make a lease on the kring for N positions. return the
1943  * lease index
1944  * XXX only used in VALE code and with is_rx = 1
1945  */
1946 static inline uint32_t
1947 nm_kr_lease(struct netmap_kring *k, u_int n, int is_rx)
1948 {
1949 	uint32_t lim = k->nkr_num_slots - 1;
1950 	uint32_t lease_idx = k->nkr_lease_idx;
1951 
1952 	k->nkr_leases[lease_idx] = NR_NOSLOT;
1953 	k->nkr_lease_idx = nm_next(lease_idx, lim);
1954 
1955 	if (n > nm_kr_space(k, is_rx)) {
1956 		D("invalid request for %d slots", n);
1957 		panic("x");
1958 	}
1959 	/* XXX verify that there are n slots */
1960 	k->nkr_hwlease += n;
1961 	if (k->nkr_hwlease > lim)
1962 		k->nkr_hwlease -= lim + 1;
1963 
1964 	if (k->nkr_hwlease >= k->nkr_num_slots ||
1965 		k->nr_hwcur >= k->nkr_num_slots ||
1966 		k->nr_hwtail >= k->nkr_num_slots ||
1967 		k->nkr_lease_idx >= k->nkr_num_slots) {
1968 		D("invalid kring %s, cur %d tail %d lease %d lease_idx %d lim %d",
1969 			k->na->name,
1970 			k->nr_hwcur, k->nr_hwtail, k->nkr_hwlease,
1971 			k->nkr_lease_idx, k->nkr_num_slots);
1972 	}
1973 	return lease_idx;
1974 }
1975 
1976 /*
1977  *
1978  * This flush routine supports only unicast and broadcast but a large
1979  * number of ports, and lets us replace the learn and dispatch functions.
1980  */
1981 int
1982 nm_bdg_flush(struct nm_bdg_fwd *ft, u_int n, struct netmap_vp_adapter *na,
1983 		u_int ring_nr)
1984 {
1985 	struct nm_bdg_q *dst_ents, *brddst;
1986 	uint16_t num_dsts = 0, *dsts;
1987 	struct nm_bridge *b = na->na_bdg;
1988 	u_int i, me = na->bdg_port;
1989 
1990 	/*
1991 	 * The work area (pointed by ft) is followed by an array of
1992 	 * pointers to queues , dst_ents; there are NM_BDG_MAXRINGS
1993 	 * queues per port plus one for the broadcast traffic.
1994 	 * Then we have an array of destination indexes.
1995 	 */
1996 	dst_ents = (struct nm_bdg_q *)(ft + NM_BDG_BATCH_MAX);
1997 	dsts = (uint16_t *)(dst_ents + NM_BDG_MAXPORTS * NM_BDG_MAXRINGS + 1);
1998 
1999 	/* first pass: find a destination for each packet in the batch */
2000 	for (i = 0; likely(i < n); i += ft[i].ft_frags) {
2001 		uint8_t dst_ring = ring_nr; /* default, same ring as origin */
2002 		uint16_t dst_port, d_i;
2003 		struct nm_bdg_q *d;
2004 		struct nm_bdg_fwd *start_ft = NULL;
2005 
2006 		ND("slot %d frags %d", i, ft[i].ft_frags);
2007 
2008 		if (na->up.virt_hdr_len < ft[i].ft_len) {
2009 			ft[i].ft_offset = na->up.virt_hdr_len;
2010 			start_ft = &ft[i];
2011 		} else if (na->up.virt_hdr_len == ft[i].ft_len && ft[i].ft_flags & NS_MOREFRAG) {
2012 			ft[i].ft_offset = ft[i].ft_len;
2013 			start_ft = &ft[i+1];
2014 		} else {
2015 			/* Drop the packet if the virtio-net header is not into the first
2016 			 * fragment nor at the very beginning of the second.
2017 			 */
2018 			continue;
2019 		}
2020 		dst_port = b->bdg_ops->lookup(start_ft, &dst_ring, na, b->private_data);
2021 		if (netmap_verbose > 255)
2022 			RD(5, "slot %d port %d -> %d", i, me, dst_port);
2023 		if (dst_port >= NM_BDG_NOPORT)
2024 			continue; /* this packet is identified to be dropped */
2025 		else if (dst_port == NM_BDG_BROADCAST)
2026 			dst_ring = 0; /* broadcasts always go to ring 0 */
2027 		else if (unlikely(dst_port == me ||
2028 		    !b->bdg_ports[dst_port]))
2029 			continue;
2030 
2031 		/* get a position in the scratch pad */
2032 		d_i = dst_port * NM_BDG_MAXRINGS + dst_ring;
2033 		d = dst_ents + d_i;
2034 
2035 		/* append the first fragment to the list */
2036 		if (d->bq_head == NM_FT_NULL) { /* new destination */
2037 			d->bq_head = d->bq_tail = i;
2038 			/* remember this position to be scanned later */
2039 			if (dst_port != NM_BDG_BROADCAST)
2040 				dsts[num_dsts++] = d_i;
2041 		} else {
2042 			ft[d->bq_tail].ft_next = i;
2043 			d->bq_tail = i;
2044 		}
2045 		d->bq_len += ft[i].ft_frags;
2046 	}
2047 
2048 	/*
2049 	 * Broadcast traffic goes to ring 0 on all destinations.
2050 	 * So we need to add these rings to the list of ports to scan.
2051 	 * XXX at the moment we scan all NM_BDG_MAXPORTS ports, which is
2052 	 * expensive. We should keep a compact list of active destinations
2053 	 * so we could shorten this loop.
2054 	 */
2055 	brddst = dst_ents + NM_BDG_BROADCAST * NM_BDG_MAXRINGS;
2056 	if (brddst->bq_head != NM_FT_NULL) {
2057 		u_int j;
2058 		for (j = 0; likely(j < b->bdg_active_ports); j++) {
2059 			uint16_t d_i;
2060 			i = b->bdg_port_index[j];
2061 			if (unlikely(i == me))
2062 				continue;
2063 			d_i = i * NM_BDG_MAXRINGS;
2064 			if (dst_ents[d_i].bq_head == NM_FT_NULL)
2065 				dsts[num_dsts++] = d_i;
2066 		}
2067 	}
2068 
2069 	ND(5, "pass 1 done %d pkts %d dsts", n, num_dsts);
2070 	/* second pass: scan destinations */
2071 	for (i = 0; i < num_dsts; i++) {
2072 		struct netmap_vp_adapter *dst_na;
2073 		struct netmap_kring *kring;
2074 		struct netmap_ring *ring;
2075 		u_int dst_nr, lim, j, d_i, next, brd_next;
2076 		u_int needed, howmany;
2077 		int retry = netmap_txsync_retry;
2078 		struct nm_bdg_q *d;
2079 		uint32_t my_start = 0, lease_idx = 0;
2080 		int nrings;
2081 		int virt_hdr_mismatch = 0;
2082 
2083 		d_i = dsts[i];
2084 		ND("second pass %d port %d", i, d_i);
2085 		d = dst_ents + d_i;
2086 		// XXX fix the division
2087 		dst_na = b->bdg_ports[d_i/NM_BDG_MAXRINGS];
2088 		/* protect from the lookup function returning an inactive
2089 		 * destination port
2090 		 */
2091 		if (unlikely(dst_na == NULL))
2092 			goto cleanup;
2093 		if (dst_na->up.na_flags & NAF_SW_ONLY)
2094 			goto cleanup;
2095 		/*
2096 		 * The interface may be in !netmap mode in two cases:
2097 		 * - when na is attached but not activated yet;
2098 		 * - when na is being deactivated but is still attached.
2099 		 */
2100 		if (unlikely(!nm_netmap_on(&dst_na->up))) {
2101 			ND("not in netmap mode!");
2102 			goto cleanup;
2103 		}
2104 
2105 		/* there is at least one either unicast or broadcast packet */
2106 		brd_next = brddst->bq_head;
2107 		next = d->bq_head;
2108 		/* we need to reserve this many slots. If fewer are
2109 		 * available, some packets will be dropped.
2110 		 * Packets may have multiple fragments, so we may not use
2111 		 * there is a chance that we may not use all of the slots
2112 		 * we have claimed, so we will need to handle the leftover
2113 		 * ones when we regain the lock.
2114 		 */
2115 		needed = d->bq_len + brddst->bq_len;
2116 
2117 		if (unlikely(dst_na->up.virt_hdr_len != na->up.virt_hdr_len)) {
2118 			if (netmap_verbose) {
2119 				RD(3, "virt_hdr_mismatch, src %d dst %d", na->up.virt_hdr_len,
2120 						dst_na->up.virt_hdr_len);
2121 			}
2122 			/* There is a virtio-net header/offloadings mismatch between
2123 			 * source and destination. The slower mismatch datapath will
2124 			 * be used to cope with all the mismatches.
2125 			 */
2126 			virt_hdr_mismatch = 1;
2127 			if (dst_na->mfs < na->mfs) {
2128 				/* We may need to do segmentation offloadings, and so
2129 				 * we may need a number of destination slots greater
2130 				 * than the number of input slots ('needed').
2131 				 * We look for the smallest integer 'x' which satisfies:
2132 				 *	needed * na->mfs + x * H <= x * na->mfs
2133 				 * where 'H' is the length of the longest header that may
2134 				 * be replicated in the segmentation process (e.g. for
2135 				 * TCPv4 we must account for ethernet header, IP header
2136 				 * and TCPv4 header).
2137 				 */
2138 				KASSERT(dst_na->mfs > 0, ("vpna->mfs is 0"));
2139 				needed = (needed * na->mfs) /
2140 						(dst_na->mfs - WORST_CASE_GSO_HEADER) + 1;
2141 				ND(3, "srcmtu=%u, dstmtu=%u, x=%u", na->mfs, dst_na->mfs, needed);
2142 			}
2143 		}
2144 
2145 		ND(5, "pass 2 dst %d is %x %s",
2146 			i, d_i, is_vp ? "virtual" : "nic/host");
2147 		dst_nr = d_i & (NM_BDG_MAXRINGS-1);
2148 		nrings = dst_na->up.num_rx_rings;
2149 		if (dst_nr >= nrings)
2150 			dst_nr = dst_nr % nrings;
2151 		kring = dst_na->up.rx_rings[dst_nr];
2152 		ring = kring->ring;
2153 		/* the destination ring may have not been opened for RX */
2154 		if (unlikely(ring == NULL || kring->nr_mode != NKR_NETMAP_ON))
2155 			goto cleanup;
2156 		lim = kring->nkr_num_slots - 1;
2157 
2158 retry:
2159 
2160 		if (dst_na->retry && retry) {
2161 			/* try to get some free slot from the previous run */
2162 			kring->nm_notify(kring, 0);
2163 			/* actually useful only for bwraps, since there
2164 			 * the notify will trigger a txsync on the hwna. VALE ports
2165 			 * have dst_na->retry == 0
2166 			 */
2167 		}
2168 		/* reserve the buffers in the queue and an entry
2169 		 * to report completion, and drop lock.
2170 		 * XXX this might become a helper function.
2171 		 */
2172 		mtx_lock(&kring->q_lock);
2173 		if (kring->nkr_stopped) {
2174 			mtx_unlock(&kring->q_lock);
2175 			goto cleanup;
2176 		}
2177 		my_start = j = kring->nkr_hwlease;
2178 		howmany = nm_kr_space(kring, 1);
2179 		if (needed < howmany)
2180 			howmany = needed;
2181 		lease_idx = nm_kr_lease(kring, howmany, 1);
2182 		mtx_unlock(&kring->q_lock);
2183 
2184 		/* only retry if we need more than available slots */
2185 		if (retry && needed <= howmany)
2186 			retry = 0;
2187 
2188 		/* copy to the destination queue */
2189 		while (howmany > 0) {
2190 			struct netmap_slot *slot;
2191 			struct nm_bdg_fwd *ft_p, *ft_end;
2192 			u_int cnt;
2193 
2194 			/* find the queue from which we pick next packet.
2195 			 * NM_FT_NULL is always higher than valid indexes
2196 			 * so we never dereference it if the other list
2197 			 * has packets (and if both are empty we never
2198 			 * get here).
2199 			 */
2200 			if (next < brd_next) {
2201 				ft_p = ft + next;
2202 				next = ft_p->ft_next;
2203 			} else { /* insert broadcast */
2204 				ft_p = ft + brd_next;
2205 				brd_next = ft_p->ft_next;
2206 			}
2207 			cnt = ft_p->ft_frags; // cnt > 0
2208 			if (unlikely(cnt > howmany))
2209 			    break; /* no more space */
2210 			if (netmap_verbose && cnt > 1)
2211 				RD(5, "rx %d frags to %d", cnt, j);
2212 			ft_end = ft_p + cnt;
2213 			if (unlikely(virt_hdr_mismatch)) {
2214 				bdg_mismatch_datapath(na, dst_na, ft_p, ring, &j, lim, &howmany);
2215 			} else {
2216 				howmany -= cnt;
2217 				do {
2218 					char *dst, *src = ft_p->ft_buf;
2219 					size_t copy_len = ft_p->ft_len, dst_len = copy_len;
2220 
2221 					slot = &ring->slot[j];
2222 					dst = NMB(&dst_na->up, slot);
2223 
2224 					ND("send [%d] %d(%d) bytes at %s:%d",
2225 							i, (int)copy_len, (int)dst_len,
2226 							NM_IFPNAME(dst_ifp), j);
2227 					/* round to a multiple of 64 */
2228 					copy_len = (copy_len + 63) & ~63;
2229 
2230 					if (unlikely(copy_len > NETMAP_BUF_SIZE(&dst_na->up) ||
2231 						     copy_len > NETMAP_BUF_SIZE(&na->up))) {
2232 						RD(5, "invalid len %d, down to 64", (int)copy_len);
2233 						copy_len = dst_len = 64; // XXX
2234 					}
2235 					if (ft_p->ft_flags & NS_INDIRECT) {
2236 						if (copyin(src, dst, copy_len)) {
2237 							// invalid user pointer, pretend len is 0
2238 							dst_len = 0;
2239 						}
2240 					} else {
2241 						//memcpy(dst, src, copy_len);
2242 						pkt_copy(src, dst, (int)copy_len);
2243 					}
2244 					slot->len = dst_len;
2245 					slot->flags = (cnt << 8)| NS_MOREFRAG;
2246 					j = nm_next(j, lim);
2247 					needed--;
2248 					ft_p++;
2249 				} while (ft_p != ft_end);
2250 				slot->flags = (cnt << 8); /* clear flag on last entry */
2251 			}
2252 			/* are we done ? */
2253 			if (next == NM_FT_NULL && brd_next == NM_FT_NULL)
2254 				break;
2255 		}
2256 		{
2257 		    /* current position */
2258 		    uint32_t *p = kring->nkr_leases; /* shorthand */
2259 		    uint32_t update_pos;
2260 		    int still_locked = 1;
2261 
2262 		    mtx_lock(&kring->q_lock);
2263 		    if (unlikely(howmany > 0)) {
2264 			/* not used all bufs. If i am the last one
2265 			 * i can recover the slots, otherwise must
2266 			 * fill them with 0 to mark empty packets.
2267 			 */
2268 			ND("leftover %d bufs", howmany);
2269 			if (nm_next(lease_idx, lim) == kring->nkr_lease_idx) {
2270 			    /* yes i am the last one */
2271 			    ND("roll back nkr_hwlease to %d", j);
2272 			    kring->nkr_hwlease = j;
2273 			} else {
2274 			    while (howmany-- > 0) {
2275 				ring->slot[j].len = 0;
2276 				ring->slot[j].flags = 0;
2277 				j = nm_next(j, lim);
2278 			    }
2279 			}
2280 		    }
2281 		    p[lease_idx] = j; /* report I am done */
2282 
2283 		    update_pos = kring->nr_hwtail;
2284 
2285 		    if (my_start == update_pos) {
2286 			/* all slots before my_start have been reported,
2287 			 * so scan subsequent leases to see if other ranges
2288 			 * have been completed, and to a selwakeup or txsync.
2289 		         */
2290 			while (lease_idx != kring->nkr_lease_idx &&
2291 				p[lease_idx] != NR_NOSLOT) {
2292 			    j = p[lease_idx];
2293 			    p[lease_idx] = NR_NOSLOT;
2294 			    lease_idx = nm_next(lease_idx, lim);
2295 			}
2296 			/* j is the new 'write' position. j != my_start
2297 			 * means there are new buffers to report
2298 			 */
2299 			if (likely(j != my_start)) {
2300 				kring->nr_hwtail = j;
2301 				still_locked = 0;
2302 				mtx_unlock(&kring->q_lock);
2303 				kring->nm_notify(kring, 0);
2304 				/* this is netmap_notify for VALE ports and
2305 				 * netmap_bwrap_notify for bwrap. The latter will
2306 				 * trigger a txsync on the underlying hwna
2307 				 */
2308 				if (dst_na->retry && retry--) {
2309 					/* XXX this is going to call nm_notify again.
2310 					 * Only useful for bwrap in virtual machines
2311 					 */
2312 					goto retry;
2313 				}
2314 			}
2315 		    }
2316 		    if (still_locked)
2317 			mtx_unlock(&kring->q_lock);
2318 		}
2319 cleanup:
2320 		d->bq_head = d->bq_tail = NM_FT_NULL; /* cleanup */
2321 		d->bq_len = 0;
2322 	}
2323 	brddst->bq_head = brddst->bq_tail = NM_FT_NULL; /* cleanup */
2324 	brddst->bq_len = 0;
2325 	return 0;
2326 }
2327 
2328 /* nm_txsync callback for VALE ports */
2329 static int
2330 netmap_vp_txsync(struct netmap_kring *kring, int flags)
2331 {
2332 	struct netmap_vp_adapter *na =
2333 		(struct netmap_vp_adapter *)kring->na;
2334 	u_int done;
2335 	u_int const lim = kring->nkr_num_slots - 1;
2336 	u_int const head = kring->rhead;
2337 
2338 	if (bridge_batch <= 0) { /* testing only */
2339 		done = head; // used all
2340 		goto done;
2341 	}
2342 	if (!na->na_bdg) {
2343 		done = head;
2344 		goto done;
2345 	}
2346 	if (bridge_batch > NM_BDG_BATCH)
2347 		bridge_batch = NM_BDG_BATCH;
2348 
2349 	done = nm_bdg_preflush(kring, head);
2350 done:
2351 	if (done != head)
2352 		D("early break at %d/ %d, tail %d", done, head, kring->nr_hwtail);
2353 	/*
2354 	 * packets between 'done' and 'cur' are left unsent.
2355 	 */
2356 	kring->nr_hwcur = done;
2357 	kring->nr_hwtail = nm_prev(done, lim);
2358 	if (netmap_verbose)
2359 		D("%s ring %d flags %d", na->up.name, kring->ring_id, flags);
2360 	return 0;
2361 }
2362 
2363 
2364 /* rxsync code used by VALE ports nm_rxsync callback and also
2365  * internally by the brwap
2366  */
2367 static int
2368 netmap_vp_rxsync_locked(struct netmap_kring *kring, int flags)
2369 {
2370 	struct netmap_adapter *na = kring->na;
2371 	struct netmap_ring *ring = kring->ring;
2372 	u_int nm_i, lim = kring->nkr_num_slots - 1;
2373 	u_int head = kring->rhead;
2374 	int n;
2375 
2376 	if (head > lim) {
2377 		D("ouch dangerous reset!!!");
2378 		n = netmap_ring_reinit(kring);
2379 		goto done;
2380 	}
2381 
2382 	/* First part, import newly received packets. */
2383 	/* actually nothing to do here, they are already in the kring */
2384 
2385 	/* Second part, skip past packets that userspace has released. */
2386 	nm_i = kring->nr_hwcur;
2387 	if (nm_i != head) {
2388 		/* consistency check, but nothing really important here */
2389 		for (n = 0; likely(nm_i != head); n++) {
2390 			struct netmap_slot *slot = &ring->slot[nm_i];
2391 			void *addr = NMB(na, slot);
2392 
2393 			if (addr == NETMAP_BUF_BASE(kring->na)) { /* bad buf */
2394 				D("bad buffer index %d, ignore ?",
2395 					slot->buf_idx);
2396 			}
2397 			slot->flags &= ~NS_BUF_CHANGED;
2398 			nm_i = nm_next(nm_i, lim);
2399 		}
2400 		kring->nr_hwcur = head;
2401 	}
2402 
2403 	n = 0;
2404 done:
2405 	return n;
2406 }
2407 
2408 /*
2409  * nm_rxsync callback for VALE ports
2410  * user process reading from a VALE switch.
2411  * Already protected against concurrent calls from userspace,
2412  * but we must acquire the queue's lock to protect against
2413  * writers on the same queue.
2414  */
2415 static int
2416 netmap_vp_rxsync(struct netmap_kring *kring, int flags)
2417 {
2418 	int n;
2419 
2420 	mtx_lock(&kring->q_lock);
2421 	n = netmap_vp_rxsync_locked(kring, flags);
2422 	mtx_unlock(&kring->q_lock);
2423 	return n;
2424 }
2425 
2426 
2427 /* nm_bdg_attach callback for VALE ports
2428  * The na_vp port is this same netmap_adapter. There is no host port.
2429  */
2430 static int
2431 netmap_vp_bdg_attach(const char *name, struct netmap_adapter *na)
2432 {
2433 	struct netmap_vp_adapter *vpna = (struct netmap_vp_adapter *)na;
2434 
2435 	if (vpna->na_bdg) {
2436 		return netmap_bwrap_attach(name, na);
2437 	}
2438 	na->na_vp = vpna;
2439 	strncpy(na->name, name, sizeof(na->name));
2440 	na->na_hostvp = NULL;
2441 	return 0;
2442 }
2443 
2444 /* create a netmap_vp_adapter that describes a VALE port.
2445  * Only persistent VALE ports have a non-null ifp.
2446  */
2447 static int
2448 netmap_vp_create(struct nmreq_header *hdr, struct ifnet *ifp,
2449 		struct netmap_mem_d *nmd, struct netmap_vp_adapter **ret)
2450 {
2451 	struct nmreq_register *req = (struct nmreq_register *)(uintptr_t)hdr->nr_body;
2452 	struct netmap_vp_adapter *vpna;
2453 	struct netmap_adapter *na;
2454 	int error = 0;
2455 	u_int npipes = 0;
2456 	u_int extrabufs = 0;
2457 
2458 	if (hdr->nr_reqtype != NETMAP_REQ_REGISTER) {
2459 		return EINVAL;
2460 	}
2461 
2462 	vpna = nm_os_malloc(sizeof(*vpna));
2463 	if (vpna == NULL)
2464 		return ENOMEM;
2465 
2466  	na = &vpna->up;
2467 
2468 	na->ifp = ifp;
2469 	strncpy(na->name, hdr->nr_name, sizeof(na->name));
2470 
2471 	/* bound checking */
2472 	na->num_tx_rings = req->nr_tx_rings;
2473 	nm_bound_var(&na->num_tx_rings, 1, 1, NM_BDG_MAXRINGS, NULL);
2474 	req->nr_tx_rings = na->num_tx_rings; /* write back */
2475 	na->num_rx_rings = req->nr_rx_rings;
2476 	nm_bound_var(&na->num_rx_rings, 1, 1, NM_BDG_MAXRINGS, NULL);
2477 	req->nr_rx_rings = na->num_rx_rings; /* write back */
2478 	nm_bound_var(&req->nr_tx_slots, NM_BRIDGE_RINGSIZE,
2479 			1, NM_BDG_MAXSLOTS, NULL);
2480 	na->num_tx_desc = req->nr_tx_slots;
2481 	nm_bound_var(&req->nr_rx_slots, NM_BRIDGE_RINGSIZE,
2482 			1, NM_BDG_MAXSLOTS, NULL);
2483 	/* validate number of pipes. We want at least 1,
2484 	 * but probably can do with some more.
2485 	 * So let's use 2 as default (when 0 is supplied)
2486 	 */
2487 	nm_bound_var(&npipes, 2, 1, NM_MAXPIPES, NULL);
2488 	/* validate extra bufs */
2489 	nm_bound_var(&extrabufs, 0, 0,
2490 			128*NM_BDG_MAXSLOTS, NULL);
2491 	req->nr_extra_bufs = extrabufs; /* write back */
2492 	na->num_rx_desc = req->nr_rx_slots;
2493 	/* Set the mfs to a default value, as it is needed on the VALE
2494 	 * mismatch datapath. XXX We should set it according to the MTU
2495 	 * known to the kernel. */
2496 	vpna->mfs = NM_BDG_MFS_DEFAULT;
2497 	vpna->last_smac = ~0llu;
2498 	/*if (vpna->mfs > netmap_buf_size)  TODO netmap_buf_size is zero??
2499 		vpna->mfs = netmap_buf_size; */
2500 	if (netmap_verbose)
2501 		D("max frame size %u", vpna->mfs);
2502 
2503 	na->na_flags |= NAF_BDG_MAYSLEEP;
2504 	/* persistent VALE ports look like hw devices
2505 	 * with a native netmap adapter
2506 	 */
2507 	if (ifp)
2508 		na->na_flags |= NAF_NATIVE;
2509 	na->nm_txsync = netmap_vp_txsync;
2510 	na->nm_rxsync = netmap_vp_rxsync;
2511 	na->nm_register = netmap_vp_reg;
2512 	na->nm_krings_create = netmap_vp_krings_create;
2513 	na->nm_krings_delete = netmap_vp_krings_delete;
2514 	na->nm_dtor = netmap_vp_dtor;
2515 	ND("nr_mem_id %d", req->nr_mem_id);
2516 	na->nm_mem = nmd ?
2517 		netmap_mem_get(nmd):
2518 		netmap_mem_private_new(
2519 			na->num_tx_rings, na->num_tx_desc,
2520 			na->num_rx_rings, na->num_rx_desc,
2521 			req->nr_extra_bufs, npipes, &error);
2522 	if (na->nm_mem == NULL)
2523 		goto err;
2524 	na->nm_bdg_attach = netmap_vp_bdg_attach;
2525 	/* other nmd fields are set in the common routine */
2526 	error = netmap_attach_common(na);
2527 	if (error)
2528 		goto err;
2529 	*ret = vpna;
2530 	return 0;
2531 
2532 err:
2533 	if (na->nm_mem != NULL)
2534 		netmap_mem_put(na->nm_mem);
2535 	nm_os_free(vpna);
2536 	return error;
2537 }
2538 
2539 /* Bridge wrapper code (bwrap).
2540  * This is used to connect a non-VALE-port netmap_adapter (hwna) to a
2541  * VALE switch.
2542  * The main task is to swap the meaning of tx and rx rings to match the
2543  * expectations of the VALE switch code (see nm_bdg_flush).
2544  *
2545  * The bwrap works by interposing a netmap_bwrap_adapter between the
2546  * rest of the system and the hwna. The netmap_bwrap_adapter looks like
2547  * a netmap_vp_adapter to the rest the system, but, internally, it
2548  * translates all callbacks to what the hwna expects.
2549  *
2550  * Note that we have to intercept callbacks coming from two sides:
2551  *
2552  *  - callbacks coming from the netmap module are intercepted by
2553  *    passing around the netmap_bwrap_adapter instead of the hwna
2554  *
2555  *  - callbacks coming from outside of the netmap module only know
2556  *    about the hwna. This, however, only happens in interrupt
2557  *    handlers, where only the hwna->nm_notify callback is called.
2558  *    What the bwrap does is to overwrite the hwna->nm_notify callback
2559  *    with its own netmap_bwrap_intr_notify.
2560  *    XXX This assumes that the hwna->nm_notify callback was the
2561  *    standard netmap_notify(), as it is the case for nic adapters.
2562  *    Any additional action performed by hwna->nm_notify will not be
2563  *    performed by netmap_bwrap_intr_notify.
2564  *
2565  * Additionally, the bwrap can optionally attach the host rings pair
2566  * of the wrapped adapter to a different port of the switch.
2567  */
2568 
2569 
2570 static void
2571 netmap_bwrap_dtor(struct netmap_adapter *na)
2572 {
2573 	struct netmap_bwrap_adapter *bna = (struct netmap_bwrap_adapter*)na;
2574 	struct netmap_adapter *hwna = bna->hwna;
2575 	struct nm_bridge *b = bna->up.na_bdg,
2576 		*bh = bna->host.na_bdg;
2577 
2578 	if (bna->host.up.nm_mem)
2579 		netmap_mem_put(bna->host.up.nm_mem);
2580 
2581 	if (b) {
2582 		netmap_bdg_detach_common(b, bna->up.bdg_port,
2583 			    (bh ? bna->host.bdg_port : -1));
2584 	}
2585 
2586 	ND("na %p", na);
2587 	na->ifp = NULL;
2588 	bna->host.up.ifp = NULL;
2589 	hwna->na_vp = bna->saved_na_vp;
2590 	hwna->na_hostvp = NULL;
2591 	hwna->na_private = NULL;
2592 	hwna->na_flags &= ~NAF_BUSY;
2593 	netmap_adapter_put(hwna);
2594 
2595 }
2596 
2597 
2598 /*
2599  * Intr callback for NICs connected to a bridge.
2600  * Simply ignore tx interrupts (maybe we could try to recover space ?)
2601  * and pass received packets from nic to the bridge.
2602  *
2603  * XXX TODO check locking: this is called from the interrupt
2604  * handler so we should make sure that the interface is not
2605  * disconnected while passing down an interrupt.
2606  *
2607  * Note, no user process can access this NIC or the host stack.
2608  * The only part of the ring that is significant are the slots,
2609  * and head/cur/tail are set from the kring as needed
2610  * (part as a receive ring, part as a transmit ring).
2611  *
2612  * callback that overwrites the hwna notify callback.
2613  * Packets come from the outside or from the host stack and are put on an
2614  * hwna rx ring.
2615  * The bridge wrapper then sends the packets through the bridge.
2616  */
2617 static int
2618 netmap_bwrap_intr_notify(struct netmap_kring *kring, int flags)
2619 {
2620 	struct netmap_adapter *na = kring->na;
2621 	struct netmap_bwrap_adapter *bna = na->na_private;
2622 	struct netmap_kring *bkring;
2623 	struct netmap_vp_adapter *vpna = &bna->up;
2624 	u_int ring_nr = kring->ring_id;
2625 	int ret = NM_IRQ_COMPLETED;
2626 	int error;
2627 
2628 	if (netmap_verbose)
2629 	    D("%s %s 0x%x", na->name, kring->name, flags);
2630 
2631 	bkring = vpna->up.tx_rings[ring_nr];
2632 
2633 	/* make sure the ring is not disabled */
2634 	if (nm_kr_tryget(kring, 0 /* can't sleep */, NULL)) {
2635 		return EIO;
2636 	}
2637 
2638 	if (netmap_verbose)
2639 	    D("%s head %d cur %d tail %d",  na->name,
2640 		kring->rhead, kring->rcur, kring->rtail);
2641 
2642 	/* simulate a user wakeup on the rx ring
2643 	 * fetch packets that have arrived.
2644 	 */
2645 	error = kring->nm_sync(kring, 0);
2646 	if (error)
2647 		goto put_out;
2648 	if (kring->nr_hwcur == kring->nr_hwtail) {
2649 		if (netmap_verbose)
2650 			D("how strange, interrupt with no packets on %s",
2651 			    na->name);
2652 		goto put_out;
2653 	}
2654 
2655 	/* new packets are kring->rcur to kring->nr_hwtail, and the bkring
2656 	 * had hwcur == bkring->rhead. So advance bkring->rhead to kring->nr_hwtail
2657 	 * to push all packets out.
2658 	 */
2659 	bkring->rhead = bkring->rcur = kring->nr_hwtail;
2660 
2661 	netmap_vp_txsync(bkring, flags);
2662 
2663 	/* mark all buffers as released on this ring */
2664 	kring->rhead = kring->rcur = kring->rtail = kring->nr_hwtail;
2665 	/* another call to actually release the buffers */
2666 	error = kring->nm_sync(kring, 0);
2667 
2668 	/* The second rxsync may have further advanced hwtail. If this happens,
2669 	 *  return NM_IRQ_RESCHED, otherwise just return NM_IRQ_COMPLETED. */
2670 	if (kring->rcur != kring->nr_hwtail) {
2671 		ret = NM_IRQ_RESCHED;
2672 	}
2673 put_out:
2674 	nm_kr_put(kring);
2675 
2676 	return error ? error : ret;
2677 }
2678 
2679 
2680 /* nm_register callback for bwrap */
2681 static int
2682 netmap_bwrap_reg(struct netmap_adapter *na, int onoff)
2683 {
2684 	struct netmap_bwrap_adapter *bna =
2685 		(struct netmap_bwrap_adapter *)na;
2686 	struct netmap_adapter *hwna = bna->hwna;
2687 	struct netmap_vp_adapter *hostna = &bna->host;
2688 	int error, i;
2689 	enum txrx t;
2690 
2691 	ND("%s %s", na->name, onoff ? "on" : "off");
2692 
2693 	if (onoff) {
2694 		/* netmap_do_regif has been called on the bwrap na.
2695 		 * We need to pass the information about the
2696 		 * memory allocator down to the hwna before
2697 		 * putting it in netmap mode
2698 		 */
2699 		hwna->na_lut = na->na_lut;
2700 
2701 		if (hostna->na_bdg) {
2702 			/* if the host rings have been attached to switch,
2703 			 * we need to copy the memory allocator information
2704 			 * in the hostna also
2705 			 */
2706 			hostna->up.na_lut = na->na_lut;
2707 		}
2708 
2709 	}
2710 
2711 	/* pass down the pending ring state information */
2712 	for_rx_tx(t) {
2713 		for (i = 0; i < nma_get_nrings(na, t) + 1; i++)
2714 			NMR(hwna, t)[i]->nr_pending_mode =
2715 				NMR(na, t)[i]->nr_pending_mode;
2716 	}
2717 
2718 	/* forward the request to the hwna */
2719 	error = hwna->nm_register(hwna, onoff);
2720 	if (error)
2721 		return error;
2722 
2723 	/* copy up the current ring state information */
2724 	for_rx_tx(t) {
2725 		for (i = 0; i < nma_get_nrings(na, t) + 1; i++) {
2726 			struct netmap_kring *kring = NMR(hwna, t)[i];
2727 			NMR(na, t)[i]->nr_mode = kring->nr_mode;
2728 		}
2729 	}
2730 
2731 	/* impersonate a netmap_vp_adapter */
2732 	netmap_vp_reg(na, onoff);
2733 	if (hostna->na_bdg)
2734 		netmap_vp_reg(&hostna->up, onoff);
2735 
2736 	if (onoff) {
2737 		u_int i;
2738 		/* intercept the hwna nm_nofify callback on the hw rings */
2739 		for (i = 0; i < hwna->num_rx_rings; i++) {
2740 			hwna->rx_rings[i]->save_notify = hwna->rx_rings[i]->nm_notify;
2741 			hwna->rx_rings[i]->nm_notify = netmap_bwrap_intr_notify;
2742 		}
2743 		i = hwna->num_rx_rings; /* for safety */
2744 		/* save the host ring notify unconditionally */
2745 		hwna->rx_rings[i]->save_notify = hwna->rx_rings[i]->nm_notify;
2746 		if (hostna->na_bdg) {
2747 			/* also intercept the host ring notify */
2748 			hwna->rx_rings[i]->nm_notify = netmap_bwrap_intr_notify;
2749 		}
2750 		if (na->active_fds == 0)
2751 			na->na_flags |= NAF_NETMAP_ON;
2752 	} else {
2753 		u_int i;
2754 
2755 		if (na->active_fds == 0)
2756 			na->na_flags &= ~NAF_NETMAP_ON;
2757 
2758 		/* reset all notify callbacks (including host ring) */
2759 		for (i = 0; i <= hwna->num_rx_rings; i++) {
2760 			hwna->rx_rings[i]->nm_notify = hwna->rx_rings[i]->save_notify;
2761 			hwna->rx_rings[i]->save_notify = NULL;
2762 		}
2763 		hwna->na_lut.lut = NULL;
2764 		hwna->na_lut.plut = NULL;
2765 		hwna->na_lut.objtotal = 0;
2766 		hwna->na_lut.objsize = 0;
2767 
2768 		/* pass ownership of the netmap rings to the hwna */
2769 		for_rx_tx(t) {
2770 			for (i = 0; i < nma_get_nrings(na, t) + 1; i++) {
2771 				NMR(na, t)[i]->ring = NULL;
2772 			}
2773 		}
2774 
2775 	}
2776 
2777 	return 0;
2778 }
2779 
2780 /* nm_config callback for bwrap */
2781 static int
2782 netmap_bwrap_config(struct netmap_adapter *na, struct nm_config_info *info)
2783 {
2784 	struct netmap_bwrap_adapter *bna =
2785 		(struct netmap_bwrap_adapter *)na;
2786 	struct netmap_adapter *hwna = bna->hwna;
2787 	int error;
2788 
2789 	/* Forward the request to the hwna. It may happen that nobody
2790 	 * registered hwna yet, so netmap_mem_get_lut() may have not
2791 	 * been called yet. */
2792 	error = netmap_mem_get_lut(hwna->nm_mem, &hwna->na_lut);
2793 	if (error)
2794 		return error;
2795 	netmap_update_config(hwna);
2796 	/* swap the results and propagate */
2797 	info->num_tx_rings = hwna->num_rx_rings;
2798 	info->num_tx_descs = hwna->num_rx_desc;
2799 	info->num_rx_rings = hwna->num_tx_rings;
2800 	info->num_rx_descs = hwna->num_tx_desc;
2801 	info->rx_buf_maxsize = hwna->rx_buf_maxsize;
2802 
2803 	return 0;
2804 }
2805 
2806 
2807 /* nm_krings_create callback for bwrap */
2808 static int
2809 netmap_bwrap_krings_create(struct netmap_adapter *na)
2810 {
2811 	struct netmap_bwrap_adapter *bna =
2812 		(struct netmap_bwrap_adapter *)na;
2813 	struct netmap_adapter *hwna = bna->hwna;
2814 	struct netmap_adapter *hostna = &bna->host.up;
2815 	int i, error = 0;
2816 	enum txrx t;
2817 
2818 	ND("%s", na->name);
2819 
2820 	/* impersonate a netmap_vp_adapter */
2821 	error = netmap_vp_krings_create(na);
2822 	if (error)
2823 		return error;
2824 
2825 	/* also create the hwna krings */
2826 	error = hwna->nm_krings_create(hwna);
2827 	if (error) {
2828 		goto err_del_vp_rings;
2829 	}
2830 
2831 	/* increment the usage counter for all the hwna krings */
2832 	for_rx_tx(t) {
2833 		for (i = 0; i < nma_get_nrings(hwna, t) + 1; i++) {
2834 			NMR(hwna, t)[i]->users++;
2835 		}
2836 	}
2837 
2838 	/* now create the actual rings */
2839 	error = netmap_mem_rings_create(hwna);
2840 	if (error) {
2841 		goto err_dec_users;
2842 	}
2843 
2844 	/* cross-link the netmap rings
2845 	 * The original number of rings comes from hwna,
2846 	 * rx rings on one side equals tx rings on the other.
2847 	 */
2848 	for_rx_tx(t) {
2849 		enum txrx r = nm_txrx_swap(t); /* swap NR_TX <-> NR_RX */
2850 		for (i = 0; i < nma_get_nrings(hwna, r) + 1; i++) {
2851 			NMR(na, t)[i]->nkr_num_slots = NMR(hwna, r)[i]->nkr_num_slots;
2852 			NMR(na, t)[i]->ring = NMR(hwna, r)[i]->ring;
2853 		}
2854 	}
2855 
2856 	if (na->na_flags & NAF_HOST_RINGS) {
2857 		/* the hostna rings are the host rings of the bwrap.
2858 		 * The corresponding krings must point back to the
2859 		 * hostna
2860 		 */
2861 		hostna->tx_rings = &na->tx_rings[na->num_tx_rings];
2862 		hostna->tx_rings[0]->na = hostna;
2863 		hostna->rx_rings = &na->rx_rings[na->num_rx_rings];
2864 		hostna->rx_rings[0]->na = hostna;
2865 	}
2866 
2867 	return 0;
2868 
2869 err_dec_users:
2870 	for_rx_tx(t) {
2871 		NMR(hwna, t)[i]->users--;
2872 	}
2873 	hwna->nm_krings_delete(hwna);
2874 err_del_vp_rings:
2875 	netmap_vp_krings_delete(na);
2876 
2877 	return error;
2878 }
2879 
2880 
2881 static void
2882 netmap_bwrap_krings_delete(struct netmap_adapter *na)
2883 {
2884 	struct netmap_bwrap_adapter *bna =
2885 		(struct netmap_bwrap_adapter *)na;
2886 	struct netmap_adapter *hwna = bna->hwna;
2887 	enum txrx t;
2888 	int i;
2889 
2890 	ND("%s", na->name);
2891 
2892 	/* decrement the usage counter for all the hwna krings */
2893 	for_rx_tx(t) {
2894 		for (i = 0; i < nma_get_nrings(hwna, t) + 1; i++) {
2895 			NMR(hwna, t)[i]->users--;
2896 		}
2897 	}
2898 
2899 	/* delete any netmap rings that are no longer needed */
2900 	netmap_mem_rings_delete(hwna);
2901 	hwna->nm_krings_delete(hwna);
2902 	netmap_vp_krings_delete(na);
2903 }
2904 
2905 
2906 /* notify method for the bridge-->hwna direction */
2907 static int
2908 netmap_bwrap_notify(struct netmap_kring *kring, int flags)
2909 {
2910 	struct netmap_adapter *na = kring->na;
2911 	struct netmap_bwrap_adapter *bna = na->na_private;
2912 	struct netmap_adapter *hwna = bna->hwna;
2913 	u_int ring_n = kring->ring_id;
2914 	u_int lim = kring->nkr_num_slots - 1;
2915 	struct netmap_kring *hw_kring;
2916 	int error;
2917 
2918 	ND("%s: na %s hwna %s",
2919 			(kring ? kring->name : "NULL!"),
2920 			(na ? na->name : "NULL!"),
2921 			(hwna ? hwna->name : "NULL!"));
2922 	hw_kring = hwna->tx_rings[ring_n];
2923 
2924 	if (nm_kr_tryget(hw_kring, 0, NULL)) {
2925 		return ENXIO;
2926 	}
2927 
2928 	/* first step: simulate a user wakeup on the rx ring */
2929 	netmap_vp_rxsync(kring, flags);
2930 	ND("%s[%d] PRE rx(c%3d t%3d l%3d) ring(h%3d c%3d t%3d) tx(c%3d ht%3d t%3d)",
2931 		na->name, ring_n,
2932 		kring->nr_hwcur, kring->nr_hwtail, kring->nkr_hwlease,
2933 		ring->head, ring->cur, ring->tail,
2934 		hw_kring->nr_hwcur, hw_kring->nr_hwtail, hw_ring->rtail);
2935 	/* second step: the new packets are sent on the tx ring
2936 	 * (which is actually the same ring)
2937 	 */
2938 	hw_kring->rhead = hw_kring->rcur = kring->nr_hwtail;
2939 	error = hw_kring->nm_sync(hw_kring, flags);
2940 	if (error)
2941 		goto put_out;
2942 
2943 	/* third step: now we are back the rx ring */
2944 	/* claim ownership on all hw owned bufs */
2945 	kring->rhead = kring->rcur = nm_next(hw_kring->nr_hwtail, lim); /* skip past reserved slot */
2946 
2947 	/* fourth step: the user goes to sleep again, causing another rxsync */
2948 	netmap_vp_rxsync(kring, flags);
2949 	ND("%s[%d] PST rx(c%3d t%3d l%3d) ring(h%3d c%3d t%3d) tx(c%3d ht%3d t%3d)",
2950 		na->name, ring_n,
2951 		kring->nr_hwcur, kring->nr_hwtail, kring->nkr_hwlease,
2952 		ring->head, ring->cur, ring->tail,
2953 		hw_kring->nr_hwcur, hw_kring->nr_hwtail, hw_kring->rtail);
2954 put_out:
2955 	nm_kr_put(hw_kring);
2956 
2957 	return error ? error : NM_IRQ_COMPLETED;
2958 }
2959 
2960 
2961 /* nm_bdg_ctl callback for the bwrap.
2962  * Called on bridge-attach and detach, as an effect of vale-ctl -[ahd].
2963  * On attach, it needs to provide a fake netmap_priv_d structure and
2964  * perform a netmap_do_regif() on the bwrap. This will put both the
2965  * bwrap and the hwna in netmap mode, with the netmap rings shared
2966  * and cross linked. Moroever, it will start intercepting interrupts
2967  * directed to hwna.
2968  */
2969 static int
2970 netmap_bwrap_bdg_ctl(struct nmreq_header *hdr, struct netmap_adapter *na)
2971 {
2972 	struct netmap_priv_d *npriv;
2973 	struct netmap_bwrap_adapter *bna = (struct netmap_bwrap_adapter*)na;
2974 	int error = 0;
2975 
2976 	if (hdr->nr_reqtype == NETMAP_REQ_VALE_ATTACH) {
2977 		struct nmreq_vale_attach *req =
2978 			(struct nmreq_vale_attach *)(uintptr_t)hdr->nr_body;
2979 		if (req->reg.nr_ringid != 0 ||
2980 			(req->reg.nr_mode != NR_REG_ALL_NIC &&
2981 				req->reg.nr_mode != NR_REG_NIC_SW)) {
2982 			/* We only support attaching all the NIC rings
2983 			 * and/or the host stack. */
2984 			return EINVAL;
2985 		}
2986 		if (NETMAP_OWNED_BY_ANY(na)) {
2987 			return EBUSY;
2988 		}
2989 		if (bna->na_kpriv) {
2990 			/* nothing to do */
2991 			return 0;
2992 		}
2993 		npriv = netmap_priv_new();
2994 		if (npriv == NULL)
2995 			return ENOMEM;
2996 		npriv->np_ifp = na->ifp; /* let the priv destructor release the ref */
2997 		error = netmap_do_regif(npriv, na, req->reg.nr_mode,
2998 					req->reg.nr_ringid, req->reg.nr_flags);
2999 		if (error) {
3000 			netmap_priv_delete(npriv);
3001 			return error;
3002 		}
3003 		bna->na_kpriv = npriv;
3004 		na->na_flags |= NAF_BUSY;
3005 	} else {
3006 		if (na->active_fds == 0) /* not registered */
3007 			return EINVAL;
3008 		netmap_priv_delete(bna->na_kpriv);
3009 		bna->na_kpriv = NULL;
3010 		na->na_flags &= ~NAF_BUSY;
3011 	}
3012 
3013 	return error;
3014 }
3015 
3016 /* attach a bridge wrapper to the 'real' device */
3017 int
3018 netmap_bwrap_attach(const char *nr_name, struct netmap_adapter *hwna)
3019 {
3020 	struct netmap_bwrap_adapter *bna;
3021 	struct netmap_adapter *na = NULL;
3022 	struct netmap_adapter *hostna = NULL;
3023 	int error = 0;
3024 	enum txrx t;
3025 
3026 	/* make sure the NIC is not already in use */
3027 	if (NETMAP_OWNED_BY_ANY(hwna)) {
3028 		D("NIC %s busy, cannot attach to bridge", hwna->name);
3029 		return EBUSY;
3030 	}
3031 
3032 	bna = nm_os_malloc(sizeof(*bna));
3033 	if (bna == NULL) {
3034 		return ENOMEM;
3035 	}
3036 
3037 	na = &bna->up.up;
3038 	/* make bwrap ifp point to the real ifp */
3039 	na->ifp = hwna->ifp;
3040 	if_ref(na->ifp);
3041 	na->na_private = bna;
3042 	strncpy(na->name, nr_name, sizeof(na->name));
3043 	/* fill the ring data for the bwrap adapter with rx/tx meanings
3044 	 * swapped. The real cross-linking will be done during register,
3045 	 * when all the krings will have been created.
3046 	 */
3047 	for_rx_tx(t) {
3048 		enum txrx r = nm_txrx_swap(t); /* swap NR_TX <-> NR_RX */
3049 		nma_set_nrings(na, t, nma_get_nrings(hwna, r));
3050 		nma_set_ndesc(na, t, nma_get_ndesc(hwna, r));
3051 	}
3052 	na->nm_dtor = netmap_bwrap_dtor;
3053 	na->nm_register = netmap_bwrap_reg;
3054 	// na->nm_txsync = netmap_bwrap_txsync;
3055 	// na->nm_rxsync = netmap_bwrap_rxsync;
3056 	na->nm_config = netmap_bwrap_config;
3057 	na->nm_krings_create = netmap_bwrap_krings_create;
3058 	na->nm_krings_delete = netmap_bwrap_krings_delete;
3059 	na->nm_notify = netmap_bwrap_notify;
3060 	na->nm_bdg_ctl = netmap_bwrap_bdg_ctl;
3061 	na->pdev = hwna->pdev;
3062 	na->nm_mem = netmap_mem_get(hwna->nm_mem);
3063 	na->virt_hdr_len = hwna->virt_hdr_len;
3064 	na->rx_buf_maxsize = hwna->rx_buf_maxsize;
3065 	bna->up.retry = 1; /* XXX maybe this should depend on the hwna */
3066 	/* Set the mfs, needed on the VALE mismatch datapath. */
3067 	bna->up.mfs = NM_BDG_MFS_DEFAULT;
3068 
3069 	bna->hwna = hwna;
3070 	netmap_adapter_get(hwna);
3071 	hwna->na_private = bna; /* weak reference */
3072 	bna->saved_na_vp = hwna->na_vp;
3073 	hwna->na_vp = &bna->up;
3074 	bna->up.up.na_vp = &(bna->up);
3075 
3076 	if (hwna->na_flags & NAF_HOST_RINGS) {
3077 		if (hwna->na_flags & NAF_SW_ONLY)
3078 			na->na_flags |= NAF_SW_ONLY;
3079 		na->na_flags |= NAF_HOST_RINGS;
3080 		hostna = &bna->host.up;
3081 		snprintf(hostna->name, sizeof(hostna->name), "%s^", nr_name);
3082 		hostna->ifp = hwna->ifp;
3083 		for_rx_tx(t) {
3084 			enum txrx r = nm_txrx_swap(t);
3085 			nma_set_nrings(hostna, t, 1);
3086 			nma_set_ndesc(hostna, t, nma_get_ndesc(hwna, r));
3087 		}
3088 		// hostna->nm_txsync = netmap_bwrap_host_txsync;
3089 		// hostna->nm_rxsync = netmap_bwrap_host_rxsync;
3090 		hostna->nm_notify = netmap_bwrap_notify;
3091 		hostna->nm_mem = netmap_mem_get(na->nm_mem);
3092 		hostna->na_private = bna;
3093 		hostna->na_vp = &bna->up;
3094 		na->na_hostvp = hwna->na_hostvp =
3095 			hostna->na_hostvp = &bna->host;
3096 		hostna->na_flags = NAF_BUSY; /* prevent NIOCREGIF */
3097 		hostna->rx_buf_maxsize = hwna->rx_buf_maxsize;
3098 		bna->host.mfs = NM_BDG_MFS_DEFAULT;
3099 	}
3100 
3101 	ND("%s<->%s txr %d txd %d rxr %d rxd %d",
3102 		na->name, ifp->if_xname,
3103 		na->num_tx_rings, na->num_tx_desc,
3104 		na->num_rx_rings, na->num_rx_desc);
3105 
3106 	error = netmap_attach_common(na);
3107 	if (error) {
3108 		goto err_free;
3109 	}
3110 	hwna->na_flags |= NAF_BUSY;
3111 	return 0;
3112 
3113 err_free:
3114 	hwna->na_vp = hwna->na_hostvp = NULL;
3115 	netmap_adapter_put(hwna);
3116 	nm_os_free(bna);
3117 	return error;
3118 
3119 }
3120 
3121 struct nm_bridge *
3122 netmap_init_bridges2(u_int n)
3123 {
3124 	int i;
3125 	struct nm_bridge *b;
3126 
3127 	b = nm_os_malloc(sizeof(struct nm_bridge) * n);
3128 	if (b == NULL)
3129 		return NULL;
3130 	for (i = 0; i < n; i++)
3131 		BDG_RWINIT(&b[i]);
3132 	return b;
3133 }
3134 
3135 void
3136 netmap_uninit_bridges2(struct nm_bridge *b, u_int n)
3137 {
3138 	int i;
3139 
3140 	if (b == NULL)
3141 		return;
3142 
3143 	for (i = 0; i < n; i++)
3144 		BDG_RWDESTROY(&b[i]);
3145 	nm_os_free(b);
3146 }
3147 
3148 int
3149 netmap_init_bridges(void)
3150 {
3151 #ifdef CONFIG_NET_NS
3152 	return netmap_bns_register();
3153 #else
3154 	nm_bridges = netmap_init_bridges2(NM_BRIDGES);
3155 	if (nm_bridges == NULL)
3156 		return ENOMEM;
3157 	return 0;
3158 #endif
3159 }
3160 
3161 void
3162 netmap_uninit_bridges(void)
3163 {
3164 #ifdef CONFIG_NET_NS
3165 	netmap_bns_unregister();
3166 #else
3167 	netmap_uninit_bridges2(nm_bridges, NM_BRIDGES);
3168 #endif
3169 }
3170 #endif /* WITH_VALE */
3171