rtnet rt_igb I210 not working with ARM
Yann Le Chevoir
yann.lechevoir at cae.com
Tue Mar 29 20:42:19 CEST 2022
> > I finally have something working with the patch bellow.
> > So:
> > - pci=nomsi to have the irq counter incrementing.
> > - dma_sync_single_for_device in igb_tx_map to have rt_igb sending
> > good data.
> > My questions:
> > What are your feeling about that?
> > Is dma_sync real-time? Is it a good fix/workaround?
> In the best case, it's just a barrier (but there is already a wmb()). In the worst
> case, Linux code is triggered that actually does more, e.g.
> because DMA is not cache-coherent. You will have to analyze what is actually
> done in that function on your platform.
> > Why do I need to add such a dma_sync with my arm SoC?
> > - I suspect that this driver would work on a regular x86...
> > - Can you tell if it works on other arm SoC?
> I don't think this was tried on ARM so far, but then the topic will actually be
> rather SoC-specific.
Maybe worth mentioning for those who face the same problem:
I did not go deeper with the DMA yet. I was happy with the tx performances.
But I faced a different issue with the rx, with 1 packets over 500 which was lost at high frequency.
I got to do a similar patch (dma_sync) for the rx. See below (tx + rx). That works for me and performances are validated.
@@ -4143,6 +4143,7 @@ static void igb_tx_map(struct igb_ring *tx_ring,
* We also need this memory barrier to make certain all of the
* status bits have been updated before next_to_watch is written.
+ dma_sync_single_for_device(tx_ring->dev, dma, size, DMA_TO_DEVICE);
@@ -4764,13 +4765,19 @@ static struct rtskb *igb_fetch_rx_buffer(struct igb_ring *rx_ring,
struct igb_rx_buffer *rx_buffer;
struct rtskb *skb;
+ dma_addr_t dma;
+ unsigned int size;
rx_buffer = &rx_ring->rx_buffer_info[rx_ring->next_to_clean];
skb = rx_buffer->skb;
+ dma = rtskb_data_dma_addr(skb, 0);
+ size = le16_to_cpu(rx_desc->wb.upper.length);
+ dma_sync_single_for_cpu(rx_ring->dev, dma, size, DMA_FROM_DEVICE);
/* pull the header of the skb in */
- rtskb_put(skb, le16_to_cpu(rx_desc->wb.upper.length));
+ rtskb_put(skb, size);
rx_buffer->skb = NULL;
rx_buffer->dma = 0;
More information about the Xenomai