daniel-p-carvalho opened a new pull request, #20571:
URL: https://github.com/apache/nuttx/pull/20571

   ## Summary
   
   Fix the RX descriptor ring handling of the PIC32MZ Ethernet driver
   (`arch/mips/src/pic32mz/pic32mz_ethernet.c`). Under load the RX path
   delivered frames out of order, lost responses and, after an RX overflow,
   stopped receiving for good until `ifdown`/`ifup`.
   
   **Commit 1 – RX descriptor ring handling**
   
   - **BUFCDEC order.** `ETHSTAT.BUFCNT` was decremented before the descriptor
     was given back to the hardware. When the RX DMA has stopped on a
     descriptor because none was available, the decrement makes it fetch that
     descriptor again; it was still owned by software at that point, so the
     reception stalled. `BUFCDEC` is now written in `pic32mz_rxreturn()`,
     after the descriptor is returned with `EOWN` set. (Not found in public
     docs; this is the order used by the Microchip Harmony ETHMAC driver,
     whose `F_EthAppendBusyList()` notes that `BUFCDEC` must be written when
     the hardware sees a new descriptor with `EOWN=1`.)
   - **Ring order.** `pic32mz_rxdesc()` returned the first software owned
     descriptor of the array instead of the next one in ring order, so frames
     could be delivered out of order. A ring index (`pd_rxnext`) is now kept.
   - **Pending response.** When no TX descriptor was available for a response,
     `pic32mz_response()` left it pending in `d_buf`, but `pic32mz_rxdone()`
     kept receiving into `d_buf` and then freed it. RX processing now stops
     while a response is pending and resumes after `pic32mz_txdone()` sends
     it. `pic32mz_txavail_work()` no longer polls over a pending response, and
     `pic32mz_ifup()` drops it.
   - The RX descriptors are also processed on `RXOVFLW` and `RXBUFNA` events,
     so they are given back to the hardware.
   
   **Commit 2 – TX done assertion**
   
   `pic32mz_txdone()` asserted that the next TX descriptor is available before
   freeing the buffers of the transmitted descriptors, but `pic32mz_txdesc()`
   only reports a descriptor as available once its buffer was freed, so with
   `CONFIG_DEBUG_ASSERTIONS` the assertion failed as soon as the TX ring
   wrapped around. It is now checked after the buffers are freed.
   
   ## Impact
   
   * PIC32MZ Ethernet driver only (shared by the PIC32MZ EC/EF and W1
     boards). No Kconfig, API or documentation change.
   * RX throughput and reliability under load; the TX abort interrupts seen
     before (~4% of frames) are also gone.
   
   ## Testing
   
   Host: Ubuntu Linux x86_64, USB Ethernet adapter connected directly to the
   board (100 Mbit/s full duplex), host 10.0.0.1, board 10.0.0.2.
   
   **Hardware:** board derived from the Microchip EV49N51A (PIC32MZ-W1,
   LAN8720A), `ev49n51a:netnsh` with the default `PIC32MZ_ETH_NRXDESC=4` /
   `PIC32MZ_ETH_NTXDESC=2`, plus `CONFIG_NETUTILS_IPERF`,
   `CONFIG_NET_STATISTICS`, `CONFIG_NETDEV_STATISTICS`. XC32 v6.00.
   
   Board: `iperf -s -B 10.0.0.2 &` / `iperf -s -u -B 10.0.0.2 &`; host:
   `iperf -c 10.0.0.2 [-u -b <rate>] -t 10`, `ss -tin dst 10.0.0.2`.
   
   | Test | Before | After |
   |---|---|---|
   | TCP host → board | 0.1–1.4 Mbit/s, 13% retransmissions, reordering | 28 
Mbit/s, no retransmissions, no reordering |
   | TCP board → host (`iperf -c 10.0.0.1 -B 10.0.0.2`) | – | 47 Mbit/s |
   | UDP 50 Mbit/s host → board | ~2 Mbit/s received, then RX dead until 
`ifdown`/`ifup` | 52 Mbit/s received |
   | UDP 95 Mbit/s flood (5×), then ping | – | RX overruns during the flood 
(expected with 4 descriptors), 0% ping loss afterwards |
   | `ifconfig eth0` TX errors | TX abort on ~4% of frames | 0 |
   
   The same tests passed with `CONFIG_DEBUG_ASSERTIONS=y` (which hit the TX
   done assertion before commit 2).
   
   Builds: `ev49n51a:netnsh` with XC32 v6.00 and with the Pinguino p32-gcc
   toolchain used by CI (also with assertions enabled). `checkpatch.sh -g`
   passes on both commits.
   


-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: [email protected]

For queries about this service, please contact Infrastructure at:
[email protected]

Reply via email to