linux/drivers/net/ethernet/qualcomm/rmnet/rmnet_config.c
<<
>>
Prefs
   1/* Copyright (c) 2013-2017, The Linux Foundation. All rights reserved.
   2 *
   3 * This program is free software; you can redistribute it and/or modify
   4 * it under the terms of the GNU General Public License version 2 and
   5 * only version 2 as published by the Free Software Foundation.
   6 *
   7 * This program is distributed in the hope that it will be useful,
   8 * but WITHOUT ANY WARRANTY; without even the implied warranty of
   9 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  10 * GNU General Public License for more details.
  11 *
  12 * RMNET configuration engine
  13 *
  14 */
  15
  16#include <net/sock.h>
  17#include <linux/module.h>
  18#include <linux/netlink.h>
  19#include <linux/netdevice.h>
  20#include "rmnet_config.h"
  21#include "rmnet_handlers.h"
  22#include "rmnet_vnd.h"
  23#include "rmnet_private.h"
  24
  25/* Locking scheme -
  26 * The shared resource which needs to be protected is realdev->rx_handler_data.
  27 * For the writer path, this is using rtnl_lock(). The writer paths are
  28 * rmnet_newlink(), rmnet_dellink() and rmnet_force_unassociate_device(). These
  29 * paths are already called with rtnl_lock() acquired in. There is also an
  30 * ASSERT_RTNL() to ensure that we are calling with rtnl acquired. For
  31 * dereference here, we will need to use rtnl_dereference(). Dev list writing
  32 * needs to happen with rtnl_lock() acquired for netdev_master_upper_dev_link().
  33 * For the reader path, the real_dev->rx_handler_data is called in the TX / RX
  34 * path. We only need rcu_read_lock() for these scenarios. In these cases,
  35 * the rcu_read_lock() is held in __dev_queue_xmit() and
  36 * netif_receive_skb_internal(), so readers need to use rcu_dereference_rtnl()
  37 * to get the relevant information. For dev list reading, we again acquire
  38 * rcu_read_lock() in rmnet_dellink() for netdev_master_upper_dev_get_rcu().
  39 * We also use unregister_netdevice_many() to free all rmnet devices in
  40 * rmnet_force_unassociate_device() so we dont lose the rtnl_lock() and free in
  41 * same context.
  42 */
  43
  44/* Local Definitions and Declarations */
  45
  46static int rmnet_is_real_dev_registered(const struct net_device *real_dev)
  47{
  48        return rcu_access_pointer(real_dev->rx_handler) == rmnet_rx_handler;
  49}
  50
  51/* Needs rtnl lock */
  52static struct rmnet_port*
  53rmnet_get_port_rtnl(const struct net_device *real_dev)
  54{
  55        return rtnl_dereference(real_dev->rx_handler_data);
  56}
  57
  58static int rmnet_unregister_real_device(struct net_device *real_dev,
  59                                        struct rmnet_port *port)
  60{
  61        if (port->nr_rmnet_devs)
  62                return -EINVAL;
  63
  64        kfree(port);
  65
  66        netdev_rx_handler_unregister(real_dev);
  67
  68        /* release reference on real_dev */
  69        dev_put(real_dev);
  70
  71        netdev_dbg(real_dev, "Removed from rmnet\n");
  72        return 0;
  73}
  74
  75static int rmnet_register_real_device(struct net_device *real_dev)
  76{
  77        struct rmnet_port *port;
  78        int rc, entry;
  79
  80        ASSERT_RTNL();
  81
  82        if (rmnet_is_real_dev_registered(real_dev))
  83                return 0;
  84
  85        port = kzalloc(sizeof(*port), GFP_ATOMIC);
  86        if (!port)
  87                return -ENOMEM;
  88
  89        port->dev = real_dev;
  90        rc = netdev_rx_handler_register(real_dev, rmnet_rx_handler, port);
  91        if (rc) {
  92                kfree(port);
  93                return -EBUSY;
  94        }
  95
  96        /* hold on to real dev for MAP data */
  97        dev_hold(real_dev);
  98
  99        for (entry = 0; entry < RMNET_MAX_LOGICAL_EP; entry++)
 100                INIT_HLIST_HEAD(&port->muxed_ep[entry]);
 101
 102        netdev_dbg(real_dev, "registered with rmnet\n");
 103        return 0;
 104}
 105
 106static void rmnet_unregister_bridge(struct net_device *dev,
 107                                    struct rmnet_port *port)
 108{
 109        struct rmnet_port *bridge_port;
 110        struct net_device *bridge_dev;
 111
 112        if (port->rmnet_mode != RMNET_EPMODE_BRIDGE)
 113                return;
 114
 115        /* bridge slave handling */
 116        if (!port->nr_rmnet_devs) {
 117                bridge_dev = port->bridge_ep;
 118
 119                bridge_port = rmnet_get_port_rtnl(bridge_dev);
 120                bridge_port->bridge_ep = NULL;
 121                bridge_port->rmnet_mode = RMNET_EPMODE_VND;
 122        } else {
 123                bridge_dev = port->bridge_ep;
 124
 125                bridge_port = rmnet_get_port_rtnl(bridge_dev);
 126                rmnet_unregister_real_device(bridge_dev, bridge_port);
 127        }
 128}
 129
 130static int rmnet_newlink(struct net *src_net, struct net_device *dev,
 131                         struct nlattr *tb[], struct nlattr *data[],
 132                         struct netlink_ext_ack *extack)
 133{
 134        u32 data_format = RMNET_INGRESS_FORMAT_DEAGGREGATION;
 135        struct net_device *real_dev;
 136        int mode = RMNET_EPMODE_VND;
 137        struct rmnet_endpoint *ep;
 138        struct rmnet_port *port;
 139        int err = 0;
 140        u16 mux_id;
 141
 142        real_dev = __dev_get_by_index(src_net, nla_get_u32(tb[IFLA_LINK]));
 143        if (!real_dev || !dev)
 144                return -ENODEV;
 145
 146        if (!data[IFLA_VLAN_ID])
 147                return -EINVAL;
 148
 149        ep = kzalloc(sizeof(*ep), GFP_ATOMIC);
 150        if (!ep)
 151                return -ENOMEM;
 152
 153        mux_id = nla_get_u16(data[IFLA_VLAN_ID]);
 154
 155        err = rmnet_register_real_device(real_dev);
 156        if (err)
 157                goto err0;
 158
 159        port = rmnet_get_port_rtnl(real_dev);
 160        err = rmnet_vnd_newlink(mux_id, dev, port, real_dev, ep);
 161        if (err)
 162                goto err1;
 163
 164        port->rmnet_mode = mode;
 165
 166        hlist_add_head_rcu(&ep->hlnode, &port->muxed_ep[mux_id]);
 167
 168        if (data[IFLA_VLAN_FLAGS]) {
 169                struct ifla_vlan_flags *flags;
 170
 171                flags = nla_data(data[IFLA_VLAN_FLAGS]);
 172                data_format = flags->flags & flags->mask;
 173        }
 174
 175        netdev_dbg(dev, "data format [0x%08X]\n", data_format);
 176        port->data_format = data_format;
 177
 178        return 0;
 179
 180err1:
 181        rmnet_unregister_real_device(real_dev, port);
 182err0:
 183        kfree(ep);
 184        return err;
 185}
 186
 187static void rmnet_dellink(struct net_device *dev, struct list_head *head)
 188{
 189        struct rmnet_priv *priv = netdev_priv(dev);
 190        struct net_device *real_dev;
 191        struct rmnet_endpoint *ep;
 192        struct rmnet_port *port;
 193        u8 mux_id;
 194
 195        real_dev = priv->real_dev;
 196
 197        if (!real_dev || !rmnet_is_real_dev_registered(real_dev))
 198                return;
 199
 200        port = rmnet_get_port_rtnl(real_dev);
 201
 202        mux_id = rmnet_vnd_get_mux(dev);
 203
 204        ep = rmnet_get_endpoint(port, mux_id);
 205        if (ep) {
 206                hlist_del_init_rcu(&ep->hlnode);
 207                rmnet_unregister_bridge(dev, port);
 208                rmnet_vnd_dellink(mux_id, port, ep);
 209                kfree(ep);
 210        }
 211        rmnet_unregister_real_device(real_dev, port);
 212
 213        unregister_netdevice_queue(dev, head);
 214}
 215
 216static void rmnet_force_unassociate_device(struct net_device *dev)
 217{
 218        struct net_device *real_dev = dev;
 219        struct hlist_node *tmp_ep;
 220        struct rmnet_endpoint *ep;
 221        struct rmnet_port *port;
 222        unsigned long bkt_ep;
 223        LIST_HEAD(list);
 224
 225        if (!rmnet_is_real_dev_registered(real_dev))
 226                return;
 227
 228        ASSERT_RTNL();
 229
 230        port = rmnet_get_port_rtnl(dev);
 231
 232        rcu_read_lock();
 233        rmnet_unregister_bridge(dev, port);
 234
 235        hash_for_each_safe(port->muxed_ep, bkt_ep, tmp_ep, ep, hlnode) {
 236                unregister_netdevice_queue(ep->egress_dev, &list);
 237                rmnet_vnd_dellink(ep->mux_id, port, ep);
 238
 239                hlist_del_init_rcu(&ep->hlnode);
 240                kfree(ep);
 241        }
 242
 243        rcu_read_unlock();
 244        unregister_netdevice_many(&list);
 245
 246        rmnet_unregister_real_device(real_dev, port);
 247}
 248
 249static int rmnet_config_notify_cb(struct notifier_block *nb,
 250                                  unsigned long event, void *data)
 251{
 252        struct net_device *dev = netdev_notifier_info_to_dev(data);
 253
 254        if (!dev)
 255                return NOTIFY_DONE;
 256
 257        switch (event) {
 258        case NETDEV_UNREGISTER:
 259                netdev_dbg(dev, "Kernel unregister\n");
 260                rmnet_force_unassociate_device(dev);
 261                break;
 262
 263        default:
 264                break;
 265        }
 266
 267        return NOTIFY_DONE;
 268}
 269
 270static struct notifier_block rmnet_dev_notifier __read_mostly = {
 271        .notifier_call = rmnet_config_notify_cb,
 272};
 273
 274static int rmnet_rtnl_validate(struct nlattr *tb[], struct nlattr *data[],
 275                               struct netlink_ext_ack *extack)
 276{
 277        u16 mux_id;
 278
 279        if (!data || !data[IFLA_VLAN_ID])
 280                return -EINVAL;
 281
 282        mux_id = nla_get_u16(data[IFLA_VLAN_ID]);
 283        if (mux_id > (RMNET_MAX_LOGICAL_EP - 1))
 284                return -ERANGE;
 285
 286        return 0;
 287}
 288
 289static int rmnet_changelink(struct net_device *dev, struct nlattr *tb[],
 290                            struct nlattr *data[],
 291                            struct netlink_ext_ack *extack)
 292{
 293        struct rmnet_priv *priv = netdev_priv(dev);
 294        struct net_device *real_dev;
 295        struct rmnet_endpoint *ep;
 296        struct rmnet_port *port;
 297        u16 mux_id;
 298
 299        real_dev = __dev_get_by_index(dev_net(dev),
 300                                      nla_get_u32(tb[IFLA_LINK]));
 301
 302        if (!real_dev || !dev || !rmnet_is_real_dev_registered(real_dev))
 303                return -ENODEV;
 304
 305        port = rmnet_get_port_rtnl(real_dev);
 306
 307        if (data[IFLA_VLAN_ID]) {
 308                mux_id = nla_get_u16(data[IFLA_VLAN_ID]);
 309                ep = rmnet_get_endpoint(port, priv->mux_id);
 310
 311                hlist_del_init_rcu(&ep->hlnode);
 312                hlist_add_head_rcu(&ep->hlnode, &port->muxed_ep[mux_id]);
 313
 314                ep->mux_id = mux_id;
 315                priv->mux_id = mux_id;
 316        }
 317
 318        if (data[IFLA_VLAN_FLAGS]) {
 319                struct ifla_vlan_flags *flags;
 320
 321                flags = nla_data(data[IFLA_VLAN_FLAGS]);
 322                port->data_format = flags->flags & flags->mask;
 323        }
 324
 325        return 0;
 326}
 327
 328static size_t rmnet_get_size(const struct net_device *dev)
 329{
 330        return nla_total_size(2) /* IFLA_VLAN_ID */ +
 331               nla_total_size(sizeof(struct ifla_vlan_flags)); /* IFLA_VLAN_FLAGS */
 332}
 333
 334struct rtnl_link_ops rmnet_link_ops __read_mostly = {
 335        .kind           = "rmnet",
 336        .maxtype        = __IFLA_VLAN_MAX,
 337        .priv_size      = sizeof(struct rmnet_priv),
 338        .setup          = rmnet_vnd_setup,
 339        .validate       = rmnet_rtnl_validate,
 340        .newlink        = rmnet_newlink,
 341        .dellink        = rmnet_dellink,
 342        .get_size       = rmnet_get_size,
 343        .changelink     = rmnet_changelink,
 344};
 345
 346/* Needs either rcu_read_lock() or rtnl lock */
 347struct rmnet_port *rmnet_get_port(struct net_device *real_dev)
 348{
 349        if (rmnet_is_real_dev_registered(real_dev))
 350                return rcu_dereference_rtnl(real_dev->rx_handler_data);
 351        else
 352                return NULL;
 353}
 354
 355struct rmnet_endpoint *rmnet_get_endpoint(struct rmnet_port *port, u8 mux_id)
 356{
 357        struct rmnet_endpoint *ep;
 358
 359        hlist_for_each_entry_rcu(ep, &port->muxed_ep[mux_id], hlnode) {
 360                if (ep->mux_id == mux_id)
 361                        return ep;
 362        }
 363
 364        return NULL;
 365}
 366
 367int rmnet_add_bridge(struct net_device *rmnet_dev,
 368                     struct net_device *slave_dev,
 369                     struct netlink_ext_ack *extack)
 370{
 371        struct rmnet_priv *priv = netdev_priv(rmnet_dev);
 372        struct net_device *real_dev = priv->real_dev;
 373        struct rmnet_port *port, *slave_port;
 374        int err;
 375
 376        port = rmnet_get_port(real_dev);
 377
 378        /* If there is more than one rmnet dev attached, its probably being
 379         * used for muxing. Skip the briding in that case
 380         */
 381        if (port->nr_rmnet_devs > 1)
 382                return -EINVAL;
 383
 384        if (rmnet_is_real_dev_registered(slave_dev))
 385                return -EBUSY;
 386
 387        err = rmnet_register_real_device(slave_dev);
 388        if (err)
 389                return -EBUSY;
 390
 391        slave_port = rmnet_get_port(slave_dev);
 392        slave_port->rmnet_mode = RMNET_EPMODE_BRIDGE;
 393        slave_port->bridge_ep = real_dev;
 394
 395        port->rmnet_mode = RMNET_EPMODE_BRIDGE;
 396        port->bridge_ep = slave_dev;
 397
 398        netdev_dbg(slave_dev, "registered with rmnet as slave\n");
 399        return 0;
 400}
 401
 402int rmnet_del_bridge(struct net_device *rmnet_dev,
 403                     struct net_device *slave_dev)
 404{
 405        struct rmnet_priv *priv = netdev_priv(rmnet_dev);
 406        struct net_device *real_dev = priv->real_dev;
 407        struct rmnet_port *port, *slave_port;
 408
 409        port = rmnet_get_port(real_dev);
 410        port->rmnet_mode = RMNET_EPMODE_VND;
 411        port->bridge_ep = NULL;
 412
 413        slave_port = rmnet_get_port(slave_dev);
 414        rmnet_unregister_real_device(slave_dev, slave_port);
 415
 416        netdev_dbg(slave_dev, "removed from rmnet as slave\n");
 417        return 0;
 418}
 419
 420/* Startup/Shutdown */
 421
 422static int __init rmnet_init(void)
 423{
 424        int rc;
 425
 426        rc = register_netdevice_notifier(&rmnet_dev_notifier);
 427        if (rc != 0)
 428                return rc;
 429
 430        rc = rtnl_link_register(&rmnet_link_ops);
 431        if (rc != 0) {
 432                unregister_netdevice_notifier(&rmnet_dev_notifier);
 433                return rc;
 434        }
 435        return rc;
 436}
 437
 438static void __exit rmnet_exit(void)
 439{
 440        unregister_netdevice_notifier(&rmnet_dev_notifier);
 441        rtnl_link_unregister(&rmnet_link_ops);
 442}
 443
 444module_init(rmnet_init)
 445module_exit(rmnet_exit)
 446MODULE_LICENSE("GPL v2");
 447