On Thu, Oct 30, 2008 at 02:42:22PM +0530, Ajay Kumar Gupta wrote:
> Fixes endpoint starvation issue when more than one bulk qhs
> are multiplexed on reserved bulk endpoint.NAK timeout interval
> is set for such qhs and next qh is scheduled when NAK timeout
> occurs.
> This scheme doesn't work for devices which are connected to a
> high to full speed tree as there is no NAK timeout interrupt
> at musb controller from such devices.
> A module parameter 'bulk_nak_timeout' is added so that this feature
> can be disabled if not required.

then if the user sets the parameter wrongly, it would break
communication, right ?

unless you can come up with a way to figure out if bulk_nak_timeout
could be set automatically, let's drop this patch.

> Signed-off-by: Ravi Babu <[EMAIL PROTECTED]>
> Signed-off-by: Swaminathan S <[EMAIL PROTECTED]>
> Signed-off-by: Thomas Abraham <[EMAIL PROTECTED]>
> Signed-off-by: Ajay Kumar Gupta <[EMAIL PROTECTED]>
> ---
> These patches have been created against latest omap git and Felipe's
> musb .28 patch series at,
> http://marc.info/?l=linux-usb&m=122528597116718&w=2
> 
>  drivers/usb/musb/musb_host.c |   70 
> ++++++++++++++++++++++++++++++++++++++++--
>  1 files changed, 67 insertions(+), 3 deletions(-)
> 
> diff --git a/drivers/usb/musb/musb_host.c b/drivers/usb/musb/musb_host.c
> index 30b5685..b77ca0b 100644
> --- a/drivers/usb/musb/musb_host.c
> +++ b/drivers/usb/musb/musb_host.c
> @@ -100,6 +100,10 @@
>   * of transfers between endpoints, or anything clever.
>   */
>  
> +static void musb_bulk_nak_timeout(struct musb *musb, struct musb_hw_ep *ep);

please, reorganize the code so we don't need this prototype here.

> +static int bulk_nak_timeout = 1;
> +module_param(bulk_nak_timeout, bool, 0);
> +MODULE_PARM_DESC(bulk_nak_timeout, "enable/disable use of bulk nak timeout");
>  
>  static void musb_ep_program(struct musb *musb, u8 epnum,
>                       struct urb *urb, unsigned int nOut,
> @@ -1449,10 +1453,15 @@ void musb_host_rx(struct musb *musb, u8 epnum)
>                        * we have a candidate... NAKing is *NOT* an error
>                        */
>                       DBG(6, "RX end %d NAK timeout\n", epnum);
> +                     if (usb_pipebulk(urb->pipe) && qh->mux == 1 &&
> +                             (musb->in_bulk.next->next != &musb->in_bulk) &&
> +                                     bulk_nak_timeout) {
> +                             musb_bulk_nak_timeout(musb, hw_ep);
> +                             return;
> +                     }
>                       musb_ep_select(mbase, epnum);
> -                     musb_writew(epio, MUSB_RXCSR,
> -                                     MUSB_RXCSR_H_WZC_BITS
> -                                     | MUSB_RXCSR_H_REQPKT);
> +                     rx_csr &= ~MUSB_RXCSR_DATAERROR;
> +                     musb_writew(epio, MUSB_RXCSR, rx_csr);
>  
>                       goto finish;
>               } else {
> @@ -1802,6 +1811,9 @@ static int musb_schedule(
>  
>       idle = 1;
>       qh->mux = 0;
> +     /* disable NAK scheme when bulk is not multiplexed */
> +     if (is_in && qh->type == USB_ENDPOINT_XFER_BULK && bulk_nak_timeout)
> +             qh->intv_reg = 0;
>       hw_ep = musb->endpoints + best_end;
>       if (is_in)
>               musb->in[best_end] = qh;
> @@ -1912,6 +1924,17 @@ static int musb_urb_enqueue(
>       case USB_ENDPOINT_XFER_ISOC:
>               /* iso always uses log encoding */
>               break;
> +     case USB_ENDPOINT_XFER_BULK:
> +             /* Enable bulk NAK time out scheme when bulk requests are
> +              * multiplxed.This scheme doen't work in high speed to full
> +              * speed scenario as NAK interrupts are not coming from a
> +              * full speed device connected to a high speed device.
> +              */
> +             if (usb_pipein(urb->pipe) && bulk_nak_timeout) {
> +                     interval = 8;
> +                     break;
> +             }
> +             /* FALLTHROUGH */
>       default:
>               /* REVISIT we actually want to use NAK limits, hinting to the
>                * transfer scheduling logic to try some other qh, e.g. try
> @@ -2265,6 +2288,47 @@ static int musb_bus_resume(struct usb_hcd *hcd)
>       return 0;
>  }
>  
> +static void musb_bulk_nak_timeout(struct musb *musb, struct musb_hw_ep *ep)
> +{
> +     struct dma_channel      *dma;
> +     struct urb      *urb;
> +     void __iomem    *mbase = musb->mregs;
> +     void __iomem    *epio = ep->regs;
> +     struct musb_qh  *cur_qh, *next_qh;
> +     u16     rx_csr;
> +
> +     musb_ep_select(mbase, ep->epnum);
> +     dma = is_dma_capable() ? ep->rx_channel : NULL;
> +
> +     /* clear nak timeout bit */
> +     rx_csr = musb_readw(epio, MUSB_RXCSR);
> +     rx_csr &= ~MUSB_RXCSR_DATAERROR;
> +     musb_writew(epio, MUSB_RXCSR, rx_csr);
> +
> +     cur_qh = first_qh(&musb->in_bulk);
> +     if (cur_qh) {
> +             urb = next_urb(cur_qh);
> +             if (dma_channel_status(dma) == MUSB_DMA_STATUS_BUSY) {
> +                     dma->status = MUSB_DMA_STATUS_CORE_ABORT;
> +                     musb->dma_controller->channel_abort(dma);
> +                     urb->actual_length += dma->actual_len;
> +                     dma->actual_len = 0L;
> +             }
> +             musb_save_toggle(ep, 1, urb);
> +
> +             /* delete cur_qh and add to tail to musb->in_bulk */
> +             list_del(&cur_qh->ring);
> +             list_add_tail(&cur_qh->ring, &musb->in_bulk);
> +
> +             /* get the next qh from musb->in_bulk */
> +             next_qh = first_qh(&musb->in_bulk);
> +
> +             /* set rx_reinit and schedule the next qh */
> +             ep->rx_reinit = 1;
> +             musb_start_urb(musb, 1, next_qh);
> +     }
> +}
> +
>  const struct hc_driver musb_hc_driver = {
>       .description            = "musb-hcd",
>       .product_desc           = "MUSB HDRC host driver",
> -- 
> 1.5.6

-- 
balbi
--
To unsubscribe from this list: send the line "unsubscribe linux-omap" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html

Reply via email to