From patchwork Thu Sep 24 08:21:30 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Thinh Nguyen X-Patchwork-Id: 258433 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-9.9 required=3.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID, DKIM_VALID_AU, HEADER_FROM_DIFFERENT_DOMAINS, INCLUDES_PATCH, MAILING_LIST_MULTI, SIGNED_OFF_BY, SPF_HELO_NONE, SPF_PASS autolearn=ham autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id A1264C2D0E2 for ; Thu, 24 Sep 2020 08:21:33 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 4B7CF23772 for ; Thu, 24 Sep 2020 08:21:33 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=synopsys.com header.i=@synopsys.com header.b="bTxvw80A" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1727268AbgIXIVc (ORCPT ); Thu, 24 Sep 2020 04:21:32 -0400 Received: from smtprelay-out1.synopsys.com ([149.117.73.133]:40364 "EHLO smtprelay-out1.synopsys.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1727265AbgIXIVc (ORCPT ); Thu, 24 Sep 2020 04:21:32 -0400 Received: from mailhost.synopsys.com (sv2-mailhost2.synopsys.com [10.205.2.134]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)) (No client certificate requested) by smtprelay-out1.synopsys.com (Postfix) with ESMTPS id 08BAE401AA; Thu, 24 Sep 2020 08:21:32 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=synopsys.com; s=mail; t=1600935692; bh=dqHUPplraHZeVjkJ+HRF3MCQmDTuBVDEFzE0+gIxUAo=; h=Date:In-Reply-To:References:From:Subject:To:Cc:From; b=bTxvw80ALmkQMvRoZbEf3yIYIytqCGFscJ9gDC9Yo67cfMELx+8S8sSgdNG4eRvL4 UsVC9nZzngHUlBCyraf+0plTYfzZ2ZHQrSUlMJrrBlBLogHp2Z8I0PqPwdbQ7Ily5r +tSxhcPWTlY2MUDZxi7aeoE+URJx/pNiVEndQMKWiVPF9+Yccyfe6B9CVVB2wLbUjv syqREJ6+0w05E1NojwnA4rkj7/8PQmO6dxqorXer041VM8Y3pcXDekhpM0noaB70r3 VqW4NZ9c8IewCSRoe+lKhUdqfckEeU96WM7840qHIo1k4leQBGOukPXx294R/SeJ2u EVwE7CrKJUimw== Received: from te-lab16 (nanobot.internal.synopsys.com [10.10.186.99]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by mailhost.synopsys.com (Postfix) with ESMTPSA id A6D59A0099; Thu, 24 Sep 2020 08:21:30 +0000 (UTC) Received: by te-lab16 (sSMTP sendmail emulation); Thu, 24 Sep 2020 01:21:30 -0700 Date: Thu, 24 Sep 2020 01:21:30 -0700 Message-Id: In-Reply-To: References: X-SNPS-Relay: synopsys.com From: Thinh Nguyen Subject: [PATCH 03/10] usb: dwc3: gadget: Refactor preparing extra TRB To: Felipe Balbi , Greg Kroah-Hartman , Thinh.Nguyen@synopsys.com, linux-usb@vger.kernel.org Cc: John Youn Precedence: bulk List-ID: X-Mailing-List: linux-usb@vger.kernel.org When the driver prepares the extra TRB, it uses bounce buffer. If we just add a new parameter to dwc3_prepare_one_trb() to indicate this, then we can refactor and simplify the driver quite a bit. dwc3_prepare_one_trb() also checks if a request had been moved to the started list. This is a prerequisite to subsequence patches improving the handling of extra TRBs. Signed-off-by: Thinh Nguyen --- drivers/usb/dwc3/gadget.c | 93 +++++++++++---------------------------- 1 file changed, 25 insertions(+), 68 deletions(-) diff --git a/drivers/usb/dwc3/gadget.c b/drivers/usb/dwc3/gadget.c index 6017263929f3..c0309ad34d28 100644 --- a/drivers/usb/dwc3/gadget.c +++ b/drivers/usb/dwc3/gadget.c @@ -1060,10 +1060,11 @@ static void __dwc3_prepare_one_trb(struct dwc3_ep *dep, struct dwc3_trb *trb, * @trb_length: buffer size of the TRB * @chain: should this TRB be chained to the next? * @node: only for isochronous endpoints. First TRB needs different type. + * @use_bounce_buffer: set to use bounce buffer */ static void dwc3_prepare_one_trb(struct dwc3_ep *dep, struct dwc3_request *req, unsigned int trb_length, - unsigned int chain, unsigned int node) + unsigned int chain, unsigned int node, bool use_bounce_buffer) { struct dwc3_trb *trb; dma_addr_t dma; @@ -1072,7 +1073,9 @@ static void dwc3_prepare_one_trb(struct dwc3_ep *dep, unsigned int no_interrupt = req->request.no_interrupt; unsigned int is_last = req->request.is_last; - if (req->request.num_sgs > 0) + if (use_bounce_buffer) + dma = dep->dwc->bounce_addr; + else if (req->request.num_sgs > 0) dma = sg_dma_address(req->start_sg); else dma = req->request.dma; @@ -1129,56 +1132,35 @@ static void dwc3_prepare_one_trb_sg(struct dwc3_ep *dep, chain = false; if (rem && usb_endpoint_dir_out(dep->endpoint.desc) && !chain) { - struct dwc3 *dwc = dep->dwc; - struct dwc3_trb *trb; - req->needs_extra_trb = true; /* prepare normal TRB */ - dwc3_prepare_one_trb(dep, req, trb_length, true, i); + dwc3_prepare_one_trb(dep, req, trb_length, + true, i, false); /* Now prepare one extra TRB to align transfer size */ - trb = &dep->trb_pool[dep->trb_enqueue]; - req->num_trbs++; - __dwc3_prepare_one_trb(dep, trb, dwc->bounce_addr, - maxp - rem, false, 1, - req->request.stream_id, - req->request.short_not_ok, - req->request.no_interrupt, - req->request.is_last); + dwc3_prepare_one_trb(dep, req, maxp - rem, + false, 1, true); } else if (req->request.zero && req->request.length && !usb_endpoint_xfer_isoc(dep->endpoint.desc) && !rem && !chain) { - struct dwc3 *dwc = dep->dwc; - struct dwc3_trb *trb; - req->needs_extra_trb = true; /* Prepare normal TRB */ - dwc3_prepare_one_trb(dep, req, trb_length, true, i); + dwc3_prepare_one_trb(dep, req, trb_length, + true, i, false); /* Prepare one extra TRB to handle ZLP */ - trb = &dep->trb_pool[dep->trb_enqueue]; - req->num_trbs++; - __dwc3_prepare_one_trb(dep, trb, dwc->bounce_addr, 0, - !req->direction, 1, - req->request.stream_id, - req->request.short_not_ok, - req->request.no_interrupt, - req->request.is_last); + dwc3_prepare_one_trb(dep, req, 0, + !req->direction, 1, true); /* Prepare one more TRB to handle MPS alignment */ - if (!req->direction) { - trb = &dep->trb_pool[dep->trb_enqueue]; - req->num_trbs++; - __dwc3_prepare_one_trb(dep, trb, dwc->bounce_addr, maxp, - false, 1, req->request.stream_id, - req->request.short_not_ok, - req->request.no_interrupt, - req->request.is_last); - } + if (!req->direction) + dwc3_prepare_one_trb(dep, req, maxp, + false, 1, true); } else { - dwc3_prepare_one_trb(dep, req, trb_length, chain, i); + dwc3_prepare_one_trb(dep, req, trb_length, + chain, i, false); } /* @@ -1216,54 +1198,29 @@ static void dwc3_prepare_one_trb_linear(struct dwc3_ep *dep, unsigned int rem = length % maxp; if ((!length || rem) && usb_endpoint_dir_out(dep->endpoint.desc)) { - struct dwc3 *dwc = dep->dwc; - struct dwc3_trb *trb; - req->needs_extra_trb = true; /* prepare normal TRB */ - dwc3_prepare_one_trb(dep, req, length, true, 0); + dwc3_prepare_one_trb(dep, req, length, true, 0, false); /* Now prepare one extra TRB to align transfer size */ - trb = &dep->trb_pool[dep->trb_enqueue]; - req->num_trbs++; - __dwc3_prepare_one_trb(dep, trb, dwc->bounce_addr, maxp - rem, - false, 1, req->request.stream_id, - req->request.short_not_ok, - req->request.no_interrupt, - req->request.is_last); + dwc3_prepare_one_trb(dep, req, maxp - rem, false, 1, true); } else if (req->request.zero && req->request.length && !usb_endpoint_xfer_isoc(dep->endpoint.desc) && (IS_ALIGNED(req->request.length, maxp))) { - struct dwc3 *dwc = dep->dwc; - struct dwc3_trb *trb; - req->needs_extra_trb = true; /* prepare normal TRB */ - dwc3_prepare_one_trb(dep, req, length, true, 0); + dwc3_prepare_one_trb(dep, req, length, true, 0, false); /* Prepare one extra TRB to handle ZLP */ - trb = &dep->trb_pool[dep->trb_enqueue]; - req->num_trbs++; - __dwc3_prepare_one_trb(dep, trb, dwc->bounce_addr, 0, - !req->direction, 1, req->request.stream_id, - req->request.short_not_ok, - req->request.no_interrupt, - req->request.is_last); + dwc3_prepare_one_trb(dep, req, 0, !req->direction, 1, true); /* Prepare one more TRB to handle MPS alignment for OUT */ - if (!req->direction) { - trb = &dep->trb_pool[dep->trb_enqueue]; - req->num_trbs++; - __dwc3_prepare_one_trb(dep, trb, dwc->bounce_addr, maxp, - false, 1, req->request.stream_id, - req->request.short_not_ok, - req->request.no_interrupt, - req->request.is_last); - } + if (!req->direction) + dwc3_prepare_one_trb(dep, req, maxp, false, 1, true); } else { - dwc3_prepare_one_trb(dep, req, length, false, 0); + dwc3_prepare_one_trb(dep, req, length, false, 0, false); } }