From patchwork Sun Sep 29 18:59:21 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Michael Grzeschik X-Patchwork-Id: 13815205 Received: from metis.whiteo.stw.pengutronix.de (metis.whiteo.stw.pengutronix.de [185.203.201.7]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id B2BEF73477 for ; Sun, 29 Sep 2024 18:59:37 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=185.203.201.7 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1727636380; cv=none; b=HfnHpibk+Z0yg3IBolC6bcfuhdALOKBtsMuqqS6dA0pcOcn4TM7DOc7hcVaxmbiAWCaZpNWdAglMH9TRoa3XCkSCTH+OMu9lSyTFrUbaG8YnKzpt/2TYtZU8mdcu9SaDVy5hP4GvPBbRZWoUEBIL7BlkUrNDAfSN9sXsLL6to2w= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1727636380; c=relaxed/simple; bh=kngrIUdohYDweYjrpeEtFY0IvoCnJzGSSuzWmk8HDPA=; h=From:Date:Subject:MIME-Version:Content-Type:Message-Id:References: In-Reply-To:To:Cc; b=DXWfOVVP+AodU7xbtL8rRVucT9/YF58KekhdSZlHlDrrboPLqswT+Et8QjEV5gkCqU0xLQ8uSsWrHonOFjH0bwNl4q9Fp9HziSJ2/bTYLV+ER3U8b3KAo5jlW1IUcanf8u1iHtmL7pr6r4VPCu8/qx/u6QYDFaczJmdZPtID8ho= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=pengutronix.de; spf=pass smtp.mailfrom=pengutronix.de; arc=none smtp.client-ip=185.203.201.7 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=pengutronix.de Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=pengutronix.de Received: from drehscheibe.grey.stw.pengutronix.de ([2a0a:edc0:0:c01:1d::a2]) by metis.whiteo.stw.pengutronix.de with esmtps (TLS1.3:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1suz8l-00053o-KL; Sun, 29 Sep 2024 20:59:31 +0200 Received: from [2a0a:edc0:0:1101:1d::ac] (helo=dude04.red.stw.pengutronix.de) by drehscheibe.grey.stw.pengutronix.de with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.94.2) (envelope-from ) id 1suz8l-002Ro2-0H; Sun, 29 Sep 2024 20:59:31 +0200 Received: from localhost ([::1] helo=dude04.red.stw.pengutronix.de) by dude04.red.stw.pengutronix.de with esmtp (Exim 4.96) (envelope-from ) id 1suz8k-0029Vj-2v; Sun, 29 Sep 2024 20:59:30 +0200 From: Michael Grzeschik Date: Sun, 29 Sep 2024 20:59:21 +0200 Subject: [PATCH v6 1/9] usb: gadget: uvc: wake pump everytime we update the free list Precedence: bulk X-Mailing-List: linux-usb@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Message-Id: <20240403-uvc_request_length_by_interval-v6-1-08c05522e1f5@pengutronix.de> References: <20240403-uvc_request_length_by_interval-v6-0-08c05522e1f5@pengutronix.de> In-Reply-To: <20240403-uvc_request_length_by_interval-v6-0-08c05522e1f5@pengutronix.de> To: Laurent Pinchart , Daniel Scally , Greg Kroah-Hartman , Avichal Rakesh , Jayant Chowdhary Cc: linux-usb@vger.kernel.org, linux-kernel@vger.kernel.org, kernel@pengutronix.de, Michael Grzeschik X-Mailer: b4 0.12.0 X-Developer-Signature: v=1; a=openpgp-sha256; l=1174; i=m.grzeschik@pengutronix.de; h=from:subject:message-id; bh=kngrIUdohYDweYjrpeEtFY0IvoCnJzGSSuzWmk8HDPA=; b=owEBbQKS/ZANAwAKAb9pWET5cfSrAcsmYgBm+aOPn/vQOXvdVMsUJ4otY8xzduWcjdZ0nf18G 09B+JXftPmJAjMEAAEKAB0WIQQV2+2Fpbqd6fvv0Gi/aVhE+XH0qwUCZvmjjwAKCRC/aVhE+XH0 q64BD/98VAGE2/ELmPGAWkPbbsyPSY+nOyMVz9dZlQJ/qjoGLrQy8h9DwIZKsJacOyMnvstH4EK ijINEOd8ppAwZUF+fdIqcyS+zrT3yGhQ8ryD0GfTTrMEqa0PR2jJVjLzW8QE9PgEWwIXuRE+Tee /eFfVk6IgeKW+WCbCAFTFtTdokcNGvS+Uh+zU6HwglqY9zKAer/7N93xj8GF9TXjsEdX9h8yB/j aoi2hefgj+O2gUZvCTaemHfjnPaHJ4HYLOgT4oLShfL4X9pGzgRkIoU0DJ+p4VTtGI1V9Phu4Fk 4pjO3/N9h7xs/zwz8/4Kb7mE+CH4VkTxTUQjWE2Qy1854OKMPHkDYIAgrAcsjk0q+BL9VyEjKMa cW6jJArRS2q1wQnwBC7zjsZATaR7npdbAxlVSR59FsuKO7UXKiP+wR1YK5htWDqhdagDR+wfvoo /CvVoTwGcH8RG/QGjg1PWLBa1clKW+Bm4TO8fC5njPW5CEOhiStmoGoEFUnFh8W1W1YZJwrWpxv dGkokA0meiJJK4ww3aiq08aN60pF2qgIn/uzRTJ3G6ZO4JLlIjEpjEWitQPTSLUYKzQ0SyvFywI pZrjRFjzBMvb5gY92YRE5nSA7ZcQ3tleOctaKkuezV9ncez5klEdEOJc5cQIIInLr5JPY+9Xvp/ dpqqj/t5G4Jq3Cg== X-Developer-Key: i=m.grzeschik@pengutronix.de; a=openpgp; fpr=957BC452CE953D7EA60CF4FC0BE9E3157A1E2C64 X-SA-Exim-Connect-IP: 2a0a:edc0:0:c01:1d::a2 X-SA-Exim-Mail-From: m.grzeschik@pengutronix.de X-SA-Exim-Scanned: No (on metis.whiteo.stw.pengutronix.de); SAEximRunCond expanded to false X-PTX-Original-Recipient: linux-usb@vger.kernel.org Since the req_free list will updated if enqueuing one request was not possible it will be added back to the free list. With every available free request in the queue it is a valid case for the pump worker to use it and continue the pending bufferdata into requests for the req_ready list. Fixes: 6acba0345b68 ("usb:gadget:uvc Do not use worker thread to pump isoc usb requests") Signed-off-by: Michael Grzeschik --- v5 -> v6: - v1 -> v5: - new patch --- drivers/usb/gadget/function/uvc_video.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/drivers/usb/gadget/function/uvc_video.c b/drivers/usb/gadget/function/uvc_video.c index a9edd60fbbf77..48fd8d3c50b0c 100644 --- a/drivers/usb/gadget/function/uvc_video.c +++ b/drivers/usb/gadget/function/uvc_video.c @@ -480,6 +480,10 @@ uvc_video_complete(struct usb_ep *ep, struct usb_request *req) * up later. */ list_add_tail(&to_queue->list, &video->req_free); + /* + * There is a new free request - wake up the pump. + */ + queue_work(video->async_wq, &video->pump); } spin_unlock_irqrestore(&video->req_lock, flags); From patchwork Sun Sep 29 18:59:22 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Michael Grzeschik X-Patchwork-Id: 13815213 Received: from metis.whiteo.stw.pengutronix.de (metis.whiteo.stw.pengutronix.de [185.203.201.7]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id AC27D6F2FE for ; Sun, 29 Sep 2024 18:59:37 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=185.203.201.7 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1727636383; cv=none; b=JPtScmUMDZxHjzQ1HZRMM3LXDnAgL0NZO7+e2aRQYGKXuB64FxdXrN+Nz59EKSOdaII1f92atuzt0v0xsCOQ/7MDRbXmoopofDev7WZkVLQC/qBCFwMpOd2QKq2YAtccoTAJM0YazKv3V3qUafF3SqTTv+zQp9R/XMoDYfmI6Z0= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1727636383; c=relaxed/simple; bh=CBqNSqIk0ltXBdmgW8Ti/RSg2E6v/8JTXpUdBmbQDJI=; h=From:Date:Subject:MIME-Version:Content-Type:Message-Id:References: In-Reply-To:To:Cc; b=LCpsn8xciPqnWGtBlr9uuM8sT5gLgwqCkQ5A5MRDDJkfZwX2tOowER0CKxMw5gUJesklpr/aSgSfJiANIp6FZokaTbr1npU6qW/zd9VBWVjeZ3CcKGaktLmb11+EDGTCYdoBR3+9/6tAdZNr4RKbZV4zO5EuwEgZxkDmpLlJH+o= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=pengutronix.de; spf=pass smtp.mailfrom=pengutronix.de; arc=none smtp.client-ip=185.203.201.7 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=pengutronix.de Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=pengutronix.de Received: from drehscheibe.grey.stw.pengutronix.de ([2a0a:edc0:0:c01:1d::a2]) by metis.whiteo.stw.pengutronix.de with esmtps (TLS1.3:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1suz8l-00053n-KK; Sun, 29 Sep 2024 20:59:31 +0200 Received: from [2a0a:edc0:0:1101:1d::ac] (helo=dude04.red.stw.pengutronix.de) by drehscheibe.grey.stw.pengutronix.de with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.94.2) (envelope-from ) id 1suz8k-002Ro4-WD; Sun, 29 Sep 2024 20:59:31 +0200 Received: from localhost ([::1] helo=dude04.red.stw.pengutronix.de) by dude04.red.stw.pengutronix.de with esmtp (Exim 4.96) (envelope-from ) id 1suz8k-0029Vj-2w; Sun, 29 Sep 2024 20:59:30 +0200 From: Michael Grzeschik Date: Sun, 29 Sep 2024 20:59:22 +0200 Subject: [PATCH v6 2/9] usb: gadget: uvc: only enqueue zero length requests in potential underrun Precedence: bulk X-Mailing-List: linux-usb@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Message-Id: <20240403-uvc_request_length_by_interval-v6-2-08c05522e1f5@pengutronix.de> References: <20240403-uvc_request_length_by_interval-v6-0-08c05522e1f5@pengutronix.de> In-Reply-To: <20240403-uvc_request_length_by_interval-v6-0-08c05522e1f5@pengutronix.de> To: Laurent Pinchart , Daniel Scally , Greg Kroah-Hartman , Avichal Rakesh , Jayant Chowdhary Cc: linux-usb@vger.kernel.org, linux-kernel@vger.kernel.org, kernel@pengutronix.de, Michael Grzeschik X-Mailer: b4 0.12.0 X-Developer-Signature: v=1; a=openpgp-sha256; l=4026; i=m.grzeschik@pengutronix.de; h=from:subject:message-id; bh=CBqNSqIk0ltXBdmgW8Ti/RSg2E6v/8JTXpUdBmbQDJI=; b=owEBbQKS/ZANAwAKAb9pWET5cfSrAcsmYgBm+aOQzPRqkwpM/eo56AIi8qjiJ5NPtmopQvtX1 vFAO/Yx9HmJAjMEAAEKAB0WIQQV2+2Fpbqd6fvv0Gi/aVhE+XH0qwUCZvmjkAAKCRC/aVhE+XH0 qzcfD/4kqh9sEHV8sQpWOsgPGbYKBN+vbucilNyg3NtkqfzfEuh0OMDVIv4siMC52DhFomcZvUT iRtfrSRC2cYfLY8T8ZeA8wfjvINtATcfxfTFzzRK9+/56XF1PAdRJVUFCFnUYHQE8zwLROJhEdY 94gRGbze6Tc4WkdF1/vBWChlsPdmo4J51aL2kuTcMOqlXUJAfnxF+EpfXc+/MtClZBy3HIvkt4J wd9/cNflx1AA3CiswCLnG9VWoPjTxev+QDZCBi3xdVOg3PKqnyAl+v4CyolYivb6+rGiizQagZk DidZRN1cXpqrRHbfvMba8KyDyk92prMMo2jSGpCGSuXwUmxuLkOFJ88FZFD9gOHUcMWxrp7aa1C EvuO93SwPlSaSRDuSEYrjKmQOpSKkZTFsGlQ8/IhNutTaZOXsQsxbkHOvgYVtNV/eDEWE2BoDRS IVJBUYlDuAumvYO03vxIXgpjFxTV+K81RHvjT9DaUVuD9dP8Fjn4goNVr5wuEw1VGf8o9zWaUdN 99Wab8aAN9yNWoCp529TiayxzbNvjIq8QtZQydEve7sMdIquFt5LHWzs3EnyhAKk5I5LokIs7z3 5q+oFCIC+16NN9FZF/huLgvRNVlZWo1M+DMD/Wu1VlB0TmMzb7eyNCv0HzeRNuBxp3jJ0pJ0pRm gL/XNN1JIsw7Fvg== X-Developer-Key: i=m.grzeschik@pengutronix.de; a=openpgp; fpr=957BC452CE953D7EA60CF4FC0BE9E3157A1E2C64 X-SA-Exim-Connect-IP: 2a0a:edc0:0:c01:1d::a2 X-SA-Exim-Mail-From: m.grzeschik@pengutronix.de X-SA-Exim-Scanned: No (on metis.whiteo.stw.pengutronix.de); SAEximRunCond expanded to false X-PTX-Original-Recipient: linux-usb@vger.kernel.org The complete handler will at least be called after 16 requests have completed, but will still handle all finisher requests. Since we have to maintain a costant filling in the isoc queue we ensure this by adding zero length requests. By counting the amount enqueued requests we can ensure that the queue is never underrun and only need to get active if the queue is running critical. This patch is setting 32 as the critical level, which is twice the request amount that is needed to create interrupts. To properly solve the amount of zero length requests that needs to be held in the hardware after one interrupt needs to be measured and depends on the runtime of the first enqueue run after the interrupt triggered. For now we just use twice the amount of requests between an interrupt. Signed-off-by: Michael Grzeschik --- v5 -> v6: - v4 -> v5: - using min to limit for UVCG_REQ_MAX_INT_COUNT as the interrupt boundary - using atomic_inc, atomic_dec on one variable to avoid rollover - reordered this patch in the series - added UVCG_REQ_MAX_ZERO_COUNT to set the threshold of zero length requests in the hw - added UVCG_REQ_MAX_INT_COUNT as quantifier for the highest amount of request between an interrupt v1 -> v4: - --- drivers/usb/gadget/function/uvc.h | 5 +++++ drivers/usb/gadget/function/uvc_video.c | 17 ++++++++++++++++- 2 files changed, 21 insertions(+), 1 deletion(-) diff --git a/drivers/usb/gadget/function/uvc.h b/drivers/usb/gadget/function/uvc.h index cb35687b11e7e..55d796f5f5e8d 100644 --- a/drivers/usb/gadget/function/uvc.h +++ b/drivers/usb/gadget/function/uvc.h @@ -71,6 +71,9 @@ extern unsigned int uvc_gadget_trace_param; #define UVCG_REQUEST_HEADER_LEN 12 +#define UVCG_REQ_MAX_INT_COUNT 16 +#define UVCG_REQ_MAX_ZERO_COUNT (2 * UVCG_REQ_MAX_INT_COUNT) + /* ------------------------------------------------------------------------ * Structures */ @@ -91,6 +94,8 @@ struct uvc_video { struct work_struct pump; struct workqueue_struct *async_wq; + atomic_t queued; + /* Frame parameters */ u8 bpp; u32 fcc; diff --git a/drivers/usb/gadget/function/uvc_video.c b/drivers/usb/gadget/function/uvc_video.c index 48fd8d3c50b0c..eb82aaed6ba13 100644 --- a/drivers/usb/gadget/function/uvc_video.c +++ b/drivers/usb/gadget/function/uvc_video.c @@ -269,6 +269,8 @@ static int uvcg_video_ep_queue(struct uvc_video *video, struct usb_request *req) } } + atomic_inc(&video->queued); + return ret; } @@ -304,7 +306,7 @@ static int uvcg_video_usb_req_queue(struct uvc_video *video, */ if (list_empty(&video->req_free) || ureq->last_buf || !(video->req_int_count % - DIV_ROUND_UP(video->uvc_num_requests, 4))) { + min(DIV_ROUND_UP(video->uvc_num_requests, 4), UVCG_REQ_MAX_INT_COUNT))) { video->req_int_count = 0; req->no_interrupt = 0; } else { @@ -379,6 +381,7 @@ uvc_video_complete(struct usb_ep *ep, struct usb_request *req) int ret = 0; spin_lock_irqsave(&video->req_lock, flags); + atomic_dec(&video->queued); if (!video->is_enabled) { /* * When is_enabled is false, uvcg_video_disable() ensures @@ -466,6 +469,16 @@ uvc_video_complete(struct usb_ep *ep, struct usb_request *req) * happen. */ queue_work(video->async_wq, &video->pump); + } else if (atomic_read(&video->queued) > UVCG_REQ_MAX_ZERO_COUNT) { + list_add_tail(&to_queue->list, &video->req_free); + /* + * There is a new free request - wake up the pump. + */ + queue_work(video->async_wq, &video->pump); + + spin_unlock_irqrestore(&video->req_lock, flags); + + return; } /* * Queue to the endpoint. The actual queueing to ep will @@ -756,6 +769,8 @@ int uvcg_video_enable(struct uvc_video *video) video->req_int_count = 0; + atomic_set(&video->queued, 0); + uvc_video_ep_queue_initial_requests(video); queue_work(video->async_wq, &video->pump); From patchwork Sun Sep 29 18:59:23 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Michael Grzeschik X-Patchwork-Id: 13815208 Received: from metis.whiteo.stw.pengutronix.de (metis.whiteo.stw.pengutronix.de [185.203.201.7]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 9EC2164A8F for ; Sun, 29 Sep 2024 18:59:37 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=185.203.201.7 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1727636381; cv=none; b=fs/rrxWFIBW+0wjjLuslqZUA3WN3MDijoEro3mRXvL4631DFrfVQjykjyN37ixK9iJMx+ryoFkB/7d0Ue1MZcUPMbDGFNjqijLnruPtMqZrx6cpoDPxGEp0T6r2mF4iwgw5/rU9irNQR6P2/HxYOpziarGBWJpMSdazKno1KTNo= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1727636381; c=relaxed/simple; bh=tqEAc4G4g5DANBIiYnngjMwLHhsQQN7FAdkIiAeqdto=; h=From:Date:Subject:MIME-Version:Content-Type:Message-Id:References: In-Reply-To:To:Cc; b=s4nOVnKoDRMze5zmmN5jgoOdo7BikvgQx3Po911Z2qCcOJLANT7V2ja0WBMG9oPIGsnyvxABv1ekaCSJBZtD7RnWCm7Sm2IJC/XS6vJJB7SQQRgpq5ZkAI7Mi4paJU4MlFUb/tjQ5RybqCqxDkXnGSbNrRL3YFWo4rNiZNJ52nc= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=pengutronix.de; spf=pass smtp.mailfrom=pengutronix.de; arc=none smtp.client-ip=185.203.201.7 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=pengutronix.de Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=pengutronix.de Received: from drehscheibe.grey.stw.pengutronix.de ([2a0a:edc0:0:c01:1d::a2]) by metis.whiteo.stw.pengutronix.de with esmtps (TLS1.3:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1suz8l-00053u-KM; Sun, 29 Sep 2024 20:59:31 +0200 Received: from [2a0a:edc0:0:1101:1d::ac] (helo=dude04.red.stw.pengutronix.de) by drehscheibe.grey.stw.pengutronix.de with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.94.2) (envelope-from ) id 1suz8l-002Ro5-0m; Sun, 29 Sep 2024 20:59:31 +0200 Received: from localhost ([::1] helo=dude04.red.stw.pengutronix.de) by dude04.red.stw.pengutronix.de with esmtp (Exim 4.96) (envelope-from ) id 1suz8k-0029Vj-2x; Sun, 29 Sep 2024 20:59:30 +0200 From: Michael Grzeschik Date: Sun, 29 Sep 2024 20:59:23 +0200 Subject: [PATCH v6 3/9] usb: gadget: uvc: rework to enqueue in pump worker from encoded queue Precedence: bulk X-Mailing-List: linux-usb@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Message-Id: <20240403-uvc_request_length_by_interval-v6-3-08c05522e1f5@pengutronix.de> References: <20240403-uvc_request_length_by_interval-v6-0-08c05522e1f5@pengutronix.de> In-Reply-To: <20240403-uvc_request_length_by_interval-v6-0-08c05522e1f5@pengutronix.de> To: Laurent Pinchart , Daniel Scally , Greg Kroah-Hartman , Avichal Rakesh , Jayant Chowdhary Cc: linux-usb@vger.kernel.org, linux-kernel@vger.kernel.org, kernel@pengutronix.de, Michael Grzeschik X-Mailer: b4 0.12.0 X-Developer-Signature: v=1; a=openpgp-sha256; l=10792; i=m.grzeschik@pengutronix.de; h=from:subject:message-id; bh=tqEAc4G4g5DANBIiYnngjMwLHhsQQN7FAdkIiAeqdto=; b=owEBbQKS/ZANAwAKAb9pWET5cfSrAcsmYgBm+aOQN/n0sMwL6+6ej/Bdp2EhaSyh8Kmbxterp AgboMcxWoSJAjMEAAEKAB0WIQQV2+2Fpbqd6fvv0Gi/aVhE+XH0qwUCZvmjkAAKCRC/aVhE+XH0 q4S1D/9/GTbNFgXjvAaRMd31R03/Xj1KhLIFy6T4XlPlKldjD1oTEbbldNgQv0RXEHTwaEGibHh HtflYw3OPbjt/E8axdXhRbv0pDg8k0Hriw/odtnHRBgjM0alKhuUmLWkyQ58pFMvOinMwDzH4YJ 2IqfUWF+YwSkS+OogtCCzEiB5m/nJnBzGtQzCSD+MiyhVOkNGvKQ5KCxcbMn2ocj5LRqsyLMtlg xxFFMhnRbvNX/jLaNsA4zf+VJnLKy4CkMW58Vz2+ze01Rdb84kHg06Gbup59APHgC/bqKEySaNw s6yUQzsscDj3EZoSD8pX/TEUZplrUYwVB7TjlGqr2TNCvS7G0laXPoAjtctq2UkBck2Lxy0RTGG HpTRH6bbKyxcK/EHYgUMqTHtnPxyk/F7EztzzD1VMDxbtY4hOO0vwGMw98LxJ0RAfcDqm1qEhX2 xi5rtz1KbES/byWUpNBdPsUgmYaFwD5/oN2bVLX8q50/sHoBWDYMZ14iGgmGCjQMXzNi2u158zH TJ6eLHBg+RkcnICE1sefWYhgqV7qWCDu3WPdSPxtlRYAbXh3FAcQuw1TG6S+RMqME6FgZuzJhMY 3Vx46L2AEXw9bz4jMoSoHCRE1GKcnAjEKDHa6ZDG2qkxzp5swi1HyM/P49qlvmWdF2kDcDJjARq eQMUnXyZwkaMGvQ== X-Developer-Key: i=m.grzeschik@pengutronix.de; a=openpgp; fpr=957BC452CE953D7EA60CF4FC0BE9E3157A1E2C64 X-SA-Exim-Connect-IP: 2a0a:edc0:0:c01:1d::a2 X-SA-Exim-Mail-From: m.grzeschik@pengutronix.de X-SA-Exim-Scanned: No (on metis.whiteo.stw.pengutronix.de); SAEximRunCond expanded to false X-PTX-Original-Recipient: linux-usb@vger.kernel.org We install an kthread with pfifo priority that is iterating over all prepared requests and keeps the isoc queue busy. This way it will be scheduled with the same priority as the interrupt handler. As the kthread is triggered with video_enable it will immediately queue some zero length requests into the hw if there is no buffer data available. It also watches the level of needed zero length requests in the hardware not to fall under the UVCG_REQ_MAX_ZERO_COUNT threshold. This way we can drop the function uvc_video_ep_queue_initial_requests entirely. By using the kthread to do the actual request handling the interrupt handler will not be running into the time consuming and eventually locking work of actually enqueueing the requests back into its own pipeline. This work can now even be scheduled on another cpu. Signed-off-by: Michael Grzeschik --- v5 -> v6: - v4 -> v5: - merging patch '(drivers/usb/gadget/function/uvc_queue.h') into this one - added initial kthread_queue_work(video->kworker, &video->hw_submit); to uvcg_video_enable - fixed error message in uvcg_video_init - reordered this patch in the series - renamed the kworker to hw_submit since the pump thread is used again with the work_queue v1 -> v4: - --- drivers/usb/gadget/function/f_uvc.c | 2 + drivers/usb/gadget/function/uvc.h | 3 + drivers/usb/gadget/function/uvc_video.c | 180 +++++++++++++++----------------- 3 files changed, 87 insertions(+), 98 deletions(-) diff --git a/drivers/usb/gadget/function/f_uvc.c b/drivers/usb/gadget/function/f_uvc.c index 40187b7112e79..f04376768bc10 100644 --- a/drivers/usb/gadget/function/f_uvc.c +++ b/drivers/usb/gadget/function/f_uvc.c @@ -991,6 +991,8 @@ static void uvc_function_unbind(struct usb_configuration *c, uvcg_info(f, "%s()\n", __func__); + kthread_cancel_work_sync(&video->hw_submit); + if (video->async_wq) destroy_workqueue(video->async_wq); diff --git a/drivers/usb/gadget/function/uvc.h b/drivers/usb/gadget/function/uvc.h index 55d796f5f5e8d..4f44a607d9f5c 100644 --- a/drivers/usb/gadget/function/uvc.h +++ b/drivers/usb/gadget/function/uvc.h @@ -94,6 +94,9 @@ struct uvc_video { struct work_struct pump; struct workqueue_struct *async_wq; + struct kthread_worker *kworker; + struct kthread_work hw_submit; + atomic_t queued; /* Frame parameters */ diff --git a/drivers/usb/gadget/function/uvc_video.c b/drivers/usb/gadget/function/uvc_video.c index eb82aaed6ba13..f43bf19218963 100644 --- a/drivers/usb/gadget/function/uvc_video.c +++ b/drivers/usb/gadget/function/uvc_video.c @@ -324,50 +324,6 @@ static int uvcg_video_usb_req_queue(struct uvc_video *video, return 0; } -/* - * Must only be called from uvcg_video_enable - since after that we only want to - * queue requests to the endpoint from the uvc_video_complete complete handler. - * This function is needed in order to 'kick start' the flow of requests from - * gadget driver to the usb controller. - */ -static void uvc_video_ep_queue_initial_requests(struct uvc_video *video) -{ - struct usb_request *req = NULL; - unsigned long flags = 0; - unsigned int count = 0; - int ret = 0; - - /* - * We only queue half of the free list since we still want to have - * some free usb_requests in the free list for the video_pump async_wq - * thread to encode uvc buffers into. Otherwise we could get into a - * situation where the free list does not have any usb requests to - * encode into - we always end up queueing 0 length requests to the - * end point. - */ - unsigned int half_list_size = video->uvc_num_requests / 2; - - spin_lock_irqsave(&video->req_lock, flags); - /* - * Take these requests off the free list and queue them all to the - * endpoint. Since we queue 0 length requests with the req_lock held, - * there isn't any 'data' race involved here with the complete handler. - */ - while (count < half_list_size) { - req = list_first_entry(&video->req_free, struct usb_request, - list); - list_del(&req->list); - req->length = 0; - ret = uvcg_video_ep_queue(video, req); - if (ret < 0) { - uvcg_queue_cancel(&video->queue, 0); - break; - } - count++; - } - spin_unlock_irqrestore(&video->req_lock, flags); -} - static void uvc_video_complete(struct usb_ep *ep, struct usb_request *req) { @@ -375,10 +331,7 @@ uvc_video_complete(struct usb_ep *ep, struct usb_request *req) struct uvc_video *video = ureq->video; struct uvc_video_queue *queue = &video->queue; struct uvc_buffer *last_buf; - struct usb_request *to_queue = req; unsigned long flags; - bool is_bulk = video->max_payload_size; - int ret = 0; spin_lock_irqsave(&video->req_lock, flags); atomic_dec(&video->queued); @@ -441,65 +394,85 @@ uvc_video_complete(struct usb_ep *ep, struct usb_request *req) return; } + list_add_tail(&req->list, &video->req_free); /* - * Here we check whether any request is available in the ready - * list. If it is, queue it to the ep and add the current - * usb_request to the req_free list - for video_pump to fill in. - * Otherwise, just use the current usb_request to queue a 0 - * length request to the ep. Since we always add to the req_free - * list if we dequeue from the ready list, there will never - * be a situation where the req_free list is completely out of - * requests and cannot recover. + * Queue work to the wq as well since it is possible that a + * buffer may not have been completely encoded with the set of + * in-flight usb requests for whih the complete callbacks are + * firing. + * In that case, if we do not queue work to the worker thread, + * the buffer will never be marked as complete - and therefore + * not be returned to userpsace. As a result, + * dequeue -> queue -> dequeue flow of uvc buffers will not + * happen. Since there are is a new free request wake up the pump. */ - to_queue->length = 0; - if (!list_empty(&video->req_ready)) { - to_queue = list_first_entry(&video->req_ready, - struct usb_request, list); - list_del(&to_queue->list); - list_add_tail(&req->list, &video->req_free); - /* - * Queue work to the wq as well since it is possible that a - * buffer may not have been completely encoded with the set of - * in-flight usb requests for whih the complete callbacks are - * firing. - * In that case, if we do not queue work to the worker thread, - * the buffer will never be marked as complete - and therefore - * not be returned to userpsace. As a result, - * dequeue -> queue -> dequeue flow of uvc buffers will not - * happen. - */ - queue_work(video->async_wq, &video->pump); - } else if (atomic_read(&video->queued) > UVCG_REQ_MAX_ZERO_COUNT) { - list_add_tail(&to_queue->list, &video->req_free); - /* - * There is a new free request - wake up the pump. - */ - queue_work(video->async_wq, &video->pump); + queue_work(video->async_wq, &video->pump); - spin_unlock_irqrestore(&video->req_lock, flags); + spin_unlock_irqrestore(&video->req_lock, flags); - return; - } - /* - * Queue to the endpoint. The actual queueing to ep will - * only happen on one thread - the async_wq for bulk endpoints - * and this thread for isoc endpoints. - */ - ret = uvcg_video_usb_req_queue(video, to_queue, !is_bulk); - if (ret < 0) { + kthread_queue_work(video->kworker, &video->hw_submit); +} + +static void uvcg_video_hw_submit(struct kthread_work *work) +{ + struct uvc_video *video = container_of(work, struct uvc_video, hw_submit); + bool is_bulk = video->max_payload_size; + unsigned long flags; + struct usb_request *req; + int ret = 0; + + while (true) { + if (!video->ep->enabled) + return; + spin_lock_irqsave(&video->req_lock, flags); /* - * Endpoint error, but the stream is still enabled. - * Put request back in req_free for it to be cleaned - * up later. + * Here we check whether any request is available in the ready + * list. If it is, queue it to the ep and add the current + * usb_request to the req_free list - for video_pump to fill in. + * Otherwise, just use the current usb_request to queue a 0 + * length request to the ep. Since we always add to the req_free + * list if we dequeue from the ready list, there will never + * be a situation where the req_free list is completely out of + * requests and cannot recover. */ - list_add_tail(&to_queue->list, &video->req_free); + if (!list_empty(&video->req_ready)) { + req = list_first_entry(&video->req_ready, + struct usb_request, list); + } else { + if (list_empty(&video->req_free) || + (atomic_read(&video->queued) > UVCG_REQ_MAX_ZERO_COUNT)) { + spin_unlock_irqrestore(&video->req_lock, flags); + + return; + } + req = list_first_entry(&video->req_free, struct usb_request, + list); + req->length = 0; + } + list_del(&req->list); + /* - * There is a new free request - wake up the pump. + * Queue to the endpoint. The actual queueing to ep will + * only happen on one thread - the async_wq for bulk endpoints + * and this thread for isoc endpoints. */ - queue_work(video->async_wq, &video->pump); - } + ret = uvcg_video_usb_req_queue(video, req, !is_bulk); + if (ret < 0) { + /* + * Endpoint error, but the stream is still enabled. + * Put request back in req_free for it to be cleaned + * up later. + */ + list_add_tail(&req->list, &video->req_free); + /* + * There is a new free request - wake up the pump. + */ + queue_work(video->async_wq, &video->pump); - spin_unlock_irqrestore(&video->req_lock, flags); + } + + spin_unlock_irqrestore(&video->req_lock, flags); + } } static int @@ -771,7 +744,7 @@ int uvcg_video_enable(struct uvc_video *video) atomic_set(&video->queued, 0); - uvc_video_ep_queue_initial_requests(video); + kthread_queue_work(video->kworker, &video->hw_submit); queue_work(video->async_wq, &video->pump); return ret; @@ -794,6 +767,17 @@ int uvcg_video_init(struct uvc_video *video, struct uvc_device *uvc) if (!video->async_wq) return -EINVAL; + /* Allocate a kthread for asynchronous hw submit handler. */ + video->kworker = kthread_create_worker(0, "UVCG"); + if (IS_ERR(video->kworker)) { + uvcg_err(&video->uvc->func, "failed to create UVCG kworker\n"); + return PTR_ERR(video->kworker); + } + + kthread_init_work(&video->hw_submit, uvcg_video_hw_submit); + + sched_set_fifo(video->kworker->task); + video->uvc = uvc; video->fcc = V4L2_PIX_FMT_YUYV; video->bpp = 16; From patchwork Sun Sep 29 18:59:24 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Michael Grzeschik X-Patchwork-Id: 13815209 Received: from metis.whiteo.stw.pengutronix.de (metis.whiteo.stw.pengutronix.de [185.203.201.7]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 9D60461FEB for ; Sun, 29 Sep 2024 18:59:37 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=185.203.201.7 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1727636381; cv=none; b=YdHVlzI9Ag+PiWy4JEP3C/4k+p6nGpnU6GBFG2S/nVGG5jXkv6/kSpKmcaA6FiITNk5dLQAwC3sL9Gh+2q0LN0WhFBRcng9YoASmG4wlUIItjnx+CWo5BRfPnVkPV/qaLfXyNjPuD/I91wtDZnRSjIIb60cONbpD4L7YuhOj7k0= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1727636381; c=relaxed/simple; bh=/7WmY7rllTF+fLfM/l5bZ3Bth2MGsfy7tmnu6bPQpww=; h=From:Date:Subject:MIME-Version:Content-Type:Message-Id:References: In-Reply-To:To:Cc; b=fZR1XkerRH3edVsZN8UfOYgiWQeRAHUMoDMy6IsIVYOnYxiL0qXbwLz+2DVYuKy9yvpXhu/NwGFm0JblUG0dzDEgibfBizrqWNtYxrrXKc8bohzicsrMuosONRqVi+nGye8iqOnDzFj4H01SevD9pHAXcz5hihKwDU2/57jCWHI= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=pengutronix.de; spf=pass smtp.mailfrom=pengutronix.de; arc=none smtp.client-ip=185.203.201.7 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=pengutronix.de Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=pengutronix.de Received: from drehscheibe.grey.stw.pengutronix.de ([2a0a:edc0:0:c01:1d::a2]) by metis.whiteo.stw.pengutronix.de with esmtps (TLS1.3:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1suz8l-00053s-KL; Sun, 29 Sep 2024 20:59:31 +0200 Received: from [2a0a:edc0:0:1101:1d::ac] (helo=dude04.red.stw.pengutronix.de) by drehscheibe.grey.stw.pengutronix.de with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.94.2) (envelope-from ) id 1suz8l-002Ro6-0y; Sun, 29 Sep 2024 20:59:31 +0200 Received: from localhost ([::1] helo=dude04.red.stw.pengutronix.de) by dude04.red.stw.pengutronix.de with esmtp (Exim 4.96) (envelope-from ) id 1suz8k-0029Vj-2y; Sun, 29 Sep 2024 20:59:30 +0200 From: Michael Grzeschik Date: Sun, 29 Sep 2024 20:59:24 +0200 Subject: [PATCH v6 4/9] usb: gadget: uvc: add g_parm and s_parm for frame interval Precedence: bulk X-Mailing-List: linux-usb@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Message-Id: <20240403-uvc_request_length_by_interval-v6-4-08c05522e1f5@pengutronix.de> References: <20240403-uvc_request_length_by_interval-v6-0-08c05522e1f5@pengutronix.de> In-Reply-To: <20240403-uvc_request_length_by_interval-v6-0-08c05522e1f5@pengutronix.de> To: Laurent Pinchart , Daniel Scally , Greg Kroah-Hartman , Avichal Rakesh , Jayant Chowdhary Cc: linux-usb@vger.kernel.org, linux-kernel@vger.kernel.org, kernel@pengutronix.de, Michael Grzeschik X-Mailer: b4 0.12.0 X-Developer-Signature: v=1; a=openpgp-sha256; l=4059; i=m.grzeschik@pengutronix.de; h=from:subject:message-id; bh=/7WmY7rllTF+fLfM/l5bZ3Bth2MGsfy7tmnu6bPQpww=; b=owEBbQKS/ZANAwAKAb9pWET5cfSrAcsmYgBm+aOQ0YuuM54qT/7GoCqU62i2l7GqjRSEy5mV8 CIS9kM1NQKJAjMEAAEKAB0WIQQV2+2Fpbqd6fvv0Gi/aVhE+XH0qwUCZvmjkAAKCRC/aVhE+XH0 qxWBD/wKvxyL2nCjQn/DtyGih2OGvFlg99bC9Y8Y8hS3H8erS1A8ujBiH3eRaN/d5wh1w+TEDKs o5jSi3vd8bAo1inK+faeJxSK3eKGZq/QATei1GDtB9hiImpSBr9VvpOAGUS9yptZ2UN8zKD9fmu MilDhr2NK32no/dSbHIRqvki3Ya2+l0oghM7Y1qA4oK/eTuhL7CoMYZThA0io2tHdD1oj01M0jO +HPh+e0SBI30+KKQQoo7SU5QpL9XzrzLI8C7GAPz91rsc56zi8+ih9G7Ck1expVHh0CrwZ8HhFx 3vRBagSWt6zRZDADJkGwmTR1E+6nRp7Q0FZfVXO+cs4FYpfqHNZc5qAdfvXUkKWBSGk4S6cz4ko lpCMGQjdh69ZTerRQGmCIfh7wICLvcyrU5wQDHmkihl1SiquptG4OTVDxvohXw8nzl/CtbCbjcR LTo8K/JXVRRYFKksagQT8YNAO9slDw0wWGQZDai4dpp5mHKpVfnU+Ec9g/JLP7MGe3lcIFxy44v 5XiqPVp4OqKBiS+4/OBqB5f40BbIMcKKvk3CHrA2l/WG/VqDb2n50nA06MlQEs3mpS7Ekp2vvWn vgH3Wl34WKyZV5qId3uQClzJyNtb/2ve/x+S3AgejI2UmzoZ8Q8KukxUV9rJRHEH3IV1NS4TaMo L8tnH5YsRlw3WjA== X-Developer-Key: i=m.grzeschik@pengutronix.de; a=openpgp; fpr=957BC452CE953D7EA60CF4FC0BE9E3157A1E2C64 X-SA-Exim-Connect-IP: 2a0a:edc0:0:c01:1d::a2 X-SA-Exim-Mail-From: m.grzeschik@pengutronix.de X-SA-Exim-Scanned: No (on metis.whiteo.stw.pengutronix.de); SAEximRunCond expanded to false X-PTX-Original-Recipient: linux-usb@vger.kernel.org The uvc gadget driver is lacking the information which frame interval was set by the host. We add this information by implementing the g_parm and s_parm callbacks. Signed-off-by: Michael Grzeschik --- v5 -> v6: - v4 -> v5: - using !V4L2_TYPE_IS_OUTPUT to check for type - initialzing interval to same default as in configfs - reordered this patch in the series v1 -> v4: - --- drivers/usb/gadget/function/uvc.h | 1 + drivers/usb/gadget/function/uvc_v4l2.c | 52 +++++++++++++++++++++++++++++++++ drivers/usb/gadget/function/uvc_video.c | 1 + 3 files changed, 54 insertions(+) diff --git a/drivers/usb/gadget/function/uvc.h b/drivers/usb/gadget/function/uvc.h index 4f44a607d9f5c..099038f1088ef 100644 --- a/drivers/usb/gadget/function/uvc.h +++ b/drivers/usb/gadget/function/uvc.h @@ -105,6 +105,7 @@ struct uvc_video { unsigned int width; unsigned int height; unsigned int imagesize; + unsigned int interval; struct mutex mutex; /* protects frame parameters */ unsigned int uvc_num_requests; diff --git a/drivers/usb/gadget/function/uvc_v4l2.c b/drivers/usb/gadget/function/uvc_v4l2.c index de1736f834e6b..ab89f1630acb0 100644 --- a/drivers/usb/gadget/function/uvc_v4l2.c +++ b/drivers/usb/gadget/function/uvc_v4l2.c @@ -314,6 +314,56 @@ uvc_v4l2_set_format(struct file *file, void *fh, struct v4l2_format *fmt) return ret; } +static int uvc_v4l2_g_parm(struct file *file, void *fh, + struct v4l2_streamparm *parm) +{ + struct video_device *vdev = video_devdata(file); + struct uvc_device *uvc = video_get_drvdata(vdev); + struct uvc_video *video = &uvc->video; + struct v4l2_fract timeperframe; + + if (!V4L2_TYPE_IS_OUTPUT(parm->type)) + return -EINVAL; + + /* Return the actual frame period. */ + timeperframe.numerator = video->interval; + timeperframe.denominator = 10000000; + v4l2_simplify_fraction(&timeperframe.numerator, + &timeperframe.denominator, 8, 333); + + uvcg_dbg(&uvc->func, "Getting frame interval of %u/%u (%u)\n", + timeperframe.numerator, timeperframe.denominator, + video->interval); + + parm->parm.output.timeperframe = timeperframe; + parm->parm.output.capability = V4L2_CAP_TIMEPERFRAME; + + return 0; +} + +static int uvc_v4l2_s_parm(struct file *file, void *fh, + struct v4l2_streamparm *parm) +{ + struct video_device *vdev = video_devdata(file); + struct uvc_device *uvc = video_get_drvdata(vdev); + struct uvc_video *video = &uvc->video; + struct v4l2_fract timeperframe; + + if (!V4L2_TYPE_IS_OUTPUT(parm->type)) + return -EINVAL; + + timeperframe = parm->parm.output.timeperframe; + + video->interval = v4l2_fraction_to_interval(timeperframe.numerator, + timeperframe.denominator); + + uvcg_dbg(&uvc->func, "Setting frame interval to %u/%u (%u)\n", + timeperframe.numerator, timeperframe.denominator, + video->interval); + + return 0; +} + static int uvc_v4l2_enum_frameintervals(struct file *file, void *fh, struct v4l2_frmivalenum *fival) @@ -587,6 +637,8 @@ const struct v4l2_ioctl_ops uvc_v4l2_ioctl_ops = { .vidioc_dqbuf = uvc_v4l2_dqbuf, .vidioc_streamon = uvc_v4l2_streamon, .vidioc_streamoff = uvc_v4l2_streamoff, + .vidioc_s_parm = uvc_v4l2_s_parm, + .vidioc_g_parm = uvc_v4l2_g_parm, .vidioc_subscribe_event = uvc_v4l2_subscribe_event, .vidioc_unsubscribe_event = uvc_v4l2_unsubscribe_event, .vidioc_default = uvc_v4l2_ioctl_default, diff --git a/drivers/usb/gadget/function/uvc_video.c b/drivers/usb/gadget/function/uvc_video.c index f43bf19218963..19ba18d5a42fb 100644 --- a/drivers/usb/gadget/function/uvc_video.c +++ b/drivers/usb/gadget/function/uvc_video.c @@ -784,6 +784,7 @@ int uvcg_video_init(struct uvc_video *video, struct uvc_device *uvc) video->width = 320; video->height = 240; video->imagesize = 320 * 240 * 2; + video->interval = 666666; /* Initialize the video buffers queue. */ uvcg_queue_init(&video->queue, uvc->v4l2_dev.dev->parent, From patchwork Sun Sep 29 18:59:25 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Michael Grzeschik X-Patchwork-Id: 13815207 Received: from metis.whiteo.stw.pengutronix.de (metis.whiteo.stw.pengutronix.de [185.203.201.7]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id AACF66F2F3 for ; Sun, 29 Sep 2024 18:59:37 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=185.203.201.7 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1727636380; cv=none; b=IcJesELqzhtrp4EBVnnF58Z2FgwMU4IiGcqHQl8PGyHA83xTMk8BVylLDsxQaWPvWPFJHyK8zT+Q5ME60b+RK3tTXMa592p/agXSI9Fh6LtXQg9IVw2Xg6oKCfBp2cECXsTdWXPgG5Mn3WDLQE35c3M2L39sYLcbVe726OOqa1g= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1727636380; c=relaxed/simple; bh=mVJsLF96hgwIhL473HnofDEXV5Pvx+Cp45sp9GS9zGQ=; h=From:Date:Subject:MIME-Version:Content-Type:Message-Id:References: In-Reply-To:To:Cc; b=QoYsr0fxU+tmkpB0gS6Mtvtxv601iER+8SdaW84cg7XmSIQRbZ/sqhgQjmrLOJJe5aJSbyDxol9IollFuMR5opIS5Y5kl9NAbCc4vae92/OQvfXc+kvAZYXJPXB2Dm9QV8bcxQRVtQ3EvSIU5oTORf9gCS86oRk7mf+sPFCG4WA= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=pengutronix.de; spf=pass smtp.mailfrom=pengutronix.de; arc=none smtp.client-ip=185.203.201.7 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=pengutronix.de Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=pengutronix.de Received: from drehscheibe.grey.stw.pengutronix.de ([2a0a:edc0:0:c01:1d::a2]) by metis.whiteo.stw.pengutronix.de with esmtps (TLS1.3:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1suz8l-00053p-KM; Sun, 29 Sep 2024 20:59:31 +0200 Received: from [2a0a:edc0:0:1101:1d::ac] (helo=dude04.red.stw.pengutronix.de) by drehscheibe.grey.stw.pengutronix.de with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.94.2) (envelope-from ) id 1suz8l-002Ro7-0K; Sun, 29 Sep 2024 20:59:31 +0200 Received: from localhost ([::1] helo=dude04.red.stw.pengutronix.de) by dude04.red.stw.pengutronix.de with esmtp (Exim 4.96) (envelope-from ) id 1suz8k-0029Vj-2z; Sun, 29 Sep 2024 20:59:30 +0200 From: Michael Grzeschik Date: Sun, 29 Sep 2024 20:59:25 +0200 Subject: [PATCH v6 5/9] usb: gadget: uvc: set req_size and n_requests based on the frame interval Precedence: bulk X-Mailing-List: linux-usb@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Message-Id: <20240403-uvc_request_length_by_interval-v6-5-08c05522e1f5@pengutronix.de> References: <20240403-uvc_request_length_by_interval-v6-0-08c05522e1f5@pengutronix.de> In-Reply-To: <20240403-uvc_request_length_by_interval-v6-0-08c05522e1f5@pengutronix.de> To: Laurent Pinchart , Daniel Scally , Greg Kroah-Hartman , Avichal Rakesh , Jayant Chowdhary Cc: linux-usb@vger.kernel.org, linux-kernel@vger.kernel.org, kernel@pengutronix.de, Michael Grzeschik X-Mailer: b4 0.12.0 X-Developer-Signature: v=1; a=openpgp-sha256; l=6421; i=m.grzeschik@pengutronix.de; h=from:subject:message-id; bh=mVJsLF96hgwIhL473HnofDEXV5Pvx+Cp45sp9GS9zGQ=; b=owEBbQKS/ZANAwAKAb9pWET5cfSrAcsmYgBm+aOR05D4BBzL3kk5rYGUbYxAbICA0AeSn0Rq2 GyRW9MaaiOJAjMEAAEKAB0WIQQV2+2Fpbqd6fvv0Gi/aVhE+XH0qwUCZvmjkQAKCRC/aVhE+XH0 q9D9D/9HWvl82tQ+CxPTXgnF12zbQFy18jJNHQvkF2XbzWKIl/TF0F53/ZvLHg2iVuwdhqJyDuZ HdcovxAIbkVA42jM6NVlVr9z2zxBx8IgNjhqdxFR1Wx4Drnru8JP8FAKBGccY8xI7JXhJn6tJif 9Cgry0qE+aTOc4CCiCIkgWAjktW7x58AwRYUyVweZQBrWpcV34pc+8vupsg/V+7F2Uh6iaXHd/e jLhThIn/xaTEyr1LAQl/HRTek89nRuqUVes9mepmLs/Te99oxy1t3p1Yu6JGINFmdkQqhPEIO7A E1nASALkTqSIWxuuQAumsGKrcuaJe4aqxTzrbGd6qBJCjK/hhR7Q1AD0uyJKwO7Gype4WGouaqz a8+lbkqOnTOvQIchrIxhlicSjgIKgZdPnXcEemFLIgu7f7VVQ/HYTEkRleS/FoVOBkoHBlgObzu t0tEhswUVOR6ag2c1lnVIaYfFtTZhFaybJ7CjKfoJyVtRliK8ROsjrimX70vjCABIkW3pw5cDKx EO9WKsIJ4DTId2eyrhK7t3iQJ6ZsB8o1G15tBgZFhHiVyi8BtFq9fI+U+e84InBlwvE76VGsPwn M45W6EsQ1l4mzEzhkPkEKDE0/3/EY0p9NxATm6eSmGiT6mp+OyJifLoUZxSST28QS/KCJ/m/mEr W/tdaO1RHB+vNww== X-Developer-Key: i=m.grzeschik@pengutronix.de; a=openpgp; fpr=957BC452CE953D7EA60CF4FC0BE9E3157A1E2C64 X-SA-Exim-Connect-IP: 2a0a:edc0:0:c01:1d::a2 X-SA-Exim-Mail-From: m.grzeschik@pengutronix.de X-SA-Exim-Scanned: No (on metis.whiteo.stw.pengutronix.de); SAEximRunCond expanded to false X-PTX-Original-Recipient: linux-usb@vger.kernel.org This patch is removing the initial imprecise and limited calculation of requests needed to be used from the queue_setup callback. It instead introduces the uvc_video_prep_requests function which is called immediately before the request allocation. With the information of the usb frame interval length it is possible to calculate the number of requests needed during one frame duration. Based on the calculated number of requests and the imagesize we calculate the actual size per request. This calculation has the benefit that the frame data is equally distributed over all allocated requests. When the req_size is not in the range for the actually configured max_req_size configured for the overall bandwidth we fallback to use the max_req_size instead. Since this calculations are only important for isoc transfers we just use max_request_size for bulk and skip it. As video->req_size will be recalculated on every video_enable resetting it to 0 is not necessary anymore. Signed-off-by: Michael Grzeschik --- v5 -> v6: - v4 -> v5: - reordered this patch in the series - merging previous extra patch: ('usb: gadget: uvc: set req_size once when the vb2 queue is calculated') - moved the overall request size calculation to one seperate function - only calculating once before enabling the video ep v3 -> v4: - v2 -> v3: - added the frame duration for full-speed devices into calculation v1 -> v2: - add headersize per request into calculation --- drivers/usb/gadget/function/uvc_queue.c | 13 ------- drivers/usb/gadget/function/uvc_video.c | 68 +++++++++++++++++++++++++++------ 2 files changed, 56 insertions(+), 25 deletions(-) diff --git a/drivers/usb/gadget/function/uvc_queue.c b/drivers/usb/gadget/function/uvc_queue.c index 0aa3d7e1f3cc3..731e3b9d21acc 100644 --- a/drivers/usb/gadget/function/uvc_queue.c +++ b/drivers/usb/gadget/function/uvc_queue.c @@ -44,8 +44,6 @@ static int uvc_queue_setup(struct vb2_queue *vq, { struct uvc_video_queue *queue = vb2_get_drv_priv(vq); struct uvc_video *video = container_of(queue, struct uvc_video, queue); - unsigned int req_size; - unsigned int nreq; if (*nbuffers > UVC_MAX_VIDEO_BUFFERS) *nbuffers = UVC_MAX_VIDEO_BUFFERS; @@ -54,17 +52,6 @@ static int uvc_queue_setup(struct vb2_queue *vq, sizes[0] = video->imagesize; - req_size = video->ep->maxpacket - * max_t(unsigned int, video->ep->maxburst, 1) - * (video->ep->mult); - - /* We divide by two, to increase the chance to run - * into fewer requests for smaller framesizes. - */ - nreq = DIV_ROUND_UP(DIV_ROUND_UP(sizes[0], 2), req_size); - nreq = clamp(nreq, 4U, 64U); - video->uvc_num_requests = nreq; - return 0; } diff --git a/drivers/usb/gadget/function/uvc_video.c b/drivers/usb/gadget/function/uvc_video.c index 19ba18d5a42fb..4efd7585d7541 100644 --- a/drivers/usb/gadget/function/uvc_video.c +++ b/drivers/usb/gadget/function/uvc_video.c @@ -486,23 +486,70 @@ uvc_video_free_requests(struct uvc_video *video) INIT_LIST_HEAD(&video->ureqs); INIT_LIST_HEAD(&video->req_free); INIT_LIST_HEAD(&video->req_ready); - video->req_size = 0; return 0; } +static void +uvc_video_prep_requests(struct uvc_video *video) +{ + struct uvc_device *uvc = container_of(video, struct uvc_device, video); + struct usb_composite_dev *cdev = uvc->func.config->cdev; + unsigned int interval_duration = video->ep->desc->bInterval * 1250; + unsigned int max_req_size, req_size, header_size; + unsigned int nreq; + + max_req_size = video->ep->maxpacket + * max_t(unsigned int, video->ep->maxburst, 1) + * (video->ep->mult); + + if (!usb_endpoint_xfer_isoc(video->ep->desc)) { + video->req_size = max_req_size; + video->uvc_num_requests = + DIV_ROUND_UP(video->imagesize, max_req_size); + + return; + } + + if (cdev->gadget->speed < USB_SPEED_HIGH) + interval_duration = video->ep->desc->bInterval * 10000; + + nreq = DIV_ROUND_UP(video->interval, interval_duration); + + header_size = nreq * UVCG_REQUEST_HEADER_LEN; + + req_size = DIV_ROUND_UP(video->imagesize + header_size, nreq); + + if (req_size > max_req_size) { + /* The prepared interval length and expected buffer size + * is not possible to stream with the currently configured + * isoc bandwidth. Fallback to the maximum. + */ + req_size = max_req_size; + } + video->req_size = req_size; + + /* We need to compensate the amount of requests to be + * allocated with the maximum amount of zero length requests. + * Since it is possible that hw_submit will initially + * enqueue some zero length requests and we then will not be + * able to fully encode one frame. + */ + video->uvc_num_requests = nreq + UVCG_REQ_MAX_ZERO_COUNT; +} + static int uvc_video_alloc_requests(struct uvc_video *video) { struct uvc_request *ureq; - unsigned int req_size; unsigned int i; int ret = -ENOMEM; - BUG_ON(video->req_size); - - req_size = video->ep->maxpacket - * max_t(unsigned int, video->ep->maxburst, 1) - * (video->ep->mult); + /* + * calculate in uvc_video_prep_requests + * - video->uvc_num_requests + * - video->req_size + */ + uvc_video_prep_requests(video); for (i = 0; i < video->uvc_num_requests; i++) { ureq = kzalloc(sizeof(struct uvc_request), GFP_KERNEL); @@ -513,7 +560,7 @@ uvc_video_alloc_requests(struct uvc_video *video) list_add_tail(&ureq->list, &video->ureqs); - ureq->req_buffer = kmalloc(req_size, GFP_KERNEL); + ureq->req_buffer = kmalloc(video->req_size, GFP_KERNEL); if (ureq->req_buffer == NULL) goto error; @@ -531,12 +578,10 @@ uvc_video_alloc_requests(struct uvc_video *video) list_add_tail(&ureq->req->list, &video->req_free); /* req_size/PAGE_SIZE + 1 for overruns and + 1 for header */ sg_alloc_table(&ureq->sgt, - DIV_ROUND_UP(req_size - UVCG_REQUEST_HEADER_LEN, + DIV_ROUND_UP(video->req_size - UVCG_REQUEST_HEADER_LEN, PAGE_SIZE) + 2, GFP_KERNEL); } - video->req_size = req_size; - return 0; error: @@ -689,7 +734,6 @@ uvcg_video_disable(struct uvc_video *video) INIT_LIST_HEAD(&video->ureqs); INIT_LIST_HEAD(&video->req_free); INIT_LIST_HEAD(&video->req_ready); - video->req_size = 0; spin_unlock_irqrestore(&video->req_lock, flags); /* From patchwork Sun Sep 29 18:59:26 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Michael Grzeschik X-Patchwork-Id: 13815212 Received: from metis.whiteo.stw.pengutronix.de (metis.whiteo.stw.pengutronix.de [185.203.201.7]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id B16B57346F for ; Sun, 29 Sep 2024 18:59:37 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=185.203.201.7 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1727636382; cv=none; b=f2COSyGOMQsGt0eSxEPh4Ya0sWT0SyAYOgi4Ua1KNVjamwrWpvOVCOnAfh3dWVJwnrByw5Hxml0g6WGXu2+UVA+MvSI1a+Bo2NfVKSXbIktmEq25lynD3bXnlLVXxm/0tqf+kOUVkmmyz6HeBgyPsXSp9feBxYxHCLgyVFFx3/0= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1727636382; c=relaxed/simple; bh=Hk7tbELgzh9caEJKk1jfev7yNN44yhrC8FT6TaKYFeM=; h=From:Date:Subject:MIME-Version:Content-Type:Message-Id:References: In-Reply-To:To:Cc; b=lvkqMkKeKGRRYy9ek972zzSXnvwYIBQqAYjkm1PU7rMedinm0Od6HXDqPUdZSrWc/pm56v7zb6K7pbuZIN0fhCeLS1RuQRzqAn2Ne1rSVfEwPHhfC/ttb25A/DP2wb2IDJNhm3IlZFsnXfz5owIkA0OlSOAXDXurrMHyPUhuU+Y= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=pengutronix.de; spf=pass smtp.mailfrom=pengutronix.de; arc=none smtp.client-ip=185.203.201.7 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=pengutronix.de Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=pengutronix.de Received: from drehscheibe.grey.stw.pengutronix.de ([2a0a:edc0:0:c01:1d::a2]) by metis.whiteo.stw.pengutronix.de with esmtps (TLS1.3:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1suz8l-00053v-KL; Sun, 29 Sep 2024 20:59:31 +0200 Received: from [2a0a:edc0:0:1101:1d::ac] (helo=dude04.red.stw.pengutronix.de) by drehscheibe.grey.stw.pengutronix.de with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.94.2) (envelope-from ) id 1suz8l-002Ro8-1m; Sun, 29 Sep 2024 20:59:31 +0200 Received: from localhost ([::1] helo=dude04.red.stw.pengutronix.de) by dude04.red.stw.pengutronix.de with esmtp (Exim 4.96) (envelope-from ) id 1suz8k-0029Vj-30; Sun, 29 Sep 2024 20:59:30 +0200 From: Michael Grzeschik Date: Sun, 29 Sep 2024 20:59:26 +0200 Subject: [PATCH v6 6/9] usb: gadget: uvc: set req_length based on payload by nreqs instead of req_size Precedence: bulk X-Mailing-List: linux-usb@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Message-Id: <20240403-uvc_request_length_by_interval-v6-6-08c05522e1f5@pengutronix.de> References: <20240403-uvc_request_length_by_interval-v6-0-08c05522e1f5@pengutronix.de> In-Reply-To: <20240403-uvc_request_length_by_interval-v6-0-08c05522e1f5@pengutronix.de> To: Laurent Pinchart , Daniel Scally , Greg Kroah-Hartman , Avichal Rakesh , Jayant Chowdhary Cc: linux-usb@vger.kernel.org, linux-kernel@vger.kernel.org, kernel@pengutronix.de, Michael Grzeschik X-Mailer: b4 0.12.0 X-Developer-Signature: v=1; a=openpgp-sha256; l=5699; i=m.grzeschik@pengutronix.de; h=from:subject:message-id; bh=Hk7tbELgzh9caEJKk1jfev7yNN44yhrC8FT6TaKYFeM=; b=owEBbQKS/ZANAwAKAb9pWET5cfSrAcsmYgBm+aORAkNKtcBauirFrPlVipbScaYLRKdKm78F1 9Lk/vP9PpqJAjMEAAEKAB0WIQQV2+2Fpbqd6fvv0Gi/aVhE+XH0qwUCZvmjkQAKCRC/aVhE+XH0 q13BEACgLwGxeIHzggCVcaJyQjOC7hKf+24RxmNZpdNCMLNIHgLC5NRKbLG4H2pwTjUDx8nnsLT tyi+E8awD9Ma+XZn7wbDpGn/Nmuimo476VJjycM38u/0UMOwCGxtQvMAgOygGSp9rHIrCaH6h0M WAaFFNS22dUjqfZ9tRxCjd6xtlAAgAJFcTxXCOxm4b4aQUlvmHS+MDAlt3NqqOfdIgJVCfsDx1H v4ZGOosmFIOdm0FbyWk+AFWUg3BlfaHitkApnLPR9mMyJowTs9wOE/OXYUUf7V6VDOah449cs/W pFO0BjipqsFGV+kInWsLd/2dkflIc+Ln+un5P2UBk6YPLh66r+i7QARhdhb0Us/rLJ6b6lqX/xa t8VToIryuSaOxwQfFA9h1IsG+c3JcKAwNHQtlwSW+XWfdG48X5IIdkmnQB4KrMshg/XOildWpCU 9rT/OBxmnQxbtKNoU7XmcjPAOj1//ZKRKsN5h/PL+FZ1GVxwVgB6BGzSKFS3j+Lyg6C9+kbBnaa fGQ7zoGYpHIIiKjBRSMqzbiCbA4OElandGTRQk/JNqduTxpapdTUTnL4LWlzOQUaMmCLb5RF/zb lkvfi6erAiA9bVAsiQeB/9NqQR6FtaEa+hsgz8gblHykTD6uoHg/psFBCBjnswtUTT2gOqfKgCZ cpJA7nq/cmiGRTw== X-Developer-Key: i=m.grzeschik@pengutronix.de; a=openpgp; fpr=957BC452CE953D7EA60CF4FC0BE9E3157A1E2C64 X-SA-Exim-Connect-IP: 2a0a:edc0:0:c01:1d::a2 X-SA-Exim-Mail-From: m.grzeschik@pengutronix.de X-SA-Exim-Scanned: No (on metis.whiteo.stw.pengutronix.de); SAEximRunCond expanded to false X-PTX-Original-Recipient: linux-usb@vger.kernel.org Compressed formats generate content depending amount of data that is set in the vb2 buffer by the payload_size. When streaming those formats it is better to scatter that smaller data over all requests. This patch is doing that by introducing the calculated req_payload_size which is updated by each frame. It the uses this amount of data to fill the isoc requests instead of the video->req_size. For uncompressed formats it will not make a difference since the payload size will be equal to the imagesize. Therefore the code will have no effecta as req_payload_size will be equal to req_size. Signed-off-by: Michael Grzeschik --- v5 -> v6: - v4 -> v5: - keep using req_size instead of len in encode_isoc_sg to be more explicit - using new initialized variable reqs_per_frame instead of two calculations - reordered this patch in the series v1 -> v4: - --- drivers/usb/gadget/function/uvc.h | 2 ++ drivers/usb/gadget/function/uvc_queue.c | 10 ++++++++-- drivers/usb/gadget/function/uvc_queue.h | 2 ++ drivers/usb/gadget/function/uvc_video.c | 15 ++++++++------- 4 files changed, 20 insertions(+), 9 deletions(-) diff --git a/drivers/usb/gadget/function/uvc.h b/drivers/usb/gadget/function/uvc.h index 099038f1088ef..bedb4ef42864f 100644 --- a/drivers/usb/gadget/function/uvc.h +++ b/drivers/usb/gadget/function/uvc.h @@ -110,6 +110,8 @@ struct uvc_video { unsigned int uvc_num_requests; + unsigned int reqs_per_frame; + /* Requests */ bool is_enabled; /* tracks whether video stream is enabled */ unsigned int req_size; diff --git a/drivers/usb/gadget/function/uvc_queue.c b/drivers/usb/gadget/function/uvc_queue.c index 731e3b9d21acc..6757a4e25a743 100644 --- a/drivers/usb/gadget/function/uvc_queue.c +++ b/drivers/usb/gadget/function/uvc_queue.c @@ -58,6 +58,7 @@ static int uvc_queue_setup(struct vb2_queue *vq, static int uvc_buffer_prepare(struct vb2_buffer *vb) { struct uvc_video_queue *queue = vb2_get_drv_priv(vb->vb2_queue); + struct uvc_video *video = container_of(queue, struct uvc_video, queue); struct vb2_v4l2_buffer *vbuf = to_vb2_v4l2_buffer(vb); struct uvc_buffer *buf = container_of(vbuf, struct uvc_buffer, buf); @@ -78,10 +79,15 @@ static int uvc_buffer_prepare(struct vb2_buffer *vb) buf->mem = vb2_plane_vaddr(vb, 0); } buf->length = vb2_plane_size(vb, 0); - if (vb->type == V4L2_BUF_TYPE_VIDEO_CAPTURE) + if (vb->type == V4L2_BUF_TYPE_VIDEO_CAPTURE) { buf->bytesused = 0; - else + } else { buf->bytesused = vb2_get_plane_payload(vb, 0); + buf->req_payload_size = + DIV_ROUND_UP(buf->bytesused + + (video->reqs_per_frame * UVCG_REQUEST_HEADER_LEN), + video->reqs_per_frame); + } return 0; } diff --git a/drivers/usb/gadget/function/uvc_queue.h b/drivers/usb/gadget/function/uvc_queue.h index 41f87b917f6bc..b54becc570a38 100644 --- a/drivers/usb/gadget/function/uvc_queue.h +++ b/drivers/usb/gadget/function/uvc_queue.h @@ -39,6 +39,8 @@ struct uvc_buffer { unsigned int offset; unsigned int length; unsigned int bytesused; + /* req_payload_size: only used with isoc */ + unsigned int req_payload_size; }; #define UVC_QUEUE_DISCONNECTED (1 << 0) diff --git a/drivers/usb/gadget/function/uvc_video.c b/drivers/usb/gadget/function/uvc_video.c index 4efd7585d7541..0287a56fa50ad 100644 --- a/drivers/usb/gadget/function/uvc_video.c +++ b/drivers/usb/gadget/function/uvc_video.c @@ -136,7 +136,7 @@ uvc_video_encode_isoc_sg(struct usb_request *req, struct uvc_video *video, unsigned int pending = buf->bytesused - video->queue.buf_used; struct uvc_request *ureq = req->context; struct scatterlist *sg, *iter; - unsigned int len = video->req_size; + unsigned int len = buf->req_payload_size; unsigned int sg_left, part = 0; unsigned int i; int header_len; @@ -146,15 +146,15 @@ uvc_video_encode_isoc_sg(struct usb_request *req, struct uvc_video *video, /* Init the header. */ header_len = uvc_video_encode_header(video, buf, ureq->header, - video->req_size); + buf->req_payload_size); sg_set_buf(sg, ureq->header, header_len); len -= header_len; if (pending <= len) len = pending; - req->length = (len == pending) ? - len + header_len : video->req_size; + req->length = (len == pending) ? len + header_len : + buf->req_payload_size; /* Init the pending sgs with payload */ sg = sg_next(sg); @@ -202,7 +202,7 @@ uvc_video_encode_isoc(struct usb_request *req, struct uvc_video *video, { void *mem = req->buf; struct uvc_request *ureq = req->context; - int len = video->req_size; + int len = buf->req_payload_size; int ret; /* Add the header. */ @@ -214,7 +214,7 @@ uvc_video_encode_isoc(struct usb_request *req, struct uvc_video *video, ret = uvc_video_encode_data(video, buf, mem, len); len -= ret; - req->length = video->req_size - len; + req->length = buf->req_payload_size - len; if (buf->bytesused == video->queue.buf_used || video->queue.flags & UVC_QUEUE_DROP_INCOMPLETE) { @@ -504,7 +504,7 @@ uvc_video_prep_requests(struct uvc_video *video) if (!usb_endpoint_xfer_isoc(video->ep->desc)) { video->req_size = max_req_size; - video->uvc_num_requests = + video->reqs_per_frame = video->uvc_num_requests = DIV_ROUND_UP(video->imagesize, max_req_size); return; @@ -535,6 +535,7 @@ uvc_video_prep_requests(struct uvc_video *video) * able to fully encode one frame. */ video->uvc_num_requests = nreq + UVCG_REQ_MAX_ZERO_COUNT; + video->reqs_per_frame = nreq; } static int From patchwork Sun Sep 29 18:59:27 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Michael Grzeschik X-Patchwork-Id: 13815211 Received: from metis.whiteo.stw.pengutronix.de (metis.whiteo.stw.pengutronix.de [185.203.201.7]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id A42DE6E2AE for ; Sun, 29 Sep 2024 18:59:37 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=185.203.201.7 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1727636382; cv=none; b=cNvp00Nnn5VRXQKk3PSMDHR9Vt48JtG1Z8tOmqC7bglIU6/xWGUAYEr7qTc4qt+dNpfDJUF7hgaBpjh+HWtCVftVdAg4E3vhs2agukD5hhE2VBm4C3sUS+qygse6lnDCRTEyFqNbi0l1gOv/pIykEeDf8CfcMKSR9xCCPr5cYpg= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1727636382; c=relaxed/simple; bh=vDOpCLv2CodGLKEpn/CIA0Ki8MmgeH3jN/oYwO6TfJ4=; h=From:Date:Subject:MIME-Version:Content-Type:Message-Id:References: In-Reply-To:To:Cc; b=mNOTE6BZemernjO+qZdaX5/HLJ+xNseDPC1EHWw3UlwNq4U2pH9Ganavxz4vzVKT+U/0pZp6DuJU+oTgk/La7E0rnAo58WanjVwNvR1v8ccOnQYyzM7h3YOZxkroXm1Ae03D4JaLotrwABxVO6k8w7pO332jzoDRlCdQds3zIkU= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=pengutronix.de; spf=pass smtp.mailfrom=pengutronix.de; arc=none smtp.client-ip=185.203.201.7 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=pengutronix.de Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=pengutronix.de Received: from drehscheibe.grey.stw.pengutronix.de ([2a0a:edc0:0:c01:1d::a2]) by metis.whiteo.stw.pengutronix.de with esmtps (TLS1.3:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1suz8l-00053q-KM; Sun, 29 Sep 2024 20:59:31 +0200 Received: from [2a0a:edc0:0:1101:1d::ac] (helo=dude04.red.stw.pengutronix.de) by drehscheibe.grey.stw.pengutronix.de with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.94.2) (envelope-from ) id 1suz8l-002Ro9-0s; Sun, 29 Sep 2024 20:59:31 +0200 Received: from localhost ([::1] helo=dude04.red.stw.pengutronix.de) by dude04.red.stw.pengutronix.de with esmtp (Exim 4.96) (envelope-from ) id 1suz8k-0029Vj-31; Sun, 29 Sep 2024 20:59:30 +0200 From: Michael Grzeschik Date: Sun, 29 Sep 2024 20:59:27 +0200 Subject: [PATCH v6 7/9] usb: gadget: uvc: set nbuffers to minimum STREAMING_MIN_BUFFERS in uvc_queue_setup Precedence: bulk X-Mailing-List: linux-usb@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Message-Id: <20240403-uvc_request_length_by_interval-v6-7-08c05522e1f5@pengutronix.de> References: <20240403-uvc_request_length_by_interval-v6-0-08c05522e1f5@pengutronix.de> In-Reply-To: <20240403-uvc_request_length_by_interval-v6-0-08c05522e1f5@pengutronix.de> To: Laurent Pinchart , Daniel Scally , Greg Kroah-Hartman , Avichal Rakesh , Jayant Chowdhary Cc: linux-usb@vger.kernel.org, linux-kernel@vger.kernel.org, kernel@pengutronix.de, Michael Grzeschik X-Mailer: b4 0.12.0 X-Developer-Signature: v=1; a=openpgp-sha256; l=1928; i=m.grzeschik@pengutronix.de; h=from:subject:message-id; bh=vDOpCLv2CodGLKEpn/CIA0Ki8MmgeH3jN/oYwO6TfJ4=; b=owEBbQKS/ZANAwAKAb9pWET5cfSrAcsmYgBm+aORsM89Bni7vKaUD/qPI80rRYmZGWy9Rh52m 4mCe1TQJLqJAjMEAAEKAB0WIQQV2+2Fpbqd6fvv0Gi/aVhE+XH0qwUCZvmjkQAKCRC/aVhE+XH0 qwgSD/wPcPsDKNVphESBHZPbJMp4JgvWOw37Xa9EBmM+e3SDYuEmcZWVOI/cZSwEEBww7klDLFP AqjPzXtJGCqxaCn33AMtp5e0bJNhr83bonSn1epfwrc67u4BslyR9ZM4CkdLHp1ZrZaodeG7l1L 0kpJGFjbmCLIXMSDLhfcPxcB7i8jZQWKH+YWTno1C42bNh7Ui0VfcOfhubTq6n54LdCLTPlmcwW M6c7EkczeCCARyOJrGhepZl/ijLw/hS+4SU2ef5ldoJts9D89ws7+JiVIFRrCXwukpcVXCa0Pfc nanbrgS6L4i8MSzIkQ3axtvgPtEXLy02hfOCp19lOHMlhV2D0tQIjPiGuTMKpkE1UWI0ijnT+yV xIRKAvdpl6/80OSXihT6n2UdsIuw87RRx5oN83WldDPL/oSWUIJEiyekwI/akmiEF0y+e1ydMxG WG5VcxMuIx7kfuLGNXjnbaoBBMx59d620ve+IEPvDSDD9WBlDJYQ/15A/2M/WLB+iSxAT6UWQN5 l+ETST3KIB4tVtQ0pAxCQqH3WLwSjJ8DmuQBPl78CB/bz6dJtezuoETSNk12UbcdHisYvMJvrZd Ru4ZtsXn8nzf1P5sRv/2vfcaTl+YJyCl+j2PKv/CPpRaf1Jcd1qjcaCsxRsLQqsmS3V7sNe17R+ n32ZctIf26wLSEA== X-Developer-Key: i=m.grzeschik@pengutronix.de; a=openpgp; fpr=957BC452CE953D7EA60CF4FC0BE9E3157A1E2C64 X-SA-Exim-Connect-IP: 2a0a:edc0:0:c01:1d::a2 X-SA-Exim-Mail-From: m.grzeschik@pengutronix.de X-SA-Exim-Scanned: No (on metis.whiteo.stw.pengutronix.de); SAEximRunCond expanded to false X-PTX-Original-Recipient: linux-usb@vger.kernel.org We set the minimum amount of v4l2 buffers that is possibly be pending to UVCG_STREAMING_MIN_BUFFERS which is two. This way the driver will always have at least one frame pending to be encoded while the other is being enqueued in the hardware. Signed-off-by: Michael Grzeschik --- v5 -> v6: - v4 -> v5: - using STREAMING_MIN_BUFFERS set the min nbuffers - renamed the patch since the function changed - removed the g_ctrl function - reordered this patch in the series v1 -> v4: - --- drivers/usb/gadget/function/uvc.h | 2 ++ drivers/usb/gadget/function/uvc_queue.c | 3 +++ 2 files changed, 5 insertions(+) diff --git a/drivers/usb/gadget/function/uvc.h b/drivers/usb/gadget/function/uvc.h index bedb4ef42864f..6f44dd7323150 100644 --- a/drivers/usb/gadget/function/uvc.h +++ b/drivers/usb/gadget/function/uvc.h @@ -74,6 +74,8 @@ extern unsigned int uvc_gadget_trace_param; #define UVCG_REQ_MAX_INT_COUNT 16 #define UVCG_REQ_MAX_ZERO_COUNT (2 * UVCG_REQ_MAX_INT_COUNT) +#define UVCG_STREAMING_MIN_BUFFERS 2 + /* ------------------------------------------------------------------------ * Structures */ diff --git a/drivers/usb/gadget/function/uvc_queue.c b/drivers/usb/gadget/function/uvc_queue.c index 6757a4e25a743..5eaeae3e2441c 100644 --- a/drivers/usb/gadget/function/uvc_queue.c +++ b/drivers/usb/gadget/function/uvc_queue.c @@ -21,6 +21,7 @@ #include #include "uvc.h" +#include "uvc_video.h" /* ------------------------------------------------------------------------ * Video buffers queue management. @@ -47,6 +48,8 @@ static int uvc_queue_setup(struct vb2_queue *vq, if (*nbuffers > UVC_MAX_VIDEO_BUFFERS) *nbuffers = UVC_MAX_VIDEO_BUFFERS; + if (*nbuffers < UVCG_STREAMING_MIN_BUFFERS) + *nbuffers = UVCG_STREAMING_MIN_BUFFERS; *nplanes = 1; From patchwork Sun Sep 29 18:59:28 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Michael Grzeschik X-Patchwork-Id: 13815210 Received: from metis.whiteo.stw.pengutronix.de (metis.whiteo.stw.pengutronix.de [185.203.201.7]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id A18816BFC0 for ; Sun, 29 Sep 2024 18:59:37 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=185.203.201.7 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1727636381; cv=none; b=iFc7Bxek1QuDWALMCRo8wl7pe7Z2lDInWMjbDvwZwaYN6+0Pl4r4ffMi/YoNhoXVvlGqycB29H+K9/7KI++tH1c2OUJqhcukSSgkkocRKLXK6GzZebE0iHvChN/fmsuiXVDwWb7pao5JywBgzWOAzq7zP0FLNPcefFCR3nVIR3w= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1727636381; c=relaxed/simple; bh=/U43Y8aGcmzcxzXv+PaUGk5zmq/qPekProSrrAIpWOw=; h=From:Date:Subject:MIME-Version:Content-Type:Message-Id:References: In-Reply-To:To:Cc; b=VR/0TYj0BNsD2RIkHt0udamup63PF4FCfs3/kISpm+NuFTNbzjswvIy934/bLwMNjm0vcLEBnYU8QUqqsvm/In+JHeTeruM8Okzvo4ONDRcQn2OAM9s+Lf39e4BTOeHmZoxyOEAYCeW8lNGgXv7aNi4Um7xGqyCMJRbAGEEj5pI= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=pengutronix.de; spf=pass smtp.mailfrom=pengutronix.de; arc=none smtp.client-ip=185.203.201.7 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=pengutronix.de Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=pengutronix.de Received: from drehscheibe.grey.stw.pengutronix.de ([2a0a:edc0:0:c01:1d::a2]) by metis.whiteo.stw.pengutronix.de with esmtps (TLS1.3:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1suz8l-00053r-KL; Sun, 29 Sep 2024 20:59:31 +0200 Received: from [2a0a:edc0:0:1101:1d::ac] (helo=dude04.red.stw.pengutronix.de) by drehscheibe.grey.stw.pengutronix.de with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.94.2) (envelope-from ) id 1suz8l-002RoA-1X; Sun, 29 Sep 2024 20:59:31 +0200 Received: from localhost ([::1] helo=dude04.red.stw.pengutronix.de) by dude04.red.stw.pengutronix.de with esmtp (Exim 4.96) (envelope-from ) id 1suz8k-0029Vj-32; Sun, 29 Sep 2024 20:59:30 +0200 From: Michael Grzeschik Date: Sun, 29 Sep 2024 20:59:28 +0200 Subject: [PATCH v6 8/9] usb: gadget: uvc: add trace of enqueued and completed requests Precedence: bulk X-Mailing-List: linux-usb@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Message-Id: <20240403-uvc_request_length_by_interval-v6-8-08c05522e1f5@pengutronix.de> References: <20240403-uvc_request_length_by_interval-v6-0-08c05522e1f5@pengutronix.de> In-Reply-To: <20240403-uvc_request_length_by_interval-v6-0-08c05522e1f5@pengutronix.de> To: Laurent Pinchart , Daniel Scally , Greg Kroah-Hartman , Avichal Rakesh , Jayant Chowdhary Cc: linux-usb@vger.kernel.org, linux-kernel@vger.kernel.org, kernel@pengutronix.de, Michael Grzeschik X-Mailer: b4 0.12.0 X-Developer-Signature: v=1; a=openpgp-sha256; l=4461; i=m.grzeschik@pengutronix.de; h=from:subject:message-id; bh=/U43Y8aGcmzcxzXv+PaUGk5zmq/qPekProSrrAIpWOw=; b=owEBbQKS/ZANAwAKAb9pWET5cfSrAcsmYgBm+aOSf/qznxVRZC+vvW01WhvqdVTildn7mQpTs pGKbVHs1miJAjMEAAEKAB0WIQQV2+2Fpbqd6fvv0Gi/aVhE+XH0qwUCZvmjkgAKCRC/aVhE+XH0 q1YgD/0WCyun+tWR3YvArZw9ZEVPGEjuRpwapw09R4ugwHgO8ymO8tCeSLwV+N1cHt/+iF9ozpQ m6OnXkmjgTbaNXocL8UcqiO+ThBVXOuFDMHMq99EFQu7AIFbfnYDP6fH5pSllv3B2DoWW/T7na8 uZni47qwusES/FiYSq7YBpmHZaWSe2nu18afMHKc9ugDOWjeK2El0cnmnIB91Y3ZJYiRZ2G99QC 2WQSF5pjL4pBXVAhh8GWjnAVGPU8U4e8ZJ3sDc7sbFw9/lFRf48pZHISSynKXG0vsdJOrwopv+V 4dod0gF9BhtNsVZwshnnOHzTkQZVu0YYjlKU6sSAMM8L1gWElfo12XbxObFLt1ZJLJdIE6vo/Tl jJtN6VfwRgHnkYmWJS64w0/NLc0XaBWmPBMT2evoKQJ8rXn7CIOx1LilKOGiHCGHVUbydpyy0kn HKXEu5KNcdQqtTOvhAlUY6vYowJ7XaRtolgfGpZJiScAg/DzzxugU4NstVvwlByGgo7/Z4+5xhe swhgRwYjWZh/uGSAZosscBkHrsPVkuBOHrScs1jdme+ubagGc20zdtJCippbj1KuydoLqGMpm3w khRTIP5/4gVhQRgmKAMk2TX5+kZ2/Fw3cg8UVQnqUJJxLuYkXrg9OSNvM01DaJZ4czFR26YD7B/ M39JLGMrQvEeLEA== X-Developer-Key: i=m.grzeschik@pengutronix.de; a=openpgp; fpr=957BC452CE953D7EA60CF4FC0BE9E3157A1E2C64 X-SA-Exim-Connect-IP: 2a0a:edc0:0:c01:1d::a2 X-SA-Exim-Mail-From: m.grzeschik@pengutronix.de X-SA-Exim-Scanned: No (on metis.whiteo.stw.pengutronix.de); SAEximRunCond expanded to false X-PTX-Original-Recipient: linux-usb@vger.kernel.org This patch is adding trace events for each request that is being enqueued into the hw and will be completed. This way it is possible to track the fill status of the gadget hardware and find potential issues. Signed-off-by: Michael Grzeschik --- v5 -> v6: - fixed compile rule as module - reordered header files v1 -> v5: - new patch --- drivers/usb/gadget/function/Makefile | 3 ++ drivers/usb/gadget/function/uvc_trace.c | 11 ++++++ drivers/usb/gadget/function/uvc_trace.h | 60 +++++++++++++++++++++++++++++++++ drivers/usb/gadget/function/uvc_video.c | 5 +++ 4 files changed, 79 insertions(+) diff --git a/drivers/usb/gadget/function/Makefile b/drivers/usb/gadget/function/Makefile index 87917a7d4a9be..92b695388611b 100644 --- a/drivers/usb/gadget/function/Makefile +++ b/drivers/usb/gadget/function/Makefile @@ -41,6 +41,9 @@ obj-$(CONFIG_USB_F_UAC1_LEGACY) += usb_f_uac1_legacy.o usb_f_uac2-y := f_uac2.o obj-$(CONFIG_USB_F_UAC2) += usb_f_uac2.o usb_f_uvc-y := f_uvc.o uvc_queue.o uvc_v4l2.o uvc_video.o uvc_configfs.o +ifneq ($(CONFIG_TRACING),) + usb_f_uvc-y += uvc_trace.o +endif obj-$(CONFIG_USB_F_UVC) += usb_f_uvc.o usb_f_midi-y := f_midi.o obj-$(CONFIG_USB_F_MIDI) += usb_f_midi.o diff --git a/drivers/usb/gadget/function/uvc_trace.c b/drivers/usb/gadget/function/uvc_trace.c new file mode 100644 index 0000000000000..d384f6d8221a5 --- /dev/null +++ b/drivers/usb/gadget/function/uvc_trace.c @@ -0,0 +1,11 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * trace.c - USB UVC Gadget Trace Support + * + * Copyright (C) 2024 Pengutronix e.K. + * + * Author: Michael Grzeschik + */ + +#define CREATE_TRACE_POINTS +#include "uvc_trace.h" diff --git a/drivers/usb/gadget/function/uvc_trace.h b/drivers/usb/gadget/function/uvc_trace.h new file mode 100644 index 0000000000000..04c33cf43cc2d --- /dev/null +++ b/drivers/usb/gadget/function/uvc_trace.h @@ -0,0 +1,60 @@ +/* SPDX-License-Identifier: GPL-2.0 */ +/* + * trace.h - USB UVC Gadget Trace Support + * + * Copyright (C) 2024 Pengutronix e.K. + * + * Author: Michael Grzeschik + */ + +#undef TRACE_SYSTEM +#define TRACE_SYSTEM uvcg + +#if !defined(__UVCG_TRACE_H) || defined(TRACE_HEADER_MULTI_READ) +#define __UVCG_TRACE_H + +#include +#include +#include +#include + +DECLARE_EVENT_CLASS(uvcg_video_req, + TP_PROTO(struct usb_request *req, u32 queued), + TP_ARGS(req, queued), + TP_STRUCT__entry( + __field(struct usb_request *, req) + __field(u32, length) + __field(u32, queued) + ), + TP_fast_assign( + __entry->req = req; + __entry->length = req->length; + __entry->queued = queued; + ), + TP_printk("req %p length %u queued %u", + __entry->req, + __entry->length, + __entry->queued) +); + +DEFINE_EVENT(uvcg_video_req, uvcg_video_complete, + TP_PROTO(struct usb_request *req, u32 queued), + TP_ARGS(req, queued) +); + +DEFINE_EVENT(uvcg_video_req, uvcg_video_queue, + TP_PROTO(struct usb_request *req, u32 queued), + TP_ARGS(req, queued) +); + +#endif /* __UVCG_TRACE_H */ + +/* this part has to be here */ + +#undef TRACE_INCLUDE_PATH +#define TRACE_INCLUDE_PATH . + +#undef TRACE_INCLUDE_FILE +#define TRACE_INCLUDE_FILE uvc_trace + +#include diff --git a/drivers/usb/gadget/function/uvc_video.c b/drivers/usb/gadget/function/uvc_video.c index 0287a56fa50ad..115524b79ebd7 100644 --- a/drivers/usb/gadget/function/uvc_video.c +++ b/drivers/usb/gadget/function/uvc_video.c @@ -19,6 +19,7 @@ #include "uvc.h" #include "uvc_queue.h" #include "uvc_video.h" +#include "uvc_trace.h" /* -------------------------------------------------------------------------- * Video codecs @@ -271,6 +272,8 @@ static int uvcg_video_ep_queue(struct uvc_video *video, struct usb_request *req) atomic_inc(&video->queued); + trace_uvcg_video_queue(req, atomic_read(&video->queued)); + return ret; } @@ -408,6 +411,8 @@ uvc_video_complete(struct usb_ep *ep, struct usb_request *req) */ queue_work(video->async_wq, &video->pump); + trace_uvcg_video_complete(req, atomic_read(&video->queued)); + spin_unlock_irqrestore(&video->req_lock, flags); kthread_queue_work(video->kworker, &video->hw_submit); From patchwork Sun Sep 29 18:59:29 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Michael Grzeschik X-Patchwork-Id: 13815204 Received: from metis.whiteo.stw.pengutronix.de (metis.whiteo.stw.pengutronix.de [185.203.201.7]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id A6D916F073 for ; Sun, 29 Sep 2024 18:59:37 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=185.203.201.7 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1727636380; cv=none; b=uhtt9jlXlEzwFbkulCSUVmPRuHTd9Xeomt/IqzseESc7xvoXT84Gm94vKSCh4FIY9IZDh3Y1pB/YuLiUyH31byRONzRNqO9953L36h2iZ7dh8rDhfEgWUZlUK4Hi1vDCXuydb3AHFjoUD6JY+02lZ6F2GQJc4O3XBOwHTRaAkdk= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1727636380; c=relaxed/simple; bh=7S+aPuRPGUbYnkcvuKpuMWRYvF73uV3ggRsPg/mMG5o=; h=From:Date:Subject:MIME-Version:Content-Type:Message-Id:References: In-Reply-To:To:Cc; b=UkTs1hHKo3rnDYGEZI0ZgHRtci2zO2z4U67gQ3EdpWA7fjV2YpSZBTylNwczcYTmrbH9lVSKBJ7Tk04REp3gYJMBeXRa4xe2Di5xbcYsSSXrJVa9ez95tzkpM2KvGvUBN3mZr2Bn4m7HgPY6fSusg8osA4/t1BPnAhMtlFI1Gd0= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=pengutronix.de; spf=pass smtp.mailfrom=pengutronix.de; arc=none smtp.client-ip=185.203.201.7 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=pengutronix.de Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=pengutronix.de Received: from drehscheibe.grey.stw.pengutronix.de ([2a0a:edc0:0:c01:1d::a2]) by metis.whiteo.stw.pengutronix.de with esmtps (TLS1.3:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1suz8l-00053t-KL; Sun, 29 Sep 2024 20:59:31 +0200 Received: from [2a0a:edc0:0:1101:1d::ac] (helo=dude04.red.stw.pengutronix.de) by drehscheibe.grey.stw.pengutronix.de with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.94.2) (envelope-from ) id 1suz8l-002RoB-1D; Sun, 29 Sep 2024 20:59:31 +0200 Received: from localhost ([::1] helo=dude04.red.stw.pengutronix.de) by dude04.red.stw.pengutronix.de with esmtp (Exim 4.96) (envelope-from ) id 1suz8k-0029Vj-33; Sun, 29 Sep 2024 20:59:30 +0200 From: Michael Grzeschik Date: Sun, 29 Sep 2024 20:59:29 +0200 Subject: [PATCH v6 9/9] usb: gadget: uvc: dont call usb_composite_setup_continue when not streaming Precedence: bulk X-Mailing-List: linux-usb@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Message-Id: <20240403-uvc_request_length_by_interval-v6-9-08c05522e1f5@pengutronix.de> References: <20240403-uvc_request_length_by_interval-v6-0-08c05522e1f5@pengutronix.de> In-Reply-To: <20240403-uvc_request_length_by_interval-v6-0-08c05522e1f5@pengutronix.de> To: Laurent Pinchart , Daniel Scally , Greg Kroah-Hartman , Avichal Rakesh , Jayant Chowdhary Cc: linux-usb@vger.kernel.org, linux-kernel@vger.kernel.org, kernel@pengutronix.de, Michael Grzeschik X-Mailer: b4 0.12.0 X-Developer-Signature: v=1; a=openpgp-sha256; l=1116; i=m.grzeschik@pengutronix.de; h=from:subject:message-id; bh=7S+aPuRPGUbYnkcvuKpuMWRYvF73uV3ggRsPg/mMG5o=; b=owEBbQKS/ZANAwAKAb9pWET5cfSrAcsmYgBm+aOSKRNJf2gHyr9LAFLASPoX8Ve4fvtg2MTYI kxp29wUvUyJAjMEAAEKAB0WIQQV2+2Fpbqd6fvv0Gi/aVhE+XH0qwUCZvmjkgAKCRC/aVhE+XH0 q1hyEAC9Ir5VllmE3JkSMXYslr0pvNe7lSHQR4q6gEsFYaviIKdKz/ufdT9Cqnv16+GgzpVRT0F TL3M17aKRLreii0Jnc3CvpcBd+YD4htM2s+m5muwx6PrQH1Hi7HsfzEgJcpruWVFsRxxGEobNWg l8huJfX7l4aQeg3gq7vcwiGoFfSSN9HxbFAfRAX08TQem77kavX4wzzT72BRvb7UtoiAckRb3TM q4jFllw9FJtkfytNOF7W7Y7B9y+q3ZSo5YdHvJ2k2KQ9MsJsQtyqMazrCdY9Wl+Pj2hJkKRTvV6 v22uXItUzb3GiL0PEX/8XvLO/JA+xYXsoyXUW+2MeVigBRdTQdat2p7+uIDvKIHuprNZv8HX/er 8EkJKkGJgFghvVXdAhHH54mefZ7+GD+16A0gSsIQVjnSwZFPFwMqb1x7yaSkcZV34RSXkSn9ErU 55svaoCTXsu2nVXTtMNyKUdJAzGeG7j+8d4Jt3WVcELDkgBkLW1Jo2kZaq2dYNo3N5ZYT0tT7LE h5D3P4W03/vv8onzx/9Nb0NYktsb06VpEl13JjBY8oFBK/FRTnKbFtv5XSLruEviufe4XXhlsnP v3U32J8eqhl0neIRJKkLPIp+Hj58gxoUuMSHfZJB/lzgXzmlVV6sFXq2gc8oV6OzveYqmvDsngn 7puAuykchMJ/Exw== X-Developer-Key: i=m.grzeschik@pengutronix.de; a=openpgp; fpr=957BC452CE953D7EA60CF4FC0BE9E3157A1E2C64 X-SA-Exim-Connect-IP: 2a0a:edc0:0:c01:1d::a2 X-SA-Exim-Mail-From: m.grzeschik@pengutronix.de X-SA-Exim-Scanned: No (on metis.whiteo.stw.pengutronix.de); SAEximRunCond expanded to false X-PTX-Original-Recipient: linux-usb@vger.kernel.org If the streamoff call was triggered by some previous disconnect or userspace application shutdown the uvc_function_setup_continue should not be called and the state should not be overwritten. For this situation the set_alt(0) was never called and the streaming ep has no USB_GADGET_DELAYED_STATUS pending. Since the state then was already updated before we also omit the state update. Signed-off-by: Michael Grzeschik --- v5 -> v6: - v1 -> v5: - new patch --- drivers/usb/gadget/function/uvc_v4l2.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/drivers/usb/gadget/function/uvc_v4l2.c b/drivers/usb/gadget/function/uvc_v4l2.c index ab89f1630acb0..3492855f0fb29 100644 --- a/drivers/usb/gadget/function/uvc_v4l2.c +++ b/drivers/usb/gadget/function/uvc_v4l2.c @@ -546,6 +546,9 @@ uvc_v4l2_streamoff(struct file *file, void *fh, enum v4l2_buf_type type) if (ret < 0) return ret; + if (uvc->state != UVC_STATE_STREAMING) + return 0; + uvc->state = UVC_STATE_CONNECTED; uvc_function_setup_continue(uvc, 1); return 0;