86 lines
		
	
	
		
			3.4 KiB
		
	
	
	
		
			ReStructuredText
		
	
	
	
	
	
			
		
		
	
	
			86 lines
		
	
	
		
			3.4 KiB
		
	
	
	
		
			ReStructuredText
		
	
	
	
	
	
| .. SPDX-License-Identifier: GPL-2.0
 | |
| 
 | |
| ==================
 | |
| AF_XDP TX Metadata
 | |
| ==================
 | |
| 
 | |
| This document describes how to enable offloads when transmitting packets
 | |
| via :doc:`af_xdp`. Refer to :doc:`xdp-rx-metadata` on how to access similar
 | |
| metadata on the receive side.
 | |
| 
 | |
| General Design
 | |
| ==============
 | |
| 
 | |
| The headroom for the metadata is reserved via ``tx_metadata_len`` and
 | |
| ``XDP_UMEM_TX_METADATA_LEN`` flag in ``struct xdp_umem_reg``. The metadata
 | |
| length is therefore the same for every socket that shares the same umem.
 | |
| The metadata layout is a fixed UAPI, refer to ``union xsk_tx_metadata`` in
 | |
| ``include/uapi/linux/if_xdp.h``. Thus, generally, the ``tx_metadata_len``
 | |
| field above should contain ``sizeof(union xsk_tx_metadata)``.
 | |
| 
 | |
| Note that in the original implementation the ``XDP_UMEM_TX_METADATA_LEN``
 | |
| flag was not required. Applications might attempt to create a umem
 | |
| with a flag first and if it fails, do another attempt without a flag.
 | |
| 
 | |
| The headroom and the metadata itself should be located right before
 | |
| ``xdp_desc->addr`` in the umem frame. Within a frame, the metadata
 | |
| layout is as follows::
 | |
| 
 | |
|            tx_metadata_len
 | |
|      /                         \
 | |
|     +-----------------+---------+----------------------------+
 | |
|     | xsk_tx_metadata | padding |          payload           |
 | |
|     +-----------------+---------+----------------------------+
 | |
|                                 ^
 | |
|                                 |
 | |
|                           xdp_desc->addr
 | |
| 
 | |
| An AF_XDP application can request headrooms larger than ``sizeof(struct
 | |
| xsk_tx_metadata)``. The kernel will ignore the padding (and will still
 | |
| use ``xdp_desc->addr - tx_metadata_len`` to locate
 | |
| the ``xsk_tx_metadata``). For the frames that shouldn't carry
 | |
| any metadata (i.e., the ones that don't have ``XDP_TX_METADATA`` option),
 | |
| the metadata area is ignored by the kernel as well.
 | |
| 
 | |
| The flags field enables the particular offload:
 | |
| 
 | |
| - ``XDP_TXMD_FLAGS_TIMESTAMP``: requests the device to put transmission
 | |
|   timestamp into ``tx_timestamp`` field of ``union xsk_tx_metadata``.
 | |
| - ``XDP_TXMD_FLAGS_CHECKSUM``: requests the device to calculate L4
 | |
|   checksum. ``csum_start`` specifies byte offset of where the checksumming
 | |
|   should start and ``csum_offset`` specifies byte offset where the
 | |
|   device should store the computed checksum.
 | |
| 
 | |
| Besides the flags above, in order to trigger the offloads, the first
 | |
| packet's ``struct xdp_desc`` descriptor should set ``XDP_TX_METADATA``
 | |
| bit in the ``options`` field. Also note that in a multi-buffer packet
 | |
| only the first chunk should carry the metadata.
 | |
| 
 | |
| Software TX Checksum
 | |
| ====================
 | |
| 
 | |
| For development and testing purposes its possible to pass
 | |
| ``XDP_UMEM_TX_SW_CSUM`` flag to ``XDP_UMEM_REG`` UMEM registration call.
 | |
| In this case, when running in ``XDK_COPY`` mode, the TX checksum
 | |
| is calculated on the CPU. Do not enable this option in production because
 | |
| it will negatively affect performance.
 | |
| 
 | |
| Querying Device Capabilities
 | |
| ============================
 | |
| 
 | |
| Every devices exports its offloads capabilities via netlink netdev family.
 | |
| Refer to ``xsk-flags`` features bitmask in
 | |
| ``Documentation/netlink/specs/netdev.yaml``.
 | |
| 
 | |
| - ``tx-timestamp``: device supports ``XDP_TXMD_FLAGS_TIMESTAMP``
 | |
| - ``tx-checksum``: device supports ``XDP_TXMD_FLAGS_CHECKSUM``
 | |
| 
 | |
| See ``tools/net/ynl/samples/netdev.c`` on how to query this information.
 | |
| 
 | |
| Example
 | |
| =======
 | |
| 
 | |
| See ``tools/testing/selftests/bpf/xdp_hw_metadata.c`` for an example
 | |
| program that handles TX metadata. Also see https://github.com/fomichev/xskgen
 | |
| for a more bare-bones example.
 |