162d03330SJakub Kicinski /* SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) */
262d03330SJakub Kicinski /* Copyright (C) 2015-2019 Netronome Systems, Inc. */
362d03330SJakub Kicinski 
462d03330SJakub Kicinski #ifndef _NFP_DP_NFD3_H_
562d03330SJakub Kicinski #define _NFP_DP_NFD3_H_
662d03330SJakub Kicinski 
762d03330SJakub Kicinski struct sk_buff;
862d03330SJakub Kicinski struct net_device;
962d03330SJakub Kicinski 
1062d03330SJakub Kicinski /* TX descriptor format */
1162d03330SJakub Kicinski 
1262d03330SJakub Kicinski #define NFD3_DESC_TX_EOP		BIT(7)
1362d03330SJakub Kicinski #define NFD3_DESC_TX_OFFSET_MASK	GENMASK(6, 0)
1462d03330SJakub Kicinski #define NFD3_DESC_TX_MSS_MASK		GENMASK(13, 0)
1562d03330SJakub Kicinski 
1662d03330SJakub Kicinski /* Flags in the host TX descriptor */
1762d03330SJakub Kicinski #define NFD3_DESC_TX_CSUM		BIT(7)
1862d03330SJakub Kicinski #define NFD3_DESC_TX_IP4_CSUM		BIT(6)
1962d03330SJakub Kicinski #define NFD3_DESC_TX_TCP_CSUM		BIT(5)
2062d03330SJakub Kicinski #define NFD3_DESC_TX_UDP_CSUM		BIT(4)
2162d03330SJakub Kicinski #define NFD3_DESC_TX_VLAN		BIT(3)
2262d03330SJakub Kicinski #define NFD3_DESC_TX_LSO		BIT(2)
2362d03330SJakub Kicinski #define NFD3_DESC_TX_ENCAP		BIT(1)
2462d03330SJakub Kicinski #define NFD3_DESC_TX_O_IP4_CSUM	BIT(0)
2562d03330SJakub Kicinski 
2662d03330SJakub Kicinski struct nfp_nfd3_tx_desc {
2762d03330SJakub Kicinski 	union {
2862d03330SJakub Kicinski 		struct {
2962d03330SJakub Kicinski 			u8 dma_addr_hi; /* High bits of host buf address */
3062d03330SJakub Kicinski 			__le16 dma_len;	/* Length to DMA for this desc */
3162d03330SJakub Kicinski 			u8 offset_eop;	/* Offset in buf where pkt starts +
3262d03330SJakub Kicinski 					 * highest bit is eop flag.
3362d03330SJakub Kicinski 					 */
3462d03330SJakub Kicinski 			__le32 dma_addr_lo; /* Low 32bit of host buf addr */
3562d03330SJakub Kicinski 
3662d03330SJakub Kicinski 			__le16 mss;	/* MSS to be used for LSO */
3762d03330SJakub Kicinski 			u8 lso_hdrlen;	/* LSO, TCP payload offset */
3862d03330SJakub Kicinski 			u8 flags;	/* TX Flags, see @NFD3_DESC_TX_* */
3962d03330SJakub Kicinski 			union {
4062d03330SJakub Kicinski 				struct {
4162d03330SJakub Kicinski 					u8 l3_offset; /* L3 header offset */
4262d03330SJakub Kicinski 					u8 l4_offset; /* L4 header offset */
4362d03330SJakub Kicinski 				};
4462d03330SJakub Kicinski 				__le16 vlan; /* VLAN tag to add if indicated */
4562d03330SJakub Kicinski 			};
4662d03330SJakub Kicinski 			__le16 data_len; /* Length of frame + meta data */
4762d03330SJakub Kicinski 		} __packed;
4862d03330SJakub Kicinski 		__le32 vals[4];
4962d03330SJakub Kicinski 		__le64 vals8[2];
5062d03330SJakub Kicinski 	};
5162d03330SJakub Kicinski };
5262d03330SJakub Kicinski 
5362d03330SJakub Kicinski /**
5462d03330SJakub Kicinski  * struct nfp_nfd3_tx_buf - software TX buffer descriptor
5562d03330SJakub Kicinski  * @skb:	normal ring, sk_buff associated with this buffer
5662d03330SJakub Kicinski  * @frag:	XDP ring, page frag associated with this buffer
5762d03330SJakub Kicinski  * @xdp:	XSK buffer pool handle (for AF_XDP)
5862d03330SJakub Kicinski  * @dma_addr:	DMA mapping address of the buffer
5962d03330SJakub Kicinski  * @fidx:	Fragment index (-1 for the head and [0..nr_frags-1] for frags)
6062d03330SJakub Kicinski  * @pkt_cnt:	Number of packets to be produced out of the skb associated
6162d03330SJakub Kicinski  *		with this buffer (valid only on the head's buffer).
6262d03330SJakub Kicinski  *		Will be 1 for all non-TSO packets.
6362d03330SJakub Kicinski  * @is_xsk_tx:	Flag if buffer is a RX buffer after a XDP_TX action and not a
6462d03330SJakub Kicinski  *		buffer from the TX queue (for AF_XDP).
6562d03330SJakub Kicinski  * @real_len:	Number of bytes which to be produced out of the skb (valid only
6662d03330SJakub Kicinski  *		on the head's buffer). Equal to skb->len for non-TSO packets.
6762d03330SJakub Kicinski  */
6862d03330SJakub Kicinski struct nfp_nfd3_tx_buf {
6962d03330SJakub Kicinski 	union {
7062d03330SJakub Kicinski 		struct sk_buff *skb;
7162d03330SJakub Kicinski 		void *frag;
7262d03330SJakub Kicinski 		struct xdp_buff *xdp;
7362d03330SJakub Kicinski 	};
7462d03330SJakub Kicinski 	dma_addr_t dma_addr;
7562d03330SJakub Kicinski 	union {
7662d03330SJakub Kicinski 		struct {
7762d03330SJakub Kicinski 			short int fidx;
7862d03330SJakub Kicinski 			u16 pkt_cnt;
7962d03330SJakub Kicinski 		};
8062d03330SJakub Kicinski 		struct {
8162d03330SJakub Kicinski 			bool is_xsk_tx;
8262d03330SJakub Kicinski 		};
8362d03330SJakub Kicinski 	};
8462d03330SJakub Kicinski 	u32 real_len;
8562d03330SJakub Kicinski };
8662d03330SJakub Kicinski 
8762d03330SJakub Kicinski void
8862d03330SJakub Kicinski nfp_nfd3_rx_csum(const struct nfp_net_dp *dp, struct nfp_net_r_vector *r_vec,
8962d03330SJakub Kicinski 		 const struct nfp_net_rx_desc *rxd,
9062d03330SJakub Kicinski 		 const struct nfp_meta_parsed *meta, struct sk_buff *skb);
9162d03330SJakub Kicinski bool
9262d03330SJakub Kicinski nfp_nfd3_parse_meta(struct net_device *netdev, struct nfp_meta_parsed *meta,
9362d03330SJakub Kicinski 		    void *data, void *pkt, unsigned int pkt_len, int meta_len);
9462d03330SJakub Kicinski void nfp_nfd3_tx_complete(struct nfp_net_tx_ring *tx_ring, int budget);
9562d03330SJakub Kicinski int nfp_nfd3_poll(struct napi_struct *napi, int budget);
966fd86efaSJakub Kicinski netdev_tx_t nfp_nfd3_tx(struct sk_buff *skb, struct net_device *netdev);
976fd86efaSJakub Kicinski bool
986fd86efaSJakub Kicinski nfp_nfd3_ctrl_tx_one(struct nfp_net *nn, struct nfp_net_r_vector *r_vec,
996fd86efaSJakub Kicinski 		     struct sk_buff *skb, bool old);
10062d03330SJakub Kicinski void nfp_nfd3_ctrl_poll(struct tasklet_struct *t);
10162d03330SJakub Kicinski void nfp_nfd3_rx_ring_fill_freelist(struct nfp_net_dp *dp,
10262d03330SJakub Kicinski 				    struct nfp_net_rx_ring *rx_ring);
10362d03330SJakub Kicinski void nfp_nfd3_xsk_tx_free(struct nfp_nfd3_tx_buf *txbuf);
10462d03330SJakub Kicinski int nfp_nfd3_xsk_poll(struct napi_struct *napi, int budget);
10562d03330SJakub Kicinski 
106*57f273adSHuanhuan Wang #ifndef CONFIG_NFP_NET_IPSEC
nfp_nfd3_ipsec_tx(struct nfp_nfd3_tx_desc * txd,struct sk_buff * skb)107*57f273adSHuanhuan Wang static inline void nfp_nfd3_ipsec_tx(struct nfp_nfd3_tx_desc *txd, struct sk_buff *skb)
108*57f273adSHuanhuan Wang {
109*57f273adSHuanhuan Wang }
110*57f273adSHuanhuan Wang #else
111*57f273adSHuanhuan Wang void nfp_nfd3_ipsec_tx(struct nfp_nfd3_tx_desc *txd, struct sk_buff *skb);
112*57f273adSHuanhuan Wang #endif
113*57f273adSHuanhuan Wang 
11462d03330SJakub Kicinski #endif
115