rtl8139: keep Tx command mode 0 and 1 separate

There are two Tx Descriptor formats called mode 0 and mode 1. The mode
is determined by the Large Send bit.

CP_TX_IPCS (bit 18) is defined in mode 1 but the code checks the bit
unconditionally. In mode 0 bit 18 is part of the Large Send MSS value.

Explicitly check the Large Send bit to distinguish Tx command modes.
This avoids bugs where modes are confused. Note that I didn't find any
actual bugs aside from needlessly computing the IP checksum when the
Large Send bit is enabled.

Acked-by: Jason Wang <jasowang@redhat.com>
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
Signed-off-by: Stefan Hajnoczi <stefanha@redhat.com>
Message-Id: <20221117165554.1773409-3-stefanha@redhat.com>
This commit is contained in:
Stefan Hajnoczi 2022-11-17 11:55:53 -05:00
parent bd142b2391
commit c74831a02c

View File

@ -2135,7 +2135,7 @@ static int rtl8139_cplus_transmit_one(RTL8139State *s)
} }
ip_data_len -= hlen; ip_data_len -= hlen;
if (txdw0 & CP_TX_IPCS) if (!(txdw0 & CP_TX_LGSEN) && (txdw0 & CP_TX_IPCS))
{ {
DPRINTF("+++ C+ mode need IP checksum\n"); DPRINTF("+++ C+ mode need IP checksum\n");
@ -2268,7 +2268,7 @@ static int rtl8139_cplus_transmit_one(RTL8139State *s)
/* Stop sending this frame */ /* Stop sending this frame */
saved_size = 0; saved_size = 0;
} }
else if (txdw0 & (CP_TX_TCPCS|CP_TX_UDPCS)) else if (!(txdw0 & CP_TX_LGSEN) && (txdw0 & (CP_TX_TCPCS|CP_TX_UDPCS)))
{ {
DPRINTF("+++ C+ mode need TCP or UDP checksum\n"); DPRINTF("+++ C+ mode need TCP or UDP checksum\n");