xref: /titanic_53/usr/src/uts/sun4v/sys/vsw.h (revision 1ae0874509b6811fdde1dfd46f0d93fd09867a3f)
1*1ae08745Sheppo /*
2*1ae08745Sheppo  * CDDL HEADER START
3*1ae08745Sheppo  *
4*1ae08745Sheppo  * The contents of this file are subject to the terms of the
5*1ae08745Sheppo  * Common Development and Distribution License (the "License").
6*1ae08745Sheppo  * You may not use this file except in compliance with the License.
7*1ae08745Sheppo  *
8*1ae08745Sheppo  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9*1ae08745Sheppo  * or http://www.opensolaris.org/os/licensing.
10*1ae08745Sheppo  * See the License for the specific language governing permissions
11*1ae08745Sheppo  * and limitations under the License.
12*1ae08745Sheppo  *
13*1ae08745Sheppo  * When distributing Covered Code, include this CDDL HEADER in each
14*1ae08745Sheppo  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15*1ae08745Sheppo  * If applicable, add the following below this CDDL HEADER, with the
16*1ae08745Sheppo  * fields enclosed by brackets "[]" replaced with your own identifying
17*1ae08745Sheppo  * information: Portions Copyright [yyyy] [name of copyright owner]
18*1ae08745Sheppo  *
19*1ae08745Sheppo  * CDDL HEADER END
20*1ae08745Sheppo  */
21*1ae08745Sheppo 
22*1ae08745Sheppo /*
23*1ae08745Sheppo  * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
24*1ae08745Sheppo  * Use is subject to license terms.
25*1ae08745Sheppo  */
26*1ae08745Sheppo 
27*1ae08745Sheppo /*
28*1ae08745Sheppo  * This header file contains the basic data structures which the
29*1ae08745Sheppo  * virtual switch (vsw) uses to communicate with its clients and
30*1ae08745Sheppo  * the outside world.
31*1ae08745Sheppo  *
32*1ae08745Sheppo  * The virtual switch reads the machine description (MD) to
33*1ae08745Sheppo  * determine how many port_t structures to create (each port_t
34*1ae08745Sheppo  * can support communications to a single network device). The
35*1ae08745Sheppo  * port_t's are maintained in a linked list.
36*1ae08745Sheppo  *
37*1ae08745Sheppo  * Each port in turn contains a number of logical domain channels
38*1ae08745Sheppo  * (ldc's) which are inter domain communications channels which
39*1ae08745Sheppo  * are used for passing small messages between the domains. Their
40*1ae08745Sheppo  * may be an unlimited number of channels associated with each port,
41*1ae08745Sheppo  * though most devices only use a single channel.
42*1ae08745Sheppo  *
43*1ae08745Sheppo  * The ldc is a bi-directional channel, which is divided up into
44*1ae08745Sheppo  * two directional 'lanes', one outbound from the switch to the
45*1ae08745Sheppo  * virtual network device, the other inbound to the switch.
46*1ae08745Sheppo  * Depending on the type of device each lane may have seperate
47*1ae08745Sheppo  * communication paramaters (such as mtu etc).
48*1ae08745Sheppo  *
49*1ae08745Sheppo  * For those network clients which use descriptor rings the
50*1ae08745Sheppo  * rings are associated with the appropriate lane. I.e. rings
51*1ae08745Sheppo  * which the switch exports are associated with the outbound lanes
52*1ae08745Sheppo  * while those which the network clients are exporting to the switch
53*1ae08745Sheppo  * are associated with the inbound lane.
54*1ae08745Sheppo  *
55*1ae08745Sheppo  * In diagram form the data structures look as follows:
56*1ae08745Sheppo  *
57*1ae08745Sheppo  * vsw instance
58*1ae08745Sheppo  *     |
59*1ae08745Sheppo  *     +----->port_t----->port_t----->port_t----->
60*1ae08745Sheppo  *		|
61*1ae08745Sheppo  *		+--->ldc_t--->ldc_t--->ldc_t--->
62*1ae08745Sheppo  *		       |
63*1ae08745Sheppo  *		       +--->lane_t (inbound)
64*1ae08745Sheppo  *		       |       |
65*1ae08745Sheppo  *		       |       +--->dring--->dring--->
66*1ae08745Sheppo  *		       |
67*1ae08745Sheppo  *		       +--->lane_t (outbound)
68*1ae08745Sheppo  *			       |
69*1ae08745Sheppo  *			       +--->dring--->dring--->
70*1ae08745Sheppo  *
71*1ae08745Sheppo  */
72*1ae08745Sheppo 
73*1ae08745Sheppo #ifndef	_VSW_H
74*1ae08745Sheppo #define	_VSW_H
75*1ae08745Sheppo 
76*1ae08745Sheppo #pragma ident	"%Z%%M%	%I%	%E% SMI"
77*1ae08745Sheppo 
78*1ae08745Sheppo #ifdef	__cplusplus
79*1ae08745Sheppo extern "C" {
80*1ae08745Sheppo #endif
81*1ae08745Sheppo 
82*1ae08745Sheppo #include <sys/vio_mailbox.h>
83*1ae08745Sheppo #include <sys/vnet_common.h>
84*1ae08745Sheppo #include <sys/ethernet.h>
85*1ae08745Sheppo 
86*1ae08745Sheppo /*
87*1ae08745Sheppo  * Default message type.
88*1ae08745Sheppo  */
89*1ae08745Sheppo typedef struct def_msg {
90*1ae08745Sheppo 	uint64_t	data[8];
91*1ae08745Sheppo } def_msg_t;
92*1ae08745Sheppo 
93*1ae08745Sheppo /*
94*1ae08745Sheppo  * Currently only support one major/minor pair.
95*1ae08745Sheppo  */
96*1ae08745Sheppo #define	VSW_NUM_VER	1
97*1ae08745Sheppo 
98*1ae08745Sheppo typedef struct ver_sup {
99*1ae08745Sheppo 	uint32_t	ver_major:16,
100*1ae08745Sheppo 			ver_minor:16;
101*1ae08745Sheppo } ver_sup_t;
102*1ae08745Sheppo 
103*1ae08745Sheppo /*
104*1ae08745Sheppo  * Only support ETHER mtu at moment.
105*1ae08745Sheppo  */
106*1ae08745Sheppo #define	VSW_MTU		ETHERMAX
107*1ae08745Sheppo 
108*1ae08745Sheppo /*
109*1ae08745Sheppo  * Lane states.
110*1ae08745Sheppo  */
111*1ae08745Sheppo #define	VSW_LANE_INACTIV	0x0	/* No params set for lane */
112*1ae08745Sheppo 
113*1ae08745Sheppo #define	VSW_VER_INFO_SENT	0x1	/* Version # sent to peer */
114*1ae08745Sheppo #define	VSW_VER_INFO_RECV	0x2	/* Version # recv from peer */
115*1ae08745Sheppo #define	VSW_VER_ACK_RECV	0x4
116*1ae08745Sheppo #define	VSW_VER_ACK_SENT	0x8
117*1ae08745Sheppo #define	VSW_VER_NACK_RECV	0x10
118*1ae08745Sheppo #define	VSW_VER_NACK_SENT	0x20
119*1ae08745Sheppo 
120*1ae08745Sheppo #define	VSW_ATTR_INFO_SENT	0x40	/* Attributes sent to peer */
121*1ae08745Sheppo #define	VSW_ATTR_INFO_RECV	0x80	/* Peer attributes received */
122*1ae08745Sheppo #define	VSW_ATTR_ACK_SENT	0x100
123*1ae08745Sheppo #define	VSW_ATTR_ACK_RECV	0x200
124*1ae08745Sheppo #define	VSW_ATTR_NACK_SENT	0x400
125*1ae08745Sheppo #define	VSW_ATTR_NACK_RECV	0x800
126*1ae08745Sheppo 
127*1ae08745Sheppo #define	VSW_DRING_INFO_SENT	0x1000	/* Dring info sent to peer */
128*1ae08745Sheppo #define	VSW_DRING_INFO_RECV	0x2000	/* Dring info received */
129*1ae08745Sheppo #define	VSW_DRING_ACK_SENT	0x4000
130*1ae08745Sheppo #define	VSW_DRING_ACK_RECV	0x8000
131*1ae08745Sheppo #define	VSW_DRING_NACK_SENT	0x10000
132*1ae08745Sheppo #define	VSW_DRING_NACK_RECV	0x20000
133*1ae08745Sheppo 
134*1ae08745Sheppo #define	VSW_RDX_INFO_SENT	0x40000	/* RDX sent to peer */
135*1ae08745Sheppo #define	VSW_RDX_INFO_RECV	0x80000	/* RDX received from peer */
136*1ae08745Sheppo #define	VSW_RDX_ACK_SENT	0x100000
137*1ae08745Sheppo #define	VSW_RDX_ACK_RECV	0x200000
138*1ae08745Sheppo #define	VSW_RDX_NACK_SENT	0x400000
139*1ae08745Sheppo #define	VSW_RDX_NACK_RECV	0x800000
140*1ae08745Sheppo 
141*1ae08745Sheppo #define	VSW_MCST_INFO_SENT	0x1000000
142*1ae08745Sheppo #define	VSW_MCST_INFO_RECV	0x2000000
143*1ae08745Sheppo #define	VSW_MCST_ACK_SENT	0x4000000
144*1ae08745Sheppo #define	VSW_MCST_ACK_RECV	0x8000000
145*1ae08745Sheppo #define	VSW_MCST_NACK_SENT	0x10000000
146*1ae08745Sheppo #define	VSW_MCST_NACK_RECV	0x20000000
147*1ae08745Sheppo 
148*1ae08745Sheppo #define	VSW_LANE_ACTIVE		0x40000000	/* Lane open to xmit data */
149*1ae08745Sheppo 
150*1ae08745Sheppo /* Handshake milestones */
151*1ae08745Sheppo #define	VSW_MILESTONE0		0x1	/* ver info exchanged */
152*1ae08745Sheppo #define	VSW_MILESTONE1		0x2	/* attribute exchanged */
153*1ae08745Sheppo #define	VSW_MILESTONE2		0x4	/* dring info exchanged */
154*1ae08745Sheppo #define	VSW_MILESTONE3		0x8	/* rdx exchanged */
155*1ae08745Sheppo #define	VSW_MILESTONE4		0x10	/* handshake complete */
156*1ae08745Sheppo 
157*1ae08745Sheppo /*
158*1ae08745Sheppo  * Lane direction (relative to ourselves).
159*1ae08745Sheppo  */
160*1ae08745Sheppo #define	INBOUND			0x1
161*1ae08745Sheppo #define	OUTBOUND		0x2
162*1ae08745Sheppo 
163*1ae08745Sheppo /* Peer session id received */
164*1ae08745Sheppo #define	VSW_PEER_SESSION	0x1
165*1ae08745Sheppo 
166*1ae08745Sheppo /*
167*1ae08745Sheppo  * Maximum number of consecutive reads of data from channel
168*1ae08745Sheppo  */
169*1ae08745Sheppo #define	VSW_MAX_CHAN_READ	50
170*1ae08745Sheppo 
171*1ae08745Sheppo /*
172*1ae08745Sheppo  * LDC queue length
173*1ae08745Sheppo  */
174*1ae08745Sheppo #define	VSW_LDC_QLEN		1024
175*1ae08745Sheppo 
176*1ae08745Sheppo /*
177*1ae08745Sheppo  * Currently only support one ldc per port.
178*1ae08745Sheppo  */
179*1ae08745Sheppo #define	VSW_PORT_MAX_LDCS	1	/* max # of ldcs per port */
180*1ae08745Sheppo 
181*1ae08745Sheppo /*
182*1ae08745Sheppo  * Used for port add/deletion.
183*1ae08745Sheppo  */
184*1ae08745Sheppo #define	VSW_PORT_UPDATED	0x1
185*1ae08745Sheppo 
186*1ae08745Sheppo #define	LDC_TX_SUCCESS		0	/* ldc transmit success */
187*1ae08745Sheppo #define	LDC_TX_FAILURE		1	/* ldc transmit failure */
188*1ae08745Sheppo #define	LDC_TX_NORESOURCES	2	/* out of descriptors */
189*1ae08745Sheppo 
190*1ae08745Sheppo /* ID of the source of a frame being switched */
191*1ae08745Sheppo #define	VSW_PHYSDEV		1	/* physical device associated */
192*1ae08745Sheppo #define	VSW_VNETPORT		2	/* port connected to vnet (over ldc) */
193*1ae08745Sheppo #define	VSW_LOCALDEV		4	/* vsw configured as an eth interface */
194*1ae08745Sheppo 
195*1ae08745Sheppo /*
196*1ae08745Sheppo  * Descriptor ring info
197*1ae08745Sheppo  *
198*1ae08745Sheppo  * Each descriptor element has a pre-allocated data buffer
199*1ae08745Sheppo  * associated with it, into which data being transmitted is
200*1ae08745Sheppo  * copied. By pre-allocating we speed up the copying process.
201*1ae08745Sheppo  * The buffer is re-used once the peer has indicated that it is
202*1ae08745Sheppo  * finished with the descriptor.
203*1ae08745Sheppo  */
204*1ae08745Sheppo #define	VSW_RING_NUM_EL		512	/* Num of entries in ring */
205*1ae08745Sheppo #define	VSW_RING_EL_DATA_SZ	2048	/* Size of data section (bytes) */
206*1ae08745Sheppo #define	VSW_PRIV_SIZE	sizeof (vnet_private_desc_t)
207*1ae08745Sheppo #define	VSW_PUB_SIZE	sizeof (vnet_public_desc_t)
208*1ae08745Sheppo 
209*1ae08745Sheppo #define	VSW_MAX_COOKIES		((ETHERMTU >> MMU_PAGESHIFT) + 2)
210*1ae08745Sheppo 
211*1ae08745Sheppo /*
212*1ae08745Sheppo  * Private descriptor
213*1ae08745Sheppo  */
214*1ae08745Sheppo typedef struct vsw_private_desc {
215*1ae08745Sheppo 	uint64_t		dstate;
216*1ae08745Sheppo 	vnet_public_desc_t	*descp;
217*1ae08745Sheppo 	ldc_mem_handle_t	memhandle;
218*1ae08745Sheppo 	void			*datap;
219*1ae08745Sheppo 	uint64_t		datalen;
220*1ae08745Sheppo 	uint64_t		ncookies;
221*1ae08745Sheppo 	ldc_mem_cookie_t	memcookie[VSW_MAX_COOKIES];
222*1ae08745Sheppo 	int			bound;
223*1ae08745Sheppo } vsw_private_desc_t;
224*1ae08745Sheppo 
225*1ae08745Sheppo /*
226*1ae08745Sheppo  * Descriptor ring structure
227*1ae08745Sheppo  */
228*1ae08745Sheppo typedef struct dring_info {
229*1ae08745Sheppo 	struct	dring_info	*next;	/* next ring in chain */
230*1ae08745Sheppo 	kmutex_t		dlock;
231*1ae08745Sheppo 	uint32_t		num_descriptors;
232*1ae08745Sheppo 	uint32_t		descriptor_size;
233*1ae08745Sheppo 	uint32_t		options;
234*1ae08745Sheppo 	uint32_t		ncookies;
235*1ae08745Sheppo 	ldc_mem_cookie_t	cookie[1];
236*1ae08745Sheppo 
237*1ae08745Sheppo 	ldc_dring_handle_t	handle;
238*1ae08745Sheppo 	uint64_t		ident;	/* identifier sent to peer */
239*1ae08745Sheppo 	uint64_t		end_idx;	/* last idx processed */
240*1ae08745Sheppo 
241*1ae08745Sheppo 	/*
242*1ae08745Sheppo 	 * base address of private and public portions of the
243*1ae08745Sheppo 	 * ring (where appropriate), and data block.
244*1ae08745Sheppo 	 */
245*1ae08745Sheppo 	void			*pub_addr;	/* base of public section */
246*1ae08745Sheppo 	void			*priv_addr;	/* base of private section */
247*1ae08745Sheppo 	void			*data_addr;	/* base of data section */
248*1ae08745Sheppo 	size_t			data_sz;	/* size of data section */
249*1ae08745Sheppo } dring_info_t;
250*1ae08745Sheppo 
251*1ae08745Sheppo /*
252*1ae08745Sheppo  * Each ldc connection is comprised of two lanes, incoming
253*1ae08745Sheppo  * from a peer, and outgoing to that peer. Each lane shares
254*1ae08745Sheppo  * common ldc parameters and also has private lane-specific
255*1ae08745Sheppo  * parameters.
256*1ae08745Sheppo  */
257*1ae08745Sheppo typedef struct lane {
258*1ae08745Sheppo 	uint64_t	lstate;		/* Lane state */
259*1ae08745Sheppo 	uint32_t	ver_major:16,	/* Version major number */
260*1ae08745Sheppo 			ver_minor:16;	/* Version minor number */
261*1ae08745Sheppo 	uint64_t	seq_num;	/* Sequence number */
262*1ae08745Sheppo 	uint64_t	mtu;		/* ETHERMTU */
263*1ae08745Sheppo 	uint64_t	addr;		/* Unique physical address */
264*1ae08745Sheppo 	uint8_t		addr_type;	/* Only MAC address at moment */
265*1ae08745Sheppo 	uint8_t		xfer_mode;	/* Dring or Pkt based */
266*1ae08745Sheppo 	uint8_t		ack_freq;	/* Only non zero for Pkt based xfer */
267*1ae08745Sheppo 	dring_info_t	*dringp;	/* List of drings for this lane */
268*1ae08745Sheppo } lane_t;
269*1ae08745Sheppo 
270*1ae08745Sheppo /* channel drain states */
271*1ae08745Sheppo #define	VSW_LDC_INIT		0x1	/* Initial non-drain state */
272*1ae08745Sheppo #define	VSW_LDC_DRAINING	0x2	/* Channel draining */
273*1ae08745Sheppo 
274*1ae08745Sheppo /* ldc information associated with a vsw-port */
275*1ae08745Sheppo typedef struct vsw_ldc {
276*1ae08745Sheppo 	struct vsw_ldc		*ldc_next;	/* next ldc in the list */
277*1ae08745Sheppo 	struct vsw_port		*ldc_port;	/* associated port */
278*1ae08745Sheppo 	struct vsw		*ldc_vswp;	/* associated vsw */
279*1ae08745Sheppo 	kmutex_t		ldc_cblock;	/* sync callback processing */
280*1ae08745Sheppo 	kmutex_t		ldc_txlock;	/* sync transmits */
281*1ae08745Sheppo 	uint64_t		ldc_id;		/* channel number */
282*1ae08745Sheppo 	ldc_handle_t		ldc_handle;	/* channel handle */
283*1ae08745Sheppo 	kmutex_t		drain_cv_lock;
284*1ae08745Sheppo 	kcondvar_t		drain_cv;	/* channel draining */
285*1ae08745Sheppo 	int			drain_state;
286*1ae08745Sheppo 	uint32_t		hphase;		/* handshake phase */
287*1ae08745Sheppo 	int			hcnt;		/* # handshake attempts */
288*1ae08745Sheppo 	ldc_status_t		ldc_status;	/* channel status */
289*1ae08745Sheppo 	uint64_t		local_session;	/* Our session id */
290*1ae08745Sheppo 	uint64_t		peer_session;	/* Our peers session id */
291*1ae08745Sheppo 	uint8_t			session_status;	/* Session recv'd, sent */
292*1ae08745Sheppo 	kmutex_t		hss_lock;
293*1ae08745Sheppo 	uint32_t		hss_id;		/* Handshake session id */
294*1ae08745Sheppo 	uint64_t		next_ident;	/* Next dring ident # to use */
295*1ae08745Sheppo 	lane_t			lane_in;	/* Inbound lane */
296*1ae08745Sheppo 	lane_t			lane_out;	/* Outbound lane */
297*1ae08745Sheppo 	uint8_t			dev_class;	/* Peer device class */
298*1ae08745Sheppo } vsw_ldc_t;
299*1ae08745Sheppo 
300*1ae08745Sheppo /* list of ldcs per port */
301*1ae08745Sheppo typedef struct vsw_ldc_list {
302*1ae08745Sheppo 	vsw_ldc_t	*head;		/* head of the list */
303*1ae08745Sheppo 	krwlock_t	lockrw;		/* sync access(rw) to the list */
304*1ae08745Sheppo 	int		num_ldcs;	/* number of ldcs in the list */
305*1ae08745Sheppo } vsw_ldc_list_t;
306*1ae08745Sheppo 
307*1ae08745Sheppo /* multicast addresses port is interested in */
308*1ae08745Sheppo typedef struct mcst_addr {
309*1ae08745Sheppo 	struct mcst_addr	*nextp;
310*1ae08745Sheppo 	uint64_t		addr;
311*1ae08745Sheppo } mcst_addr_t;
312*1ae08745Sheppo 
313*1ae08745Sheppo /* Port detach states */
314*1ae08745Sheppo #define	VSW_PORT_INIT		0x1	/* Initial non-detach state */
315*1ae08745Sheppo #define	VSW_PORT_DETACHING	0x2	/* In process of being detached */
316*1ae08745Sheppo #define	VSW_PORT_DETACHABLE	0x4	/* Safe to detach */
317*1ae08745Sheppo 
318*1ae08745Sheppo /* port information associated with a vsw */
319*1ae08745Sheppo typedef struct vsw_port {
320*1ae08745Sheppo 	int			p_instance;	/* port instance */
321*1ae08745Sheppo 	struct vsw_port		*p_next;	/* next port in the list */
322*1ae08745Sheppo 	struct vsw		*p_vswp;	/* associated vsw */
323*1ae08745Sheppo 	vsw_ldc_list_t		p_ldclist;	/* list of ldcs for this port */
324*1ae08745Sheppo 
325*1ae08745Sheppo 	kmutex_t		tx_lock;	/* transmit lock */
326*1ae08745Sheppo 	int			(*transmit)(vsw_ldc_t *, mblk_t *);
327*1ae08745Sheppo 
328*1ae08745Sheppo 	int			state;		/* port state */
329*1ae08745Sheppo 	kmutex_t		state_lock;
330*1ae08745Sheppo 	kcondvar_t		state_cv;
331*1ae08745Sheppo 
332*1ae08745Sheppo 	int			ref_cnt;	/* # of active references */
333*1ae08745Sheppo 	kmutex_t		ref_lock;
334*1ae08745Sheppo 	kcondvar_t		ref_cv;
335*1ae08745Sheppo 
336*1ae08745Sheppo 	kmutex_t		mca_lock;	/* multicast lock */
337*1ae08745Sheppo 	mcst_addr_t		*mcap;		/* list of multicast addrs */
338*1ae08745Sheppo 
339*1ae08745Sheppo 	/*
340*1ae08745Sheppo 	 * mac address of the port & connected device
341*1ae08745Sheppo 	 */
342*1ae08745Sheppo 	struct ether_addr	p_macaddr;
343*1ae08745Sheppo } vsw_port_t;
344*1ae08745Sheppo 
345*1ae08745Sheppo /* list of ports per vsw */
346*1ae08745Sheppo typedef struct vsw_port_list {
347*1ae08745Sheppo 	vsw_port_t	*head;		/* head of the list */
348*1ae08745Sheppo 	krwlock_t	lockrw;		/* sync access(rw) to the list */
349*1ae08745Sheppo 	int		num_ports;	/* number of ports in the list */
350*1ae08745Sheppo } vsw_port_list_t;
351*1ae08745Sheppo 
352*1ae08745Sheppo /*
353*1ae08745Sheppo  * Taskq control message
354*1ae08745Sheppo  */
355*1ae08745Sheppo typedef struct vsw_ctrl_task {
356*1ae08745Sheppo 	vsw_ldc_t	*ldcp;
357*1ae08745Sheppo 	def_msg_t	pktp;
358*1ae08745Sheppo 	uint32_t	hss_id;
359*1ae08745Sheppo } vsw_ctrl_task_t;
360*1ae08745Sheppo 
361*1ae08745Sheppo /*
362*1ae08745Sheppo  * Number of hash chains in the multicast forwarding database.
363*1ae08745Sheppo  */
364*1ae08745Sheppo #define		VSW_NCHAINS	8
365*1ae08745Sheppo 
366*1ae08745Sheppo /*
367*1ae08745Sheppo  * State of interface if switch plumbed as network device.
368*1ae08745Sheppo  */
369*1ae08745Sheppo #define		VSW_IF_UP	0x1	/* Interface UP */
370*1ae08745Sheppo #define		VSW_IF_PROMISC	0x2	/* Interface in promiscious mode */
371*1ae08745Sheppo 
372*1ae08745Sheppo #define		VSW_U_P(state)	\
373*1ae08745Sheppo 			(state == (VSW_IF_UP | VSW_IF_PROMISC))
374*1ae08745Sheppo 
375*1ae08745Sheppo /*
376*1ae08745Sheppo  * Switching modes.
377*1ae08745Sheppo  */
378*1ae08745Sheppo #define		VSW_LAYER2		0x1	/* Layer 2 - MAC switching */
379*1ae08745Sheppo #define		VSW_LAYER2_PROMISC	0x2	/* Layer 2 + promisc mode */
380*1ae08745Sheppo #define		VSW_LAYER3		0x4	/* Layer 3 - IP switching */
381*1ae08745Sheppo 
382*1ae08745Sheppo #define		NUM_SMODES	3	/* number of switching modes */
383*1ae08745Sheppo 
384*1ae08745Sheppo /*
385*1ae08745Sheppo  * Bits indicating which properties we've read from MD.
386*1ae08745Sheppo  */
387*1ae08745Sheppo #define		VSW_MD_PHYSNAME	0x1
388*1ae08745Sheppo #define		VSW_MD_MACADDR	0x2
389*1ae08745Sheppo #define		VSW_MD_SMODE	0x4
390*1ae08745Sheppo 
391*1ae08745Sheppo /*
392*1ae08745Sheppo  * vsw instance state information.
393*1ae08745Sheppo  */
394*1ae08745Sheppo typedef struct	vsw {
395*1ae08745Sheppo 	int			instance;	/* instance # */
396*1ae08745Sheppo 	dev_info_t		*dip;		/* associated dev_info */
397*1ae08745Sheppo 	struct vsw		*next;		/* next in list */
398*1ae08745Sheppo 	char			physname[LIFNAMSIZ];	/* phys-dev */
399*1ae08745Sheppo 	uint8_t			smode[NUM_SMODES];	/* switching mode */
400*1ae08745Sheppo 	int			smode_idx;	/* curr pos in smode array */
401*1ae08745Sheppo 	uint8_t			mdprops;	/* bitmask of props found */
402*1ae08745Sheppo 	vsw_port_list_t		plist;		/* associated ports */
403*1ae08745Sheppo 	ddi_taskq_t		*taskq_p;	/* VIO ctrl msg taskq */
404*1ae08745Sheppo 	mod_hash_t		*fdb;		/* forwarding database */
405*1ae08745Sheppo 
406*1ae08745Sheppo 	mod_hash_t		*mfdb;		/* multicast FDB */
407*1ae08745Sheppo 	krwlock_t		mfdbrw;		/* rwlock for mFDB */
408*1ae08745Sheppo 
409*1ae08745Sheppo 	/* mac layer */
410*1ae08745Sheppo 	mac_handle_t		mh;
411*1ae08745Sheppo 	mac_rx_handle_t		mrh;
412*1ae08745Sheppo 	mac_notify_handle_t	mnh;
413*1ae08745Sheppo 	const mac_txinfo_t	*txinfo;	/* MAC tx routine */
414*1ae08745Sheppo 
415*1ae08745Sheppo 	/* Initial promisc setting of interface */
416*1ae08745Sheppo 	boolean_t		init_promisc;
417*1ae08745Sheppo 
418*1ae08745Sheppo 	/* Machine Description updates  */
419*1ae08745Sheppo 	mdeg_node_spec_t	*inst_spec;
420*1ae08745Sheppo 	mdeg_handle_t		mdeg_hdl;
421*1ae08745Sheppo 
422*1ae08745Sheppo 	/* if configured as an ethernet interface */
423*1ae08745Sheppo 	mac_t			*if_macp;	/* MAC structure */
424*1ae08745Sheppo 	mac_resource_handle_t	if_mrh;
425*1ae08745Sheppo 	struct ether_addr	if_addr;	/* interface address */
426*1ae08745Sheppo 	krwlock_t		if_lockrw;
427*1ae08745Sheppo 	uint8_t			if_state;	/* interface state */
428*1ae08745Sheppo 
429*1ae08745Sheppo 	/* multicast addresses when configured as eth interface */
430*1ae08745Sheppo 	kmutex_t		mca_lock;	/* multicast lock */
431*1ae08745Sheppo 	mcst_addr_t		*mcap;		/* list of multicast addrs */
432*1ae08745Sheppo } vsw_t;
433*1ae08745Sheppo 
434*1ae08745Sheppo 
435*1ae08745Sheppo /*
436*1ae08745Sheppo  * Ethernet broadcast address definition.
437*1ae08745Sheppo  */
438*1ae08745Sheppo static	struct	ether_addr	etherbroadcastaddr = {
439*1ae08745Sheppo 	0xff, 0xff, 0xff, 0xff, 0xff, 0xff
440*1ae08745Sheppo };
441*1ae08745Sheppo 
442*1ae08745Sheppo #define	IS_BROADCAST(ehp) \
443*1ae08745Sheppo 	(ether_cmp(&ehp->ether_dhost, &etherbroadcastaddr) == 0)
444*1ae08745Sheppo #define	IS_MULTICAST(ehp) \
445*1ae08745Sheppo 	((ehp->ether_dhost.ether_addr_octet[0] & 01) == 1)
446*1ae08745Sheppo 
447*1ae08745Sheppo #define	READ_ENTER(x)	rw_enter(x, RW_READER)
448*1ae08745Sheppo #define	WRITE_ENTER(x)	rw_enter(x, RW_WRITER)
449*1ae08745Sheppo #define	RW_EXIT(x)	rw_exit(x)
450*1ae08745Sheppo 
451*1ae08745Sheppo #ifdef	__cplusplus
452*1ae08745Sheppo }
453*1ae08745Sheppo #endif
454*1ae08745Sheppo 
455*1ae08745Sheppo #endif	/* _VSW_H */
456