Received: by 2002:ac0:e34a:0:0:0:0:0 with SMTP id g10csp708605imn; Tue, 26 Jul 2022 07:19:13 -0700 (PDT) X-Google-Smtp-Source: AGRyM1vkv2eMjAddvWF+svIG81ab9RgAwoYu+/rf8V/7DVYLeIAAavIi+4N1HpUMcvfgKE7NVoaf X-Received: by 2002:a17:903:2c7:b0:16c:ebf6:db22 with SMTP id s7-20020a17090302c700b0016cebf6db22mr17312676plk.16.1658845152867; Tue, 26 Jul 2022 07:19:12 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1658845152; cv=none; d=google.com; s=arc-20160816; b=uYp/PxEyyJ+PK0UUo0PUoKNyHSRiQofmjPYlQNGPWBi7xMDus4Sw5gyxrDCm6fnUD1 /QVIbnFHCUQCIchbtyUesAol5+sej4m1lTeQTBkTLLIHZWZiz7MS+u1qT7v6oPFUGWQL L3kHJ0UgnSyoU1skqhj/VeGUfWgj90pyMidMCmdUyMMl6dcYx0JQBPTkq1aJ2JzOBC9t 4D2QZAYqbmNrFLXXmNsgt/KueSPDvcjeWXs092pkMHcHWuTV0muoNzRSis2kn6ETzsm9 Lm4DPkF9oZA8mcAp2S5ohqhC1PuJ+WZ2H+8CzBx0prqXvwZgqYzzcdwPB3sZTL21bK6t k55w== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:in-reply-to:content-disposition:mime-version :references:message-id:subject:cc:to:from:date; bh=O1SpzHL0YahE9blGhLYlOMtsG2fevaKaN/B+45cXlSk=; b=J+0YyQYTEnzZvGmAeHcrNBKuhwWDJBETkTbw0e/Rgv1m8UBJVCWI7//onUlaxRZN+w bUS38x/ROqHdGthOfeqXrqslXRA4GuGU2vzJ79W3vF4utCfJhdA+S9at4rxtrulJ5IXP w7ikoSc6LlRWUDRF7QdJ61CrmdCXi87UPlridz0LjoOPvYZcHlKxr/VrvYsKWQeW8Z9N +k0fC5XR+QFiBLEhnu/9TukJTFFSWKt+bCBBhxpz1s1gzZgx/cJW+ky9HLNsEsZfPhFV FqP669T29SR1zlbmavB3xxgor8/v2ciL3XKL9ldgfzw3kSczgoDGII8rdezQEPRD3MDt nPow== ARC-Authentication-Results: i=1; mx.google.com; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org Return-Path: Received: from out1.vger.email (out1.vger.email. [2620:137:e000::1:20]) by mx.google.com with ESMTP id u126-20020a626084000000b005061eb330a1si16597137pfb.351.2022.07.26.07.18.57; Tue, 26 Jul 2022 07:19:12 -0700 (PDT) Received-SPF: pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) client-ip=2620:137:e000::1:20; Authentication-Results: mx.google.com; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S233426AbiGZOCH (ORCPT + 99 others); Tue, 26 Jul 2022 10:02:07 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:44042 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S233247AbiGZOCF (ORCPT ); Tue, 26 Jul 2022 10:02:05 -0400 Received: from netrider.rowland.org (netrider.rowland.org [192.131.102.5]) by lindbergh.monkeyblade.net (Postfix) with SMTP id CEC7EF1C for ; Tue, 26 Jul 2022 07:02:03 -0700 (PDT) Received: (qmail 386446 invoked by uid 1000); 26 Jul 2022 10:02:02 -0400 Date: Tue, 26 Jul 2022 10:02:02 -0400 From: Alan Stern To: Weitao Wang Cc: gregkh@linuxfoundation.org, kishon@ti.com, dianders@chromium.org, s.shtylyov@omp.ru, mka@chromium.org, ming.lei@canonical.com, linux-usb@vger.kernel.org, linux-kernel@vger.kernel.org, tonywwang@zhaoxin.com, weitaowang@zhaoxin.com Subject: Re: [PATCH v3] USB: HCD: Fix URB giveback issue in tasklet function Message-ID: References: <20220726074918.5114-1-WeitaoWang-oc@zhaoxin.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20220726074918.5114-1-WeitaoWang-oc@zhaoxin.com> X-Spam-Status: No, score=-1.7 required=5.0 tests=BAYES_00, HEADER_FROM_DIFFERENT_DOMAINS,SPF_HELO_PASS,SPF_PASS autolearn=no autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on lindbergh.monkeyblade.net Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org On Tue, Jul 26, 2022 at 03:49:18PM +0800, Weitao Wang wrote: > Usb core introduce the mechanism of giveback of URB in tasklet context to > reduce hardware interrupt handling time. On some test situation(such as > FIO with 4KB block size), when tasklet callback function called to > giveback URB, interrupt handler add URB node to the bh->head list also. > If check bh->head list again after finish all URB giveback of local_list, > then it may introduce a "dynamic balance" between giveback URB and add URB > to bh->head list. This tasklet callback function may not exit for a long > time, which will cause other tasklet function calls to be delayed. Some > real-time applications(such as KB and Mouse) will see noticeable lag. > > In order to prevent the tasklet function from occupying the cpu for a long > time at a time, new URBS will not be added to the local_list even though > the bh->head list is not empty. But also need to ensure the left URB > giveback to be processed in time, so add a member high_prio for structure > giveback_urb_bh to prioritize tasklet and schelule this tasklet again if > bh->head list is not empty. > > At the same time, we are able to prioritize tasklet through structure > member high_prio. So, replace the local high_prio_bh variable with this > structure member in usb_hcd_giveback_urb. > > Fixes: 94dfd7edfd5c ("USB: HCD: support giveback of URB in tasklet context") > Signed-off-by: Weitao Wang > --- Reviewed-by: Alan Stern > v2->v3 > - Add more detail info about how to patch this issue. > - Change initial value of boolean variable high_prio from 1 to true. > > drivers/usb/core/hcd.c | 26 +++++++++++++++----------- > include/linux/usb/hcd.h | 1 + > 2 files changed, 16 insertions(+), 11 deletions(-) > > diff --git a/drivers/usb/core/hcd.c b/drivers/usb/core/hcd.c > index 06eea8848ccc..11c8ea0cccc8 100644 > --- a/drivers/usb/core/hcd.c > +++ b/drivers/usb/core/hcd.c > @@ -1691,7 +1691,6 @@ static void usb_giveback_urb_bh(struct tasklet_struct *t) > > spin_lock_irq(&bh->lock); > bh->running = true; > - restart: > list_replace_init(&bh->head, &local_list); > spin_unlock_irq(&bh->lock); > > @@ -1705,10 +1704,17 @@ static void usb_giveback_urb_bh(struct tasklet_struct *t) > bh->completing_ep = NULL; > } > > - /* check if there are new URBs to giveback */ > + /* > + * giveback new URBs next time to prevent this function > + * from not exiting for a long time. > + */ > spin_lock_irq(&bh->lock); > - if (!list_empty(&bh->head)) > - goto restart; > + if (!list_empty(&bh->head)) { > + if (bh->high_prio) > + tasklet_hi_schedule(&bh->bh); > + else > + tasklet_schedule(&bh->bh); > + } > bh->running = false; > spin_unlock_irq(&bh->lock); > } > @@ -1737,7 +1743,7 @@ static void usb_giveback_urb_bh(struct tasklet_struct *t) > void usb_hcd_giveback_urb(struct usb_hcd *hcd, struct urb *urb, int status) > { > struct giveback_urb_bh *bh; > - bool running, high_prio_bh; > + bool running; > > /* pass status to tasklet via unlinked */ > if (likely(!urb->unlinked)) > @@ -1748,13 +1754,10 @@ void usb_hcd_giveback_urb(struct usb_hcd *hcd, struct urb *urb, int status) > return; > } > > - if (usb_pipeisoc(urb->pipe) || usb_pipeint(urb->pipe)) { > + if (usb_pipeisoc(urb->pipe) || usb_pipeint(urb->pipe)) > bh = &hcd->high_prio_bh; > - high_prio_bh = true; > - } else { > + else > bh = &hcd->low_prio_bh; > - high_prio_bh = false; > - } > > spin_lock(&bh->lock); > list_add_tail(&urb->urb_list, &bh->head); > @@ -1763,7 +1766,7 @@ void usb_hcd_giveback_urb(struct usb_hcd *hcd, struct urb *urb, int status) > > if (running) > ; > - else if (high_prio_bh) > + else if (bh->high_prio) > tasklet_hi_schedule(&bh->bh); > else > tasklet_schedule(&bh->bh); > @@ -2959,6 +2962,7 @@ int usb_add_hcd(struct usb_hcd *hcd, > > /* initialize tasklets */ > init_giveback_urb_bh(&hcd->high_prio_bh); > + hcd->high_prio_bh.high_prio = true; > init_giveback_urb_bh(&hcd->low_prio_bh); > > /* enable irqs just before we start the controller, > diff --git a/include/linux/usb/hcd.h b/include/linux/usb/hcd.h > index 2c1fc9212cf2..98d1921f02b1 100644 > --- a/include/linux/usb/hcd.h > +++ b/include/linux/usb/hcd.h > @@ -66,6 +66,7 @@ > > struct giveback_urb_bh { > bool running; > + bool high_prio; > spinlock_t lock; > struct list_head head; > struct tasklet_struct bh; > -- > 2.32.0