From 4a69d77b388cc42e7cedae419eb6ca56d82794d1 Mon Sep 17 00:00:00 2001 From: raul_chen Date: Mon, 13 Jul 2026 14:38:05 +0800 Subject: [PATCH] arch/arm/ameba: tune WHC Wi-Fi TCP throughput on both boards Tune the TCP stack and driver resources for the WHC Wi-Fi data path on both rtl8720f_evb and pke8721daf (NuttX runs on the application core; the Wi-Fi MAC runs on a companion core reached over an on-chip IPC): - Cap the advertised TCP receive window (NET_RECV_BUFSIZE=10000) to about the out-of-order reassembly capacity and bound in-flight TX (NET_SEND_BUFSIZE=16384). The stock unbounded window/queue let the peer and the local stack burst far more than the Wi-Fi path can smooth, causing bursty loss/reordering and RTO stalls (RX), and starving incoming-ACK processing so the peer window collapses and spurious retransmits tear the link down (TX). - Keep out-of-order reassembly (NET_TCP_OUT_OF_ORDER) but disable selective ACK. PR #19353 enabled NET_TCP_SELECTIVE_ACK on both boards; on the lossy Wi-Fi TX path the sender-side selective-ACK recovery does not reliably repair multi-segment holes and stalls TX, so NewReno with out-of-order reassembly is used instead -- same steady-state throughput, robust recovery. - Widen IOB buffers to 512 bytes; the window and out-of-order buffers draw from the shared IOB pool at run time and add no static memory. - Drop the busy-wait retry in the transmit path (the send-buffer cap makes it dead code) and lower the forced host TX skb count (skb_num_ap) to 8, which covers the NP's transient TX backlog without over-reserving AP heap. Signed-off-by: raul_chen --- arch/arm/src/common/ameba/ameba_wlan.c | 9 +++++++-- arch/arm/src/common/ameba/wifi/ameba_wifi.c | 18 ++++++++++-------- .../rtl8720f_evb/configs/nsh/defconfig | 7 +++++-- .../rtl8721dx/pke8721daf/configs/nsh/defconfig | 7 +++++-- 4 files changed, 27 insertions(+), 14 deletions(-) diff --git a/arch/arm/src/common/ameba/ameba_wlan.c b/arch/arm/src/common/ameba/ameba_wlan.c index 48f15d6ecef..fa6622cfa00 100644 --- a/arch/arm/src/common/ameba/ameba_wlan.c +++ b/arch/arm/src/common/ameba/ameba_wlan.c @@ -226,8 +226,13 @@ static int ameba_wlan_transmit(struct netdev_lowerhalf_s *dev, if (ret != 0) { - /* NP skb pool full: let the upper half recycle the packet and pause - * the poll (backpressure). Do NOT free here. + /* NP host skb pool full: recycle the packet (do NOT free) and + * let the upper half pause the poll -- genuine backpressure. + * This stays off the hot path because CONFIG_NET_SEND_BUFSIZE + * bounds a stream's in-flight data and the NP drains at line + * rate, so the transient host skb backlog stays well under the + * pool (skb_num_ap). A momentary full pool just pauses here and + * resumes on the next poll. */ return -EIO; diff --git a/arch/arm/src/common/ameba/wifi/ameba_wifi.c b/arch/arm/src/common/ameba/wifi/ameba_wifi.c index 0a9eba93013..75f23cd4ec5 100644 --- a/arch/arm/src/common/ameba/wifi/ameba_wifi.c +++ b/arch/arm/src/common/ameba/wifi/ameba_wifi.c @@ -108,17 +108,19 @@ int ameba_wifi_start(void) g_rtw_task_size.ipc_unblk_api_task = 4096; } - /* Host TX skb pool: the SDK default (4) is too small for sustained TCP - * TX. The pool drains, whc_ipc_host_send() returns -2 (drops the frame), - * TCP retransmits, and under load the retransmits exhaust and the link is - * torn down (send -> ENOTCONN). UDP tolerates the drops so is unaffected. - * A modest pool keeps TCP TX stable; 16 skbs ~= 27 KB of AP heap (vs 53 KB - * at 32). + /* Host TX skb pool: the SDK default (4) is too small for sustained + * TCP TX (the pool drains, whc_ipc_host_send() returns -2, the frame + * is dropped and TCP stalls). CONFIG_NET_SEND_BUFSIZE now bounds a + * stream's in-flight data and the NP drains at line rate, so the pool + * only has to cover the NP's transient TX backlog, not the whole + * window -- 8 skbs (~13 KB of AP heap) is enough here, well above the + * SDK stack's own high-throughput profile of 5. Raise if bulk TX + * regresses. */ - if (wifi_user_config.skb_num_ap < 16) + if (wifi_user_config.skb_num_ap < 8) { - wifi_user_config.skb_num_ap = 16; + wifi_user_config.skb_num_ap = 8; } whc_ipc_host_init(); diff --git a/boards/arm/rtl8720f/rtl8720f_evb/configs/nsh/defconfig b/boards/arm/rtl8720f/rtl8720f_evb/configs/nsh/defconfig index b18613f488f..f5a19d5f619 100644 --- a/boards/arm/rtl8720f/rtl8720f_evb/configs/nsh/defconfig +++ b/boards/arm/rtl8720f/rtl8720f_evb/configs/nsh/defconfig @@ -28,7 +28,7 @@ CONFIG_FS_PROCFS=y CONFIG_FS_TMPFS=y CONFIG_IDLETHREAD_STACKSIZE=4096 CONFIG_INIT_ENTRYPOINT="nsh_main" -CONFIG_IOB_BUFSIZE=400 +CONFIG_IOB_BUFSIZE=512 CONFIG_IOB_NBUFFERS=100 CONFIG_IOB_NCHAINS=36 CONFIG_IOB_THROTTLE=40 @@ -50,11 +50,14 @@ CONFIG_NET_ARP_IPIN=y CONFIG_NET_BROADCAST=y CONFIG_NET_ETH_PKTSIZE=1514 CONFIG_NET_ICMP_SOCKET=y +CONFIG_NET_RECV_BUFSIZE=10000 +CONFIG_NET_SEND_BUFSIZE=16384 CONFIG_NET_TCP=y CONFIG_NET_TCP_DELAYED_ACK=y CONFIG_NET_TCP_KEEPALIVE=y CONFIG_NET_TCP_NOTIFIER=y -CONFIG_NET_TCP_SELECTIVE_ACK=y +CONFIG_NET_TCP_OUT_OF_ORDER=y +CONFIG_NET_TCP_OUT_OF_ORDER_BUFSIZE=10000 CONFIG_NET_TCP_WRITE_BUFFERS=y CONFIG_NET_UDP=y CONFIG_NSH_BUILTIN_APPS=y diff --git a/boards/arm/rtl8721dx/pke8721daf/configs/nsh/defconfig b/boards/arm/rtl8721dx/pke8721daf/configs/nsh/defconfig index e50b5c94877..7ff53c25adb 100644 --- a/boards/arm/rtl8721dx/pke8721daf/configs/nsh/defconfig +++ b/boards/arm/rtl8721dx/pke8721daf/configs/nsh/defconfig @@ -28,7 +28,7 @@ CONFIG_FS_PROCFS=y CONFIG_FS_TMPFS=y CONFIG_IDLETHREAD_STACKSIZE=4096 CONFIG_INIT_ENTRYPOINT="nsh_main" -CONFIG_IOB_BUFSIZE=400 +CONFIG_IOB_BUFSIZE=512 CONFIG_IOB_NBUFFERS=100 CONFIG_IOB_NCHAINS=36 CONFIG_IOB_THROTTLE=40 @@ -50,11 +50,14 @@ CONFIG_NET_ARP_IPIN=y CONFIG_NET_BROADCAST=y CONFIG_NET_ETH_PKTSIZE=1514 CONFIG_NET_ICMP_SOCKET=y +CONFIG_NET_RECV_BUFSIZE=10000 +CONFIG_NET_SEND_BUFSIZE=16384 CONFIG_NET_TCP=y CONFIG_NET_TCP_DELAYED_ACK=y CONFIG_NET_TCP_KEEPALIVE=y CONFIG_NET_TCP_NOTIFIER=y -CONFIG_NET_TCP_SELECTIVE_ACK=y +CONFIG_NET_TCP_OUT_OF_ORDER=y +CONFIG_NET_TCP_OUT_OF_ORDER_BUFSIZE=10000 CONFIG_NET_TCP_WRITE_BUFFERS=y CONFIG_NET_UDP=y CONFIG_NSH_BUILTIN_APPS=y