K-ANOY opened a new issue, #21111:
URL: https://github.com/apache/nuttx/issues/21111
### Description / Steps to reproduce the issue
In `drivers/net/ftmac100.c` (Faraday FTMAC100 10/100 MAC) the RX path
`memcpy`s the DMA-descriptor
frame length into the fixed packet buffer with no clamp against buffer
capacity. The bound is
**absent** in all build configurations (not assert-gated). This is an
out-of-bounds **write** of up
to ~1455 bytes of wire-controlled data past the per-interface packet buffer,
into adjacent interface
buffers / BSS. The attacker is a link peer (or a malfunctioning/compromised
MAC) that reports an
oversized RX frame length in the DMA descriptor status word.
`ftmac100_receive()` reads the RX frame length directly from the DMA
descriptor and `memcpy`s
that many bytes into the device packet buffer with no clamp against the
buffer capacity:
```c
/* drivers/net/ftmac100.c */
624 len = FTMAC100_RXDES0_RFL(rxdes->rxdes0); /* RX Frame Length from
DMA descriptor */
625 data = (FAR uint8_t *)rxdes->rxdes2; /* DMA RX buffer pointer
*/
...
635 memcpy(priv->ft_dev.d_buf, data, len); /* no clamp vs d_buf
capacity */
636 priv->ft_dev.d_len = len;
```
`FTMAC100_RXDES0_RFL` (`include/nuttx/net/ftmac100.h:118`) is `((des) &
0x7ff)`, i.e. a value
of **0..2047** taken verbatim from the descriptor status word the MAC/DMA
writes.
The destination `priv->ft_dev.d_buf` is `g_pktbuf[intf]`
(`ftmac100.c:180,1353`), sized
`PKTBUF_SIZE = MAX_NETDEV_PKTSIZE + CONFIG_NET_GUARDSIZE`. With the default
`CONFIG_NET_ETH_PKTSIZE = 590` (`include/nuttx/net/netconfig.h:207`) the
buffer is ~592 bytes,
so a reported length up to 2047 overflows it by up to ~1455 bytes.
There is **no length check at all** — not even a `DEBUGASSERT` — between the
RFL read at `:624`
and the `memcpy` at `:635`. `ftmac100_receive()` runs off the RX interrupt
work path for every
received frame; the length field is attacker/wire controlled and no
userspace `open()`/`read()` is
required. Gated by `CONFIG_FTMAC100` (e.g. QEMU/moxart, k210-class targets).
**Why this is a bug (smoking gun):** a sibling MAC driver rejects the
oversized length.
`drivers/net/encx24j600.c:1620-1628` reads the hardware RX status-vector
length and drops the
frame when it is out of range:
```c
else if (pktlen > (CONFIG_NET_ETH_PKTSIZE + 4) || pktlen <= (ETH_HDRLEN + 4))
{ nerr("Bad packet size dropped"); enc_rxrmpkt(...); NETDEV_RXERRORS(...);
}
```
ftmac100 omits this equivalent bounds check on the same kind of
device-reported RX length.
Note the precondition is modest: the destination is only ~592 bytes (default
config) while the RFL
field allows up to 2047 and the DMA RX region is 2044 bytes, so **any
ordinary receivable frame larger
than ~592 bytes** (a normal ~1000-byte Ethernet frame) already overflows via
the unchecked `memcpy` —
no forged 2000-byte giant frame is required. The ~1455-byte figure is just
the worst case
(`2047 - 592`).
Steps:
1. Build with `CONFIG_FTMAC100` and bring up the interface.
2. From a link peer (or a malfunctioning/compromised MAC) deliver/report an
RX frame larger than the
~592-byte `d_buf` — an ordinary ~1000-byte Ethernet frame suffices; up to
2047 is possible.
3. `ftmac100_receive()` `memcpy`s that many bytes into the ~592-byte
`g_pktbuf`, overflowing it.
An AddressSanitizer build with the RFL mask (`0x7ff`), the 592-byte
`g_pktbuf`, and an unclamped
`memcpy` of a normal oversize frame (e.g. `len=1000`) reports:
```
heap-buffer-overflow WRITE past the 592-byte region
```
**Suggested fix:** before the `memcpy`, reject or clamp the reported length,
mirroring the
encx24j600 check:
```c
if (len > CONFIG_NET_ETH_PKTSIZE || len <= ETH_HDRLEN)
{
NETDEV_RXERRORS(&priv->ft_dev);
/* drop the frame, advance the descriptor */
}
```
### On which OS does this issue occur?
[OS: Linux]
### What is the version of your OS?
ubuntu 22
### NuttX Version
master
### Issue Architecture
[Arch: all]
### Issue Area
[Area: Drivers]
### Host information
_No response_
### Verification
- [x] I have verified before submitting the report.
--
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]