Print this page
11490 SRS ring polling disabled for VLANs
11491 Want DLS bypass for VLAN traffic
11492 add VLVF bypass to ixgbe core
2869 duplicate packets with vnics over aggrs
11489 DLS stat delete and aggr kstat can deadlock
Portions contributed by: Theo Schlossnagle <jesus@omniti.com>
Reviewed by: Patrick Mooney <patrick.mooney@joyent.com>
Reviewed by: Robert Mustacchi <rm@joyent.com>
Reviewed by: Dan McDonald <danmcd@joyent.com>
Split |
Close |
Expand all |
Collapse all |
--- old/usr/src/uts/common/sys/mac_client_impl.h
+++ new/usr/src/uts/common/sys/mac_client_impl.h
1 1 /*
2 2 * CDDL HEADER START
3 3 *
4 4 * The contents of this file are subject to the terms of the
5 5 * Common Development and Distribution License (the "License").
6 6 * You may not use this file except in compliance with the License.
7 7 *
8 8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 9 * or http://www.opensolaris.org/os/licensing.
10 10 * See the License for the specific language governing permissions
11 11 * and limitations under the License.
12 12 *
13 13 * When distributing Covered Code, include this CDDL HEADER in each
14 14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 15 * If applicable, add the following below this CDDL HEADER, with the
16 16 * fields enclosed by brackets "[]" replaced with your own identifying
↓ open down ↓ |
16 lines elided |
↑ open up ↑ |
17 17 * information: Portions Copyright [yyyy] [name of copyright owner]
18 18 *
19 19 * CDDL HEADER END
20 20 */
21 21 /*
22 22 * Copyright 2010 Sun Microsystems, Inc. All rights reserved.
23 23 * Use is subject to license terms.
24 24 * Copyright (c) 2012, Joyent, Inc. All rights reserved.
25 25 */
26 26 /*
27 - * Copyright (c) 2013, Joyent, Inc. All rights reserved.
27 + * Copyright 2018 Joyent, Inc.
28 28 */
29 29
30 30 #ifndef _SYS_MAC_CLIENT_IMPL_H
31 31 #define _SYS_MAC_CLIENT_IMPL_H
32 32
33 33 #include <sys/modhash.h>
34 34 #include <sys/mac_client.h>
35 35 #include <sys/mac_provider.h>
36 36 #include <sys/mac.h>
37 37 #include <sys/mac_impl.h>
38 38 #include <sys/mac_stat.h>
39 39 #include <net/if.h>
40 40 #include <sys/mac_flow_impl.h>
41 41
42 42 #ifdef __cplusplus
43 43 extern "C" {
44 44 #endif
45 45
46 46 extern kmem_cache_t *mac_client_impl_cache;
47 47 extern kmem_cache_t *mac_unicast_impl_cache;
48 48 extern kmem_cache_t *mac_promisc_impl_cache;
49 49
↓ open down ↓ |
12 lines elided |
↑ open up ↑ |
50 50 /*
51 51 * Need a list to chain all VIDs assigned to a client. Normally, one
52 52 * MAC client only has one VID. But vsw might need multiple VIDs.
53 53 */
54 54 typedef struct mac_unicast_impl_s { /* Protected by */
55 55 struct mac_unicast_impl_s *mui_next; /* SL */
56 56 mac_address_t *mui_map; /* SL */
57 57 uint16_t mui_vid; /* SL */
58 58 } mac_unicast_impl_t;
59 59
60 -#define MAC_CLIENT_FLAGS_PRIMARY 0X0001
60 +#define MAC_CLIENT_FLAGS_PRIMARY 0x0001
61 61 #define MAC_CLIENT_FLAGS_VNIC_PRIMARY 0x0002
62 62 #define MAC_CLIENT_FLAGS_MULTI_PRIMARY 0x0004
63 63 #define MAC_CLIENT_FLAGS_PASSIVE_PRIMARY 0x0008
64 64
65 65 /*
66 66 * One of these is instantiated per MAC client promiscuous callback.
67 67 *
68 68 * Each element of this structure belongs to two linked list. One
69 69 * for the mac_client_impl_t (mci_promisc_list) which created allocated
70 70 * the callback, the other for the mac_impl_t (mi_promisc_list) corresponding
71 71 * to the MAC client.
72 72 * The former allows us to do bookkeeping, the latter allows us
73 73 * to more efficiently dispatch packets to the promiscuous callbacks.
74 74 */
75 75 typedef struct mac_promisc_impl_s { /* Protected by */
76 76 mac_cb_t mpi_mci_link; /* mi_promisc_lock */
77 77 mac_cb_t mpi_mi_link; /* mi_promisc_lock */
78 78 mac_client_promisc_type_t mpi_type; /* WO */
79 79 mac_rx_t mpi_fn; /* WO */
80 80 void *mpi_arg; /* WO */
81 81 struct mac_client_impl_s *mpi_mcip; /* WO */
82 82 boolean_t mpi_no_tx_loop; /* WO */
83 83 boolean_t mpi_no_phys; /* WO */
84 84 boolean_t mpi_strip_vlan_tag; /* WO */
85 85 boolean_t mpi_no_copy; /* WO */
86 86 } mac_promisc_impl_t;
87 87
88 88 typedef union mac_tx_percpu_s {
89 89 struct {
90 90 kmutex_t _pcpu_tx_lock;
91 91 uint_t _pcpu_tx_refcnt;
92 92 } pcpu_lr;
93 93 uchar_t pcpu_pad[64];
94 94 } mac_tx_percpu_t;
95 95
96 96 #define pcpu_tx_lock pcpu_lr._pcpu_tx_lock
97 97 #define pcpu_tx_refcnt pcpu_lr._pcpu_tx_refcnt
98 98
99 99 /*
100 100 * One of these is instantiated for each MAC client.
101 101 */
102 102 struct mac_client_impl_s { /* Protected by */
103 103 struct mac_client_impl_s *mci_client_next; /* mi_rw_lock */
104 104 char mci_name[MAXNAMELEN]; /* mi_rw_lock */
105 105 /*
106 106 * This flow entry will contain all the internal constructs
107 107 * such as SRS etc. for this MAC client. The MAC client may
108 108 * have more than one flow corresponding to each upper client
109 109 * sharing this mac_client_impl_t.
110 110 */
111 111 flow_entry_t *mci_flent; /* mi_rw_lock */
112 112 struct mac_impl_s *mci_mip; /* WO */
113 113 /*
114 114 * If this is a client that has a pass thru MAC (e.g. a VNIC),
115 115 * then we also keep the handle for the client's upper MAC.
116 116 */
117 117 struct mac_impl_s *mci_upper_mip; /* WO */
118 118
119 119 uint32_t mci_state_flags; /* WO */
120 120 mac_rx_t mci_rx_fn; /* Rx Quiescence */
121 121 void *mci_rx_arg; /* Rx Quiescence */
122 122 mac_direct_rx_t mci_direct_rx_fn; /* SL */
123 123 void *mci_direct_rx_arg; /* SL */
↓ open down ↓ |
53 lines elided |
↑ open up ↑ |
124 124 mac_rx_t mci_rx_p_fn; /* Rx Quiescence */
125 125 void *mci_rx_p_arg; /* Rx Quiescence */
126 126 void *mci_p_unicast_list;
127 127
128 128 mac_cb_t *mci_promisc_list; /* mi_promisc_lock */
129 129
130 130 mac_address_t *mci_unicast;
131 131 uint32_t mci_flags; /* SL */
132 132 krwlock_t mci_rw_lock;
133 133 mac_unicast_impl_t *mci_unicast_list; /* mci_rw_lock */
134 +
134 135 /*
135 136 * The mac_client_impl_t may be shared by multiple clients, i.e
136 137 * multiple VLANs sharing the same MAC client. In this case the
137 - * address/vid tubles differ and are each associated with their
138 + * address/vid tuples differ and are each associated with their
138 139 * own flow entry, but the rest underlying components SRS, etc,
139 140 * are common.
141 + *
142 + * This is only needed to support sun4v vsw. There are several
143 + * places in MAC we could simplify the code if we removed
144 + * sun4v support.
140 145 */
141 146 flow_entry_t *mci_flent_list; /* mci_rw_lock */
142 147 uint_t mci_nflents; /* mci_rw_lock */
143 148 uint_t mci_nvids; /* mci_rw_lock */
144 149 volatile uint32_t mci_vidcache; /* VID cache */
145 150
146 151 /* Resource Management Functions */
147 152 mac_resource_add_t mci_resource_add; /* SL */
148 153 mac_resource_remove_t mci_resource_remove; /* SL */
149 154 mac_resource_quiesce_t mci_resource_quiesce; /* SL */
150 155 mac_resource_restart_t mci_resource_restart; /* SL */
151 156 mac_resource_bind_t mci_resource_bind; /* SL */
152 157 void *mci_resource_arg; /* SL */
153 158
154 159
155 160 /* Tx notify callback */
156 161 kmutex_t mci_tx_cb_lock;
157 162 mac_cb_info_t mci_tx_notify_cb_info; /* cb list info */
158 163 mac_cb_t *mci_tx_notify_cb_list; /* The cb list */
159 164 uintptr_t mci_tx_notify_id;
160 165
161 166 /* per MAC client stats */ /* None */
162 167 mac_misc_stats_t mci_misc_stat;
163 168
164 169 flow_tab_t *mci_subflow_tab; /* Rx quiescence */
165 170
166 171 /*
167 172 * Priority range for this MAC client. This the range
168 173 * corresponding to the priority configured (nr_flow_priority).
169 174 */
170 175 pri_t mci_min_pri;
171 176 pri_t mci_max_pri;
172 177
173 178 /*
174 179 * Hybrid I/O related definitions.
175 180 */
176 181 mac_share_handle_t mci_share;
177 182
178 183 /* for multicast support */
179 184 struct mac_mcast_addrs_s *mci_mcast_addrs; /* mi_rw_lock */
180 185
181 186 /*
182 187 * Mac protection related fields
183 188 */
184 189 kmutex_t mci_protect_lock;
185 190 uint32_t mci_protect_flags; /* SL */
186 191 in6_addr_t mci_v6_mac_token; /* SL */
187 192 in6_addr_t mci_v6_local_addr; /* SL */
188 193 avl_tree_t mci_v4_pending_txn; /* mci_protect_lock */
189 194 avl_tree_t mci_v4_completed_txn; /* mci_protect_lock */
190 195 avl_tree_t mci_v4_dyn_ip; /* mci_protect_lock */
191 196 avl_tree_t mci_v6_pending_txn; /* mci_protect_lock */
192 197 avl_tree_t mci_v6_cid; /* mci_protect_lock */
193 198 avl_tree_t mci_v6_dyn_ip; /* mci_protect_lock */
194 199 avl_tree_t mci_v6_slaac_ip; /* mci_protect_lock */
195 200 timeout_id_t mci_txn_cleanup_tid; /* mci_protect_lock */
196 201
197 202 /*
198 203 * Protected by mci_tx_pcpu[0].pcpu_tx_lock
199 204 */
200 205 uint_t mci_tx_flag;
201 206 kcondvar_t mci_tx_cv;
202 207
203 208 /* Must be last in the structure for dynamic sizing */
204 209 mac_tx_percpu_t mci_tx_pcpu[1]; /* SL */
205 210 };
206 211
207 212 #define MAC_CLIENT_IMPL_SIZE \
208 213 (sizeof (mac_client_impl_t) + \
209 214 (mac_tx_percpu_cnt * sizeof (mac_tx_percpu_t)))
210 215
211 216 extern int mac_tx_percpu_cnt;
212 217
213 218 #define MCIP_TX_SRS(mcip) \
214 219 ((mcip)->mci_flent == NULL ? NULL : (mcip)->mci_flent->fe_tx_srs)
215 220
216 221 /* Defensive coding, non-null mcip_flent could be an assert */
↓ open down ↓ |
67 lines elided |
↑ open up ↑ |
217 222
218 223 #define MCIP_DATAPATH_SETUP(mcip) \
219 224 ((mcip)->mci_flent == NULL ? B_FALSE : \
220 225 !((mcip)->mci_flent->fe_flags & FE_MC_NO_DATAPATH))
221 226
222 227 #define MCIP_RESOURCE_PROPS(mcip) \
223 228 ((mcip)->mci_flent == NULL ? NULL : \
224 229 &(mcip)->mci_flent->fe_resource_props)
225 230
226 231 #define MCIP_EFFECTIVE_PROPS(mcip) \
227 - (mcip->mci_flent == NULL ? NULL : \
232 + (mcip->mci_flent == NULL ? NULL : \
228 233 &(mcip)->mci_flent->fe_effective_props)
229 234
230 235 #define MCIP_RESOURCE_PROPS_MASK(mcip) \
231 236 ((mcip)->mci_flent == NULL ? 0 : \
232 237 (mcip)->mci_flent->fe_resource_props.mrp_mask)
233 238
234 239 #define MCIP_RESOURCE_PROPS_MAXBW(mcip) \
235 240 ((mcip)->mci_flent == NULL ? 0 : \
236 241 (mcip)->mci_flent->fe_resource_props.mrp_maxbw)
237 242
238 243 #define MCIP_RESOURCE_PROPS_PRIORITY(mcip) \
239 244 ((mcip)->mci_flent == NULL ? 0 : \
240 245 (mcip)->mci_flent->fe_resource_props.mrp_priority)
241 246
242 247 #define MCIP_RESOURCE_PROPS_CPUS(mcip) \
243 248 ((mcip)->mci_flent == NULL ? 0 : \
244 249 &(mcip)->mci_flent->fe_resource_props.mrp_cpus)
245 250
246 251 #define MCIP_RESOURCE_PROPS_NCPUS(mcip) \
247 252 ((mcip)->mci_flent == NULL ? 0 : \
248 253 (mcip)->mci_flent->fe_resource_props.mrp_ncpus)
249 254
250 255 #define MCIP_RESOURCE_PROPS_CPU(mcip) \
251 256 ((mcip)->mci_flent == NULL ? 0 : \
252 257 (mcip)->mci_flent->fe_resource_props.mrp_ncpu)
253 258
254 259 /*
255 260 * We validate the VLAN id of the packet w.r.t the client's vid,
256 261 * if required (i.e. !MCIS_DISABLE_TX_VID_CHECK). DLS clients
257 262 * will have MCIS_DISABLE_TX_VID_CHECK set.
258 263 * (In the case of aggr when we get back packets, due to
259 264 * the underlying driver being flow controlled, we won't
260 265 * drop the packet even if it is VLAN tagged as we
261 266 * don't set MCIS_DISABLE_TX_VID_CHECK for an aggr.)
262 267 */
263 268 #define MAC_VID_CHECK_NEEDED(mcip) \
264 269 (((mcip)->mci_state_flags & MCIS_DISABLE_TX_VID_CHECK) == 0 && \
265 270 (mcip)->mci_mip->mi_info.mi_nativemedia == DL_ETHER)
266 271
267 272 #define MAC_VID_CHECK(mcip, mp, err) { \
268 273 if (ntohs(((struct ether_header *)(mp)->b_rptr)->ether_type) == \
269 274 ETHERTYPE_VLAN) { \
270 275 /* \
271 276 * err is set to EINVAL (so the caller can take the \
272 277 * appropriate action. e.g. freemsg()) for two cases: \
273 278 * -client is not responsible for filling in the vid. \
274 279 * -client is responsible for filling in the vid, but \
275 280 * the vid doesn't match the vid of the MAC client. \
276 281 */ \
277 282 (err) = EINVAL; \
278 283 if (((mcip)->mci_state_flags & MCIS_TAG_DISABLE) != 0) {\
279 284 struct ether_vlan_header *evhp; \
280 285 uint16_t vlanid; \
281 286 \
282 287 evhp = (struct ether_vlan_header *)(mp)->b_rptr;\
283 288 vlanid = VLAN_ID(ntohs(evhp->ether_tci)); \
284 289 if (mac_client_check_flow_vid((mcip), vlanid)) \
285 290 (err) = 0; \
286 291 } \
287 292 } \
288 293 }
289 294
290 295 /*
291 296 * To allow the hot path to not grab any additional locks, we keep a single
292 297 * entry VLAN ID cache that caches whether or not a given VID belongs to a
293 298 * MAC client.
294 299 */
295 300 #define MCIP_VIDCACHE_VALIDSHIFT 31
296 301 #define MCIP_VIDCACHE_VIDSHIFT 1
297 302 #define MCIP_VIDCACHE_VIDMASK (UINT16_MAX << MCIP_VIDCACHE_VIDSHIFT)
298 303 #define MCIP_VIDCACHE_BOOLSHIFT 0
299 304
300 305 #define MCIP_VIDCACHE_INVALID 0
301 306
302 307 #define MCIP_VIDCACHE_CACHE(vid, bool) \
303 308 ((1U << MCIP_VIDCACHE_VALIDSHIFT) | \
304 309 ((vid) << MCIP_VIDCACHE_VIDSHIFT) | \
305 310 ((bool) ? (1U << MCIP_VIDCACHE_BOOLSHIFT) : 0))
↓ open down ↓ |
68 lines elided |
↑ open up ↑ |
306 311
307 312 #define MCIP_VIDCACHE_ISVALID(v) ((v) & (1U << MCIP_VIDCACHE_VALIDSHIFT))
308 313 #define MCIP_VIDCACHE_VID(v) \
309 314 (((v) & MCIP_VIDCACHE_VIDMASK) >> MCIP_VIDCACHE_VIDSHIFT)
310 315 #define MCIP_VIDCACHE_BOOL(v) ((v) & (1U << MCIP_VIDCACHE_BOOLSHIFT))
311 316
312 317 #define MAC_TAG_NEEDED(mcip) \
313 318 (((mcip)->mci_state_flags & MCIS_TAG_DISABLE) == 0 && \
314 319 (mcip)->mci_nvids == 1) \
315 320
321 +/*
322 + * MAC Client Implementation State (mci_state_flags)
323 + *
324 + * MCIS_IS_VNIC
325 + *
326 + * The client is a VNIC.
327 + *
328 + * MCIS_EXCLUSIVE
329 + *
330 + * The client has exclusive control over the MAC, such that it is
331 + * the sole client of the MAC.
332 + *
333 + * MCIS_TAG_DISABLE
334 + *
335 + * MAC will not add VLAN tags to outgoing traffic. If this flag
336 + * is set it is up to the client to add the correct VLAN tag.
337 + *
338 + * MCIS_STRIP_DISABLE
339 + *
340 + * MAC will not strip the VLAN tags on incoming traffic before
341 + * passing it to mci_rx_fn. This only applies to non-bypass
342 + * traffic.
343 + *
344 + * MCIS_IS_AGGR_PORT
345 + *
346 + * The client represents a port on an aggr.
347 + *
348 + * MCIS_CLIENT_POLL_CAPABLE
349 + *
350 + * The client is capable of polling the Rx TCP/UDP softrings.
351 + *
352 + * MCIS_DESC_LOGGED
353 + *
354 + * This flag is set when the client's link info has been logged
355 + * by the mac_log_linkinfo() timer. This ensures that the
356 + * client's link info is only logged once.
357 + *
358 + * MCIS_SHARE_BOUND
359 + *
360 + * This client has an HIO share bound to it.
361 + *
362 + * MCIS_DISABLE_TX_VID_CHECK
363 + *
364 + * MAC will not check the VID of the client's Tx traffic.
365 + *
366 + * MCIS_USE_DATALINK_NAME
367 + *
368 + * The client is using the same name as its underlying MAC. This
369 + * happens when dlmgmtd is unreachable during client creation.
370 + *
371 + * MCIS_UNICAST_HW
372 + *
373 + * The client requires MAC address hardware classification. This
374 + * is only used by sun4v vsw.
375 + *
376 + * MCIS_IS_AGGR_CLIENT
377 + *
378 + * The client sits atop an aggr.
379 + *
380 + * MCIS_RX_BYPASS_DISABLE
381 + *
382 + * Do not allow the client to enable DLS bypass.
383 + *
384 + * MCIS_NO_UNICAST_ADDR
385 + *
386 + * This client has no MAC unicast addresss associated with it.
387 + *
388 + */
316 389 /* MCI state flags */
317 390 #define MCIS_IS_VNIC 0x0001
318 391 #define MCIS_EXCLUSIVE 0x0002
319 392 #define MCIS_TAG_DISABLE 0x0004
320 393 #define MCIS_STRIP_DISABLE 0x0008
321 394 #define MCIS_IS_AGGR_PORT 0x0010
322 395 #define MCIS_CLIENT_POLL_CAPABLE 0x0020
323 396 #define MCIS_DESC_LOGGED 0x0040
324 397 #define MCIS_SHARE_BOUND 0x0080
325 398 #define MCIS_DISABLE_TX_VID_CHECK 0x0100
326 399 #define MCIS_USE_DATALINK_NAME 0x0200
327 400 #define MCIS_UNICAST_HW 0x0400
328 -#define MCIS_IS_AGGR 0x0800
401 +#define MCIS_IS_AGGR_CLIENT 0x0800
329 402 #define MCIS_RX_BYPASS_DISABLE 0x1000
330 403 #define MCIS_NO_UNICAST_ADDR 0x2000
331 404
332 405 /* Mac protection flags */
333 406 #define MPT_FLAG_V6_LOCAL_ADDR_SET 0x0001
334 407 #define MPT_FLAG_PROMISC_FILTERED 0x0002
335 408
336 409 /* in mac_client.c */
337 410 extern void mac_promisc_client_dispatch(mac_client_impl_t *, mblk_t *);
338 411 extern void mac_client_init(void);
339 412 extern void mac_client_fini(void);
340 413 extern void mac_promisc_dispatch(mac_impl_t *, mblk_t *,
341 414 mac_client_impl_t *);
342 415
343 416 extern int mac_validate_props(mac_impl_t *, mac_resource_props_t *);
344 417
345 418 extern mac_client_impl_t *mac_vnic_lower(mac_impl_t *);
346 419 extern mac_client_impl_t *mac_primary_client_handle(mac_impl_t *);
347 420 extern uint16_t i_mac_flow_vid(flow_entry_t *);
348 421 extern boolean_t i_mac_capab_get(mac_handle_t, mac_capab_t, void *);
349 422
350 423 extern void mac_unicast_update_clients(mac_impl_t *, mac_address_t *);
351 424 extern void mac_update_resources(mac_resource_props_t *,
352 425 mac_resource_props_t *, boolean_t);
353 426
354 427 boolean_t mac_client_check_flow_vid(mac_client_impl_t *, uint16_t);
355 428
356 429 extern boolean_t mac_is_primary_client(mac_client_impl_t *);
357 430
358 431 extern int mac_client_set_rings_prop(mac_client_impl_t *,
359 432 mac_resource_props_t *, mac_resource_props_t *);
360 433 extern void mac_set_prim_vlan_rings(mac_impl_t *, mac_resource_props_t *);
361 434
362 435 #ifdef __cplusplus
363 436 }
364 437 #endif
365 438
366 439 #endif /* _SYS_MAC_CLIENT_IMPL_H */
↓ open down ↓ |
28 lines elided |
↑ open up ↑ |
XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX