mirror of
https://github.com/apache/nuttx.git
synced 2026-06-04 23:03:27 +08:00
USB class drivers need to call DEV_CONNECT
git-svn-id: svn://svn.code.sf.net/p/nuttx/code/trunk@3159 42af7a65-404d-4744-a932-0658087f49c3
This commit is contained in:
@@ -8,7 +8,7 @@
|
|||||||
<tr align="center" bgcolor="#e4e4e4">
|
<tr align="center" bgcolor="#e4e4e4">
|
||||||
<td>
|
<td>
|
||||||
<h1><big><font color="#3c34ec"><i>NuttX RTOS</i></font></big></h1>
|
<h1><big><font color="#3c34ec"><i>NuttX RTOS</i></font></big></h1>
|
||||||
<p>Last Updated: December 3, 2010</p>
|
<p>Last Updated: December 4, 2010</p>
|
||||||
</td>
|
</td>
|
||||||
</tr>
|
</tr>
|
||||||
</table>
|
</table>
|
||||||
@@ -2011,6 +2011,10 @@ nuttx-5.15 2010-xx-xx Gregory Nutt <spudmonkey@racsa.co.cr>
|
|||||||
or data. This is typical, for example, in "9-bit" displays where the 9th bit
|
or data. This is typical, for example, in "9-bit" displays where the 9th bit
|
||||||
is the CMD/DATA bit. The cmddata method provides selection of command or data.
|
is the CMD/DATA bit. The cmddata method provides selection of command or data.
|
||||||
* drivers/lcd/p14201.c -- Now used the cmddata() method of the SPI interface.
|
* drivers/lcd/p14201.c -- Now used the cmddata() method of the SPI interface.
|
||||||
|
* arch/arm/src/lpc17xx/lpc17_usbdev.c -- LPC17xx USB driver is not functional.
|
||||||
|
* drivers/usbdev/usbserial.c and usbstorage.c -- All USB class drivers need
|
||||||
|
to call DEV_CONNECT() when they are ready to be enumerated. That is,
|
||||||
|
(1) initially when bound to the USB driver, and (2) after a USB reset.
|
||||||
|
|
||||||
pascal-2.1 2010-xx-xx Gregory Nutt <spudmonkey@racsa.co.cr>
|
pascal-2.1 2010-xx-xx Gregory Nutt <spudmonkey@racsa.co.cr>
|
||||||
|
|
||||||
|
|||||||
@@ -716,13 +716,8 @@ o ARM/LPC17xx (arch/arm/src/lpc17xx/)
|
|||||||
Status: Open
|
Status: Open
|
||||||
Priority: High
|
Priority: High
|
||||||
|
|
||||||
Description: a) USB DMA not fully implemented. Partial logic is in place but it is
|
Description: USB DMA not fully implemented. Partial logic is in place but it is
|
||||||
fragmentary and bogus. (Leveraged from the lpc214x)
|
fragmentary and bogus. (Leveraged from the lpc214x)
|
||||||
b) Possible errors in USB device driver reported "I suspect there's a few
|
|
||||||
issues in the lpc214x USB driver -- in particular it doesn't stall both
|
|
||||||
in/out endpoints for unsupported setup requests and it doesn't call
|
|
||||||
CLASS_DISCONNCET on a USB reset -- I don't have any access to that hardware
|
|
||||||
so can't pursue it really."
|
|
||||||
Status: Open
|
Status: Open
|
||||||
Priority: Low
|
Priority: Low
|
||||||
|
|
||||||
|
|||||||
@@ -1487,6 +1487,15 @@ static void lpc17_usbreset(struct lpc17_usbdev_s *priv)
|
|||||||
|
|
||||||
lpc17_putreg(USB_SLOW_INT|USB_DEVSTATUS_INT|USB_FAST_INT|USB_FRAME_INT|USB_ERROR_INT,
|
lpc17_putreg(USB_SLOW_INT|USB_DEVSTATUS_INT|USB_FAST_INT|USB_FRAME_INT|USB_ERROR_INT,
|
||||||
LPC17_USBDEV_INTEN);
|
LPC17_USBDEV_INTEN);
|
||||||
|
|
||||||
|
/* Tell the class driver that we are disconnected. The class
|
||||||
|
* driver should then accept any new configurations.
|
||||||
|
*/
|
||||||
|
|
||||||
|
if (priv->driver)
|
||||||
|
{
|
||||||
|
CLASS_DISCONNECT(priv->driver, &priv->usbdev);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/*******************************************************************************
|
/*******************************************************************************
|
||||||
@@ -1895,8 +1904,8 @@ static inline void lpc17_ep0setup(struct lpc17_usbdev_s *priv)
|
|||||||
if (priv->stalled)
|
if (priv->stalled)
|
||||||
{
|
{
|
||||||
usbtrace(TRACE_DEVERROR(LPC17_TRACEERR_EP0SETUPSTALLED), priv->ep0state);
|
usbtrace(TRACE_DEVERROR(LPC17_TRACEERR_EP0SETUPSTALLED), priv->ep0state);
|
||||||
lpc17_epstall(&ep0->ep, false);
|
lpc17_epstall(&priv->eplist[LPC17_EP0_IN].ep, false);
|
||||||
lpc17_epstall(&ep0->ep, false);
|
lpc17_epstall(&priv->eplist[LPC17_EP0_OUT].ep, false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1957,9 +1966,8 @@ static inline void lpc17_ep0dataoutinterrupt(struct lpc17_usbdev_s *priv)
|
|||||||
if (priv->stalled)
|
if (priv->stalled)
|
||||||
{
|
{
|
||||||
usbtrace(TRACE_DEVERROR(LPC17_TRACEERR_EP0OUTSTALLED), priv->ep0state);
|
usbtrace(TRACE_DEVERROR(LPC17_TRACEERR_EP0OUTSTALLED), priv->ep0state);
|
||||||
ep0 = &priv->eplist[LPC17_EP0_OUT];
|
lpc17_epstall(&priv->eplist[LPC17_EP0_IN].ep, false);
|
||||||
lpc17_epstall(&ep0->ep, false);
|
lpc17_epstall(&priv->eplist[LPC17_EP0_OUT].ep, false);
|
||||||
lpc17_epstall(&ep0->ep, false);
|
|
||||||
}
|
}
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -2024,9 +2032,8 @@ static inline void lpc17_ep0dataininterrupt(struct lpc17_usbdev_s *priv)
|
|||||||
if (priv->stalled)
|
if (priv->stalled)
|
||||||
{
|
{
|
||||||
usbtrace(TRACE_DEVERROR(LPC17_TRACEERR_EP0INSTALLED), priv->ep0state);
|
usbtrace(TRACE_DEVERROR(LPC17_TRACEERR_EP0INSTALLED), priv->ep0state);
|
||||||
ep0 = &priv->eplist[LPC17_EP0_IN];
|
lpc17_epstall(&priv->eplist[LPC17_EP0_IN].ep, false);
|
||||||
lpc17_epstall(&ep0->ep, false);
|
lpc17_epstall(&priv->eplist[LPC17_EP0_OUT].ep, false);
|
||||||
lpc17_epstall(&ep0->ep, false);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -2604,7 +2604,11 @@ int usbdev_register(struct usbdevclass_driver_s *driver)
|
|||||||
|
|
||||||
/* FIXME: nothing seems to call DEV_CONNECT(), but we need to set
|
/* FIXME: nothing seems to call DEV_CONNECT(), but we need to set
|
||||||
* the RS bit to enable the controller. It kind of makes sense
|
* the RS bit to enable the controller. It kind of makes sense
|
||||||
* to do this after the class has bound to us... */
|
* to do this after the class has bound to us...
|
||||||
|
* GEN: This bug is really in the class driver. It should make the
|
||||||
|
* soft connect when it is ready to be enumerated. I have added
|
||||||
|
* that logic to the class drivers but left this logic here.
|
||||||
|
*/
|
||||||
|
|
||||||
lpc313x_pullup(&g_usbdev.usbdev, true);
|
lpc313x_pullup(&g_usbdev.usbdev, true);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -853,6 +853,12 @@ CONFIG_EXAMPLES_USBSTRG_TRACETRANSFERS=n
|
|||||||
CONFIG_EXAMPLES_USBSTRG_TRACECONTROLLER=n
|
CONFIG_EXAMPLES_USBSTRG_TRACECONTROLLER=n
|
||||||
CONFIG_EXAMPLES_USBSTRG_TRACEINTERRUPTS=n
|
CONFIG_EXAMPLES_USBSTRG_TRACEINTERRUPTS=n
|
||||||
|
|
||||||
|
CONFIG_EXAMPLES_USBSTRG_TRACEINIT=n
|
||||||
|
CONFIG_EXAMPLES_USBSTRG_TRACECLASS=n
|
||||||
|
CONFIG_EXAMPLES_USBSTRG_TRACETRANSFERS=n
|
||||||
|
CONFIG_EXAMPLES_USBSTRG_TRACECONTROLLER=n
|
||||||
|
CONFIG_EXAMPLES_USBSTRG_TRACEINTERRUPTS=n
|
||||||
|
|
||||||
#
|
#
|
||||||
# Stack and heap information
|
# Stack and heap information
|
||||||
#
|
#
|
||||||
|
|||||||
@@ -60,6 +60,7 @@
|
|||||||
#include <sys/types.h>
|
#include <sys/types.h>
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <stdbool.h>
|
#include <stdbool.h>
|
||||||
|
#include <unistd.h>
|
||||||
#include <pthread.h>
|
#include <pthread.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
|
|||||||
@@ -1392,6 +1392,10 @@ static int usbclass_bind(FAR struct usbdev_s *dev, FAR struct usbdevclass_driver
|
|||||||
#ifdef CONFIG_USBDEV_SELFPOWERED
|
#ifdef CONFIG_USBDEV_SELFPOWERED
|
||||||
DEV_SETSELFPOWERED(dev);
|
DEV_SETSELFPOWERED(dev);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
/* And pull-up the data line for the soft connect function */
|
||||||
|
|
||||||
|
DEV_CONNECT(dev);
|
||||||
return OK;
|
return OK;
|
||||||
|
|
||||||
errout:
|
errout:
|
||||||
@@ -1830,6 +1834,12 @@ static void usbclass_disconnect(FAR struct usbdev_s *dev)
|
|||||||
priv->serdev.xmit.head = 0;
|
priv->serdev.xmit.head = 0;
|
||||||
priv->serdev.xmit.tail = 0;
|
priv->serdev.xmit.tail = 0;
|
||||||
irqrestore(flags);
|
irqrestore(flags);
|
||||||
|
|
||||||
|
/* Perform the soft connect function so that we will we can be
|
||||||
|
* re-enumerated.
|
||||||
|
*/
|
||||||
|
|
||||||
|
DEV_CONNECT(dev);
|
||||||
}
|
}
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
|
|||||||
@@ -601,6 +601,10 @@ static int usbstrg_bind(FAR struct usbdev_s *dev, FAR struct usbdevclass_driver_
|
|||||||
#ifdef CONFIG_USBDEV_SELFPOWERED
|
#ifdef CONFIG_USBDEV_SELFPOWERED
|
||||||
DEV_SETSELFPOWERED(dev);
|
DEV_SETSELFPOWERED(dev);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
/* And pull-up the data line for the soft connect function */
|
||||||
|
|
||||||
|
DEV_CONNECT(dev);
|
||||||
return OK;
|
return OK;
|
||||||
|
|
||||||
errout:
|
errout:
|
||||||
@@ -1045,6 +1049,12 @@ static void usbstrg_disconnect(FAR struct usbdev_s *dev)
|
|||||||
priv->theventset |= USBSTRG_EVENT_DISCONNECT;
|
priv->theventset |= USBSTRG_EVENT_DISCONNECT;
|
||||||
pthread_cond_signal(&priv->cond);
|
pthread_cond_signal(&priv->cond);
|
||||||
irqrestore(flags);
|
irqrestore(flags);
|
||||||
|
|
||||||
|
/* Perform the soft connect function so that we will we can be
|
||||||
|
* re-enumerated.
|
||||||
|
*/
|
||||||
|
|
||||||
|
DEV_CONNECT(dev);
|
||||||
}
|
}
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
|
|||||||
@@ -367,21 +367,21 @@ struct usbstrg_lun_s
|
|||||||
|
|
||||||
struct usbstrg_dev_s
|
struct usbstrg_dev_s
|
||||||
{
|
{
|
||||||
FAR struct usbdev_s *usbdev; /* usbdev driver pointer (Non-null if registered) */
|
FAR struct usbdev_s *usbdev; /* usbdev driver pointer (Non-null if registered) */
|
||||||
|
|
||||||
/* Worker thread interface */
|
/* Worker thread interface */
|
||||||
|
|
||||||
pthread_t thread; /* The worker thread */
|
pthread_t thread; /* The worker thread */
|
||||||
pthread_mutex_t mutex; /* Mutually exclusive access to resources*/
|
pthread_mutex_t mutex; /* Mutually exclusive access to resources*/
|
||||||
pthread_cond_t cond; /* Used to signal worker thread */
|
pthread_cond_t cond; /* Used to signal worker thread */
|
||||||
volatile uint8_t thstate; /* State of the worker thread */
|
volatile uint8_t thstate; /* State of the worker thread */
|
||||||
volatile uint16_t theventset; /* Set of pending events signaled to worker thread */
|
volatile uint16_t theventset; /* Set of pending events signaled to worker thread */
|
||||||
volatile uint8_t thvalue; /* Value passed with the event (must persist) */
|
volatile uint8_t thvalue; /* Value passed with the event (must persist) */
|
||||||
|
|
||||||
/* Storage class configuration and state */
|
/* Storage class configuration and state */
|
||||||
|
|
||||||
uint8_t nluns:4; /* Number of LUNs */
|
uint8_t nluns:4; /* Number of LUNs */
|
||||||
uint8_t config; /* Configuration number */
|
uint8_t config; /* Configuration number */
|
||||||
|
|
||||||
/* Endpoints */
|
/* Endpoints */
|
||||||
|
|
||||||
@@ -394,29 +394,29 @@ struct usbstrg_dev_s
|
|||||||
struct usbstrg_lun_s *lun; /* Currently selected LUN */
|
struct usbstrg_lun_s *lun; /* Currently selected LUN */
|
||||||
struct usbstrg_lun_s *luntab; /* Allocated table of all LUNs */
|
struct usbstrg_lun_s *luntab; /* Allocated table of all LUNs */
|
||||||
uint8_t cdb[USBSTRG_MAXCDBLEN]; /* Command data (cdb[]) from CBW */
|
uint8_t cdb[USBSTRG_MAXCDBLEN]; /* Command data (cdb[]) from CBW */
|
||||||
uint8_t phaseerror:1; /* Need to send phase sensing status */
|
uint8_t phaseerror:1; /* Need to send phase sensing status */
|
||||||
uint8_t shortpacket:1; /* Host transmission stopped unexpectedly */
|
uint8_t shortpacket:1; /* Host transmission stopped unexpectedly */
|
||||||
uint8_t cbwdir:2; /* Direction from CBW. See USBSTRG_FLAGS_DIR* definitions */
|
uint8_t cbwdir:2; /* Direction from CBW. See USBSTRG_FLAGS_DIR* definitions */
|
||||||
uint8_t cdblen; /* Length of cdb[] from CBW */
|
uint8_t cdblen; /* Length of cdb[] from CBW */
|
||||||
uint8_t cbwlun; /* LUN from the CBW */
|
uint8_t cbwlun; /* LUN from the CBW */
|
||||||
uint16_t nsectbytes; /* Bytes buffered in iobuffer[] */
|
uint16_t nsectbytes; /* Bytes buffered in iobuffer[] */
|
||||||
uint16_t nreqbytes; /* Bytes buffered in head write requests */
|
uint16_t nreqbytes; /* Bytes buffered in head write requests */
|
||||||
uint16_t iosize; /* Size of iobuffer[] */
|
uint16_t iosize; /* Size of iobuffer[] */
|
||||||
uint32_t cbwlen; /* Length of data from CBW */
|
uint32_t cbwlen; /* Length of data from CBW */
|
||||||
uint32_t cbwtag; /* Tag from the CBW */
|
uint32_t cbwtag; /* Tag from the CBW */
|
||||||
union
|
union
|
||||||
{
|
{
|
||||||
uint32_t xfrlen; /* Read/Write: Sectors remaining to be transferred */
|
uint32_t xfrlen; /* Read/Write: Sectors remaining to be transferred */
|
||||||
uint32_t alloclen; /* Other device-to-host: Host allocation length */
|
uint32_t alloclen; /* Other device-to-host: Host allocation length */
|
||||||
} u;
|
} u;
|
||||||
uint32_t sector; /* Current sector (relative to lun->startsector) */
|
uint32_t sector; /* Current sector (relative to lun->startsector) */
|
||||||
uint32_t residue; /* Untransferred amount reported in the CSW */
|
uint32_t residue; /* Untransferred amount reported in the CSW */
|
||||||
uint8_t *iobuffer; /* Buffer for data transfers */
|
uint8_t *iobuffer; /* Buffer for data transfers */
|
||||||
|
|
||||||
/* Write request list */
|
/* Write request list */
|
||||||
|
|
||||||
struct sq_queue_s wrreqlist; /* List of empty write request containers */
|
struct sq_queue_s wrreqlist; /* List of empty write request containers */
|
||||||
struct sq_queue_s rdreqlist; /* List of filled read request containers */
|
struct sq_queue_s rdreqlist; /* List of filled read request containers */
|
||||||
|
|
||||||
/* Pre-allocated write request containers. The write requests will
|
/* Pre-allocated write request containers. The write requests will
|
||||||
* be linked in a free list (wrreqlist), and used to send requests to
|
* be linked in a free list (wrreqlist), and used to send requests to
|
||||||
|
|||||||
@@ -135,7 +135,10 @@
|
|||||||
|
|
||||||
#define DEV_CLRSELFPOWERED(dev) (dev)->ops->selfpowered(dev, false)
|
#define DEV_CLRSELFPOWERED(dev) (dev)->ops->selfpowered(dev, false)
|
||||||
|
|
||||||
/* Software-controlled connect to USB host */
|
/* Software-controlled connect to USB host. All USB class drivers need to call
|
||||||
|
* DEV_CONNECT() when they are ready to be enumerated. That is, (1) initially when
|
||||||
|
* bound to the USB driver, and (2) after a USB reset.
|
||||||
|
*/
|
||||||
|
|
||||||
#define DEV_CONNECT(dev) (dev)->ops->pullup ? (dev)->ops->pullup(dev,true) : -EOPNOTSUPP
|
#define DEV_CONNECT(dev) (dev)->ops->pullup ? (dev)->ops->pullup(dev,true) : -EOPNOTSUPP
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user