This adds usb framework support for super-speed usb, which will
further facilitate to add stack support for xHCI.

Signed-off-by: Vikas C Sajjan <vikas.saj...@samsung.com>
Signedoff-by: Vivek Gautam <gautam.vi...@samsung.com>
---
 common/cmd_usb.c         |    6 +-
 common/usb.c             |   41 ++++++++-
 common/usb_hub.c         |   26 +++++-
 common/usb_storage.c     |   35 +++++----
 include/common.h         |    2 +
 include/linux/usb/ch9.h  |    2 +-
 include/usb.h            |   15 +++-
 include/usb_defs.h       |   26 ++++++-
 include/usbdescriptors.h |  201 ++++++++++++++++++++++++++++++++++++++++++++++
 9 files changed, 322 insertions(+), 32 deletions(-)

diff --git a/common/cmd_usb.c b/common/cmd_usb.c
index c128455..013b2e8 100644
--- a/common/cmd_usb.c
+++ b/common/cmd_usb.c
@@ -262,7 +262,7 @@ void usb_display_config(struct usb_device *dev)
                ifdesc = &config->if_desc[i];
                usb_display_if_desc(&ifdesc->desc, dev);
                for (ii = 0; ii < ifdesc->no_of_ep; ii++) {
-                       epdesc = &ifdesc->ep_desc[ii];
+                       epdesc = &ifdesc->ep_desc[ii].ep_desc;
                        usb_display_ep_desc(epdesc);
                }
        }
@@ -271,7 +271,9 @@ void usb_display_config(struct usb_device *dev)
 
 static inline char *portspeed(int speed)
 {
-       if (speed == USB_SPEED_HIGH)
+       if (speed == USB_SPEED_SUPER)
+               return "5 Gb/s";
+       else if (speed == USB_SPEED_HIGH)
                return "480 Mb/s";
        else if (speed == USB_SPEED_LOW)
                return "1.5 Mb/s";
diff --git a/common/usb.c b/common/usb.c
index 50b8175..691d9ac 100644
--- a/common/usb.c
+++ b/common/usb.c
@@ -304,7 +304,7 @@ usb_set_maxpacket_ep(struct usb_device *dev, int if_idx, 
int ep_idx)
        struct usb_endpoint_descriptor *ep;
        u16 ep_wMaxPacketSize;
 
-       ep = &dev->config.if_desc[if_idx].ep_desc[ep_idx];
+       ep = &dev->config.if_desc[if_idx].ep_desc[ep_idx].ep_desc;
 
        b = ep->bEndpointAddress & USB_ENDPOINT_NUMBER_MASK;
        ep_wMaxPacketSize = get_unaligned(&ep->wMaxPacketSize);
@@ -360,6 +360,7 @@ static int usb_parse_config(struct usb_device *dev,
        int index, ifno, epno, curr_if_num;
        int i;
        u16 ep_wMaxPacketSize;
+       struct usb_interface *if_desc = NULL;
 
        ifno = -1;
        epno = -1;
@@ -401,21 +402,27 @@ static int usb_parse_config(struct usb_device *dev,
                        break;
                case USB_DT_ENDPOINT:
                        epno = dev->config.if_desc[ifno].no_of_ep;
+                       if_desc = &dev->config.if_desc[ifno];
                        /* found an endpoint */
-                       dev->config.if_desc[ifno].no_of_ep++;
-                       memcpy(&dev->config.if_desc[ifno].ep_desc[epno],
+                       if_desc->no_of_ep++;
+                       memcpy(&if_desc->ep_desc[epno].ep_desc,
                                &buffer[index], buffer[index]);
                        ep_wMaxPacketSize = get_unaligned(&dev->config.\
                                                        if_desc[ifno].\
                                                        ep_desc[epno].\
-                                                       wMaxPacketSize);
+                                                       ep_desc.wMaxPacketSize);
                        put_unaligned(le16_to_cpu(ep_wMaxPacketSize),
                                        &dev->config.\
                                        if_desc[ifno].\
                                        ep_desc[epno].\
-                                       wMaxPacketSize);
+                                       ep_desc.wMaxPacketSize);
                        USB_PRINTF("if %d, ep %d\n", ifno, epno);
                        break;
+               case USB_DT_SS_ENDPOINT_COMP:
+                       if_desc = &dev->config.if_desc[ifno];
+                       memcpy(&(if_desc->ep_desc[epno].ss_ep_comp),
+                               &buffer[index], buffer[index]);
+                       break;
                default:
                        if (head->bLength == 0)
                                return 1;
@@ -659,6 +666,18 @@ static int usb_get_string(struct usb_device *dev, unsigned 
short langid,
        return result;
 }
 
+/* Allocate usb device */
+int usb_alloc_dev(struct usb_device *dev)
+{
+       int res;
+
+       USB_PRINTF("alloc device\n");
+       res = usb_control_msg(dev, usb_sndctrlpipe(dev->parent, 0),
+                               USB_REQ_ALLOC_DEV, 0, 0, 0,
+                               NULL, 0, USB_CNTL_TIMEOUT);
+
+       return res;
+}
 
 static void usb_try_string_workarounds(unsigned char *buf, int *length)
 {
@@ -852,7 +871,10 @@ int usb_new_device(struct usb_device *dev)
        struct usb_device_descriptor *desc;
        int port = -1;
        struct usb_device *parent = dev->parent;
+
+#ifndef CONFIG_USB_XHCI
        unsigned short portstatus;
+#endif
 
        /* send 64-byte GET-DEVICE-DESCRIPTOR request.  Since the descriptor is
         * only 18 bytes long, this will terminate with a short packet.  But if
@@ -889,12 +911,21 @@ int usb_new_device(struct usb_device *dev)
                        return 1;
                }
 
+       /*
+        * Putting up the code here for slot assignment and initialization:
+        * xHCI spec sec 4.3.2, 4.3.3
+        */
+#ifdef CONFIG_USB_XHCI
+               /* Call if and only if device is attached and detected */
+               usb_alloc_dev(dev);
+#else
                /* reset the port for the second time */
                err = hub_port_reset(dev->parent, port, &portstatus);
                if (err < 0) {
                        printf("\n     Couldn't reset port %i\n", port);
                        return 1;
                }
+#endif
        }
 #endif
 
diff --git a/common/usb_hub.c b/common/usb_hub.c
index e4a1201..8a00894 100644
--- a/common/usb_hub.c
+++ b/common/usb_hub.c
@@ -204,7 +204,12 @@ int hub_port_reset(struct usb_device *dev, int port,
 }
 
 
-void usb_hub_port_connect_change(struct usb_device *dev, int port)
+/*
+ * Adding the flag do_port_reset: USB 2.0 device requires port reset
+ * while USB 3.0 device does not.
+ */
+void usb_hub_port_connect_change(struct usb_device *dev, int port,
+                                                       int do_port_reset)
 {
        struct usb_device *usb;
        ALLOC_CACHE_ALIGN_BUFFER(struct usb_port_status, portsts, 1);
@@ -235,11 +240,21 @@ void usb_hub_port_connect_change(struct usb_device *dev, 
int port)
        }
        mdelay(200);
 
+#ifdef CONFIG_USB_XHCI
+       /* Reset the port */
+       if (do_port_reset) {
+               if (hub_port_reset(dev, port, &portstatus) < 0) {
+                       printf("cannot reset port %i!?\n", port + 1);
+                       return;
+               }
+       }
+#else
        /* Reset the port */
        if (hub_port_reset(dev, port, &portstatus) < 0) {
                printf("cannot reset port %i!?\n", port + 1);
                return;
        }
+#endif
 
        mdelay(200);
 
@@ -409,7 +424,10 @@ static int usb_hub_configure(struct usb_device *dev)
 
                if (portchange & USB_PORT_STAT_C_CONNECTION) {
                        USB_HUB_PRINTF("port %d connection change\n", i + 1);
-                       usb_hub_port_connect_change(dev, i);
+                       usb_hub_port_connect_change(dev, i, 0);
+               } else if ((portstatus & 0x1) == 1) {
+                       USB_HUB_PRINTF("port %d connection change\n", i + 1);
+                       usb_hub_port_connect_change(dev, i, 1);
                }
                if (portchange & USB_PORT_STAT_C_ENABLE) {
                        USB_HUB_PRINTF("port %d enable change, status %x\n",
@@ -426,7 +444,7 @@ static int usb_hub_configure(struct usb_device *dev)
                                USB_HUB_PRINTF("already running port %i "  \
                                                "disabled by hub (EMI?), " \
                                                "re-enabling...\n", i + 1);
-                                       usb_hub_port_connect_change(dev, i);
+                                       usb_hub_port_connect_change(dev, i, 0);
                        }
                }
                if (portstatus & USB_PORT_STAT_SUSPEND) {
@@ -470,7 +488,7 @@ int usb_hub_probe(struct usb_device *dev, int ifnum)
        /* Multiple endpoints? What kind of mutant ninja-hub is this? */
        if (iface->desc.bNumEndpoints != 1)
                return 0;
-       ep = &iface->ep_desc[0];
+       ep = &iface->ep_desc[0].ep_desc;
        /* Output endpoint? Curiousier and curiousier.. */
        if (!(ep->bEndpointAddress & USB_DIR_IN))
                return 0;
diff --git a/common/usb_storage.c b/common/usb_storage.c
index 0c2a4c7..53d41d8 100644
--- a/common/usb_storage.c
+++ b/common/usb_storage.c
@@ -262,7 +262,7 @@ int usb_stor_scan(int mode)
        usb_max_devs = 0;
        for (i = 0; i < USB_MAX_DEVICE; i++) {
                dev = usb_get_dev_index(i); /* get device */
-               USB_STOR_PRINTF("i=%d\n", i);
+               USB_STOR_PRINTF("i=%d, dev_num=%d\n", i, dev->devnum);
                if (dev == NULL)
                        break; /* no more devices available */
 
@@ -278,10 +278,11 @@ int usb_stor_scan(int mode)
                             lun++) {
                                usb_dev_desc[usb_max_devs].lun = lun;
                                if (usb_stor_get_info(dev, &usb_stor[start],
-                                                     
&usb_dev_desc[usb_max_devs]) == 1) {
-                               usb_max_devs++;
-               }
+                                               &usb_dev_desc[usb_max_devs]) == 
1) {
+                                       usb_max_devs++;
+                               }
                        }
+
                }
                /* if storage device */
                if (usb_max_devs == USB_MAX_STOR_DEV) {
@@ -511,7 +512,7 @@ int usb_stor_BBB_comdat(ccb *srb, struct us_data *us)
        dir_in = US_DIRECTION(srb->cmd[0]);
 
 #ifdef BBB_COMDAT_TRACE
-       printf("dir %d lun %d cmdlen %d cmd %p datalen %d pdata %p\n",
+       printf("dir %d lun %d cmdlen %d cmd %p datalen %lu pdata %p\n",
                dir_in, srb->lun, srb->cmdlen, srb->cmd, srb->datalen,
                srb->pdata);
        if (srb->cmdlen) {
@@ -1208,6 +1209,7 @@ int usb_storage_probe(struct usb_device *dev, unsigned 
int ifnum,
 {
        struct usb_interface *iface;
        int i;
+       struct usb_endpoint_descriptor *ep_desc;
        unsigned int flags = 0;
 
        int protocol = 0;
@@ -1290,24 +1292,25 @@ int usb_storage_probe(struct usb_device *dev, unsigned 
int ifnum,
         * We will ignore any others.
         */
        for (i = 0; i < iface->desc.bNumEndpoints; i++) {
+               ep_desc = &iface->ep_desc[i].ep_desc;
                /* is it an BULK endpoint? */
-               if ((iface->ep_desc[i].bmAttributes &
-                    USB_ENDPOINT_XFERTYPE_MASK) == USB_ENDPOINT_XFER_BULK) {
-                       if (iface->ep_desc[i].bEndpointAddress & USB_DIR_IN)
-                               ss->ep_in = iface->ep_desc[i].bEndpointAddress &
-                                       USB_ENDPOINT_NUMBER_MASK;
+               if ((ep_desc->bmAttributes &
+                       USB_ENDPOINT_XFERTYPE_MASK) == USB_ENDPOINT_XFER_BULK) {
+                       if (ep_desc->bEndpointAddress & USB_DIR_IN)
+                               ss->ep_in = ep_desc->bEndpointAddress &
+                                               USB_ENDPOINT_NUMBER_MASK;
                        else
                                ss->ep_out =
-                                       iface->ep_desc[i].bEndpointAddress &
+                                       ep_desc->bEndpointAddress &
                                        USB_ENDPOINT_NUMBER_MASK;
                }
 
                /* is it an interrupt endpoint? */
-               if ((iface->ep_desc[i].bmAttributes &
-                   USB_ENDPOINT_XFERTYPE_MASK) == USB_ENDPOINT_XFER_INT) {
-                       ss->ep_int = iface->ep_desc[i].bEndpointAddress &
-                               USB_ENDPOINT_NUMBER_MASK;
-                       ss->irqinterval = iface->ep_desc[i].bInterval;
+               if ((ep_desc->bmAttributes & USB_ENDPOINT_XFERTYPE_MASK)
+                                               == USB_ENDPOINT_XFER_INT) {
+                       ss->ep_int = ep_desc->bEndpointAddress &
+                                               USB_ENDPOINT_NUMBER_MASK;
+                       ss->irqinterval = ep_desc->bInterval;
                }
        }
        USB_STOR_PRINTF("Endpoints In %d Out %d Int %d\n",
diff --git a/include/common.h b/include/common.h
index b23e90b..ef5f687 100644
--- a/include/common.h
+++ b/include/common.h
@@ -211,6 +211,8 @@ typedef void (interrupt_handler_t)(void *);
 #define MIN(x, y)  min(x, y)
 #define MAX(x, y)  max(x, y)
 
+#define min3(a, b, c)  min(min(a, b), c)
+
 /*
  * Return the absolute value of a number.
  *
diff --git a/include/linux/usb/ch9.h b/include/linux/usb/ch9.h
index ce1d1e1..33af2f4 100644
--- a/include/linux/usb/ch9.h
+++ b/include/linux/usb/ch9.h
@@ -122,7 +122,6 @@
 
 #define USB_ENDPOINT_HALT              0       /* IN/OUT will STALL */
 
-
 /**
  * struct usb_ctrlrequest - SETUP data for a USB device control request
  * @bRequestType: matches the USB bmRequestType field
@@ -491,6 +490,7 @@ enum usb_device_speed {
        USB_SPEED_UNKNOWN = 0,                  /* enumerating */
        USB_SPEED_LOW, USB_SPEED_FULL,          /* usb 1.1 */
        USB_SPEED_HIGH,                         /* usb 2.0 */
+       USB_SPEED_SUPER,                        /* usb 3.0 */
        USB_SPEED_VARIABLE,                     /* wireless (usb 2.5) */
 };
 
diff --git a/include/usb.h b/include/usb.h
index 9dd8791..a7a0f22 100644
--- a/include/usb.h
+++ b/include/usb.h
@@ -73,6 +73,16 @@ struct usb_descriptor_header {
        unsigned char   bDescriptorType;
 } __attribute__ ((packed));
 
+struct usb_ep_desc {
+       struct usb_endpoint_descriptor          ep_desc;
+       /*
+        * Super Speed Device will have Super Speed Endpoint
+        * Companion Descriptor  (section 9.6.7 of usb 3.0 spec)
+        * Revision 1.0 June 6th 2011
+        */
+       struct usb_ss_ep_comp_descriptor        ss_ep_comp;
+};
+
 /* Interface */
 struct usb_interface {
        struct usb_interface_descriptor desc;
@@ -81,7 +91,7 @@ struct usb_interface {
        unsigned char   num_altsetting;
        unsigned char   act_altsetting;
 
-       struct usb_endpoint_descriptor ep_desc[USB_MAXENDPOINTS];
+       struct usb_ep_desc ep_desc[USB_MAXENDPOINTS];
 } __attribute__ ((packed));
 
 /* Configuration information.. */
@@ -153,7 +163,8 @@ struct usb_device {
        defined(CONFIG_USB_SL811HS) || defined(CONFIG_USB_ISP116X_HCD) || \
        defined(CONFIG_USB_R8A66597_HCD) || defined(CONFIG_USB_DAVINCI) || \
        defined(CONFIG_USB_OMAP3) || defined(CONFIG_USB_DA8XX) || \
-       defined(CONFIG_USB_BLACKFIN) || defined(CONFIG_USB_AM35X)
+       defined(CONFIG_USB_BLACKFIN) || defined(CONFIG_USB_AM35X) || \
+       defined(CONFIG_USB_XHCI)
 
 int usb_lowlevel_init(int index, void **controller);
 int usb_lowlevel_stop(int index);
diff --git a/include/usb_defs.h b/include/usb_defs.h
index 8032e57..e681609 100644
--- a/include/usb_defs.h
+++ b/include/usb_defs.h
@@ -84,7 +84,8 @@
 #define USB_SPEED_FULL         0x0     /* 12Mbps */
 #define USB_SPEED_LOW          0x1     /* 1.5Mbps */
 #define USB_SPEED_HIGH         0x2     /* 480Mbps */
-#define USB_SPEED_RESERVED     0x3
+#define USB_SPEED_SUPER                0x3     /* 5Gbps */
+#define USB_SPEED_RESERVED     0x4
 
 /* Descriptor types */
 #define USB_DT_DEVICE        0x01
@@ -93,6 +94,9 @@
 #define USB_DT_INTERFACE     0x04
 #define USB_DT_ENDPOINT      0x05
 
+/* From the USB 3.0 spec */
+#define USB_DT_SS_ENDPOINT_COMP                0x30
+
 #define USB_DT_HID          (USB_TYPE_CLASS | 0x01)
 #define USB_DT_REPORT       (USB_TYPE_CLASS | 0x02)
 #define USB_DT_PHYSICAL     (USB_TYPE_CLASS | 0x03)
@@ -156,6 +160,7 @@
 #define USB_REQ_SET_IDLE            0x0A
 #define USB_REQ_SET_PROTOCOL        0x0B
 
+#define USB_REQ_ALLOC_DEV              0xDE
 
 /* "pipe" definitions */
 
@@ -227,6 +232,23 @@
 #define USB_PORT_STAT_SPEED    \
        (USB_PORT_STAT_LOW_SPEED | USB_PORT_STAT_HIGH_SPEED)
 
+/*
+ * Additions to wPortStatus bit field from USB 3.0
+ * See USB 3.0 spec Table 10-10
+ */
+#define USB_PORT_STAT_LINK_STATE       0x01e0
+#define USB_SS_PORT_STAT_POWER         0x0200
+#define USB_SS_PORT_STAT_SPEED         0x1c00
+#define USB_PORT_STAT_SPEED_5GBPS      0x0000
+
+/*
+ * USB 3.0 wPortChange bit fields
+ * See USB 3.0 spec Table 10-11
+ */
+#define USB_PORT_STAT_C_BH_RESET       0x0020
+#define USB_PORT_STAT_C_LINK_STATE     0x0040
+#define USB_PORT_STAT_C_CONFIG_ERROR   0x0080
+
 /* wPortChange bits */
 #define USB_PORT_STAT_C_CONNECTION  0x0001
 #define USB_PORT_STAT_C_ENABLE      0x0002
@@ -240,7 +262,7 @@
 #define HUB_CHAR_OCPM               0x0018
 
 /*
- *Hub Status & Hub Change bit masks
+ * Hub Status & Hub Change bit masks
  */
 #define HUB_STATUS_LOCAL_POWER 0x0001
 #define HUB_STATUS_OVERCURRENT 0x0002
diff --git a/include/usbdescriptors.h b/include/usbdescriptors.h
index de1069f..527e895 100644
--- a/include/usbdescriptors.h
+++ b/include/usbdescriptors.h
@@ -192,6 +192,15 @@
  * standard usb descriptor structures
  */
 
+/* USB_DT_SS_ENDPOINT_COMP: SuperSpeed Endpoint Companion descriptor */
+struct usb_ss_ep_comp_descriptor {
+       u8  bLength;
+       u8  bDescriptorType;    /* 0x30 */
+       u8  bMaxBurst;
+       u8  bmAttributes;
+       u16 wBytesPerInterval;
+} __attribute__ ((packed));
+
 struct usb_endpoint_descriptor {
        u8 bLength;
        u8 bDescriptorType;     /* 0x5 */
@@ -545,4 +554,196 @@ static inline void print_device_descriptor(struct 
usb_device_descriptor *d)
 #define print_device_descriptor(d)
 
 #endif /* DEBUG */
+
+/*-------------------------------------------------------------------------*/
+
+/**
+ * Get the endpoint's number
+ *
+ * @param epd  Endpoint descriptor to be checked
+ * @return epd's number, 0 to 15.
+ */
+static inline int usb_endpoint_num(struct usb_endpoint_descriptor *epd)
+{
+       return epd->bEndpointAddress & USB_ENDPOINT_NUMBER_MASK;
+}
+
+/**
+ * Get the endpoint's transfer type
+ *
+ * @param epd  Endpoint to be checked
+ * @return     One of USB_ENDPOINT_XFER_{CONTROL, ISOC, BULK, INT} according
+ *             to @epd's transfer type.
+ */
+static inline int usb_endpoint_type(struct usb_endpoint_descriptor *epd)
+{
+       return epd->bmAttributes & USB_ENDPOINT_XFERTYPE_MASK;
+}
+
+/**
+ * usb_endpoint_dir_in - check if the endpoint has IN direction
+ * @epd: endpoint to be checked
+ *
+ * Returns true if the endpoint is of type IN, otherwise it returns false.
+ */
+static inline int usb_endpoint_dir_in(struct usb_endpoint_descriptor *epd)
+{
+       return (epd->bEndpointAddress & USB_ENDPOINT_DIR_MASK) == USB_DIR_IN;
+}
+
+/**
+ * usb_endpoint_dir_out - check if the endpoint has OUT direction
+ * @epd: endpoint to be checked
+ *
+ * Returns true if the endpoint is of type OUT, otherwise it returns false.
+ */
+static inline int usb_endpoint_dir_out(
+                               struct usb_endpoint_descriptor *epd)
+{
+       return (epd->bEndpointAddress & USB_ENDPOINT_DIR_MASK) == USB_DIR_OUT;
+}
+
+/**
+ * usb_endpoint_xfer_bulk - check if the endpoint has bulk transfer type
+ * @epd: endpoint to be checked
+ *
+ * Returns true if the endpoint is of type bulk, otherwise it returns false.
+ */
+static inline int usb_endpoint_xfer_bulk(
+                               struct usb_endpoint_descriptor *epd)
+{
+       return (epd->bmAttributes & USB_ENDPOINT_XFERTYPE_MASK) ==
+               USB_ENDPOINT_XFER_BULK;
+}
+
+/**
+ * usb_endpoint_xfer_control - check if the endpoint has control transfer type
+ * @epd: endpoint to be checked
+ *
+ * Returns true if the endpoint is of type control, otherwise it returns false.
+ */
+static inline int usb_endpoint_xfer_control(
+                               struct usb_endpoint_descriptor *epd)
+{
+       return (epd->bmAttributes & USB_ENDPOINT_XFERTYPE_MASK) ==
+               USB_ENDPOINT_XFER_CONTROL;
+}
+
+/**
+ * usb_endpoint_xfer_int - check if the endpoint has interrupt transfer type
+ * @epd: endpoint to be checked
+ *
+ * Returns true if the endpoint is of type interrupt, otherwise it returns
+ * false.
+ */
+static inline int usb_endpoint_xfer_int(
+                               struct usb_endpoint_descriptor *epd)
+{
+       return (epd->bmAttributes & USB_ENDPOINT_XFERTYPE_MASK) ==
+               USB_ENDPOINT_XFER_INT;
+}
+
+/**
+ * usb_endpoint_xfer_isoc - check if the endpoint has isochronous transfer type
+ * @epd: endpoint to be checked
+ *
+ * Returns true if the endpoint is of type isochronous, otherwise it returns
+ * false.
+ */
+static inline int usb_endpoint_xfer_isoc(
+                               struct usb_endpoint_descriptor *epd)
+{
+       return (epd->bmAttributes & USB_ENDPOINT_XFERTYPE_MASK) ==
+               USB_ENDPOINT_XFER_ISOC;
+}
+
+/**
+ * usb_endpoint_is_bulk_in - check if the endpoint is bulk IN
+ * @epd: endpoint to be checked
+ *
+ * Returns true if the endpoint has bulk transfer type and IN direction,
+ * otherwise it returns false.
+ */
+static inline int usb_endpoint_is_bulk_in(
+                               struct usb_endpoint_descriptor *epd)
+{
+       return usb_endpoint_xfer_bulk(epd) && usb_endpoint_dir_in(epd);
+}
+
+/**
+ * usb_endpoint_is_bulk_out - check if the endpoint is bulk OUT
+ * @epd: endpoint to be checked
+ *
+ * Returns true if the endpoint has bulk transfer type and OUT direction,
+ * otherwise it returns false.
+ */
+static inline int usb_endpoint_is_bulk_out(
+                               struct usb_endpoint_descriptor *epd)
+{
+       return usb_endpoint_xfer_bulk(epd) && usb_endpoint_dir_out(epd);
+}
+
+/**
+ * usb_endpoint_is_int_in - check if the endpoint is interrupt IN
+ * @epd: endpoint to be checked
+ *
+ * Returns true if the endpoint has interrupt transfer type and IN direction,
+ * otherwise it returns false.
+ */
+static inline int usb_endpoint_is_int_in(
+                               struct usb_endpoint_descriptor *epd)
+{
+       return usb_endpoint_xfer_int(epd) && usb_endpoint_dir_in(epd);
+}
+
+/**
+ * usb_endpoint_is_int_out - check if the endpoint is interrupt OUT
+ * @epd: endpoint to be checked
+ *
+ * Returns true if the endpoint has interrupt transfer type and OUT direction,
+ * otherwise it returns false.
+ */
+static inline int usb_endpoint_is_int_out(
+                               struct usb_endpoint_descriptor *epd)
+{
+       return usb_endpoint_xfer_int(epd) && usb_endpoint_dir_out(epd);
+}
+
+/**
+ * usb_endpoint_is_isoc_in - check if the endpoint is isochronous IN
+ * @epd: endpoint to be checked
+ *
+ * Returns true if the endpoint has isochronous transfer type and IN direction,
+ * otherwise it returns false.
+ */
+static inline int usb_endpoint_is_isoc_in(
+                               struct usb_endpoint_descriptor *epd)
+{
+       return usb_endpoint_xfer_isoc(epd) && usb_endpoint_dir_in(epd);
+}
+
+/**
+ * usb_endpoint_is_isoc_out - check if the endpoint is isochronous OUT
+ * @epd: endpoint to be checked
+ *
+ * Returns true if the endpoint has isochronous transfer type and OUT 
direction,
+ * otherwise it returns false.
+ */
+static inline int usb_endpoint_is_isoc_out(
+                               struct usb_endpoint_descriptor *epd)
+{
+       return usb_endpoint_xfer_isoc(epd) && usb_endpoint_dir_out(epd);
+}
+
+/**
+ * usb_endpoint_maxp - get endpoint's max packet size
+ * @epd: endpoint to be checked
+ *
+ * Returns @epd's max packet
+ */
+static inline int usb_endpoint_maxp(struct usb_endpoint_descriptor *epd)
+{
+       return le16_to_cpu(epd->wMaxPacketSize);
+}
+
 #endif
-- 
1.7.6.5

_______________________________________________
U-Boot mailing list
U-Boot@lists.denx.de
http://lists.denx.de/mailman/listinfo/u-boot

Reply via email to