rndis: support iob offload
Signed-off-by: zhanghongyu <zhanghongyu@xiaomi.com>
This commit is contained in:
parent
51c30289ae
commit
16ea80e53b
@ -97,6 +97,7 @@ CONFIG_NET_BROADCAST=y
|
|||||||
CONFIG_NET_ETH_PKTSIZE=1514
|
CONFIG_NET_ETH_PKTSIZE=1514
|
||||||
CONFIG_NET_ICMP=y
|
CONFIG_NET_ICMP=y
|
||||||
CONFIG_NET_ICMP_SOCKET=y
|
CONFIG_NET_ICMP_SOCKET=y
|
||||||
|
CONFIG_NET_LL_GUARDSIZE=50
|
||||||
CONFIG_NET_LOOPBACK=y
|
CONFIG_NET_LOOPBACK=y
|
||||||
CONFIG_NET_PKT=y
|
CONFIG_NET_PKT=y
|
||||||
CONFIG_NET_ROUTE=y
|
CONFIG_NET_ROUTE=y
|
||||||
|
@ -97,6 +97,7 @@ CONFIG_NET_BROADCAST=y
|
|||||||
CONFIG_NET_ETH_PKTSIZE=1514
|
CONFIG_NET_ETH_PKTSIZE=1514
|
||||||
CONFIG_NET_ICMP=y
|
CONFIG_NET_ICMP=y
|
||||||
CONFIG_NET_ICMP_SOCKET=y
|
CONFIG_NET_ICMP_SOCKET=y
|
||||||
|
CONFIG_NET_LL_GUARDSIZE=50
|
||||||
CONFIG_NET_LOOPBACK=y
|
CONFIG_NET_LOOPBACK=y
|
||||||
CONFIG_NET_PKT=y
|
CONFIG_NET_PKT=y
|
||||||
CONFIG_NET_ROUTE=y
|
CONFIG_NET_ROUTE=y
|
||||||
|
@ -52,6 +52,7 @@ CONFIG_NETUTILS_TELNETD=y
|
|||||||
CONFIG_NET_ARP_SEND=y
|
CONFIG_NET_ARP_SEND=y
|
||||||
CONFIG_NET_BROADCAST=y
|
CONFIG_NET_BROADCAST=y
|
||||||
CONFIG_NET_ICMP=y
|
CONFIG_NET_ICMP=y
|
||||||
|
CONFIG_NET_LL_GUARDSIZE=50
|
||||||
CONFIG_NET_LOOPBACK=y
|
CONFIG_NET_LOOPBACK=y
|
||||||
CONFIG_NET_SOCKOPTS=y
|
CONFIG_NET_SOCKOPTS=y
|
||||||
CONFIG_NET_STATISTICS=y
|
CONFIG_NET_STATISTICS=y
|
||||||
|
@ -100,6 +100,7 @@ CONFIG_NET_BROADCAST=y
|
|||||||
CONFIG_NET_ETH_PKTSIZE=1500
|
CONFIG_NET_ETH_PKTSIZE=1500
|
||||||
CONFIG_NET_ICMP=y
|
CONFIG_NET_ICMP=y
|
||||||
CONFIG_NET_ICMP_SOCKET=y
|
CONFIG_NET_ICMP_SOCKET=y
|
||||||
|
CONFIG_NET_LL_GUARDSIZE=50
|
||||||
CONFIG_NET_LOOPBACK=y
|
CONFIG_NET_LOOPBACK=y
|
||||||
CONFIG_NET_PKT=y
|
CONFIG_NET_PKT=y
|
||||||
CONFIG_NET_ROUTE=y
|
CONFIG_NET_ROUTE=y
|
||||||
|
@ -97,6 +97,7 @@ CONFIG_NET_BROADCAST=y
|
|||||||
CONFIG_NET_ETH_PKTSIZE=1514
|
CONFIG_NET_ETH_PKTSIZE=1514
|
||||||
CONFIG_NET_ICMP=y
|
CONFIG_NET_ICMP=y
|
||||||
CONFIG_NET_ICMP_SOCKET=y
|
CONFIG_NET_ICMP_SOCKET=y
|
||||||
|
CONFIG_NET_LL_GUARDSIZE=50
|
||||||
CONFIG_NET_LOOPBACK=y
|
CONFIG_NET_LOOPBACK=y
|
||||||
CONFIG_NET_PKT=y
|
CONFIG_NET_PKT=y
|
||||||
CONFIG_NET_ROUTE=y
|
CONFIG_NET_ROUTE=y
|
||||||
|
@ -53,6 +53,7 @@ CONFIG_NET_ARP_SEND=y
|
|||||||
CONFIG_NET_BROADCAST=y
|
CONFIG_NET_BROADCAST=y
|
||||||
CONFIG_NET_ICMP=y
|
CONFIG_NET_ICMP=y
|
||||||
CONFIG_NET_ICMP_SOCKET=y
|
CONFIG_NET_ICMP_SOCKET=y
|
||||||
|
CONFIG_NET_LL_GUARDSIZE=50
|
||||||
CONFIG_NET_LOOPBACK=y
|
CONFIG_NET_LOOPBACK=y
|
||||||
CONFIG_NET_STATISTICS=y
|
CONFIG_NET_STATISTICS=y
|
||||||
CONFIG_NET_TCP=y
|
CONFIG_NET_TCP=y
|
||||||
|
@ -70,6 +70,14 @@
|
|||||||
(CONFIG_NET_ETH_PKTSIZE + CONFIG_NET_GUARDSIZE + RNDIS_PACKET_HDR_SIZE)
|
(CONFIG_NET_ETH_PKTSIZE + CONFIG_NET_GUARDSIZE + RNDIS_PACKET_HDR_SIZE)
|
||||||
#define CONFIG_RNDIS_BULKOUT_REQLEN CONFIG_RNDIS_BULKIN_REQLEN
|
#define CONFIG_RNDIS_BULKOUT_REQLEN CONFIG_RNDIS_BULKIN_REQLEN
|
||||||
|
|
||||||
|
static_assert(CONFIG_NET_LL_GUARDSIZE >= RNDIS_PACKET_HDR_SIZE + ETH_HDRLEN,
|
||||||
|
"CONFIG_NET_LL_GUARDSIZE cannot be less than ETH_HDRLEN"
|
||||||
|
" + RNDIS_PACKET_HDR_SIZE");
|
||||||
|
|
||||||
|
static_assert((CONFIG_NET_LL_GUARDSIZE % 4) == 2,
|
||||||
|
"CONFIG_NET_LL_GUARDSIZE - ETH_HDRLEN "
|
||||||
|
"should be aligned to 4 bytes");
|
||||||
|
|
||||||
#define RNDIS_NCONFIGS (1)
|
#define RNDIS_NCONFIGS (1)
|
||||||
#define RNDIS_CONFIGID (1)
|
#define RNDIS_CONFIGID (1)
|
||||||
#define RNDIS_CONFIGIDNONE (0)
|
#define RNDIS_CONFIGIDNONE (0)
|
||||||
@ -108,6 +116,8 @@ struct rndis_req_s
|
|||||||
{
|
{
|
||||||
FAR struct rndis_req_s *flink; /* Implements a singly linked list */
|
FAR struct rndis_req_s *flink; /* Implements a singly linked list */
|
||||||
FAR struct usbdev_req_s *req; /* The contained request */
|
FAR struct usbdev_req_s *req; /* The contained request */
|
||||||
|
FAR struct iob_s *iob; /* IOB offload */
|
||||||
|
FAR uint8_t *buf; /* Use malloc buffer when config IOB_LEN < CONFIG_RNDIS_BULKIN_REQLEN */
|
||||||
};
|
};
|
||||||
|
|
||||||
/* This structure describes the internal state of the driver */
|
/* This structure describes the internal state of the driver */
|
||||||
@ -632,6 +642,14 @@ static void rndis_freewrreq(FAR struct rndis_dev_s *priv,
|
|||||||
FAR struct rndis_req_s *req)
|
FAR struct rndis_req_s *req)
|
||||||
{
|
{
|
||||||
DEBUGASSERT(req != NULL);
|
DEBUGASSERT(req != NULL);
|
||||||
|
if (req->iob)
|
||||||
|
{
|
||||||
|
/* In ep submit case, need release iob chain when write complete */
|
||||||
|
|
||||||
|
iob_free_chain(req->iob);
|
||||||
|
req->iob = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
sq_addlast((FAR sq_entry_t *)req, &priv->reqlist);
|
sq_addlast((FAR sq_entry_t *)req, &priv->reqlist);
|
||||||
rndis_submit_rdreq(priv);
|
rndis_submit_rdreq(priv);
|
||||||
}
|
}
|
||||||
@ -665,11 +683,6 @@ static bool rndis_allocnetreq(FAR struct rndis_dev_s *priv)
|
|||||||
}
|
}
|
||||||
|
|
||||||
priv->net_req = rndis_allocwrreq(priv);
|
priv->net_req = rndis_allocwrreq(priv);
|
||||||
if (priv->net_req)
|
|
||||||
{
|
|
||||||
priv->netdev.d_buf = &priv->net_req->req->buf[RNDIS_PACKET_HDR_SIZE];
|
|
||||||
priv->netdev.d_len = CONFIG_NET_ETH_PKTSIZE;
|
|
||||||
}
|
|
||||||
|
|
||||||
leave_critical_section(flags);
|
leave_critical_section(flags);
|
||||||
return priv->net_req != NULL;
|
return priv->net_req != NULL;
|
||||||
@ -699,8 +712,6 @@ static void rndis_sendnetreq(FAR struct rndis_dev_s *priv)
|
|||||||
EP_SUBMIT(priv->epbulkin, priv->net_req->req);
|
EP_SUBMIT(priv->epbulkin, priv->net_req->req);
|
||||||
|
|
||||||
priv->net_req = NULL;
|
priv->net_req = NULL;
|
||||||
priv->netdev.d_buf = NULL;
|
|
||||||
priv->netdev.d_len = 0;
|
|
||||||
leave_critical_section(flags);
|
leave_critical_section(flags);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -724,11 +735,55 @@ static void rndis_freenetreq(FAR struct rndis_dev_s *priv)
|
|||||||
|
|
||||||
rndis_freewrreq(priv, priv->net_req);
|
rndis_freewrreq(priv, priv->net_req);
|
||||||
priv->net_req = NULL;
|
priv->net_req = NULL;
|
||||||
priv->netdev.d_buf = NULL;
|
|
||||||
priv->netdev.d_len = 0;
|
|
||||||
leave_critical_section(flags);
|
leave_critical_section(flags);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/****************************************************************************
|
||||||
|
* Name: rndis_iob2buf
|
||||||
|
*
|
||||||
|
* Description:
|
||||||
|
* Map the appropriate location of req iob to buf.
|
||||||
|
*
|
||||||
|
* Input Parameters:
|
||||||
|
* priv: pointer to RNDIS device driver structure
|
||||||
|
* req: the request whose buffer we should fill
|
||||||
|
* Assumptions:
|
||||||
|
* Caller holds the network lock
|
||||||
|
*
|
||||||
|
****************************************************************************/
|
||||||
|
|
||||||
|
static void rndis_iob2buf(FAR struct rndis_dev_s *priv,
|
||||||
|
FAR struct rndis_req_s *req)
|
||||||
|
{
|
||||||
|
uint16_t llhdrlen = NET_LL_HDRLEN(&priv->netdev);
|
||||||
|
uint32_t offset = CONFIG_NET_LL_GUARDSIZE - llhdrlen -
|
||||||
|
RNDIS_PACKET_HDR_SIZE;
|
||||||
|
|
||||||
|
/* ----------------------------------------------------------------
|
||||||
|
* |<--- CONFIG_NET_LL_GUARDSIZE ---->|<-- io_len/io_pktlen(0) -->|
|
||||||
|
* ---------------------------------------------------------------|
|
||||||
|
* |unused | rndis hdr size |llhdrlen |<-- io_len/io_pktlen(0) -->|
|
||||||
|
* ---------------------------------------------------------------|
|
||||||
|
* |unused | req->buf(0) |
|
||||||
|
* ---------------------------------------------------------------|
|
||||||
|
*/
|
||||||
|
|
||||||
|
if (req->iob->io_flink == NULL)
|
||||||
|
{
|
||||||
|
req->req->buf = &req->iob->io_data[offset];
|
||||||
|
req->req->len = CONFIG_RNDIS_BULKIN_REQLEN;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
req->req->buf = req->buf;
|
||||||
|
iob_copyout(&req->req->buf[RNDIS_PACKET_HDR_SIZE], req->iob,
|
||||||
|
req->iob->io_pktlen + llhdrlen, -llhdrlen);
|
||||||
|
iob_free_chain(req->iob);
|
||||||
|
req->iob = NULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
* Name: rndis_allocrxreq
|
* Name: rndis_allocrxreq
|
||||||
*
|
*
|
||||||
@ -748,13 +803,33 @@ static void rndis_freenetreq(FAR struct rndis_dev_s *priv)
|
|||||||
|
|
||||||
static bool rndis_allocrxreq(FAR struct rndis_dev_s *priv)
|
static bool rndis_allocrxreq(FAR struct rndis_dev_s *priv)
|
||||||
{
|
{
|
||||||
|
FAR struct iob_s *iob;
|
||||||
|
|
||||||
if (priv->rx_req != NULL)
|
if (priv->rx_req != NULL)
|
||||||
{
|
{
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
priv->rx_req = rndis_allocwrreq(priv);
|
/* Prepare buffer to receivce data from usb driver */
|
||||||
return priv->rx_req != NULL;
|
|
||||||
|
iob = iob_tryalloc(false);
|
||||||
|
if (iob == NULL)
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
iob_reserve(iob, CONFIG_NET_LL_GUARDSIZE);
|
||||||
|
|
||||||
|
if ((priv->rx_req = rndis_allocwrreq(priv)) == NULL)
|
||||||
|
{
|
||||||
|
iob_free_chain(iob);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
priv->rx_req->iob = iob;
|
||||||
|
rndis_iob2buf(priv, priv->rx_req);
|
||||||
|
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
@ -777,9 +852,15 @@ static void rndis_giverxreq(FAR struct rndis_dev_s *priv)
|
|||||||
DEBUGASSERT(priv->net_req == NULL);
|
DEBUGASSERT(priv->net_req == NULL);
|
||||||
|
|
||||||
priv->net_req = priv->rx_req;
|
priv->net_req = priv->rx_req;
|
||||||
priv->netdev.d_buf = &priv->net_req->req->buf[RNDIS_PACKET_HDR_SIZE];
|
|
||||||
priv->netdev.d_len = CONFIG_NET_ETH_PKTSIZE;
|
|
||||||
priv->rx_req = NULL;
|
priv->rx_req = NULL;
|
||||||
|
|
||||||
|
/* Move iob from net_req to netdev */
|
||||||
|
|
||||||
|
netdev_iob_release(&priv->netdev);
|
||||||
|
|
||||||
|
priv->netdev.d_iob = priv->net_req->iob;
|
||||||
|
priv->netdev.d_len = priv->net_req->iob->io_pktlen;
|
||||||
|
priv->net_req->iob = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
@ -801,20 +882,23 @@ static void rndis_giverxreq(FAR struct rndis_dev_s *priv)
|
|||||||
****************************************************************************/
|
****************************************************************************/
|
||||||
|
|
||||||
static uint16_t rndis_fillrequest(FAR struct rndis_dev_s *priv,
|
static uint16_t rndis_fillrequest(FAR struct rndis_dev_s *priv,
|
||||||
FAR struct usbdev_req_s *req)
|
FAR struct rndis_req_s *req)
|
||||||
{
|
{
|
||||||
size_t datalen;
|
size_t datalen;
|
||||||
|
|
||||||
req->len = 0;
|
req->req->len = 0;
|
||||||
|
|
||||||
datalen = MIN(priv->netdev.d_len,
|
datalen = MIN(priv->netdev.d_len,
|
||||||
CONFIG_RNDIS_BULKIN_REQLEN - RNDIS_PACKET_HDR_SIZE);
|
CONFIG_RNDIS_BULKIN_REQLEN - RNDIS_PACKET_HDR_SIZE);
|
||||||
if (datalen > 0)
|
if (datalen > 0)
|
||||||
{
|
{
|
||||||
/* Send the required headers */
|
/* Move iob from netdev to net_req and send the required headers */
|
||||||
|
|
||||||
|
req->iob = priv->netdev.d_iob;
|
||||||
|
netdev_iob_clear(&priv->netdev);
|
||||||
|
rndis_iob2buf(priv, req);
|
||||||
FAR struct rndis_packet_msg *msg =
|
FAR struct rndis_packet_msg *msg =
|
||||||
(FAR struct rndis_packet_msg *)req->buf;
|
(FAR struct rndis_packet_msg *)req->req->buf;
|
||||||
memset(msg, 0, RNDIS_PACKET_HDR_SIZE);
|
memset(msg, 0, RNDIS_PACKET_HDR_SIZE);
|
||||||
|
|
||||||
msg->msgtype = RNDIS_PACKET_MSG;
|
msg->msgtype = RNDIS_PACKET_MSG;
|
||||||
@ -822,11 +906,11 @@ static uint16_t rndis_fillrequest(FAR struct rndis_dev_s *priv,
|
|||||||
msg->dataoffset = RNDIS_PACKET_HDR_SIZE - 8;
|
msg->dataoffset = RNDIS_PACKET_HDR_SIZE - 8;
|
||||||
msg->datalen = datalen;
|
msg->datalen = datalen;
|
||||||
|
|
||||||
req->flags = USBDEV_REQFLAGS_NULLPKT;
|
req->req->flags = USBDEV_REQFLAGS_NULLPKT;
|
||||||
req->len = datalen + RNDIS_PACKET_HDR_SIZE;
|
req->req->len = datalen + RNDIS_PACKET_HDR_SIZE;
|
||||||
}
|
}
|
||||||
|
|
||||||
return req->len;
|
return req->req->len;
|
||||||
}
|
}
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
@ -852,7 +936,9 @@ static void rndis_rxdispatch(FAR void *arg)
|
|||||||
priv->netdev.d_len = priv->current_rx_datagram_size;
|
priv->netdev.d_len = priv->current_rx_datagram_size;
|
||||||
leave_critical_section(flags);
|
leave_critical_section(flags);
|
||||||
|
|
||||||
hdr = (FAR struct eth_hdr_s *)priv->netdev.d_buf;
|
hdr = (FAR struct eth_hdr_s *)
|
||||||
|
&priv->netdev.d_iob->io_data[CONFIG_NET_LL_GUARDSIZE -
|
||||||
|
NET_LL_HDRLEN(&priv->netdev)];
|
||||||
|
|
||||||
/* We only accept IP packets of the configured type and ARP packets */
|
/* We only accept IP packets of the configured type and ARP packets */
|
||||||
|
|
||||||
@ -965,7 +1051,7 @@ static int rndis_transmit(FAR struct rndis_dev_s *priv)
|
|||||||
|
|
||||||
/* Queue the packet */
|
/* Queue the packet */
|
||||||
|
|
||||||
rndis_fillrequest(priv, priv->net_req->req);
|
rndis_fillrequest(priv, priv->net_req);
|
||||||
rndis_sendnetreq(priv);
|
rndis_sendnetreq(priv);
|
||||||
|
|
||||||
if (!rndis_allocnetreq(priv))
|
if (!rndis_allocnetreq(priv))
|
||||||
@ -1110,9 +1196,10 @@ static inline int rndis_recvpacket(FAR struct rndis_dev_s *priv,
|
|||||||
priv->current_rx_datagram_offset = msg->dataoffset + 8;
|
priv->current_rx_datagram_offset = msg->dataoffset + 8;
|
||||||
if (priv->current_rx_datagram_offset < reqlen)
|
if (priv->current_rx_datagram_offset < reqlen)
|
||||||
{
|
{
|
||||||
memcpy(&priv->rx_req->req->buf[RNDIS_PACKET_HDR_SIZE],
|
iob_trycopyin(priv->rx_req->iob,
|
||||||
&reqbuf[priv->current_rx_datagram_offset],
|
&reqbuf[priv->current_rx_datagram_offset],
|
||||||
reqlen - priv->current_rx_datagram_offset);
|
reqlen - priv->current_rx_datagram_offset,
|
||||||
|
-NET_LL_HDRLEN(&priv->netdev), false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@ -1136,8 +1223,8 @@ static inline int rndis_recvpacket(FAR struct rndis_dev_s *priv,
|
|||||||
|
|
||||||
if ((index + copysize) <= CONFIG_NET_ETH_PKTSIZE)
|
if ((index + copysize) <= CONFIG_NET_ETH_PKTSIZE)
|
||||||
{
|
{
|
||||||
memcpy(&priv->rx_req->req->buf[RNDIS_PACKET_HDR_SIZE + index],
|
iob_trycopyin(priv->rx_req->iob, reqbuf, copysize,
|
||||||
reqbuf, copysize);
|
priv->rx_req->iob->io_pktlen, false);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@ -1721,7 +1808,13 @@ static FAR struct usbdev_req_s *usbclass_allocreq(FAR struct usbdev_ep_s *ep,
|
|||||||
req = EP_ALLOCREQ(ep);
|
req = EP_ALLOCREQ(ep);
|
||||||
if (req != NULL)
|
if (req != NULL)
|
||||||
{
|
{
|
||||||
|
/* rdreq/epintin_req/ctrlreq use fixed memory
|
||||||
|
* reqcontainer use iob dynamically when needed
|
||||||
|
*/
|
||||||
|
|
||||||
req->len = len;
|
req->len = len;
|
||||||
|
if (len > 0)
|
||||||
|
{
|
||||||
req->buf = EP_ALLOCBUFFER(ep, len);
|
req->buf = EP_ALLOCBUFFER(ep, len);
|
||||||
|
|
||||||
if (req->buf == NULL)
|
if (req->buf == NULL)
|
||||||
@ -1730,6 +1823,11 @@ static FAR struct usbdev_req_s *usbclass_allocreq(FAR struct usbdev_ep_s *ep,
|
|||||||
req = NULL;
|
req = NULL;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
req->buf = NULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return req;
|
return req;
|
||||||
}
|
}
|
||||||
@ -2109,9 +2207,11 @@ static int usbclass_bind(FAR struct usbdevclass_driver_s *driver,
|
|||||||
* size.
|
* size.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
reqlen = 64;
|
if (CONFIG_IOB_BUFSIZE >= CONFIG_RNDIS_BULKIN_REQLEN)
|
||||||
|
{
|
||||||
if (CONFIG_RNDIS_BULKIN_REQLEN > reqlen)
|
reqlen = 0;
|
||||||
|
}
|
||||||
|
else
|
||||||
{
|
{
|
||||||
reqlen = CONFIG_RNDIS_BULKIN_REQLEN;
|
reqlen = CONFIG_RNDIS_BULKIN_REQLEN;
|
||||||
}
|
}
|
||||||
@ -2128,6 +2228,7 @@ static int usbclass_bind(FAR struct usbdevclass_driver_s *driver,
|
|||||||
goto errout;
|
goto errout;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
reqcontainer->buf = reqcontainer->req->buf;
|
||||||
reqcontainer->req->priv = reqcontainer;
|
reqcontainer->req->priv = reqcontainer;
|
||||||
reqcontainer->req->callback = rndis_wrcomplete;
|
reqcontainer->req->callback = rndis_wrcomplete;
|
||||||
|
|
||||||
@ -2269,6 +2370,7 @@ static void usbclass_unbind(FAR struct usbdevclass_driver_s *driver,
|
|||||||
reqcontainer = (struct rndis_req_s *)sq_remfirst(&priv->reqlist);
|
reqcontainer = (struct rndis_req_s *)sq_remfirst(&priv->reqlist);
|
||||||
if (reqcontainer->req != NULL)
|
if (reqcontainer->req != NULL)
|
||||||
{
|
{
|
||||||
|
reqcontainer->req->buf = reqcontainer->buf;
|
||||||
usbclass_freereq(priv->epbulkin, reqcontainer->req);
|
usbclass_freereq(priv->epbulkin, reqcontainer->req);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user