linux/include/net/switchdev.h
<<
>>
Prefs
   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#include <net/ip_fib.h>
  18
  19#include <linux/rh_kabi.h>
  20
  21#define SWITCHDEV_F_NO_RECURSE          BIT(0)
  22#define SWITCHDEV_F_SKIP_EOPNOTSUPP     BIT(1)
  23#define SWITCHDEV_F_DEFER               BIT(2)
  24
  25struct switchdev_trans_item {
  26        struct list_head list;
  27        void *data;
  28        void (*destructor)(const void *data);
  29};
  30
  31struct switchdev_trans {
  32        struct list_head item_list;
  33        bool ph_prepare;
  34};
  35
  36static inline bool switchdev_trans_ph_prepare(struct switchdev_trans *trans)
  37{
  38        return trans && trans->ph_prepare;
  39}
  40
  41static inline bool switchdev_trans_ph_commit(struct switchdev_trans *trans)
  42{
  43        return trans && !trans->ph_prepare;
  44}
  45
  46enum switchdev_attr_id {
  47        SWITCHDEV_ATTR_ID_UNDEFINED,
  48        RH_KABI_RENAME(SWITCHDEV_ATTR_ID_PORT_PARENT_ID,
  49                       RH_DEPRECATED_SWITCHDEV_ATTR_ID_PORT_PARENT_ID),
  50        SWITCHDEV_ATTR_ID_PORT_STP_STATE,
  51        SWITCHDEV_ATTR_ID_PORT_BRIDGE_FLAGS,
  52        RH_KABI_RENAME(SWITCHDEV_ATTR_ID_PORT_BRIDGE_FLAGS_SUPPORT,
  53                       RH_DEPRECATED_SWITCHDEV_ATTR_ID_PORT_BRIDGE_FLAGS_SUPPORT),
  54        SWITCHDEV_ATTR_ID_PORT_MROUTER,
  55        SWITCHDEV_ATTR_ID_BRIDGE_AGEING_TIME,
  56        SWITCHDEV_ATTR_ID_BRIDGE_VLAN_FILTERING,
  57        SWITCHDEV_ATTR_ID_BRIDGE_MC_DISABLED,
  58        SWITCHDEV_ATTR_ID_BRIDGE_MROUTER,
  59#ifndef __GENKSYMS__
  60        SWITCHDEV_ATTR_ID_PORT_PRE_BRIDGE_FLAGS,
  61#endif
  62};
  63
  64struct switchdev_attr {
  65        struct net_device *orig_dev;
  66        enum switchdev_attr_id id;
  67        u32 flags;
  68        void *complete_priv;
  69        void (*complete)(struct net_device *dev, int err, void *priv);
  70        union {
  71                RH_KABI_DEPRECATE(struct netdev_phys_item_id, ppid)
  72                u8 stp_state;                           /* PORT_STP_STATE */
  73                unsigned long brport_flags;             /* PORT_{PRE}_BRIDGE_FLAGS */
  74                RH_KABI_DEPRECATE(unsigned long, brport_flags_support)
  75                bool mrouter;                           /* PORT_MROUTER */
  76                clock_t ageing_time;                    /* BRIDGE_AGEING_TIME */
  77                bool vlan_filtering;                    /* BRIDGE_VLAN_FILTERING */
  78                bool mc_disabled;                       /* MC_DISABLED */
  79        } u;
  80};
  81
  82enum switchdev_obj_id {
  83        SWITCHDEV_OBJ_ID_UNDEFINED,
  84        SWITCHDEV_OBJ_ID_PORT_VLAN,
  85        SWITCHDEV_OBJ_ID_PORT_MDB,
  86        SWITCHDEV_OBJ_ID_HOST_MDB,
  87};
  88
  89struct switchdev_obj {
  90        struct net_device *orig_dev;
  91        enum switchdev_obj_id id;
  92        u32 flags;
  93        void *complete_priv;
  94        void (*complete)(struct net_device *dev, int err, void *priv);
  95
  96        RH_KABI_RESERVE(1)
  97        RH_KABI_RESERVE(2)
  98        RH_KABI_RESERVE(3)
  99        RH_KABI_RESERVE(4)
 100};
 101
 102/* SWITCHDEV_OBJ_ID_PORT_VLAN */
 103struct switchdev_obj_port_vlan {
 104        struct switchdev_obj obj;
 105        u16 flags;
 106        u16 vid_begin;
 107        u16 vid_end;
 108};
 109
 110#define SWITCHDEV_OBJ_PORT_VLAN(OBJ) \
 111        container_of((OBJ), struct switchdev_obj_port_vlan, obj)
 112
 113/* SWITCHDEV_OBJ_ID_PORT_MDB */
 114struct switchdev_obj_port_mdb {
 115        struct switchdev_obj obj;
 116        unsigned char addr[ETH_ALEN];
 117        u16 vid;
 118};
 119
 120#define SWITCHDEV_OBJ_PORT_MDB(OBJ) \
 121        container_of((OBJ), struct switchdev_obj_port_mdb, obj)
 122
 123void switchdev_trans_item_enqueue(struct switchdev_trans *trans,
 124                                  void *data, void (*destructor)(void const *),
 125                                  struct switchdev_trans_item *tritem);
 126void *switchdev_trans_item_dequeue(struct switchdev_trans *trans);
 127
 128typedef int switchdev_obj_dump_cb_t(struct switchdev_obj *obj);
 129
 130struct switchdev_ops_extended_rh {
 131};
 132
 133/**
 134 * struct switchdev_ops - switchdev operations
 135 *
 136 * @switchdev_port_attr_set: Set a port attribute (see switchdev_attr).
 137 */
 138struct RH_KABI_RENAME(switchdev_ops, rh_deprecated_switchdev_ops) {
 139        RH_KABI_DEPRECATE_FN(int, switchdev_port_attr_get, struct net_device *dev,
 140                                           struct switchdev_attr *attr)
 141        RH_KABI_DEPRECATE_FN(int, switchdev_port_attr_set, struct net_device *dev,
 142                                           const struct switchdev_attr *attr,
 143                                           struct switchdev_trans *trans)
 144        RH_KABI_DEPRECATE_FN(int, switchdev_port_obj_add, struct net_device *dev,
 145                                          const struct switchdev_obj *obj,
 146                                          struct switchdev_trans *trans)
 147        RH_KABI_DEPRECATE_FN(int, switchdev_port_obj_del, struct net_device *dev,
 148                                          const struct switchdev_obj *obj)
 149
 150        RH_KABI_RESERVE(1)
 151        RH_KABI_RESERVE(2)
 152        RH_KABI_RESERVE(3)
 153        RH_KABI_RESERVE(4)
 154        RH_KABI_RESERVE(5)
 155        RH_KABI_RESERVE(6)
 156        RH_KABI_RESERVE(7)
 157        RH_KABI_AUX_EMBED(switchdev_ops_extended)
 158};
 159
 160enum switchdev_notifier_type {
 161        SWITCHDEV_FDB_ADD_TO_BRIDGE = 1,
 162        SWITCHDEV_FDB_DEL_TO_BRIDGE,
 163        SWITCHDEV_FDB_ADD_TO_DEVICE,
 164        SWITCHDEV_FDB_DEL_TO_DEVICE,
 165        SWITCHDEV_FDB_OFFLOADED,
 166
 167        SWITCHDEV_PORT_OBJ_ADD, /* Blocking. */
 168        SWITCHDEV_PORT_OBJ_DEL, /* Blocking. */
 169        SWITCHDEV_PORT_ATTR_SET, /* May be blocking . */
 170
 171        SWITCHDEV_VXLAN_FDB_ADD_TO_BRIDGE,
 172        SWITCHDEV_VXLAN_FDB_DEL_TO_BRIDGE,
 173        SWITCHDEV_VXLAN_FDB_ADD_TO_DEVICE,
 174        SWITCHDEV_VXLAN_FDB_DEL_TO_DEVICE,
 175        SWITCHDEV_VXLAN_FDB_OFFLOADED,
 176};
 177
 178struct switchdev_notifier_info {
 179        struct net_device *dev;
 180        struct netlink_ext_ack *extack;
 181};
 182
 183struct switchdev_notifier_fdb_info {
 184        struct switchdev_notifier_info info; /* must be first */
 185        const unsigned char *addr;
 186        u16 vid;
 187        u8 added_by_user:1,
 188           offloaded:1;
 189};
 190
 191struct switchdev_notifier_port_obj_info {
 192        struct switchdev_notifier_info info; /* must be first */
 193        const struct switchdev_obj *obj;
 194        struct switchdev_trans *trans;
 195        bool handled;
 196};
 197
 198struct switchdev_notifier_port_attr_info {
 199        struct switchdev_notifier_info info; /* must be first */
 200        const struct switchdev_attr *attr;
 201        struct switchdev_trans *trans;
 202        bool handled;
 203};
 204
 205static inline struct net_device *
 206switchdev_notifier_info_to_dev(const struct switchdev_notifier_info *info)
 207{
 208        return info->dev;
 209}
 210
 211static inline struct netlink_ext_ack *
 212switchdev_notifier_info_to_extack(const struct switchdev_notifier_info *info)
 213{
 214        return info->extack;
 215}
 216
 217#ifdef CONFIG_NET_SWITCHDEV
 218
 219void switchdev_deferred_process(void);
 220int switchdev_port_attr_set(struct net_device *dev,
 221                            const struct switchdev_attr *attr);
 222int switchdev_port_obj_add(struct net_device *dev,
 223                           const struct switchdev_obj *obj,
 224                           struct netlink_ext_ack *extack);
 225int switchdev_port_obj_del(struct net_device *dev,
 226                           const struct switchdev_obj *obj);
 227
 228int register_switchdev_notifier(struct notifier_block *nb);
 229int unregister_switchdev_notifier(struct notifier_block *nb);
 230int call_switchdev_notifiers(unsigned long val, struct net_device *dev,
 231                             struct switchdev_notifier_info *info,
 232                             struct netlink_ext_ack *extack);
 233
 234int register_switchdev_blocking_notifier(struct notifier_block *nb);
 235int unregister_switchdev_blocking_notifier(struct notifier_block *nb);
 236int call_switchdev_blocking_notifiers(unsigned long val, struct net_device *dev,
 237                                      struct switchdev_notifier_info *info,
 238                                      struct netlink_ext_ack *extack);
 239
 240void switchdev_port_fwd_mark_set(struct net_device *dev,
 241                                 struct net_device *group_dev,
 242                                 bool joining);
 243
 244int switchdev_handle_port_obj_add(struct net_device *dev,
 245                        struct switchdev_notifier_port_obj_info *port_obj_info,
 246                        bool (*check_cb)(const struct net_device *dev),
 247                        int (*add_cb)(struct net_device *dev,
 248                                      const struct switchdev_obj *obj,
 249                                      struct switchdev_trans *trans,
 250                                      struct netlink_ext_ack *extack));
 251int switchdev_handle_port_obj_del(struct net_device *dev,
 252                        struct switchdev_notifier_port_obj_info *port_obj_info,
 253                        bool (*check_cb)(const struct net_device *dev),
 254                        int (*del_cb)(struct net_device *dev,
 255                                      const struct switchdev_obj *obj));
 256
 257int switchdev_handle_port_attr_set(struct net_device *dev,
 258                        struct switchdev_notifier_port_attr_info *port_attr_info,
 259                        bool (*check_cb)(const struct net_device *dev),
 260                        int (*set_cb)(struct net_device *dev,
 261                                      const struct switchdev_attr *attr,
 262                                      struct switchdev_trans *trans));
 263#else
 264
 265static inline void switchdev_deferred_process(void)
 266{
 267}
 268
 269static inline int switchdev_port_attr_set(struct net_device *dev,
 270                                          const struct switchdev_attr *attr)
 271{
 272        return -EOPNOTSUPP;
 273}
 274
 275static inline int switchdev_port_obj_add(struct net_device *dev,
 276                                         const struct switchdev_obj *obj,
 277                                         struct netlink_ext_ack *extack)
 278{
 279        return -EOPNOTSUPP;
 280}
 281
 282static inline int switchdev_port_obj_del(struct net_device *dev,
 283                                         const struct switchdev_obj *obj)
 284{
 285        return -EOPNOTSUPP;
 286}
 287
 288static inline int register_switchdev_notifier(struct notifier_block *nb)
 289{
 290        return 0;
 291}
 292
 293static inline int unregister_switchdev_notifier(struct notifier_block *nb)
 294{
 295        return 0;
 296}
 297
 298static inline int call_switchdev_notifiers(unsigned long val,
 299                                           struct net_device *dev,
 300                                           struct switchdev_notifier_info *info,
 301                                           struct netlink_ext_ack *extack)
 302{
 303        return NOTIFY_DONE;
 304}
 305
 306static inline int
 307register_switchdev_blocking_notifier(struct notifier_block *nb)
 308{
 309        return 0;
 310}
 311
 312static inline int
 313unregister_switchdev_blocking_notifier(struct notifier_block *nb)
 314{
 315        return 0;
 316}
 317
 318static inline int
 319call_switchdev_blocking_notifiers(unsigned long val,
 320                                  struct net_device *dev,
 321                                  struct switchdev_notifier_info *info,
 322                                  struct netlink_ext_ack *extack)
 323{
 324        return NOTIFY_DONE;
 325}
 326
 327static inline int
 328switchdev_handle_port_obj_add(struct net_device *dev,
 329                        struct switchdev_notifier_port_obj_info *port_obj_info,
 330                        bool (*check_cb)(const struct net_device *dev),
 331                        int (*add_cb)(struct net_device *dev,
 332                                      const struct switchdev_obj *obj,
 333                                      struct switchdev_trans *trans,
 334                                      struct netlink_ext_ack *extack))
 335{
 336        return 0;
 337}
 338
 339static inline int
 340switchdev_handle_port_obj_del(struct net_device *dev,
 341                        struct switchdev_notifier_port_obj_info *port_obj_info,
 342                        bool (*check_cb)(const struct net_device *dev),
 343                        int (*del_cb)(struct net_device *dev,
 344                                      const struct switchdev_obj *obj))
 345{
 346        return 0;
 347}
 348
 349static inline int
 350switchdev_handle_port_attr_set(struct net_device *dev,
 351                        struct switchdev_notifier_port_attr_info *port_attr_info,
 352                        bool (*check_cb)(const struct net_device *dev),
 353                        int (*set_cb)(struct net_device *dev,
 354                                      const struct switchdev_attr *attr,
 355                                      struct switchdev_trans *trans))
 356{
 357        return 0;
 358}
 359#endif
 360
 361#endif /* _LINUX_SWITCHDEV_H_ */
 362