xref: /linux-6.15/include/net/switchdev.h (revision 80bebebd)
1 /* SPDX-License-Identifier: GPL-2.0-or-later */
2 /*
3  * include/net/switchdev.h - Switch device API
4  * Copyright (c) 2014-2015 Jiri Pirko <[email protected]>
5  * Copyright (c) 2014-2015 Scott Feldman <[email protected]>
6  */
7 #ifndef _LINUX_SWITCHDEV_H_
8 #define _LINUX_SWITCHDEV_H_
9 
10 #include <linux/netdevice.h>
11 #include <linux/notifier.h>
12 #include <linux/list.h>
13 #include <net/ip_fib.h>
14 
15 #define SWITCHDEV_F_NO_RECURSE		BIT(0)
16 #define SWITCHDEV_F_SKIP_EOPNOTSUPP	BIT(1)
17 #define SWITCHDEV_F_DEFER		BIT(2)
18 
19 enum switchdev_attr_id {
20 	SWITCHDEV_ATTR_ID_UNDEFINED,
21 	SWITCHDEV_ATTR_ID_PORT_STP_STATE,
22 	SWITCHDEV_ATTR_ID_PORT_BRIDGE_FLAGS,
23 	SWITCHDEV_ATTR_ID_PORT_PRE_BRIDGE_FLAGS,
24 	SWITCHDEV_ATTR_ID_PORT_MROUTER,
25 	SWITCHDEV_ATTR_ID_BRIDGE_AGEING_TIME,
26 	SWITCHDEV_ATTR_ID_BRIDGE_VLAN_FILTERING,
27 	SWITCHDEV_ATTR_ID_BRIDGE_VLAN_PROTOCOL,
28 	SWITCHDEV_ATTR_ID_BRIDGE_MC_DISABLED,
29 	SWITCHDEV_ATTR_ID_BRIDGE_MROUTER,
30 	SWITCHDEV_ATTR_ID_MRP_PORT_ROLE,
31 };
32 
33 struct switchdev_brport_flags {
34 	unsigned long val;
35 	unsigned long mask;
36 };
37 
38 struct switchdev_attr {
39 	struct net_device *orig_dev;
40 	enum switchdev_attr_id id;
41 	u32 flags;
42 	void *complete_priv;
43 	void (*complete)(struct net_device *dev, int err, void *priv);
44 	union {
45 		u8 stp_state;				/* PORT_STP_STATE */
46 		struct switchdev_brport_flags brport_flags; /* PORT_BRIDGE_FLAGS */
47 		bool mrouter;				/* PORT_MROUTER */
48 		clock_t ageing_time;			/* BRIDGE_AGEING_TIME */
49 		bool vlan_filtering;			/* BRIDGE_VLAN_FILTERING */
50 		u16 vlan_protocol;			/* BRIDGE_VLAN_PROTOCOL */
51 		bool mc_disabled;			/* MC_DISABLED */
52 		u8 mrp_port_role;			/* MRP_PORT_ROLE */
53 	} u;
54 };
55 
56 enum switchdev_obj_id {
57 	SWITCHDEV_OBJ_ID_UNDEFINED,
58 	SWITCHDEV_OBJ_ID_PORT_VLAN,
59 	SWITCHDEV_OBJ_ID_PORT_MDB,
60 	SWITCHDEV_OBJ_ID_HOST_MDB,
61 	SWITCHDEV_OBJ_ID_MRP,
62 	SWITCHDEV_OBJ_ID_RING_TEST_MRP,
63 	SWITCHDEV_OBJ_ID_RING_ROLE_MRP,
64 	SWITCHDEV_OBJ_ID_RING_STATE_MRP,
65 	SWITCHDEV_OBJ_ID_IN_TEST_MRP,
66 	SWITCHDEV_OBJ_ID_IN_ROLE_MRP,
67 	SWITCHDEV_OBJ_ID_IN_STATE_MRP,
68 };
69 
70 struct switchdev_obj {
71 	struct list_head list;
72 	struct net_device *orig_dev;
73 	enum switchdev_obj_id id;
74 	u32 flags;
75 	void *complete_priv;
76 	void (*complete)(struct net_device *dev, int err, void *priv);
77 };
78 
79 /* SWITCHDEV_OBJ_ID_PORT_VLAN */
80 struct switchdev_obj_port_vlan {
81 	struct switchdev_obj obj;
82 	u16 flags;
83 	u16 vid;
84 	/* If set, the notifier signifies a change of one of the following
85 	 * flags for a VLAN that already exists:
86 	 * - BRIDGE_VLAN_INFO_PVID
87 	 * - BRIDGE_VLAN_INFO_UNTAGGED
88 	 * Entries with BRIDGE_VLAN_INFO_BRENTRY unset are not notified at all.
89 	 */
90 	bool changed;
91 };
92 
93 #define SWITCHDEV_OBJ_PORT_VLAN(OBJ) \
94 	container_of((OBJ), struct switchdev_obj_port_vlan, obj)
95 
96 /* SWITCHDEV_OBJ_ID_PORT_MDB */
97 struct switchdev_obj_port_mdb {
98 	struct switchdev_obj obj;
99 	unsigned char addr[ETH_ALEN];
100 	u16 vid;
101 };
102 
103 #define SWITCHDEV_OBJ_PORT_MDB(OBJ) \
104 	container_of((OBJ), struct switchdev_obj_port_mdb, obj)
105 
106 
107 /* SWITCHDEV_OBJ_ID_MRP */
108 struct switchdev_obj_mrp {
109 	struct switchdev_obj obj;
110 	struct net_device *p_port;
111 	struct net_device *s_port;
112 	u32 ring_id;
113 	u16 prio;
114 };
115 
116 #define SWITCHDEV_OBJ_MRP(OBJ) \
117 	container_of((OBJ), struct switchdev_obj_mrp, obj)
118 
119 /* SWITCHDEV_OBJ_ID_RING_TEST_MRP */
120 struct switchdev_obj_ring_test_mrp {
121 	struct switchdev_obj obj;
122 	/* The value is in us and a value of 0 represents to stop */
123 	u32 interval;
124 	u8 max_miss;
125 	u32 ring_id;
126 	u32 period;
127 	bool monitor;
128 };
129 
130 #define SWITCHDEV_OBJ_RING_TEST_MRP(OBJ) \
131 	container_of((OBJ), struct switchdev_obj_ring_test_mrp, obj)
132 
133 /* SWICHDEV_OBJ_ID_RING_ROLE_MRP */
134 struct switchdev_obj_ring_role_mrp {
135 	struct switchdev_obj obj;
136 	u8 ring_role;
137 	u32 ring_id;
138 	u8 sw_backup;
139 };
140 
141 #define SWITCHDEV_OBJ_RING_ROLE_MRP(OBJ) \
142 	container_of((OBJ), struct switchdev_obj_ring_role_mrp, obj)
143 
144 struct switchdev_obj_ring_state_mrp {
145 	struct switchdev_obj obj;
146 	u8 ring_state;
147 	u32 ring_id;
148 };
149 
150 #define SWITCHDEV_OBJ_RING_STATE_MRP(OBJ) \
151 	container_of((OBJ), struct switchdev_obj_ring_state_mrp, obj)
152 
153 /* SWITCHDEV_OBJ_ID_IN_TEST_MRP */
154 struct switchdev_obj_in_test_mrp {
155 	struct switchdev_obj obj;
156 	/* The value is in us and a value of 0 represents to stop */
157 	u32 interval;
158 	u32 in_id;
159 	u32 period;
160 	u8 max_miss;
161 };
162 
163 #define SWITCHDEV_OBJ_IN_TEST_MRP(OBJ) \
164 	container_of((OBJ), struct switchdev_obj_in_test_mrp, obj)
165 
166 /* SWICHDEV_OBJ_ID_IN_ROLE_MRP */
167 struct switchdev_obj_in_role_mrp {
168 	struct switchdev_obj obj;
169 	struct net_device *i_port;
170 	u32 ring_id;
171 	u16 in_id;
172 	u8 in_role;
173 	u8 sw_backup;
174 };
175 
176 #define SWITCHDEV_OBJ_IN_ROLE_MRP(OBJ) \
177 	container_of((OBJ), struct switchdev_obj_in_role_mrp, obj)
178 
179 struct switchdev_obj_in_state_mrp {
180 	struct switchdev_obj obj;
181 	u32 in_id;
182 	u8 in_state;
183 };
184 
185 #define SWITCHDEV_OBJ_IN_STATE_MRP(OBJ) \
186 	container_of((OBJ), struct switchdev_obj_in_state_mrp, obj)
187 
188 typedef int switchdev_obj_dump_cb_t(struct switchdev_obj *obj);
189 
190 struct switchdev_brport {
191 	struct net_device *dev;
192 	const void *ctx;
193 	struct notifier_block *atomic_nb;
194 	struct notifier_block *blocking_nb;
195 	bool tx_fwd_offload;
196 };
197 
198 enum switchdev_notifier_type {
199 	SWITCHDEV_FDB_ADD_TO_BRIDGE = 1,
200 	SWITCHDEV_FDB_DEL_TO_BRIDGE,
201 	SWITCHDEV_FDB_ADD_TO_DEVICE,
202 	SWITCHDEV_FDB_DEL_TO_DEVICE,
203 	SWITCHDEV_FDB_OFFLOADED,
204 	SWITCHDEV_FDB_FLUSH_TO_BRIDGE,
205 
206 	SWITCHDEV_PORT_OBJ_ADD, /* Blocking. */
207 	SWITCHDEV_PORT_OBJ_DEL, /* Blocking. */
208 	SWITCHDEV_PORT_ATTR_SET, /* May be blocking . */
209 
210 	SWITCHDEV_VXLAN_FDB_ADD_TO_BRIDGE,
211 	SWITCHDEV_VXLAN_FDB_DEL_TO_BRIDGE,
212 	SWITCHDEV_VXLAN_FDB_ADD_TO_DEVICE,
213 	SWITCHDEV_VXLAN_FDB_DEL_TO_DEVICE,
214 	SWITCHDEV_VXLAN_FDB_OFFLOADED,
215 
216 	SWITCHDEV_BRPORT_OFFLOADED,
217 	SWITCHDEV_BRPORT_UNOFFLOADED,
218 };
219 
220 struct switchdev_notifier_info {
221 	struct net_device *dev;
222 	struct netlink_ext_ack *extack;
223 	const void *ctx;
224 };
225 
226 struct switchdev_notifier_fdb_info {
227 	struct switchdev_notifier_info info; /* must be first */
228 	const unsigned char *addr;
229 	u16 vid;
230 	u8 added_by_user:1,
231 	   is_local:1,
232 	   offloaded:1;
233 };
234 
235 struct switchdev_notifier_port_obj_info {
236 	struct switchdev_notifier_info info; /* must be first */
237 	const struct switchdev_obj *obj;
238 	bool handled;
239 };
240 
241 struct switchdev_notifier_port_attr_info {
242 	struct switchdev_notifier_info info; /* must be first */
243 	const struct switchdev_attr *attr;
244 	bool handled;
245 };
246 
247 struct switchdev_notifier_brport_info {
248 	struct switchdev_notifier_info info; /* must be first */
249 	const struct switchdev_brport brport;
250 };
251 
252 static inline struct net_device *
253 switchdev_notifier_info_to_dev(const struct switchdev_notifier_info *info)
254 {
255 	return info->dev;
256 }
257 
258 static inline struct netlink_ext_ack *
259 switchdev_notifier_info_to_extack(const struct switchdev_notifier_info *info)
260 {
261 	return info->extack;
262 }
263 
264 static inline bool
265 switchdev_fdb_is_dynamically_learned(const struct switchdev_notifier_fdb_info *fdb_info)
266 {
267 	return !fdb_info->added_by_user && !fdb_info->is_local;
268 }
269 
270 #ifdef CONFIG_NET_SWITCHDEV
271 
272 int switchdev_bridge_port_offload(struct net_device *brport_dev,
273 				  struct net_device *dev, const void *ctx,
274 				  struct notifier_block *atomic_nb,
275 				  struct notifier_block *blocking_nb,
276 				  bool tx_fwd_offload,
277 				  struct netlink_ext_ack *extack);
278 void switchdev_bridge_port_unoffload(struct net_device *brport_dev,
279 				     const void *ctx,
280 				     struct notifier_block *atomic_nb,
281 				     struct notifier_block *blocking_nb);
282 
283 void switchdev_deferred_process(void);
284 int switchdev_port_attr_set(struct net_device *dev,
285 			    const struct switchdev_attr *attr,
286 			    struct netlink_ext_ack *extack);
287 int switchdev_port_obj_add(struct net_device *dev,
288 			   const struct switchdev_obj *obj,
289 			   struct netlink_ext_ack *extack);
290 int switchdev_port_obj_del(struct net_device *dev,
291 			   const struct switchdev_obj *obj);
292 
293 int register_switchdev_notifier(struct notifier_block *nb);
294 int unregister_switchdev_notifier(struct notifier_block *nb);
295 int call_switchdev_notifiers(unsigned long val, struct net_device *dev,
296 			     struct switchdev_notifier_info *info,
297 			     struct netlink_ext_ack *extack);
298 
299 int register_switchdev_blocking_notifier(struct notifier_block *nb);
300 int unregister_switchdev_blocking_notifier(struct notifier_block *nb);
301 int call_switchdev_blocking_notifiers(unsigned long val, struct net_device *dev,
302 				      struct switchdev_notifier_info *info,
303 				      struct netlink_ext_ack *extack);
304 
305 void switchdev_port_fwd_mark_set(struct net_device *dev,
306 				 struct net_device *group_dev,
307 				 bool joining);
308 
309 int switchdev_handle_fdb_event_to_device(struct net_device *dev, unsigned long event,
310 		const struct switchdev_notifier_fdb_info *fdb_info,
311 		bool (*check_cb)(const struct net_device *dev),
312 		bool (*foreign_dev_check_cb)(const struct net_device *dev,
313 					     const struct net_device *foreign_dev),
314 		int (*mod_cb)(struct net_device *dev, struct net_device *orig_dev,
315 			      unsigned long event, const void *ctx,
316 			      const struct switchdev_notifier_fdb_info *fdb_info),
317 		int (*lag_mod_cb)(struct net_device *dev, struct net_device *orig_dev,
318 				  unsigned long event, const void *ctx,
319 				  const struct switchdev_notifier_fdb_info *fdb_info));
320 
321 int switchdev_handle_port_obj_add(struct net_device *dev,
322 			struct switchdev_notifier_port_obj_info *port_obj_info,
323 			bool (*check_cb)(const struct net_device *dev),
324 			int (*add_cb)(struct net_device *dev, const void *ctx,
325 				      const struct switchdev_obj *obj,
326 				      struct netlink_ext_ack *extack));
327 int switchdev_handle_port_obj_add_foreign(struct net_device *dev,
328 			struct switchdev_notifier_port_obj_info *port_obj_info,
329 			bool (*check_cb)(const struct net_device *dev),
330 			bool (*foreign_dev_check_cb)(const struct net_device *dev,
331 						     const struct net_device *foreign_dev),
332 			int (*add_cb)(struct net_device *dev, const void *ctx,
333 				      const struct switchdev_obj *obj,
334 				      struct netlink_ext_ack *extack));
335 int switchdev_handle_port_obj_del(struct net_device *dev,
336 			struct switchdev_notifier_port_obj_info *port_obj_info,
337 			bool (*check_cb)(const struct net_device *dev),
338 			int (*del_cb)(struct net_device *dev, const void *ctx,
339 				      const struct switchdev_obj *obj));
340 int switchdev_handle_port_obj_del_foreign(struct net_device *dev,
341 			struct switchdev_notifier_port_obj_info *port_obj_info,
342 			bool (*check_cb)(const struct net_device *dev),
343 			bool (*foreign_dev_check_cb)(const struct net_device *dev,
344 						     const struct net_device *foreign_dev),
345 			int (*del_cb)(struct net_device *dev, const void *ctx,
346 				      const struct switchdev_obj *obj));
347 
348 int switchdev_handle_port_attr_set(struct net_device *dev,
349 			struct switchdev_notifier_port_attr_info *port_attr_info,
350 			bool (*check_cb)(const struct net_device *dev),
351 			int (*set_cb)(struct net_device *dev, const void *ctx,
352 				      const struct switchdev_attr *attr,
353 				      struct netlink_ext_ack *extack));
354 #else
355 
356 static inline int
357 switchdev_bridge_port_offload(struct net_device *brport_dev,
358 			      struct net_device *dev, const void *ctx,
359 			      struct notifier_block *atomic_nb,
360 			      struct notifier_block *blocking_nb,
361 			      bool tx_fwd_offload,
362 			      struct netlink_ext_ack *extack)
363 {
364 	return -EOPNOTSUPP;
365 }
366 
367 static inline void
368 switchdev_bridge_port_unoffload(struct net_device *brport_dev,
369 				const void *ctx,
370 				struct notifier_block *atomic_nb,
371 				struct notifier_block *blocking_nb)
372 {
373 }
374 
375 static inline void switchdev_deferred_process(void)
376 {
377 }
378 
379 static inline int switchdev_port_attr_set(struct net_device *dev,
380 					  const struct switchdev_attr *attr,
381 					  struct netlink_ext_ack *extack)
382 {
383 	return -EOPNOTSUPP;
384 }
385 
386 static inline int switchdev_port_obj_add(struct net_device *dev,
387 					 const struct switchdev_obj *obj,
388 					 struct netlink_ext_ack *extack)
389 {
390 	return -EOPNOTSUPP;
391 }
392 
393 static inline int switchdev_port_obj_del(struct net_device *dev,
394 					 const struct switchdev_obj *obj)
395 {
396 	return -EOPNOTSUPP;
397 }
398 
399 static inline int register_switchdev_notifier(struct notifier_block *nb)
400 {
401 	return 0;
402 }
403 
404 static inline int unregister_switchdev_notifier(struct notifier_block *nb)
405 {
406 	return 0;
407 }
408 
409 static inline int call_switchdev_notifiers(unsigned long val,
410 					   struct net_device *dev,
411 					   struct switchdev_notifier_info *info,
412 					   struct netlink_ext_ack *extack)
413 {
414 	return NOTIFY_DONE;
415 }
416 
417 static inline int
418 register_switchdev_blocking_notifier(struct notifier_block *nb)
419 {
420 	return 0;
421 }
422 
423 static inline int
424 unregister_switchdev_blocking_notifier(struct notifier_block *nb)
425 {
426 	return 0;
427 }
428 
429 static inline int
430 call_switchdev_blocking_notifiers(unsigned long val,
431 				  struct net_device *dev,
432 				  struct switchdev_notifier_info *info,
433 				  struct netlink_ext_ack *extack)
434 {
435 	return NOTIFY_DONE;
436 }
437 
438 static inline int
439 switchdev_handle_fdb_event_to_device(struct net_device *dev, unsigned long event,
440 		const struct switchdev_notifier_fdb_info *fdb_info,
441 		bool (*check_cb)(const struct net_device *dev),
442 		bool (*foreign_dev_check_cb)(const struct net_device *dev,
443 					     const struct net_device *foreign_dev),
444 		int (*mod_cb)(struct net_device *dev, struct net_device *orig_dev,
445 			      unsigned long event, const void *ctx,
446 			      const struct switchdev_notifier_fdb_info *fdb_info),
447 		int (*lag_mod_cb)(struct net_device *dev, struct net_device *orig_dev,
448 				  unsigned long event, const void *ctx,
449 				  const struct switchdev_notifier_fdb_info *fdb_info))
450 {
451 	return 0;
452 }
453 
454 static inline int
455 switchdev_handle_port_obj_add(struct net_device *dev,
456 			struct switchdev_notifier_port_obj_info *port_obj_info,
457 			bool (*check_cb)(const struct net_device *dev),
458 			int (*add_cb)(struct net_device *dev, const void *ctx,
459 				      const struct switchdev_obj *obj,
460 				      struct netlink_ext_ack *extack))
461 {
462 	return 0;
463 }
464 
465 static inline int switchdev_handle_port_obj_add_foreign(struct net_device *dev,
466 			struct switchdev_notifier_port_obj_info *port_obj_info,
467 			bool (*check_cb)(const struct net_device *dev),
468 			bool (*foreign_dev_check_cb)(const struct net_device *dev,
469 						     const struct net_device *foreign_dev),
470 			int (*add_cb)(struct net_device *dev, const void *ctx,
471 				      const struct switchdev_obj *obj,
472 				      struct netlink_ext_ack *extack))
473 {
474 	return 0;
475 }
476 
477 static inline int
478 switchdev_handle_port_obj_del(struct net_device *dev,
479 			struct switchdev_notifier_port_obj_info *port_obj_info,
480 			bool (*check_cb)(const struct net_device *dev),
481 			int (*del_cb)(struct net_device *dev, const void *ctx,
482 				      const struct switchdev_obj *obj))
483 {
484 	return 0;
485 }
486 
487 static inline int
488 switchdev_handle_port_obj_del_foreign(struct net_device *dev,
489 			struct switchdev_notifier_port_obj_info *port_obj_info,
490 			bool (*check_cb)(const struct net_device *dev),
491 			bool (*foreign_dev_check_cb)(const struct net_device *dev,
492 						     const struct net_device *foreign_dev),
493 			int (*del_cb)(struct net_device *dev, const void *ctx,
494 				      const struct switchdev_obj *obj))
495 {
496 	return 0;
497 }
498 
499 static inline int
500 switchdev_handle_port_attr_set(struct net_device *dev,
501 			struct switchdev_notifier_port_attr_info *port_attr_info,
502 			bool (*check_cb)(const struct net_device *dev),
503 			int (*set_cb)(struct net_device *dev, const void *ctx,
504 				      const struct switchdev_attr *attr,
505 				      struct netlink_ext_ack *extack))
506 {
507 	return 0;
508 }
509 #endif
510 
511 #endif /* _LINUX_SWITCHDEV_H_ */
512