switchdev: bring back switchdev_obj and use it as a generic object param
[cascardo/linux.git] / include / net / switchdev.h
1 /*
2  * include/net/switchdev.h - Switch device API
3  * Copyright (c) 2014-2015 Jiri Pirko <jiri@resnulli.us>
4  * Copyright (c) 2014-2015 Scott Feldman <sfeldma@gmail.com>
5  *
6  * This program is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation; either version 2 of the License, or
9  * (at your option) any later version.
10  */
11 #ifndef _LINUX_SWITCHDEV_H_
12 #define _LINUX_SWITCHDEV_H_
13
14 #include <linux/netdevice.h>
15 #include <linux/notifier.h>
16 #include <linux/list.h>
17
18 #define SWITCHDEV_F_NO_RECURSE          BIT(0)
19
20 struct switchdev_trans_item {
21         struct list_head list;
22         void *data;
23         void (*destructor)(const void *data);
24 };
25
26 struct switchdev_trans {
27         struct list_head item_list;
28         bool ph_prepare;
29 };
30
31 static inline bool switchdev_trans_ph_prepare(struct switchdev_trans *trans)
32 {
33         return trans && trans->ph_prepare;
34 }
35
36 static inline bool switchdev_trans_ph_commit(struct switchdev_trans *trans)
37 {
38         return trans && !trans->ph_prepare;
39 }
40
41 enum switchdev_attr_id {
42         SWITCHDEV_ATTR_ID_UNDEFINED,
43         SWITCHDEV_ATTR_ID_PORT_PARENT_ID,
44         SWITCHDEV_ATTR_ID_PORT_STP_STATE,
45         SWITCHDEV_ATTR_ID_PORT_BRIDGE_FLAGS,
46 };
47
48 struct switchdev_attr {
49         enum switchdev_attr_id id;
50         u32 flags;
51         union {
52                 struct netdev_phys_item_id ppid;        /* PORT_PARENT_ID */
53                 u8 stp_state;                           /* PORT_STP_STATE */
54                 unsigned long brport_flags;             /* PORT_BRIDGE_FLAGS */
55         } u;
56 };
57
58 struct fib_info;
59
60 enum switchdev_obj_id {
61         SWITCHDEV_OBJ_ID_UNDEFINED,
62         SWITCHDEV_OBJ_ID_PORT_VLAN,
63         SWITCHDEV_OBJ_ID_IPV4_FIB,
64         SWITCHDEV_OBJ_ID_PORT_FDB,
65 };
66
67 struct switchdev_obj {
68 };
69
70 /* SWITCHDEV_OBJ_ID_PORT_VLAN */
71 struct switchdev_obj_port_vlan {
72         struct switchdev_obj obj;
73         u16 flags;
74         u16 vid_begin;
75         u16 vid_end;
76 };
77
78 #define SWITCHDEV_OBJ_PORT_VLAN(obj) \
79         container_of(obj, struct switchdev_obj_port_vlan, obj)
80
81 /* SWITCHDEV_OBJ_ID_IPV4_FIB */
82 struct switchdev_obj_ipv4_fib {
83         struct switchdev_obj obj;
84         u32 dst;
85         int dst_len;
86         struct fib_info *fi;
87         u8 tos;
88         u8 type;
89         u32 nlflags;
90         u32 tb_id;
91 };
92
93 #define SWITCHDEV_OBJ_IPV4_FIB(obj) \
94         container_of(obj, struct switchdev_obj_ipv4_fib, obj)
95
96 /* SWITCHDEV_OBJ_ID_PORT_FDB */
97 struct switchdev_obj_port_fdb {
98         struct switchdev_obj obj;
99         const unsigned char *addr;
100         u16 vid;
101         u16 ndm_state;
102 };
103
104 #define SWITCHDEV_OBJ_PORT_FDB(obj) \
105         container_of(obj, struct switchdev_obj_port_fdb, obj)
106
107 void switchdev_trans_item_enqueue(struct switchdev_trans *trans,
108                                   void *data, void (*destructor)(void const *),
109                                   struct switchdev_trans_item *tritem);
110 void *switchdev_trans_item_dequeue(struct switchdev_trans *trans);
111
112 typedef int switchdev_obj_dump_cb_t(struct switchdev_obj *obj);
113
114 /**
115  * struct switchdev_ops - switchdev operations
116  *
117  * @switchdev_port_attr_get: Get a port attribute (see switchdev_attr).
118  *
119  * @switchdev_port_attr_set: Set a port attribute (see switchdev_attr).
120  *
121  * @switchdev_port_obj_add: Add an object to port (see switchdev_obj_*).
122  *
123  * @switchdev_port_obj_del: Delete an object from port (see switchdev_obj_*).
124  *
125  * @switchdev_port_obj_dump: Dump port objects (see switchdev_obj_*).
126  */
127 struct switchdev_ops {
128         int     (*switchdev_port_attr_get)(struct net_device *dev,
129                                            struct switchdev_attr *attr);
130         int     (*switchdev_port_attr_set)(struct net_device *dev,
131                                            struct switchdev_attr *attr,
132                                            struct switchdev_trans *trans);
133         int     (*switchdev_port_obj_add)(struct net_device *dev,
134                                           enum switchdev_obj_id id,
135                                           const struct switchdev_obj *obj,
136                                           struct switchdev_trans *trans);
137         int     (*switchdev_port_obj_del)(struct net_device *dev,
138                                           enum switchdev_obj_id id,
139                                           const struct switchdev_obj *obj);
140         int     (*switchdev_port_obj_dump)(struct net_device *dev,
141                                            enum switchdev_obj_id id,
142                                            struct switchdev_obj *obj,
143                                            switchdev_obj_dump_cb_t *cb);
144 };
145
146 enum switchdev_notifier_type {
147         SWITCHDEV_FDB_ADD = 1,
148         SWITCHDEV_FDB_DEL,
149 };
150
151 struct switchdev_notifier_info {
152         struct net_device *dev;
153 };
154
155 struct switchdev_notifier_fdb_info {
156         struct switchdev_notifier_info info; /* must be first */
157         const unsigned char *addr;
158         u16 vid;
159 };
160
161 static inline struct net_device *
162 switchdev_notifier_info_to_dev(const struct switchdev_notifier_info *info)
163 {
164         return info->dev;
165 }
166
167 #ifdef CONFIG_NET_SWITCHDEV
168
169 int switchdev_port_attr_get(struct net_device *dev,
170                             struct switchdev_attr *attr);
171 int switchdev_port_attr_set(struct net_device *dev,
172                             struct switchdev_attr *attr);
173 int switchdev_port_obj_add(struct net_device *dev, enum switchdev_obj_id id,
174                            const struct switchdev_obj *obj);
175 int switchdev_port_obj_del(struct net_device *dev, enum switchdev_obj_id id,
176                            const struct switchdev_obj *obj);
177 int switchdev_port_obj_dump(struct net_device *dev, enum switchdev_obj_id id,
178                             struct switchdev_obj *obj,
179                             switchdev_obj_dump_cb_t *cb);
180 int register_switchdev_notifier(struct notifier_block *nb);
181 int unregister_switchdev_notifier(struct notifier_block *nb);
182 int call_switchdev_notifiers(unsigned long val, struct net_device *dev,
183                              struct switchdev_notifier_info *info);
184 int switchdev_port_bridge_getlink(struct sk_buff *skb, u32 pid, u32 seq,
185                                   struct net_device *dev, u32 filter_mask,
186                                   int nlflags);
187 int switchdev_port_bridge_setlink(struct net_device *dev,
188                                   struct nlmsghdr *nlh, u16 flags);
189 int switchdev_port_bridge_dellink(struct net_device *dev,
190                                   struct nlmsghdr *nlh, u16 flags);
191 int switchdev_fib_ipv4_add(u32 dst, int dst_len, struct fib_info *fi,
192                            u8 tos, u8 type, u32 nlflags, u32 tb_id);
193 int switchdev_fib_ipv4_del(u32 dst, int dst_len, struct fib_info *fi,
194                            u8 tos, u8 type, u32 tb_id);
195 void switchdev_fib_ipv4_abort(struct fib_info *fi);
196 int switchdev_port_fdb_add(struct ndmsg *ndm, struct nlattr *tb[],
197                            struct net_device *dev, const unsigned char *addr,
198                            u16 vid, u16 nlm_flags);
199 int switchdev_port_fdb_del(struct ndmsg *ndm, struct nlattr *tb[],
200                            struct net_device *dev, const unsigned char *addr,
201                            u16 vid);
202 int switchdev_port_fdb_dump(struct sk_buff *skb, struct netlink_callback *cb,
203                             struct net_device *dev,
204                             struct net_device *filter_dev, int idx);
205 void switchdev_port_fwd_mark_set(struct net_device *dev,
206                                  struct net_device *group_dev,
207                                  bool joining);
208
209 #else
210
211 static inline int switchdev_port_attr_get(struct net_device *dev,
212                                           struct switchdev_attr *attr)
213 {
214         return -EOPNOTSUPP;
215 }
216
217 static inline int switchdev_port_attr_set(struct net_device *dev,
218                                           struct switchdev_attr *attr)
219 {
220         return -EOPNOTSUPP;
221 }
222
223 static inline int switchdev_port_obj_add(struct net_device *dev,
224                                          enum switchdev_obj_id id,
225                                          const struct switchdev_obj *obj)
226 {
227         return -EOPNOTSUPP;
228 }
229
230 static inline int switchdev_port_obj_del(struct net_device *dev,
231                                          enum switchdev_obj_id id,
232                                          const struct switchdev_obj *obj)
233 {
234         return -EOPNOTSUPP;
235 }
236
237 static inline int switchdev_port_obj_dump(struct net_device *dev,
238                                           enum switchdev_obj_id id,
239                                           const struct switchdev_obj *obj,
240                                           switchdev_obj_dump_cb_t *cb)
241 {
242         return -EOPNOTSUPP;
243 }
244
245 static inline int register_switchdev_notifier(struct notifier_block *nb)
246 {
247         return 0;
248 }
249
250 static inline int unregister_switchdev_notifier(struct notifier_block *nb)
251 {
252         return 0;
253 }
254
255 static inline int call_switchdev_notifiers(unsigned long val,
256                                            struct net_device *dev,
257                                            struct switchdev_notifier_info *info)
258 {
259         return NOTIFY_DONE;
260 }
261
262 static inline int switchdev_port_bridge_getlink(struct sk_buff *skb, u32 pid,
263                                             u32 seq, struct net_device *dev,
264                                             u32 filter_mask, int nlflags)
265 {
266         return -EOPNOTSUPP;
267 }
268
269 static inline int switchdev_port_bridge_setlink(struct net_device *dev,
270                                                 struct nlmsghdr *nlh,
271                                                 u16 flags)
272 {
273         return -EOPNOTSUPP;
274 }
275
276 static inline int switchdev_port_bridge_dellink(struct net_device *dev,
277                                                 struct nlmsghdr *nlh,
278                                                 u16 flags)
279 {
280         return -EOPNOTSUPP;
281 }
282
283 static inline int switchdev_fib_ipv4_add(u32 dst, int dst_len,
284                                          struct fib_info *fi,
285                                          u8 tos, u8 type,
286                                          u32 nlflags, u32 tb_id)
287 {
288         return 0;
289 }
290
291 static inline int switchdev_fib_ipv4_del(u32 dst, int dst_len,
292                                          struct fib_info *fi,
293                                          u8 tos, u8 type, u32 tb_id)
294 {
295         return 0;
296 }
297
298 static inline void switchdev_fib_ipv4_abort(struct fib_info *fi)
299 {
300 }
301
302 static inline int switchdev_port_fdb_add(struct ndmsg *ndm, struct nlattr *tb[],
303                                          struct net_device *dev,
304                                          const unsigned char *addr,
305                                          u16 vid, u16 nlm_flags)
306 {
307         return -EOPNOTSUPP;
308 }
309
310 static inline int switchdev_port_fdb_del(struct ndmsg *ndm, struct nlattr *tb[],
311                                          struct net_device *dev,
312                                          const unsigned char *addr, u16 vid)
313 {
314         return -EOPNOTSUPP;
315 }
316
317 static inline int switchdev_port_fdb_dump(struct sk_buff *skb,
318                                           struct netlink_callback *cb,
319                                           struct net_device *dev,
320                                           struct net_device *filter_dev,
321                                           int idx)
322 {
323         return -EOPNOTSUPP;
324 }
325
326 static inline void switchdev_port_fwd_mark_set(struct net_device *dev,
327                                                struct net_device *group_dev,
328                                                bool joining)
329 {
330 }
331
332 #endif
333
334 #endif /* _LINUX_SWITCHDEV_H_ */