mirror of
https://github.com/AuxXxilium/linux_dsm_epyc7002.git
synced 2024-12-23 02:54:10 +07:00
2b9aecdce2
The RX buffer split causes packet loss in the hardware: What happens is: RX Packet 1 --> message buffer 1 (newdat bit is not cleared) RX Packet 2 --> message buffer 2 (newdat bit is not cleared) RX Packet 3 --> message buffer 3 (newdat bit is not cleared) RX Packet 4 --> message buffer 4 (newdat bit is not cleared) RX Packet 5 --> message buffer 5 (newdat bit is not cleared) RX Packet 6 --> message buffer 6 (newdat bit is not cleared) RX Packet 7 --> message buffer 7 (newdat bit is not cleared) RX Packet 8 --> message buffer 8 (newdat bit is not cleared) Clear newdat bit in message buffer 1 Clear newdat bit in message buffer 2 Clear newdat bit in message buffer 3 Clear newdat bit in message buffer 4 Clear newdat bit in message buffer 5 Clear newdat bit in message buffer 6 Clear newdat bit in message buffer 7 Clear newdat bit in message buffer 8 Now if during that clearing of newdat bits, a new message comes in, the HW gets confused and drops it. It does not matter how many of them you clear. I put a delay between clear of buffer 1 and buffer 2 which was long enough that the message should have been queued either in buffer 1 or buffer 9. But it did not show up anywhere. The next message ended up in buffer 1. So the hardware lost a packet of course without telling it via one of the error handlers. That does not happen on all clear newdat bit events. I see one of 10k packets dropped in the scenario which allows us to reproduce. But the trace looks always the same. Not splitting the RX Buffer avoids the packet loss but can cause reordering. It's hard to trigger, but it CAN happen. With that mode we use the HW as it was probably designed for. We read from the buffer 1 upwards and clear the buffer as we get the message. That's how all microcontrollers use it. So I assume that the way we handle the buffers was never really tested. According to the public documentation it should just work :) Let the user decide which evil is the lesser one. [ Oliver Hartkopp: Provided a sane config option and help text and made me switch to favour potential and unlikely reordering over packet loss ] Signed-off-by: Thomas Gleixner <tglx@linutronix.de> Tested-by: Alexander Stein <alexander.stein@systec-electronic.com> Signed-off-by: Marc Kleine-Budde <mkl@pengutronix.de>
31 lines
1.0 KiB
Plaintext
31 lines
1.0 KiB
Plaintext
menuconfig CAN_C_CAN
|
|
tristate "Bosch C_CAN/D_CAN devices"
|
|
depends on HAS_IOMEM
|
|
|
|
if CAN_C_CAN
|
|
|
|
config CAN_C_CAN_PLATFORM
|
|
tristate "Generic Platform Bus based C_CAN/D_CAN driver"
|
|
---help---
|
|
This driver adds support for the C_CAN/D_CAN chips connected
|
|
to the "platform bus" (Linux abstraction for directly to the
|
|
processor attached devices) which can be found on various
|
|
boards from ST Microelectronics (http://www.st.com) like the
|
|
SPEAr1310 and SPEAr320 evaluation boards & TI (www.ti.com)
|
|
boards like am335x, dm814x, dm813x and dm811x.
|
|
|
|
config CAN_C_CAN_STRICT_FRAME_ORDERING
|
|
bool "Force a strict RX CAN frame order (may cause frame loss)"
|
|
---help---
|
|
The RX split buffer prevents packet reordering but can cause packet
|
|
loss. Only enable this option when you accept to lose CAN frames
|
|
in favour of getting the received CAN frames in the correct order.
|
|
|
|
config CAN_C_CAN_PCI
|
|
tristate "Generic PCI Bus based C_CAN/D_CAN driver"
|
|
depends on PCI
|
|
---help---
|
|
This driver adds support for the C_CAN/D_CAN chips connected
|
|
to the PCI bus.
|
|
endif
|