Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit c0ed8b23 authored by Yoshihiro Shimoda's avatar Yoshihiro Shimoda Committed by Felipe Balbi
Browse files

usb: renesas_usbhs: fix the condition of is_done in usbhsf_dma_push_done



This patch fixes the condition of is_done in usbhsf_dma_push_done().
This function will be called after a transmission finished by DMAC.
So, the function should check if the transmission packet is short packet
or not. Also the function should call try_run to send the zero packet
by the pio handler if the "*is_done" is not set. Otherwize, the
transaction will not finish if a gadget driver sets the "zero" flag
in a transmission.

Signed-off-by: default avatarYoshihiro Shimoda <yoshihiro.shimoda.uh@renesas.com>
Signed-off-by: default avatarFelipe Balbi <balbi@ti.com>
parent c4d8199b
Loading
Loading
Loading
Loading
+15 −2
Original line number Diff line number Diff line
@@ -889,16 +889,29 @@ static int usbhsf_dma_prepare_push(struct usbhs_pkt *pkt, int *is_done)
static int usbhsf_dma_push_done(struct usbhs_pkt *pkt, int *is_done)
{
	struct usbhs_pipe *pipe = pkt->pipe;
	int is_short = pkt->trans % usbhs_pipe_get_maxpacket(pipe);

	pkt->actual = pkt->trans;
	pkt->actual += pkt->trans;

	if (pkt->actual < pkt->length)
		*is_done = 0;		/* there are remainder data */
	else if (is_short)
		*is_done = 1;		/* short packet */
	else
		*is_done = !pkt->zero;	/* send zero packet? */

	usbhs_pipe_running(pipe, !*is_done);

	usbhsf_dma_stop(pipe, pipe->fifo);
	usbhsf_dma_unmap(pkt);
	usbhsf_fifo_unselect(pipe, pipe->fifo);

	if (!*is_done) {
		/* change handler to PIO */
		pkt->handler = &usbhs_fifo_pio_push_handler;
		return pkt->handler->try_run(pkt, is_done);
	}

	return 0;
}