[PATCH v8] net: airoha: npu: use cacheline-sized buffers for mailbox DMA

Daniel Pawlik pawlik.dan at gmail.com
Thu Aug 20 13:28:00 PDT 2026


Hi Kuba,
Fair point - the interesting part is the mechanism. I don't have the
EN7581 TRM, so I can't name the exact register. From ATF, DT, NPU
firmware, and the instrumented kernel path, the picture looks like this:

TL;DR: Sub-cacheline map length forces SWIOTLB on this non-coherent
arm64 setup. SWIOTLB sync/invalidation doesn't explain the failure -
the response never appears in the bounce buffer. Cache-line-aligned
streaming buffers avoid SWIOTLB entirely and the probe reads 0.1111. The
remaining question is why the NPU doesn't produce visible writes in
the bounce region (high phys ~0xFF6x vs vendor DMA pools ~0x84-0x91).

What's ruled out:
- No IOMMU/SMMU on this SoC; DMA addresses equal physical addresses.
- No EMI MPU - unlike MT7622/MT7986, the Airoha ATF [1] configures
  only TZPC (secure/non-secure for NPU SRAM and EFUSE), not DMA
  address ranges.
- No PMP in NPU firmware — disassembly of the RISC-V binary shows
  zero accesses to pmpcfg*/pmpaddr* CSRs.
- No dma-ranges in DT - the soc node uses identity-mapped ranges;
  the kernel sees no address translation for NPU DMA.
- set_memory_decrypted() on swiotlb pages is a no-op on standard
  arm64 (no CCA/memory encryption on EN7581).

What the bus fabric looks like:
The ATF bus test code [2] reveals the internal topology. Each DMA
engine has a dedicated port through the R2C (RBUS-to-DRAM converter)
bridge:

    port 0: GDMA/HSDMA
    port 1: PPE
    port 2: QDMA LAN (TX)
    port 3: QDMA WAN (TX)
    port 4: TDMA
    port 5: NPU

The RBUS also has a "DMA block" mechanism (0x1FA000EC) that
serializes CPU writes against DMA reads within 64B/128B-masked
regions, with per-engine block counters at 0x1FA000F4-0x1FA00108.

All vendor DMA buffers sit in one contiguous region:

    npu-binary:   0x84000000 (10MB)
    qdma0-buf:    0x87000000 (32MB)
    qdma1-buf:    0x89000000 (16MB)
    npu-pkt:      0x8A000000 (44MB)
    npu-txpkt:    0x8CC00000 (64MB)
    npu-txbufid:  0x90C00000
    npu-ba:       0x90C06800

The ATF bus test uses DRAM_TEST_BASE = 0x84000000 exclusively -
no test exercises DMA at high physical addresses.

The NPU reads the mailbox command from the swiotlb bounce address
(~0xFF6D0000) successfully - mbox_status returns success. But it
never writes the response back; the buffer stays zero, causing a
timeout.

Read-succeeds/write-fails at a high physical address, while all
production DMA stays in 0x84-0x91, points to the R2C bridge's
write path having a narrower address reach than the read path.
Whether that's an address decode window, a write-buffer range
check, or a port-specific routing constraint isn't visible in
the open-source ATF or kernel code - likely hardwired or set by
boot ROM before ATF runs.

So I suspect this is less "swiotlb unaligned-length sync is broken"
and more "this DMA master shouldn't be bounced to that DRAM region" -
but I can't prove the bridge/decode story without vendor docs.

Regards,
Dan

[1] https://github.com/Ansuel/atf-airoha
[2] atf-airoha/plat/ecnt/en7523/cpu_bus_bl2_test.c


czw., 20 sie 2026 o 19:18 Jakub Kicinski <kuba at kernel.org> napisał(a):
>
> On Thu, 20 Aug 2026 10:20:08 +0200 Daniel Pawlik wrote:
> > size=24 < cache_line=64 fails this regardless of address alignment.
> > The swiotlb sync code itself is fine, but the NPU cannot DMA-write to
> > the bounce buffer address range (it reads commands fine, never writes
> > responses back). This is probably an EN7581 platform limitation.
>
> Sure, that's pretty much what GPT told us some revisions ago.
> The question is why.



-- 
Z poważaniem,
Daniel Pawlik



More information about the Linux-mediatek mailing list