Skip to content

Commit

Permalink
usb: dwc3: gadget: introduce dwc3_process_event_buf
Browse files Browse the repository at this point in the history
in order to make our IRQ handler thread easier
to read, we re-factor the inner loop to a separate
function.

Signed-off-by: Felipe Balbi <balbi@ti.com>
  • Loading branch information
Felipe Balbi committed Jul 29, 2013
1 parent 7f97aa9 commit f42f244
Showing 1 changed file with 44 additions and 37 deletions.
81 changes: 44 additions & 37 deletions drivers/usb/dwc3/gadget.c
Original file line number Diff line number Diff line change
Expand Up @@ -2442,57 +2442,64 @@ static void dwc3_process_event_entry(struct dwc3 *dwc,
}
}

static irqreturn_t dwc3_thread_interrupt(int irq, void *_dwc)
static irqreturn_t dwc3_process_event_buf(struct dwc3 *dwc, u32 buf)
{
struct dwc3 *dwc = _dwc;
unsigned long flags;
struct dwc3_event_buffer *evt;
irqreturn_t ret = IRQ_NONE;
int left;
u32 reg;
int i;

spin_lock_irqsave(&dwc->lock, flags);
evt = dwc->ev_buffs[buf];
left = evt->count;

for (i = 0; i < dwc->num_event_buffers; i++) {
struct dwc3_event_buffer *evt;
int left;
if (!(evt->flags & DWC3_EVENT_PENDING))
return IRQ_NONE;

evt = dwc->ev_buffs[i];
left = evt->count;
while (left > 0) {
union dwc3_event event;

if (!(evt->flags & DWC3_EVENT_PENDING))
continue;
event.raw = *(u32 *) (evt->buf + evt->lpos);

while (left > 0) {
union dwc3_event event;
dwc3_process_event_entry(dwc, &event);

event.raw = *(u32 *) (evt->buf + evt->lpos);
/*
* FIXME we wrap around correctly to the next entry as
* almost all entries are 4 bytes in size. There is one
* entry which has 12 bytes which is a regular entry
* followed by 8 bytes data. ATM I don't know how
* things are organized if we get next to the a
* boundary so I worry about that once we try to handle
* that.
*/
evt->lpos = (evt->lpos + 4) % DWC3_EVENT_BUFFERS_SIZE;
left -= 4;

dwc3_process_event_entry(dwc, &event);
dwc3_writel(dwc->regs, DWC3_GEVNTCOUNT(buf), 4);
}

/*
* FIXME we wrap around correctly to the next entry as
* almost all entries are 4 bytes in size. There is one
* entry which has 12 bytes which is a regular entry
* followed by 8 bytes data. ATM I don't know how
* things are organized if we get next to the a
* boundary so I worry about that once we try to handle
* that.
*/
evt->lpos = (evt->lpos + 4) % DWC3_EVENT_BUFFERS_SIZE;
left -= 4;
evt->count = 0;
evt->flags &= ~DWC3_EVENT_PENDING;
ret = IRQ_HANDLED;

dwc3_writel(dwc->regs, DWC3_GEVNTCOUNT(i), 4);
}
/* Unmask interrupt */
reg = dwc3_readl(dwc->regs, DWC3_GEVNTSIZ(buf));
reg &= ~DWC3_GEVNTSIZ_INTMASK;
dwc3_writel(dwc->regs, DWC3_GEVNTSIZ(buf), reg);

evt->count = 0;
evt->flags &= ~DWC3_EVENT_PENDING;
ret = IRQ_HANDLED;
return ret;
}

/* Unmask interrupt */
reg = dwc3_readl(dwc->regs, DWC3_GEVNTSIZ(i));
reg &= ~DWC3_GEVNTSIZ_INTMASK;
dwc3_writel(dwc->regs, DWC3_GEVNTSIZ(i), reg);
}
static irqreturn_t dwc3_thread_interrupt(int irq, void *_dwc)
{
struct dwc3 *dwc = _dwc;
unsigned long flags;
irqreturn_t ret = IRQ_NONE;
int i;

spin_lock_irqsave(&dwc->lock, flags);

for (i = 0; i < dwc->num_event_buffers; i++)
ret |= dwc3_process_event_buf(dwc, i);

spin_unlock_irqrestore(&dwc->lock, flags);

Expand Down

0 comments on commit f42f244

Please sign in to comment.