From patchwork Wed Dec 18 22:33:20 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Bitterblue Smith X-Patchwork-Id: 13914182 X-Patchwork-Delegate: pkshih@realtek.com Received: from mail-ej1-f50.google.com (mail-ej1-f50.google.com [209.85.218.50]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 4186935948 for ; Wed, 18 Dec 2024 22:33:24 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=209.85.218.50 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1734561207; cv=none; b=LEqJBpH5n+9C8iHzbeolqt2YgvFI4kER3LNqx8TkvhErMYDHRVTVWj0L+2kaT+ssdv/9f3L0MXzhvRPEuIU1Bm6JuIJDS6j7YtyRK35qX41ETluMnjSu3eH63laHKwrmEs/NeLCtFDwxIrh31ynLoV+jeXSOeYWUsakHQ9x6lyc= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1734561207; c=relaxed/simple; bh=gJti6UIvVj7b8u81nqgmnYFQJBtDHmYrPQbjgsdeW8M=; h=Message-ID:Date:MIME-Version:To:Cc:From:Subject:Content-Type; b=juJRz977X8f6fDc0opZGW7m1fHZ8o0t+l42Lrh9K1SZPVd2X9ICH5FUDP3AhM2rJ1OlUplv0liOq8+jO/JkwbD33/vvMRQs22q7+Anx5TukB0yV+VWYLhkxl5hTz22h8GaVJXndbpSIUAeae5qL+7Q7Wu8lmGgwJeRj0EK1gXIY= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=gmail.com; spf=pass smtp.mailfrom=gmail.com; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b=WgCPIE/+; arc=none smtp.client-ip=209.85.218.50 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=gmail.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=gmail.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="WgCPIE/+" Received: by mail-ej1-f50.google.com with SMTP id a640c23a62f3a-aabfb33aff8so40477966b.0 for ; Wed, 18 Dec 2024 14:33:24 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20230601; t=1734561203; x=1735166003; darn=vger.kernel.org; h=content-transfer-encoding:subject:from:cc:to:content-language :user-agent:mime-version:date:message-id:from:to:cc:subject:date :message-id:reply-to; bh=l1LtM4D+RAOANoTg5UBfWOeqCJ9YeYukS4mq2nMbLd0=; b=WgCPIE/+dEEi3CnrleIiIraZ538N1MOwjbouoVkIVRhJ6mW+jWquMHgfZHX9DuXFvr wR/xln4E0fxVsoHys697DBLYnx23pRbJBp2f76G5NlPijsDyRBTDRUCNLMH3CGhrO/Lz au+H0y57bwgjXRccn1wloOstiVCzfHyDt5yYZPyERagSmkRdu7962o8oP+OsL76GVnOz 92CtgjH8wz6OjFyFa3bHAGR8YpwXaOnw+7ztT1EKPsLN1vX0iQhIZuwjQUhZf4wjpVMb FMWFK+sg8AUFUCpFq5RQjRuOikcLtyrue96WE7UDMzIp1G6Yfemy52dkn6DbN7N0J0Ok zkOA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1734561203; x=1735166003; h=content-transfer-encoding:subject:from:cc:to:content-language :user-agent:mime-version:date:message-id:x-gm-message-state:from:to :cc:subject:date:message-id:reply-to; bh=l1LtM4D+RAOANoTg5UBfWOeqCJ9YeYukS4mq2nMbLd0=; b=J2puxj1fsslN2rgU7FF8sqOIgDYawa66lks5G/AKxIsfLjVh1z78hXA0fF4jV9r4qC yitQ02AFyNzz05TsfcmAA8trddRZoTKTyx0v5mQ6KzyfsIoi3Z7vhqGhENDHR+V52p/O FgnMTrd9dlodpI7AESgQq+pj5o2TVNkq7DEIsIq4nSfX4wrDFUgTIn6ZFyBgXv6Hn9bd LGWni+l6KtCQ+jzxZfl0gCfp0eFOhWK/NqZkkY7wIVFIA/71fvlI0p/7uuJIq4OI3cKY 8+TKTiMykpXKwszZ1klO5NxgmVpUBgp1X1BsgXw48fz3nbvCTQvfuh8JgYcdd/62m/Us zTJA== X-Gm-Message-State: AOJu0YwFK70xJ1wZp96ZqBebGPI8e0pE4wGUlZoGZ60K9froF10wbhq2 rXcmgqE/GMfzVsQXuodELVf9ZB1cavXV7kcYyu0FGvbnyNkr8bFm5MjIKQ== X-Gm-Gg: ASbGncuQOpRLS1y0EdW0qiCd57f0aiAh8S+QLvBuk0fSOG5s9J/aki7Za5c32DmaXoD d2H1X1mXBpy715eO9zQrrak5JC4xn8kwgjUPjZigOKEZIn7gETSrIqn5ShLJU3TwwJmuFfVp9Sm QboSf3WRQuxnCwhtpBGut5lwDPkOyfH/tZUA48kgL3W2gHRhxKR1vgzltikbHUKdkLbi23foMM8 zH/tn8ndritXrKipFKH65GQ2s09yB2co7exTTGe+YX7QZeqbv50pFiBJi2gMn4L X-Google-Smtp-Source: AGHT+IHK1cmCBVU2spyi1HXsrmysqPUdkTt1tp5jQ9t/jImthkFlOLq56ElvFivVj9ZKNg9svx63aA== X-Received: by 2002:a17:906:32ce:b0:aa6:832b:8d70 with SMTP id a640c23a62f3a-aac081134afmr85146366b.3.1734561203270; Wed, 18 Dec 2024 14:33:23 -0800 (PST) Received: from [192.168.0.50] ([79.119.240.80]) by smtp.gmail.com with ESMTPSA id a640c23a62f3a-aab9638ec32sm595133666b.151.2024.12.18.14.33.21 (version=TLS1_3 cipher=TLS_AES_128_GCM_SHA256 bits=128/128); Wed, 18 Dec 2024 14:33:22 -0800 (PST) Message-ID: <8c9d4f9d-ebd8-4dc0-a0c4-9ebe430521dd@gmail.com> Date: Thu, 19 Dec 2024 00:33:20 +0200 Precedence: bulk X-Mailing-List: linux-wireless@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 User-Agent: Mozilla Thunderbird Content-Language: en-US To: "linux-wireless@vger.kernel.org" Cc: Ping-Ke Shih , Sascha Hauer From: Bitterblue Smith Subject: [PATCH v2 1/3] wifi: rtw88: usb: Copy instead of cloning the RX skb "iperf3 -c 192.168.0.1 -R --udp -b 0" shows about 40% of datagrams are lost. Many torrents don't download faster than 3 MiB/s, probably because the Bittorrent protocol uses UDP. This is somehow related to the use of skb_clone() in the RX path. Don't use skb_clone(). Instead allocate a new skb for each 802.11 frame received and copy the data from the big (32768 byte) skb. With this patch, "iperf3 -c 192.168.0.1 -R --udp -b 0" shows only 1-2% of datagrams are lost, and torrents can reach download speeds of 36 MiB/s. Tested with RTL8812AU and RTL8822CU. Signed-off-by: Bitterblue Smith --- v2: - No change. --- drivers/net/wireless/realtek/rtw88/usb.c | 52 ++++++++++++++---------- 1 file changed, 31 insertions(+), 21 deletions(-) diff --git a/drivers/net/wireless/realtek/rtw88/usb.c b/drivers/net/wireless/realtek/rtw88/usb.c index 34df371e599b..4dbd5167faa4 100644 --- a/drivers/net/wireless/realtek/rtw88/usb.c +++ b/drivers/net/wireless/realtek/rtw88/usb.c @@ -7,6 +7,7 @@ #include #include "main.h" #include "debug.h" +#include "mac.h" #include "reg.h" #include "tx.h" #include "rx.h" @@ -546,49 +547,58 @@ static void rtw_usb_rx_handler(struct work_struct *work) { struct rtw_usb *rtwusb = container_of(work, struct rtw_usb, rx_work); struct rtw_dev *rtwdev = rtwusb->rtwdev; - const struct rtw_chip_info *chip = rtwdev->chip; - u32 pkt_desc_sz = chip->rx_pkt_desc_sz; struct ieee80211_rx_status rx_status; - u32 pkt_offset, next_pkt, urb_len; struct rtw_rx_pkt_stat pkt_stat; - struct sk_buff *next_skb; + struct sk_buff *rx_skb; struct sk_buff *skb; + u32 pkt_desc_sz = rtwdev->chip->rx_pkt_desc_sz; + u32 max_skb_len = pkt_desc_sz + PHY_STATUS_SIZE * 8 + + IEEE80211_MAX_MPDU_LEN_VHT_11454; + u32 pkt_offset, next_pkt, skb_len; u8 *rx_desc; int limit; for (limit = 0; limit < 200; limit++) { - skb = skb_dequeue(&rtwusb->rx_queue); - if (!skb) + rx_skb = skb_dequeue(&rtwusb->rx_queue); + if (!rx_skb) break; if (skb_queue_len(&rtwusb->rx_queue) >= RTW_USB_MAX_RXQ_LEN) { dev_dbg_ratelimited(rtwdev->dev, "failed to get rx_queue, overflow\n"); - dev_kfree_skb_any(skb); + dev_kfree_skb_any(rx_skb); continue; } - urb_len = skb->len; + rx_desc = rx_skb->data; do { - rx_desc = skb->data; rtw_rx_query_rx_desc(rtwdev, rx_desc, &pkt_stat, &rx_status); pkt_offset = pkt_desc_sz + pkt_stat.drv_info_sz + pkt_stat.shift; - next_pkt = round_up(pkt_stat.pkt_len + pkt_offset, 8); + skb_len = pkt_stat.pkt_len + pkt_offset; + if (skb_len > max_skb_len) { + rtw_dbg(rtwdev, RTW_DBG_USB, + "skipping too big packet: %u\n", + skb_len); + goto skip_packet; + } - if (urb_len >= next_pkt + pkt_desc_sz) - next_skb = skb_clone(skb, GFP_KERNEL); - else - next_skb = NULL; + skb = alloc_skb(skb_len, GFP_KERNEL); + if (!skb) { + rtw_dbg(rtwdev, RTW_DBG_USB, + "failed to allocate RX skb of size %u\n", + skb_len); + goto skip_packet; + } + + skb_put_data(skb, rx_desc, skb_len); if (pkt_stat.is_c2h) { - skb_trim(skb, pkt_stat.pkt_len + pkt_offset); rtw_fw_c2h_cmd_rx_irqsafe(rtwdev, pkt_offset, skb); } else { skb_pull(skb, pkt_offset); - skb_trim(skb, pkt_stat.pkt_len); rtw_update_rx_freq_for_invalid(rtwdev, skb, &rx_status, &pkt_stat); @@ -597,12 +607,12 @@ static void rtw_usb_rx_handler(struct work_struct *work) ieee80211_rx_irqsafe(rtwdev->hw, skb); } - skb = next_skb; - if (skb) - skb_pull(skb, next_pkt); +skip_packet: + next_pkt = round_up(skb_len, 8); + rx_desc += next_pkt; + } while (rx_desc + pkt_desc_sz < rx_skb->data + rx_skb->len); - urb_len -= next_pkt; - } while (skb); + dev_kfree_skb_any(rx_skb); } } From patchwork Wed Dec 18 22:34:42 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Bitterblue Smith X-Patchwork-Id: 13914191 X-Patchwork-Delegate: pkshih@realtek.com Received: from mail-ej1-f43.google.com (mail-ej1-f43.google.com [209.85.218.43]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 8C6C835948 for ; Wed, 18 Dec 2024 22:34:46 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=209.85.218.43 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1734561288; cv=none; b=fRZKIud0pExOOcDFJS2NSj3EdRuKiRxAYQl5ZWzeEcFAkAjiu9J0GyTRz1imqHCnyYOX/1n3tIpai9QCXUTCGu6Z5aNvNqiR70DCIjga0DCu4Mw75J5aGEOmjpH7ajMJ8tllaK8Cm34Y+WwUo9uY/1Ixb1n/a1KfypMLkbnpkTs= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1734561288; c=relaxed/simple; bh=A5qPgCfwF0amE9jjgnUEWoMGM6d2vSeguLtLEuXbRsA=; h=Message-ID:Date:MIME-Version:Subject:From:To:Cc:References: In-Reply-To:Content-Type; b=tQmAutGza2GnFzGvOqaHi6Zyjt3MbjUeNQ2M2yNmg+8qhRNq0gpq7M0YXZUQRfbnnKgKPYZRIF8mdKHimeFyIZ4LaMvcbj3A2bcE+2I80yHj1qJHKSdpDuilc2xYJoDkaeUEvupJps8osa9DQ90QTviv1D5RBM++cIp5WBW3vck= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=gmail.com; spf=pass smtp.mailfrom=gmail.com; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b=SBGnTzzy; arc=none smtp.client-ip=209.85.218.43 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=gmail.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=gmail.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="SBGnTzzy" Received: by mail-ej1-f43.google.com with SMTP id a640c23a62f3a-aab9e281bc0so22460966b.3 for ; Wed, 18 Dec 2024 14:34:46 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20230601; t=1734561285; x=1735166085; darn=vger.kernel.org; h=content-transfer-encoding:in-reply-to:content-language:references :cc:to:from:subject:user-agent:mime-version:date:message-id:from:to :cc:subject:date:message-id:reply-to; bh=UC/89hyJasDnNRzp7vVO2ZMP/Krjl65TO8/+3e7IHBk=; b=SBGnTzzyUDYg5/nUdK9+ljt+zNrItNfhjTn9dieyIwSWMG7lmll1qpEj1E2p8ANN13 8PqzA7w/38KIDNBRg/gKZywrCrS5s1dRxFGuZHAxqX+JqzZLQrZErC09Cp/F4HJnIx4W +gN70/CefztLZdHM9tlgCSKZGKwXlfZMqv1Wma/m/gUT9uFOH6XHqj7ylFFuIwLUyO4s QyRfUZdCQm9Ky7zcbSETRFhW5X3Dhj9VMvXgTWPSAsJTuIu49dm4hzO2KV49FidG3dir 5Z1DQPULo5BQq3jDtPQSsXTUEDqYuYMV5mCNuJONstKiT2dJ18QiuXlNaBvNvBRDV6yb ArNw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1734561285; x=1735166085; h=content-transfer-encoding:in-reply-to:content-language:references :cc:to:from:subject:user-agent:mime-version:date:message-id :x-gm-message-state:from:to:cc:subject:date:message-id:reply-to; bh=UC/89hyJasDnNRzp7vVO2ZMP/Krjl65TO8/+3e7IHBk=; b=gtjgI/w7SfqLeRWxcmsdvs8m5mpawJA5BKUT0hZ/dW6BeCeBlCk9NMLFVToRtIE+GG FSjRmARgRvv7kUMo48diLrWmf3Z3X/UroWToXqESlzzeAKgbCSadPCzhThOhsJWNJPY6 0iUWp6+0Gjdo7YB/60wBeE1CKPCBmIcsWFzqd7riC3kn3MW4yOtUNzpMDFXDHd86/S6W HRyFzrVegahKeXStVVDW8ozC99Gm5MGzfVuZdkMAPYdblZhYr+gZ2lq32NptB2Yq/ils Hb6L3lI/i2n4DGk+jq2Fvq50/7EQKzwjzj+64UhGUAVgGToQ90AN3e8lEeVMz5AxhJk3 eFAQ== X-Gm-Message-State: AOJu0YykYnnITLEN+jIFGISu/KiO1wRQALw2iAdttN3I80XFE7ZNqNLP BTCZ0vYVj26mesY1QhNjrJyYoJrdDLNf4TbQPa8CE4uFuGiF5pCezIDaKg== X-Gm-Gg: ASbGncs8RBrwLxDGsrHKCwy7J8mkbuzTBRmgdeiQW7zX/fDXik6OXTJwNdL9FjKdVd4 WPx8ePVpQmok7/anieMBwTSyPS9T10+XZA6jlwVvG4BjKjQnO/5CMSAaOgtVHAX5XnmtAhnRzni rU7jG2C1vHFWxStX8282vxQZdPMZB4OYyVa+ydtZELYURlKTDhsz16qZ3IqBmmUzl55nMgwCsmV Cz2wic3Y+ZgiQLH9vzOijcy4H/MW6zBlRj82zScEY52dLgq27B0co/4UwrNsXOs X-Google-Smtp-Source: AGHT+IE5URIzi5Q7++wdklzH8ktmZ3V8ZeHTPRoa1qWclNria/12XUfDfooxQYHI3r1MQE9f4Ev6CQ== X-Received: by 2002:a17:907:2d9e:b0:aa6:4a5b:b729 with SMTP id a640c23a62f3a-aac079611fdmr85204866b.33.1734561284795; Wed, 18 Dec 2024 14:34:44 -0800 (PST) Received: from [192.168.0.50] ([79.119.240.80]) by smtp.gmail.com with ESMTPSA id a640c23a62f3a-aab963b268asm593441766b.176.2024.12.18.14.34.42 (version=TLS1_3 cipher=TLS_AES_128_GCM_SHA256 bits=128/128); Wed, 18 Dec 2024 14:34:43 -0800 (PST) Message-ID: <96e52b03-be8d-4050-ae71-bfdb478ff42f@gmail.com> Date: Thu, 19 Dec 2024 00:34:42 +0200 Precedence: bulk X-Mailing-List: linux-wireless@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 User-Agent: Mozilla Thunderbird Subject: [PATCH v2 2/3] wifi: rtw88: Handle C2H_ADAPTIVITY in rtw_fw_c2h_cmd_handle() From: Bitterblue Smith To: "linux-wireless@vger.kernel.org" Cc: Ping-Ke Shih , Sascha Hauer References: <8c9d4f9d-ebd8-4dc0-a0c4-9ebe430521dd@gmail.com> Content-Language: en-US In-Reply-To: <8c9d4f9d-ebd8-4dc0-a0c4-9ebe430521dd@gmail.com> The firmware message C2H_ADAPTIVITY is currently handled in rtw_fw_c2h_cmd_rx_irqsafe(), which runs in the RX workqueue, but it's not "irqsafe" with USB because it sleeps (reads hardware registers). This becomes a problem after the next patch, which will create the RX workqueue with the flag WQ_BH. To avoid sleeping when it's not allowed, handle C2H_ADAPTIVITY in rtw_fw_c2h_cmd_handle(), which runs in the c2h workqueue. Signed-off-by: Bitterblue Smith Acked-by: Ping-Ke Shih --- v2: - Patch is new in v2. --- drivers/net/wireless/realtek/rtw88/fw.c | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/drivers/net/wireless/realtek/rtw88/fw.c b/drivers/net/wireless/realtek/rtw88/fw.c index e6e9946fbf44..02389b7c6876 100644 --- a/drivers/net/wireless/realtek/rtw88/fw.c +++ b/drivers/net/wireless/realtek/rtw88/fw.c @@ -332,6 +332,9 @@ void rtw_fw_c2h_cmd_handle(struct rtw_dev *rtwdev, struct sk_buff *skb) case C2H_RA_RPT: rtw_fw_ra_report_handle(rtwdev, c2h->payload, len); break; + case C2H_ADAPTIVITY: + rtw_fw_adaptivity_result(rtwdev, c2h->payload, len); + break; default: rtw_dbg(rtwdev, RTW_DBG_FW, "C2H 0x%x isn't handled\n", c2h->id); break; @@ -367,10 +370,6 @@ void rtw_fw_c2h_cmd_rx_irqsafe(struct rtw_dev *rtwdev, u32 pkt_offset, rtw_fw_scan_result(rtwdev, c2h->payload, len); dev_kfree_skb_any(skb); break; - case C2H_ADAPTIVITY: - rtw_fw_adaptivity_result(rtwdev, c2h->payload, len); - dev_kfree_skb_any(skb); - break; default: /* pass offset for further operation */ *((u32 *)skb->cb) = pkt_offset; From patchwork Wed Dec 18 22:35:49 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Bitterblue Smith X-Patchwork-Id: 13914192 X-Patchwork-Delegate: pkshih@realtek.com Received: from mail-ed1-f41.google.com (mail-ed1-f41.google.com [209.85.208.41]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id ED1A835948 for ; Wed, 18 Dec 2024 22:35:53 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=209.85.208.41 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1734561355; cv=none; b=RN1hiCzzfro90Aj7Lt1MnJKT+H/+9qUWPilVwhoVanME8WHrZCzxuL8fTb1t3XIh69VWPdlR31HqRVEqJcDwq33fhVYRgGZPtqJFmMi8tzrpRvUJJdKK1TgnTVmn5+hMMuFYYeAT6xYWWF+ssHT3Z36VbK/DmDVOIrywl64BkCc= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1734561355; c=relaxed/simple; bh=3xcfigb3IHA0dIzCFqWTaaCVsIsQHsvxJCOp7P1LawM=; h=Message-ID:Date:MIME-Version:Subject:From:To:Cc:References: In-Reply-To:Content-Type; b=cYbU4JWHb94TUuQpUbz0+tu5VXpUf4S2xrAVQmmE6LFir/3QBv0I1Eh41Nj+L4VHrrexYUFwAqnrVPJAYGJ93RhESbjovDVAjGGafCpU50M9M37/qM0jKcpeJTLCIzLwRFAaTZklXgZQi5ZkAxPpZAIPTyIHnYpP9mEnKzNQbDo= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=gmail.com; spf=pass smtp.mailfrom=gmail.com; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b=FxKXScZZ; arc=none smtp.client-ip=209.85.208.41 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=gmail.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=gmail.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="FxKXScZZ" Received: by mail-ed1-f41.google.com with SMTP id 4fb4d7f45d1cf-5d27243ba8bso230219a12.2 for ; Wed, 18 Dec 2024 14:35:53 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20230601; t=1734561352; x=1735166152; darn=vger.kernel.org; h=content-transfer-encoding:in-reply-to:content-language:references :cc:to:from:subject:user-agent:mime-version:date:message-id:from:to :cc:subject:date:message-id:reply-to; bh=fJ2gHbKoqM9i6XR47e0TKuDWjHxNW1wjgSVRL5Of1nA=; b=FxKXScZZ7VRTtGdCQryQwwZyAtpGMEK03bm2cSetmRstrjFZTIcNOvRPUosXOlChs0 cHL+sxXm2H9HhUSTm86jld238cro8vHW1tVJEBgoCxQkYIJybs+cT1f4Zu5k0a1+6+b+ TfSRKZ6HXpeOtxWfAoG6hohUT94DIHk9oM2tHHs2KcPqF6GmYXdZGfzXrhnZmid6IryW VeE/CHCddMEMwTAmaQE7S1qnin4nU8AUBMxfPCtsYu/CmTT4T1LrzsPtwkg0WwHZOUu1 06VIE9gME1pa2QCtt0uMMjReJV8Xl6K/+yILRdMHaG11uYT1Ks7B/jJDBdxUInQ1RrwS ADvg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1734561352; x=1735166152; h=content-transfer-encoding:in-reply-to:content-language:references :cc:to:from:subject:user-agent:mime-version:date:message-id :x-gm-message-state:from:to:cc:subject:date:message-id:reply-to; bh=fJ2gHbKoqM9i6XR47e0TKuDWjHxNW1wjgSVRL5Of1nA=; b=wnsx/r+lgs+s2KRK5kTOhGTBGWtqpuLpBfavl+i0TlSyQMIEqszK0Zmz5AL3Gdmt5H kSyT2bd3TgrgJPRkx8Lw82twiGRVLGWRd/QrG+tDhrYUqWfqlEyjnkG42LIPcatSrBPr d2OhqJHVp4R0b8JeRDCIRGKjrjgz2Se+Fl83Ddi6hKLQl2g9RdYgmMA/8D9TYQwLA6nv w4MFAjVE4e3nQG/9dHxQsgzTlHo1G/b70lGJyP9swkl2UR6Q31IMFtJSCvYC1FJk20fl 33uQn7u5uo9zffTpVeSI0Vz6UiJJoIVmwyIa6cVgC5VKmsw5taV6fGe1D06veVrK5iY3 wswQ== X-Gm-Message-State: AOJu0YwvY+J1P3jWJlEkJ2NSVwyo3N+HBVPJCyhjKj1HaY9SWLxmnq4Z nD5B2zBwnBgqtlZIhXm1rdgc/Is6RJu5OcSgCnvHTYfMzTMxdh7YINLBTQ== X-Gm-Gg: ASbGncuRu7S7XB6qkAKjQdYIzfIiUhVDFuN7+4cUNwdPLQc+1fmPArKgCt72C2gaagS Pj85q5xv3PvAc6SjwKMSZkgELQTplPz/RjtgaMqquDNu5lqfQqzQfdoQ9Qw9oDerQIplMzWqDZG dG7kDfCfEQAc/ZMrHX9MpKZKi8KsabuUtsCDEmQ/TqAXErFFMlxgj9GYTIj+n8OdqFJOAnqWXaH SPSQAOkFRNBUsDdVYa+V4kjz+itzL0aj6OPxICbtWwW5Ptwt9Xq+Fh7uhiGigTu X-Google-Smtp-Source: AGHT+IEVpcU9MNdtEQm0e1NVe8/EEGqOLuSoNYo8AZx6K3dfkVM789CeZAs60eEWp+iWxftZwgxxOQ== X-Received: by 2002:a05:6402:51c8:b0:5d2:729f:995b with SMTP id 4fb4d7f45d1cf-5d7ee418449mr4175303a12.24.1734561351905; Wed, 18 Dec 2024 14:35:51 -0800 (PST) Received: from [192.168.0.50] ([79.119.240.80]) by smtp.gmail.com with ESMTPSA id 4fb4d7f45d1cf-5d80679eebcsm6200a12.41.2024.12.18.14.35.49 (version=TLS1_3 cipher=TLS_AES_128_GCM_SHA256 bits=128/128); Wed, 18 Dec 2024 14:35:50 -0800 (PST) Message-ID: <9cee7a34-c38d-4128-824d-0ec139ca5a4e@gmail.com> Date: Thu, 19 Dec 2024 00:35:49 +0200 Precedence: bulk X-Mailing-List: linux-wireless@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 User-Agent: Mozilla Thunderbird Subject: [PATCH v2 3/3] wifi: rtw88: usb: Preallocate and reuse the RX skbs From: Bitterblue Smith To: "linux-wireless@vger.kernel.org" Cc: Ping-Ke Shih , Sascha Hauer References: <8c9d4f9d-ebd8-4dc0-a0c4-9ebe430521dd@gmail.com> Content-Language: en-US In-Reply-To: <8c9d4f9d-ebd8-4dc0-a0c4-9ebe430521dd@gmail.com> The USB driver uses four USB Request Blocks for RX. Before submitting one, it allocates a 32768 byte skb for the RX data. This allocation can fail, maybe due to temporary memory fragmentation. When the allocation fails, the corresponding URB is never submitted again. After four such allocation failures, all RX stops because the driver is not requesting data from the device anymore. Don't allocate a 32768 byte skb when submitting a USB Request Block (which happens very often). Instead preallocate 8 such skbs, and reuse them over and over. If all 8 are busy, allocate a new one. This is pretty rare. If the allocation fails, use a work to try again later. When there are enough free skbs again, free the excess skbs. Also, use WQ_BH for the RX workqueue. With a normal or high priority workqueue the skbs are processed too slowly when the system is even a little busy, like when opening a new page in a browser, and the driver runs out of free skbs and allocates a lot of new ones. This is more or less what the out-of-tree Realtek drivers do, except they use a tasklet instead of a BH workqueue. Tested with RTL8723DU, RTL8821AU, RTL8812AU, RTL8812BU, RTL8822CU, RTL8811CU. Closes: https://lore.kernel.org/linux-wireless/6e7ecb47-7ea0-433a-a19f-05f88a2edf6b@gmail.com/ Signed-off-by: Bitterblue Smith Acked-by: Ping-Ke Shih --- v2: - Pass the appropriate gfp_t flags as a parameter to rtw_usb_rx_resubmit() instead of using in_interrupt(). Call it "gfp" instead of "priority". - Initialise rx_skb a little earlier in rtw_usb_rx_resubmit(). - Move C2H_ADAPTIVITY in a new patch (2/3). - Allow the driver to allocate 4 more persistent skbs after the initial 8. --- drivers/net/wireless/realtek/rtw88/usb.c | 79 +++++++++++++++++++----- drivers/net/wireless/realtek/rtw88/usb.h | 3 + 2 files changed, 67 insertions(+), 15 deletions(-) diff --git a/drivers/net/wireless/realtek/rtw88/usb.c b/drivers/net/wireless/realtek/rtw88/usb.c index 4dbd5167faa4..b405f8317021 100644 --- a/drivers/net/wireless/realtek/rtw88/usb.c +++ b/drivers/net/wireless/realtek/rtw88/usb.c @@ -585,7 +585,7 @@ static void rtw_usb_rx_handler(struct work_struct *work) goto skip_packet; } - skb = alloc_skb(skb_len, GFP_KERNEL); + skb = alloc_skb(skb_len, GFP_ATOMIC); if (!skb) { rtw_dbg(rtwdev, RTW_DBG_USB, "failed to allocate RX skb of size %u\n", @@ -612,32 +612,70 @@ static void rtw_usb_rx_handler(struct work_struct *work) rx_desc += next_pkt; } while (rx_desc + pkt_desc_sz < rx_skb->data + rx_skb->len); - dev_kfree_skb_any(rx_skb); + if (skb_queue_len(&rtwusb->rx_free_queue) >= RTW_USB_RX_SKB_NUM) + dev_kfree_skb_any(rx_skb); + else + skb_queue_tail(&rtwusb->rx_free_queue, rx_skb); } } static void rtw_usb_read_port_complete(struct urb *urb); -static void rtw_usb_rx_resubmit(struct rtw_usb *rtwusb, struct rx_usb_ctrl_block *rxcb) +static void rtw_usb_rx_resubmit(struct rtw_usb *rtwusb, + struct rx_usb_ctrl_block *rxcb, + gfp_t gfp) { struct rtw_dev *rtwdev = rtwusb->rtwdev; + struct sk_buff *rx_skb; int error; - rxcb->rx_skb = alloc_skb(RTW_USB_MAX_RECVBUF_SZ, GFP_ATOMIC); - if (!rxcb->rx_skb) - return; + rx_skb = skb_dequeue(&rtwusb->rx_free_queue); + if (!rx_skb) + rx_skb = alloc_skb(RTW_USB_MAX_RECVBUF_SZ, gfp); + + if (!rx_skb) + goto try_later; + + skb_reset_tail_pointer(rx_skb); + rx_skb->len = 0; + + rxcb->rx_skb = rx_skb; usb_fill_bulk_urb(rxcb->rx_urb, rtwusb->udev, usb_rcvbulkpipe(rtwusb->udev, rtwusb->pipe_in), rxcb->rx_skb->data, RTW_USB_MAX_RECVBUF_SZ, rtw_usb_read_port_complete, rxcb); - error = usb_submit_urb(rxcb->rx_urb, GFP_ATOMIC); + error = usb_submit_urb(rxcb->rx_urb, gfp); if (error) { - kfree_skb(rxcb->rx_skb); + skb_queue_tail(&rtwusb->rx_free_queue, rxcb->rx_skb); + if (error != -ENODEV) rtw_err(rtwdev, "Err sending rx data urb %d\n", error); + + if (error == -ENOMEM) + goto try_later; + } + + return; + +try_later: + rxcb->rx_skb = NULL; + queue_work(rtwusb->rxwq, &rtwusb->rx_urb_work); +} + +static void rtw_usb_rx_resubmit_work(struct work_struct *work) +{ + struct rtw_usb *rtwusb = container_of(work, struct rtw_usb, rx_urb_work); + struct rx_usb_ctrl_block *rxcb; + int i; + + for (i = 0; i < RTW_USB_RXCB_NUM; i++) { + rxcb = &rtwusb->rx_cb[i]; + + if (!rxcb->rx_skb) + rtw_usb_rx_resubmit(rtwusb, rxcb, GFP_ATOMIC); } } @@ -653,15 +691,16 @@ static void rtw_usb_read_port_complete(struct urb *urb) urb->actual_length < 24) { rtw_err(rtwdev, "failed to get urb length:%d\n", urb->actual_length); - if (skb) - dev_kfree_skb_any(skb); + skb_queue_tail(&rtwusb->rx_free_queue, skb); } else { skb_put(skb, urb->actual_length); skb_queue_tail(&rtwusb->rx_queue, skb); queue_work(rtwusb->rxwq, &rtwusb->rx_work); } - rtw_usb_rx_resubmit(rtwusb, rxcb); + rtw_usb_rx_resubmit(rtwusb, rxcb, GFP_ATOMIC); } else { + skb_queue_tail(&rtwusb->rx_free_queue, skb); + switch (urb->status) { case -EINVAL: case -EPIPE: @@ -679,8 +718,6 @@ static void rtw_usb_read_port_complete(struct urb *urb) rtw_err(rtwdev, "status %d\n", urb->status); break; } - if (skb) - dev_kfree_skb_any(skb); } } @@ -868,16 +905,26 @@ static struct rtw_hci_ops rtw_usb_ops = { static int rtw_usb_init_rx(struct rtw_dev *rtwdev) { struct rtw_usb *rtwusb = rtw_get_usb_priv(rtwdev); + struct sk_buff *rx_skb; + int i; - rtwusb->rxwq = create_singlethread_workqueue("rtw88_usb: rx wq"); + rtwusb->rxwq = alloc_workqueue("rtw88_usb: rx wq", WQ_BH, 0); if (!rtwusb->rxwq) { rtw_err(rtwdev, "failed to create RX work queue\n"); return -ENOMEM; } skb_queue_head_init(&rtwusb->rx_queue); + skb_queue_head_init(&rtwusb->rx_free_queue); INIT_WORK(&rtwusb->rx_work, rtw_usb_rx_handler); + INIT_WORK(&rtwusb->rx_urb_work, rtw_usb_rx_resubmit_work); + + for (i = 0; i < RTW_USB_RX_SKB_NUM; i++) { + rx_skb = alloc_skb(RTW_USB_MAX_RECVBUF_SZ, GFP_KERNEL); + if (rx_skb) + skb_queue_tail(&rtwusb->rx_free_queue, rx_skb); + } return 0; } @@ -890,7 +937,7 @@ static void rtw_usb_setup_rx(struct rtw_dev *rtwdev) for (i = 0; i < RTW_USB_RXCB_NUM; i++) { struct rx_usb_ctrl_block *rxcb = &rtwusb->rx_cb[i]; - rtw_usb_rx_resubmit(rtwusb, rxcb); + rtw_usb_rx_resubmit(rtwusb, rxcb, GFP_KERNEL); } } @@ -902,6 +949,8 @@ static void rtw_usb_deinit_rx(struct rtw_dev *rtwdev) flush_workqueue(rtwusb->rxwq); destroy_workqueue(rtwusb->rxwq); + + skb_queue_purge(&rtwusb->rx_free_queue); } static int rtw_usb_init_tx(struct rtw_dev *rtwdev) diff --git a/drivers/net/wireless/realtek/rtw88/usb.h b/drivers/net/wireless/realtek/rtw88/usb.h index 86697a5c0103..9b695b688b24 100644 --- a/drivers/net/wireless/realtek/rtw88/usb.h +++ b/drivers/net/wireless/realtek/rtw88/usb.h @@ -38,6 +38,7 @@ #define RTW_USB_RXAGG_TIMEOUT 10 #define RTW_USB_RXCB_NUM 4 +#define RTW_USB_RX_SKB_NUM 8 #define RTW_USB_EP_MAX 4 @@ -81,7 +82,9 @@ struct rtw_usb { struct rx_usb_ctrl_block rx_cb[RTW_USB_RXCB_NUM]; struct sk_buff_head rx_queue; + struct sk_buff_head rx_free_queue; struct work_struct rx_work; + struct work_struct rx_urb_work; }; static inline struct rtw_usb_tx_data *rtw_usb_get_tx_data(struct sk_buff *skb)