On 2024-05-10 16:21, Mina Almasry wrote:
+/* This returns the absolute dma_addr_t calculated from
- net_iov_owner(niov)->owner->base_dma_addr, not the page_pool-owned
- niov->dma_addr.
- The absolute dma_addr_t is a dma_addr_t that is always uncompressed.
- The page_pool-owner niov->dma_addr is the absolute dma_addr compressed into
- an unsigned long. Special handling is done when the unsigned long is 32-bit
- but the dma_addr_t is 64-bit.
- In general code looking for the dma_addr_t should use net_iov_dma_addr(),
- while page_pool code looking for the unsigned long dma_addr which mirrors
- the field in struct page should use niov->dma_addr.
- */
+static inline dma_addr_t net_iov_dma_addr(const struct net_iov *niov) +{
- struct dmabuf_genpool_chunk_owner *owner = net_iov_owner(niov);
- return owner->base_dma_addr +
((dma_addr_t)net_iov_idx(niov) << PAGE_SHIFT);
+}
This part feels like devmem TCP specific, yet the function is in netmem.h. Please consider moving it into devmem.{h,c} which makes it less likely that people not reading your comment will try using it.
+static inline struct net_devmem_dmabuf_binding * +net_iov_binding(const struct net_iov *niov) +{
- return net_iov_owner(niov)->binding;
+}
/* netmem */ /** diff --git a/net/core/devmem.c b/net/core/devmem.c index d82f92d7cf9ce..1f90e23a81441 100644 --- a/net/core/devmem.c +++ b/net/core/devmem.c @@ -54,6 +54,42 @@ void __net_devmem_dmabuf_binding_free(struct net_devmem_dmabuf_binding *binding) kfree(binding); } +struct net_iov * +net_devmem_alloc_dmabuf(struct net_devmem_dmabuf_binding *binding) +{
- struct dmabuf_genpool_chunk_owner *owner;
- unsigned long dma_addr;
- struct net_iov *niov;
- ssize_t offset;
- ssize_t index;
- dma_addr = gen_pool_alloc_owner(binding->chunk_pool, PAGE_SIZE,
(void **)&owner);
- if (!dma_addr)
return NULL;
- offset = dma_addr - owner->base_dma_addr;
- index = offset / PAGE_SIZE;
- niov = &owner->niovs[index];
- niov->dma_addr = 0;
- net_devmem_dmabuf_binding_get(binding);
- return niov;
+}
+void net_devmem_free_dmabuf(struct net_iov *niov) +{
- struct net_devmem_dmabuf_binding *binding = net_iov_binding(niov);
- unsigned long dma_addr = net_iov_dma_addr(niov);
- if (gen_pool_has_addr(binding->chunk_pool, dma_addr, PAGE_SIZE))
gen_pool_free(binding->chunk_pool, dma_addr, PAGE_SIZE);
- net_devmem_dmabuf_binding_put(binding);
+}
/* Protected by rtnl_lock() */ static DEFINE_XARRAY_FLAGS(net_devmem_dmabuf_bindings, XA_FLAGS_ALLOC1);