linux/drivers/usb/gadget/f_phonet.c
<<
>>
Prefs
   1/*
   2 * f_phonet.c -- USB CDC Phonet function
   3 *
   4 * Copyright (C) 2007-2008 Nokia Corporation. All rights reserved.
   5 *
   6 * Author: Rémi Denis-Courmont
   7 *
   8 * This program is free software; you can redistribute it and/or
   9 * modify it under the terms of the GNU General Public License
  10 * version 2 as published by the Free Software Foundation.
  11 *
  12 * This program is distributed in the hope that it will be useful, but
  13 * WITHOUT ANY WARRANTY; without even the implied warranty of
  14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
  15 * General Public License for more details.
  16 *
  17 * You should have received a copy of the GNU General Public License
  18 * along with this program; if not, write to the Free Software
  19 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
  20 * 02110-1301 USA
  21 */
  22
  23#include <linux/kernel.h>
  24#include <linux/device.h>
  25
  26#include <linux/netdevice.h>
  27#include <linux/if_ether.h>
  28#include <linux/if_phonet.h>
  29#include <linux/if_arp.h>
  30
  31#include <linux/usb/ch9.h>
  32#include <linux/usb/cdc.h>
  33#include <linux/usb/composite.h>
  34
  35#include "u_phonet.h"
  36
  37#define PN_MEDIA_USB    0x1B
  38#define MAXPACKET       512
  39#if (PAGE_SIZE % MAXPACKET)
  40#error MAXPACKET must divide PAGE_SIZE!
  41#endif
  42
  43/*-------------------------------------------------------------------------*/
  44
  45struct phonet_port {
  46        struct f_phonet                 *usb;
  47        spinlock_t                      lock;
  48};
  49
  50struct f_phonet {
  51        struct usb_function             function;
  52        struct {
  53                struct sk_buff          *skb;
  54                spinlock_t              lock;
  55        } rx;
  56        struct net_device               *dev;
  57        struct usb_ep                   *in_ep, *out_ep;
  58
  59        struct usb_request              *in_req;
  60        struct usb_request              *out_reqv[0];
  61};
  62
  63static int phonet_rxq_size = 17;
  64
  65static inline struct f_phonet *func_to_pn(struct usb_function *f)
  66{
  67        return container_of(f, struct f_phonet, function);
  68}
  69
  70/*-------------------------------------------------------------------------*/
  71
  72#define USB_CDC_SUBCLASS_PHONET 0xfe
  73#define USB_CDC_PHONET_TYPE     0xab
  74
  75static struct usb_interface_descriptor
  76pn_control_intf_desc = {
  77        .bLength =              sizeof pn_control_intf_desc,
  78        .bDescriptorType =      USB_DT_INTERFACE,
  79
  80        /* .bInterfaceNumber =  DYNAMIC, */
  81        .bInterfaceClass =      USB_CLASS_COMM,
  82        .bInterfaceSubClass =   USB_CDC_SUBCLASS_PHONET,
  83};
  84
  85static const struct usb_cdc_header_desc
  86pn_header_desc = {
  87        .bLength =              sizeof pn_header_desc,
  88        .bDescriptorType =      USB_DT_CS_INTERFACE,
  89        .bDescriptorSubType =   USB_CDC_HEADER_TYPE,
  90        .bcdCDC =               cpu_to_le16(0x0110),
  91};
  92
  93static const struct usb_cdc_header_desc
  94pn_phonet_desc = {
  95        .bLength =              sizeof pn_phonet_desc,
  96        .bDescriptorType =      USB_DT_CS_INTERFACE,
  97        .bDescriptorSubType =   USB_CDC_PHONET_TYPE,
  98        .bcdCDC =               cpu_to_le16(0x1505), /* ??? */
  99};
 100
 101static struct usb_cdc_union_desc
 102pn_union_desc = {
 103        .bLength =              sizeof pn_union_desc,
 104        .bDescriptorType =      USB_DT_CS_INTERFACE,
 105        .bDescriptorSubType =   USB_CDC_UNION_TYPE,
 106
 107        /* .bMasterInterface0 = DYNAMIC, */
 108        /* .bSlaveInterface0 =  DYNAMIC, */
 109};
 110
 111static struct usb_interface_descriptor
 112pn_data_nop_intf_desc = {
 113        .bLength =              sizeof pn_data_nop_intf_desc,
 114        .bDescriptorType =      USB_DT_INTERFACE,
 115
 116        /* .bInterfaceNumber =  DYNAMIC, */
 117        .bAlternateSetting =    0,
 118        .bNumEndpoints =        0,
 119        .bInterfaceClass =      USB_CLASS_CDC_DATA,
 120};
 121
 122static struct usb_interface_descriptor
 123pn_data_intf_desc = {
 124        .bLength =              sizeof pn_data_intf_desc,
 125        .bDescriptorType =      USB_DT_INTERFACE,
 126
 127        /* .bInterfaceNumber =  DYNAMIC, */
 128        .bAlternateSetting =    1,
 129        .bNumEndpoints =        2,
 130        .bInterfaceClass =      USB_CLASS_CDC_DATA,
 131};
 132
 133static struct usb_endpoint_descriptor
 134pn_fs_sink_desc = {
 135        .bLength =              USB_DT_ENDPOINT_SIZE,
 136        .bDescriptorType =      USB_DT_ENDPOINT,
 137
 138        .bEndpointAddress =     USB_DIR_OUT,
 139        .bmAttributes =         USB_ENDPOINT_XFER_BULK,
 140};
 141
 142static struct usb_endpoint_descriptor
 143pn_hs_sink_desc = {
 144        .bLength =              USB_DT_ENDPOINT_SIZE,
 145        .bDescriptorType =      USB_DT_ENDPOINT,
 146
 147        .bEndpointAddress =     USB_DIR_OUT,
 148        .bmAttributes =         USB_ENDPOINT_XFER_BULK,
 149        .wMaxPacketSize =       cpu_to_le16(MAXPACKET),
 150};
 151
 152static struct usb_endpoint_descriptor
 153pn_fs_source_desc = {
 154        .bLength =              USB_DT_ENDPOINT_SIZE,
 155        .bDescriptorType =      USB_DT_ENDPOINT,
 156
 157        .bEndpointAddress =     USB_DIR_IN,
 158        .bmAttributes =         USB_ENDPOINT_XFER_BULK,
 159};
 160
 161static struct usb_endpoint_descriptor
 162pn_hs_source_desc = {
 163        .bLength =              USB_DT_ENDPOINT_SIZE,
 164        .bDescriptorType =      USB_DT_ENDPOINT,
 165
 166        .bEndpointAddress =     USB_DIR_IN,
 167        .bmAttributes =         USB_ENDPOINT_XFER_BULK,
 168        .wMaxPacketSize =       cpu_to_le16(512),
 169};
 170
 171static struct usb_descriptor_header *fs_pn_function[] = {
 172        (struct usb_descriptor_header *) &pn_control_intf_desc,
 173        (struct usb_descriptor_header *) &pn_header_desc,
 174        (struct usb_descriptor_header *) &pn_phonet_desc,
 175        (struct usb_descriptor_header *) &pn_union_desc,
 176        (struct usb_descriptor_header *) &pn_data_nop_intf_desc,
 177        (struct usb_descriptor_header *) &pn_data_intf_desc,
 178        (struct usb_descriptor_header *) &pn_fs_sink_desc,
 179        (struct usb_descriptor_header *) &pn_fs_source_desc,
 180        NULL,
 181};
 182
 183static struct usb_descriptor_header *hs_pn_function[] = {
 184        (struct usb_descriptor_header *) &pn_control_intf_desc,
 185        (struct usb_descriptor_header *) &pn_header_desc,
 186        (struct usb_descriptor_header *) &pn_phonet_desc,
 187        (struct usb_descriptor_header *) &pn_union_desc,
 188        (struct usb_descriptor_header *) &pn_data_nop_intf_desc,
 189        (struct usb_descriptor_header *) &pn_data_intf_desc,
 190        (struct usb_descriptor_header *) &pn_hs_sink_desc,
 191        (struct usb_descriptor_header *) &pn_hs_source_desc,
 192        NULL,
 193};
 194
 195/*-------------------------------------------------------------------------*/
 196
 197static int pn_net_open(struct net_device *dev)
 198{
 199        netif_wake_queue(dev);
 200        return 0;
 201}
 202
 203static int pn_net_close(struct net_device *dev)
 204{
 205        netif_stop_queue(dev);
 206        return 0;
 207}
 208
 209static void pn_tx_complete(struct usb_ep *ep, struct usb_request *req)
 210{
 211        struct f_phonet *fp = ep->driver_data;
 212        struct net_device *dev = fp->dev;
 213        struct sk_buff *skb = req->context;
 214
 215        switch (req->status) {
 216        case 0:
 217                dev->stats.tx_packets++;
 218                dev->stats.tx_bytes += skb->len;
 219                break;
 220
 221        case -ESHUTDOWN: /* disconnected */
 222        case -ECONNRESET: /* disabled */
 223                dev->stats.tx_aborted_errors++;
 224        default:
 225                dev->stats.tx_errors++;
 226        }
 227
 228        dev_kfree_skb_any(skb);
 229        netif_wake_queue(dev);
 230}
 231
 232static int pn_net_xmit(struct sk_buff *skb, struct net_device *dev)
 233{
 234        struct phonet_port *port = netdev_priv(dev);
 235        struct f_phonet *fp;
 236        struct usb_request *req;
 237        unsigned long flags;
 238
 239        if (skb->protocol != htons(ETH_P_PHONET))
 240                goto out;
 241
 242        spin_lock_irqsave(&port->lock, flags);
 243        fp = port->usb;
 244        if (unlikely(!fp)) /* race with carrier loss */
 245                goto out_unlock;
 246
 247        req = fp->in_req;
 248        req->buf = skb->data;
 249        req->length = skb->len;
 250        req->complete = pn_tx_complete;
 251        req->zero = 1;
 252        req->context = skb;
 253
 254        if (unlikely(usb_ep_queue(fp->in_ep, req, GFP_ATOMIC)))
 255                goto out_unlock;
 256
 257        netif_stop_queue(dev);
 258        skb = NULL;
 259
 260out_unlock:
 261        spin_unlock_irqrestore(&port->lock, flags);
 262out:
 263        if (unlikely(skb)) {
 264                dev_kfree_skb(skb);
 265                dev->stats.tx_dropped++;
 266        }
 267        return NETDEV_TX_OK;
 268}
 269
 270static int pn_net_mtu(struct net_device *dev, int new_mtu)
 271{
 272        if ((new_mtu < PHONET_MIN_MTU) || (new_mtu > PHONET_MAX_MTU))
 273                return -EINVAL;
 274        dev->mtu = new_mtu;
 275        return 0;
 276}
 277
 278static const struct net_device_ops pn_netdev_ops = {
 279        .ndo_open       = pn_net_open,
 280        .ndo_stop       = pn_net_close,
 281        .ndo_start_xmit = pn_net_xmit,
 282        .ndo_change_mtu = pn_net_mtu,
 283};
 284
 285static void pn_net_setup(struct net_device *dev)
 286{
 287        dev->features           = 0;
 288        dev->type               = ARPHRD_PHONET;
 289        dev->flags              = IFF_POINTOPOINT | IFF_NOARP;
 290        dev->mtu                = PHONET_DEV_MTU;
 291        dev->hard_header_len    = 1;
 292        dev->dev_addr[0]        = PN_MEDIA_USB;
 293        dev->addr_len           = 1;
 294        dev->tx_queue_len       = 1;
 295
 296        dev->netdev_ops         = &pn_netdev_ops;
 297        dev->destructor         = free_netdev;
 298        dev->header_ops         = &phonet_header_ops;
 299}
 300
 301/*-------------------------------------------------------------------------*/
 302
 303/*
 304 * Queue buffer for data from the host
 305 */
 306static int
 307pn_rx_submit(struct f_phonet *fp, struct usb_request *req, gfp_t gfp_flags)
 308{
 309        struct net_device *dev = fp->dev;
 310        struct page *page;
 311        int err;
 312
 313        page = __netdev_alloc_page(dev, gfp_flags);
 314        if (!page)
 315                return -ENOMEM;
 316
 317        req->buf = page_address(page);
 318        req->length = PAGE_SIZE;
 319        req->context = page;
 320
 321        err = usb_ep_queue(fp->out_ep, req, gfp_flags);
 322        if (unlikely(err))
 323                netdev_free_page(dev, page);
 324        return err;
 325}
 326
 327static void pn_rx_complete(struct usb_ep *ep, struct usb_request *req)
 328{
 329        struct f_phonet *fp = ep->driver_data;
 330        struct net_device *dev = fp->dev;
 331        struct page *page = req->context;
 332        struct sk_buff *skb;
 333        unsigned long flags;
 334        int status = req->status;
 335
 336        switch (status) {
 337        case 0:
 338                spin_lock_irqsave(&fp->rx.lock, flags);
 339                skb = fp->rx.skb;
 340                if (!skb)
 341                        skb = fp->rx.skb = netdev_alloc_skb(dev, 12);
 342                if (req->actual < req->length) /* Last fragment */
 343                        fp->rx.skb = NULL;
 344                spin_unlock_irqrestore(&fp->rx.lock, flags);
 345
 346                if (unlikely(!skb))
 347                        break;
 348                skb_add_rx_frag(skb, skb_shinfo(skb)->nr_frags, page, 0,
 349                                req->actual);
 350                page = NULL;
 351
 352                if (req->actual < req->length) { /* Last fragment */
 353                        skb->protocol = htons(ETH_P_PHONET);
 354                        skb_reset_mac_header(skb);
 355                        pskb_pull(skb, 1);
 356                        skb->dev = dev;
 357                        dev->stats.rx_packets++;
 358                        dev->stats.rx_bytes += skb->len;
 359
 360                        netif_rx(skb);
 361                }
 362                break;
 363
 364        /* Do not resubmit in these cases: */
 365        case -ESHUTDOWN: /* disconnect */
 366        case -ECONNABORTED: /* hw reset */
 367        case -ECONNRESET: /* dequeued (unlink or netif down) */
 368                req = NULL;
 369                break;
 370
 371        /* Do resubmit in these cases: */
 372        case -EOVERFLOW: /* request buffer overflow */
 373                dev->stats.rx_over_errors++;
 374        default:
 375                dev->stats.rx_errors++;
 376                break;
 377        }
 378
 379        if (page)
 380                netdev_free_page(dev, page);
 381        if (req)
 382                pn_rx_submit(fp, req, GFP_ATOMIC);
 383}
 384
 385/*-------------------------------------------------------------------------*/
 386
 387static void __pn_reset(struct usb_function *f)
 388{
 389        struct f_phonet *fp = func_to_pn(f);
 390        struct net_device *dev = fp->dev;
 391        struct phonet_port *port = netdev_priv(dev);
 392
 393        netif_carrier_off(dev);
 394        port->usb = NULL;
 395
 396        usb_ep_disable(fp->out_ep);
 397        usb_ep_disable(fp->in_ep);
 398        if (fp->rx.skb) {
 399                dev_kfree_skb_irq(fp->rx.skb);
 400                fp->rx.skb = NULL;
 401        }
 402}
 403
 404static int pn_set_alt(struct usb_function *f, unsigned intf, unsigned alt)
 405{
 406        struct f_phonet *fp = func_to_pn(f);
 407        struct usb_gadget *gadget = fp->function.config->cdev->gadget;
 408
 409        if (intf == pn_control_intf_desc.bInterfaceNumber)
 410                /* control interface, no altsetting */
 411                return (alt > 0) ? -EINVAL : 0;
 412
 413        if (intf == pn_data_intf_desc.bInterfaceNumber) {
 414                struct net_device *dev = fp->dev;
 415                struct phonet_port *port = netdev_priv(dev);
 416
 417                /* data intf (0: inactive, 1: active) */
 418                if (alt > 1)
 419                        return -EINVAL;
 420
 421                spin_lock(&port->lock);
 422                __pn_reset(f);
 423                if (alt == 1) {
 424                        struct usb_endpoint_descriptor *out, *in;
 425                        int i;
 426
 427                        out = ep_choose(gadget,
 428                                        &pn_hs_sink_desc,
 429                                        &pn_fs_sink_desc);
 430                        in = ep_choose(gadget,
 431                                        &pn_hs_source_desc,
 432                                        &pn_fs_source_desc);
 433                        usb_ep_enable(fp->out_ep, out);
 434                        usb_ep_enable(fp->in_ep, in);
 435
 436                        port->usb = fp;
 437                        fp->out_ep->driver_data = fp;
 438                        fp->in_ep->driver_data = fp;
 439
 440                        netif_carrier_on(dev);
 441                        for (i = 0; i < phonet_rxq_size; i++)
 442                                pn_rx_submit(fp, fp->out_reqv[i], GFP_ATOMIC);
 443                }
 444                spin_unlock(&port->lock);
 445                return 0;
 446        }
 447
 448        return -EINVAL;
 449}
 450
 451static int pn_get_alt(struct usb_function *f, unsigned intf)
 452{
 453        struct f_phonet *fp = func_to_pn(f);
 454
 455        if (intf == pn_control_intf_desc.bInterfaceNumber)
 456                return 0;
 457
 458        if (intf == pn_data_intf_desc.bInterfaceNumber) {
 459                struct phonet_port *port = netdev_priv(fp->dev);
 460                u8 alt;
 461
 462                spin_lock(&port->lock);
 463                alt = port->usb != NULL;
 464                spin_unlock(&port->lock);
 465                return alt;
 466        }
 467
 468        return -EINVAL;
 469}
 470
 471static void pn_disconnect(struct usb_function *f)
 472{
 473        struct f_phonet *fp = func_to_pn(f);
 474        struct phonet_port *port = netdev_priv(fp->dev);
 475        unsigned long flags;
 476
 477        /* remain disabled until set_alt */
 478        spin_lock_irqsave(&port->lock, flags);
 479        __pn_reset(f);
 480        spin_unlock_irqrestore(&port->lock, flags);
 481}
 482
 483/*-------------------------------------------------------------------------*/
 484
 485static __init
 486int pn_bind(struct usb_configuration *c, struct usb_function *f)
 487{
 488        struct usb_composite_dev *cdev = c->cdev;
 489        struct usb_gadget *gadget = cdev->gadget;
 490        struct f_phonet *fp = func_to_pn(f);
 491        struct usb_ep *ep;
 492        int status, i;
 493
 494        /* Reserve interface IDs */
 495        status = usb_interface_id(c, f);
 496        if (status < 0)
 497                goto err;
 498        pn_control_intf_desc.bInterfaceNumber = status;
 499        pn_union_desc.bMasterInterface0 = status;
 500
 501        status = usb_interface_id(c, f);
 502        if (status < 0)
 503                goto err;
 504        pn_data_nop_intf_desc.bInterfaceNumber = status;
 505        pn_data_intf_desc.bInterfaceNumber = status;
 506        pn_union_desc.bSlaveInterface0 = status;
 507
 508        /* Reserve endpoints */
 509        status = -ENODEV;
 510        ep = usb_ep_autoconfig(gadget, &pn_fs_sink_desc);
 511        if (!ep)
 512                goto err;
 513        fp->out_ep = ep;
 514        ep->driver_data = fp; /* Claim */
 515
 516        ep = usb_ep_autoconfig(gadget, &pn_fs_source_desc);
 517        if (!ep)
 518                goto err;
 519        fp->in_ep = ep;
 520        ep->driver_data = fp; /* Claim */
 521
 522        pn_hs_sink_desc.bEndpointAddress =
 523                pn_fs_sink_desc.bEndpointAddress;
 524        pn_hs_source_desc.bEndpointAddress =
 525                pn_fs_source_desc.bEndpointAddress;
 526
 527        /* Do not try to bind Phonet twice... */
 528        fp->function.descriptors = fs_pn_function;
 529        fp->function.hs_descriptors = hs_pn_function;
 530
 531        /* Incoming USB requests */
 532        status = -ENOMEM;
 533        for (i = 0; i < phonet_rxq_size; i++) {
 534                struct usb_request *req;
 535
 536                req = usb_ep_alloc_request(fp->out_ep, GFP_KERNEL);
 537                if (!req)
 538                        goto err;
 539
 540                req->complete = pn_rx_complete;
 541                fp->out_reqv[i] = req;
 542        }
 543
 544        /* Outgoing USB requests */
 545        fp->in_req = usb_ep_alloc_request(fp->in_ep, GFP_KERNEL);
 546        if (!fp->in_req)
 547                goto err;
 548
 549        INFO(cdev, "USB CDC Phonet function\n");
 550        INFO(cdev, "using %s, OUT %s, IN %s\n", cdev->gadget->name,
 551                fp->out_ep->name, fp->in_ep->name);
 552        return 0;
 553
 554err:
 555        if (fp->out_ep)
 556                fp->out_ep->driver_data = NULL;
 557        if (fp->in_ep)
 558                fp->in_ep->driver_data = NULL;
 559        ERROR(cdev, "USB CDC Phonet: cannot autoconfigure\n");
 560        return status;
 561}
 562
 563static void
 564pn_unbind(struct usb_configuration *c, struct usb_function *f)
 565{
 566        struct f_phonet *fp = func_to_pn(f);
 567        int i;
 568
 569        /* We are already disconnected */
 570        if (fp->in_req)
 571                usb_ep_free_request(fp->in_ep, fp->in_req);
 572        for (i = 0; i < phonet_rxq_size; i++)
 573                if (fp->out_reqv[i])
 574                        usb_ep_free_request(fp->out_ep, fp->out_reqv[i]);
 575
 576        kfree(fp);
 577}
 578
 579/*-------------------------------------------------------------------------*/
 580
 581static struct net_device *dev;
 582
 583int __init phonet_bind_config(struct usb_configuration *c)
 584{
 585        struct f_phonet *fp;
 586        int err, size;
 587
 588        size = sizeof(*fp) + (phonet_rxq_size * sizeof(struct usb_request *));
 589        fp = kzalloc(size, GFP_KERNEL);
 590        if (!fp)
 591                return -ENOMEM;
 592
 593        fp->dev = dev;
 594        fp->function.name = "phonet";
 595        fp->function.bind = pn_bind;
 596        fp->function.unbind = pn_unbind;
 597        fp->function.set_alt = pn_set_alt;
 598        fp->function.get_alt = pn_get_alt;
 599        fp->function.disable = pn_disconnect;
 600        spin_lock_init(&fp->rx.lock);
 601
 602        err = usb_add_function(c, &fp->function);
 603        if (err)
 604                kfree(fp);
 605        return err;
 606}
 607
 608int __init gphonet_setup(struct usb_gadget *gadget)
 609{
 610        struct phonet_port *port;
 611        int err;
 612
 613        /* Create net device */
 614        BUG_ON(dev);
 615        dev = alloc_netdev(sizeof(*port), "upnlink%d", pn_net_setup);
 616        if (!dev)
 617                return -ENOMEM;
 618
 619        port = netdev_priv(dev);
 620        spin_lock_init(&port->lock);
 621        netif_carrier_off(dev);
 622        SET_NETDEV_DEV(dev, &gadget->dev);
 623
 624        err = register_netdev(dev);
 625        if (err)
 626                free_netdev(dev);
 627        return err;
 628}
 629
 630void gphonet_cleanup(void)
 631{
 632        unregister_netdev(dev);
 633}
 634