1aaf4363eSJerin Jacob /* SPDX-License-Identifier: BSD-3-Clause 2aaf4363eSJerin Jacob * Copyright(c) 2017 Cavium, Inc 39e747589SJerin Jacob */ 49e747589SJerin Jacob 59e747589SJerin Jacob #ifndef __OCTEONTX_RXTX_H__ 69e747589SJerin Jacob #define __OCTEONTX_RXTX_H__ 79e747589SJerin Jacob 8df96fd0dSBruce Richardson #include <ethdev_driver.h> 99e747589SJerin Jacob 1085221a0cSHarman Kalra #define OFFLOAD_FLAGS \ 1185221a0cSHarman Kalra uint16_t rx_offload_flags; \ 1285221a0cSHarman Kalra uint16_t tx_offload_flags 1385221a0cSHarman Kalra 1485221a0cSHarman Kalra #define BIT(nr) (1UL << (nr)) 1585221a0cSHarman Kalra 1685221a0cSHarman Kalra #define OCCTX_RX_OFFLOAD_NONE (0) 17100f6992SHarman Kalra #define OCCTX_RX_MULTI_SEG_F BIT(0) 18100f6992SHarman Kalra #define OCCTX_RX_OFFLOAD_CSUM_F BIT(1) 19100f6992SHarman Kalra #define OCCTX_RX_VLAN_FLTR_F BIT(2) 2085221a0cSHarman Kalra 2185221a0cSHarman Kalra #define OCCTX_TX_OFFLOAD_NONE (0) 22100f6992SHarman Kalra #define OCCTX_TX_MULTI_SEG_F BIT(0) 23100f6992SHarman Kalra #define OCCTX_TX_OFFLOAD_L3_L4_CSUM_F BIT(1) 24100f6992SHarman Kalra #define OCCTX_TX_OFFLOAD_OL3_OL4_CSUM_F BIT(2) 255cbe1848SHarman Kalra #define OCCTX_TX_OFFLOAD_MBUF_NOFF_F BIT(3) 2685221a0cSHarman Kalra 27d0d65498SPavan Nikhilesh /* Packet type table */ 28d0d65498SPavan Nikhilesh #define PTYPE_SIZE OCCTX_PKI_LTYPE_LAST 29d0d65498SPavan Nikhilesh 30100f6992SHarman Kalra /* octeontx send header sub descriptor structure */ 31100f6992SHarman Kalra RTE_STD_C11 32100f6992SHarman Kalra union octeontx_send_hdr_w0_u { 33100f6992SHarman Kalra uint64_t u; 34100f6992SHarman Kalra struct { 35100f6992SHarman Kalra uint64_t total : 16; 36100f6992SHarman Kalra uint64_t markptr : 8; 37100f6992SHarman Kalra uint64_t l3ptr : 8; 38100f6992SHarman Kalra uint64_t l4ptr : 8; 39100f6992SHarman Kalra uint64_t ii : 1; 40100f6992SHarman Kalra uint64_t shp_dis : 1; 41100f6992SHarman Kalra uint64_t ckle : 1; 42100f6992SHarman Kalra uint64_t cklf : 2; 43100f6992SHarman Kalra uint64_t ckl3 : 1; 44100f6992SHarman Kalra uint64_t ckl4 : 2; 45100f6992SHarman Kalra uint64_t p : 1; 46100f6992SHarman Kalra uint64_t format : 7; 47100f6992SHarman Kalra uint64_t tstamp : 1; 48100f6992SHarman Kalra uint64_t tso_eom : 1; 49100f6992SHarman Kalra uint64_t df : 1; 50100f6992SHarman Kalra uint64_t tso : 1; 51100f6992SHarman Kalra uint64_t n2 : 1; 52100f6992SHarman Kalra uint64_t scntn1 : 3; 53100f6992SHarman Kalra }; 54100f6992SHarman Kalra }; 55100f6992SHarman Kalra 56100f6992SHarman Kalra RTE_STD_C11 57100f6992SHarman Kalra union octeontx_send_hdr_w1_u { 58100f6992SHarman Kalra uint64_t u; 59100f6992SHarman Kalra struct { 60100f6992SHarman Kalra uint64_t tso_mss : 14; 61100f6992SHarman Kalra uint64_t shp_ra : 2; 62100f6992SHarman Kalra uint64_t tso_sb : 8; 63100f6992SHarman Kalra uint64_t leptr : 8; 64100f6992SHarman Kalra uint64_t lfptr : 8; 65100f6992SHarman Kalra uint64_t shp_chg : 9; 66100f6992SHarman Kalra uint64_t tso_fn : 7; 67100f6992SHarman Kalra uint64_t l2len : 8; 68100f6992SHarman Kalra }; 69100f6992SHarman Kalra }; 70100f6992SHarman Kalra 71100f6992SHarman Kalra struct octeontx_send_hdr_s { 72100f6992SHarman Kalra union octeontx_send_hdr_w0_u w0; 73100f6992SHarman Kalra union octeontx_send_hdr_w1_u w1; 74100f6992SHarman Kalra }; 75100f6992SHarman Kalra 76d0d65498SPavan Nikhilesh static const uint32_t __rte_cache_aligned 77d0d65498SPavan Nikhilesh ptype_table[PTYPE_SIZE][PTYPE_SIZE][PTYPE_SIZE] = { 78d0d65498SPavan Nikhilesh [LC_NONE][LE_NONE][LF_NONE] = RTE_PTYPE_UNKNOWN, 79d0d65498SPavan Nikhilesh [LC_NONE][LE_NONE][LF_IPSEC_ESP] = RTE_PTYPE_UNKNOWN, 80d0d65498SPavan Nikhilesh [LC_NONE][LE_NONE][LF_IPFRAG] = RTE_PTYPE_L4_FRAG, 81d0d65498SPavan Nikhilesh [LC_NONE][LE_NONE][LF_IPCOMP] = RTE_PTYPE_UNKNOWN, 82d0d65498SPavan Nikhilesh [LC_NONE][LE_NONE][LF_TCP] = RTE_PTYPE_L4_TCP, 83d0d65498SPavan Nikhilesh [LC_NONE][LE_NONE][LF_UDP] = RTE_PTYPE_L4_UDP, 84d0d65498SPavan Nikhilesh [LC_NONE][LE_NONE][LF_GRE] = RTE_PTYPE_TUNNEL_GRE, 85d0d65498SPavan Nikhilesh [LC_NONE][LE_NONE][LF_UDP_GENEVE] = RTE_PTYPE_TUNNEL_GENEVE, 86d0d65498SPavan Nikhilesh [LC_NONE][LE_NONE][LF_UDP_VXLAN] = RTE_PTYPE_TUNNEL_VXLAN, 87d0d65498SPavan Nikhilesh [LC_NONE][LE_NONE][LF_NVGRE] = RTE_PTYPE_TUNNEL_NVGRE, 88d0d65498SPavan Nikhilesh 89d0d65498SPavan Nikhilesh [LC_IPV4][LE_NONE][LF_NONE] = RTE_PTYPE_L3_IPV4 | RTE_PTYPE_UNKNOWN, 90d0d65498SPavan Nikhilesh [LC_IPV4][LE_NONE][LF_IPSEC_ESP] = 91d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV4 | RTE_PTYPE_L3_IPV4, 92d0d65498SPavan Nikhilesh [LC_IPV4][LE_NONE][LF_IPFRAG] = RTE_PTYPE_L3_IPV4 | RTE_PTYPE_L4_FRAG, 93d0d65498SPavan Nikhilesh [LC_IPV4][LE_NONE][LF_IPCOMP] = RTE_PTYPE_L3_IPV4 | RTE_PTYPE_UNKNOWN, 94d0d65498SPavan Nikhilesh [LC_IPV4][LE_NONE][LF_TCP] = RTE_PTYPE_L3_IPV4 | RTE_PTYPE_L4_TCP, 95d0d65498SPavan Nikhilesh [LC_IPV4][LE_NONE][LF_UDP] = RTE_PTYPE_L3_IPV4 | RTE_PTYPE_L4_UDP, 96d0d65498SPavan Nikhilesh [LC_IPV4][LE_NONE][LF_GRE] = RTE_PTYPE_L3_IPV4 | RTE_PTYPE_TUNNEL_GRE, 97d0d65498SPavan Nikhilesh [LC_IPV4][LE_NONE][LF_UDP_GENEVE] = 98d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV4 | RTE_PTYPE_TUNNEL_GENEVE, 99d0d65498SPavan Nikhilesh [LC_IPV4][LE_NONE][LF_UDP_VXLAN] = 100d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV4 | RTE_PTYPE_TUNNEL_VXLAN, 101d0d65498SPavan Nikhilesh [LC_IPV4][LE_NONE][LF_NVGRE] = 102d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV4 | RTE_PTYPE_TUNNEL_NVGRE, 103d0d65498SPavan Nikhilesh 104d0d65498SPavan Nikhilesh [LC_IPV4_OPT][LE_NONE][LF_NONE] = 105d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV4_EXT | RTE_PTYPE_UNKNOWN, 106d0d65498SPavan Nikhilesh [LC_IPV4_OPT][LE_NONE][LF_IPSEC_ESP] = 107d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV4_EXT | RTE_PTYPE_L3_IPV4, 108d0d65498SPavan Nikhilesh [LC_IPV4_OPT][LE_NONE][LF_IPFRAG] = 109d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV4_EXT | RTE_PTYPE_L4_FRAG, 110d0d65498SPavan Nikhilesh [LC_IPV4_OPT][LE_NONE][LF_IPCOMP] = 111d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV4_EXT | RTE_PTYPE_UNKNOWN, 112d0d65498SPavan Nikhilesh [LC_IPV4_OPT][LE_NONE][LF_TCP] = 113d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV4_EXT | RTE_PTYPE_L4_TCP, 114d0d65498SPavan Nikhilesh [LC_IPV4_OPT][LE_NONE][LF_UDP] = 115d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV4_EXT | RTE_PTYPE_L4_UDP, 116d0d65498SPavan Nikhilesh [LC_IPV4_OPT][LE_NONE][LF_GRE] = 117d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV4_EXT | RTE_PTYPE_TUNNEL_GRE, 118d0d65498SPavan Nikhilesh [LC_IPV4_OPT][LE_NONE][LF_UDP_GENEVE] = 119d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV4_EXT | RTE_PTYPE_TUNNEL_GENEVE, 120d0d65498SPavan Nikhilesh [LC_IPV4_OPT][LE_NONE][LF_UDP_VXLAN] = 121d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV4_EXT | RTE_PTYPE_TUNNEL_VXLAN, 122d0d65498SPavan Nikhilesh [LC_IPV4_OPT][LE_NONE][LF_NVGRE] = 123d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV4_EXT | RTE_PTYPE_TUNNEL_NVGRE, 124d0d65498SPavan Nikhilesh 125d0d65498SPavan Nikhilesh [LC_IPV6][LE_NONE][LF_NONE] = RTE_PTYPE_L3_IPV6 | RTE_PTYPE_UNKNOWN, 126d0d65498SPavan Nikhilesh [LC_IPV6][LE_NONE][LF_IPSEC_ESP] = 127d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV6 | RTE_PTYPE_L3_IPV4, 128d0d65498SPavan Nikhilesh [LC_IPV6][LE_NONE][LF_IPFRAG] = RTE_PTYPE_L3_IPV6 | RTE_PTYPE_L4_FRAG, 129d0d65498SPavan Nikhilesh [LC_IPV6][LE_NONE][LF_IPCOMP] = RTE_PTYPE_L3_IPV6 | RTE_PTYPE_UNKNOWN, 130d0d65498SPavan Nikhilesh [LC_IPV6][LE_NONE][LF_TCP] = RTE_PTYPE_L3_IPV6 | RTE_PTYPE_L4_TCP, 131d0d65498SPavan Nikhilesh [LC_IPV6][LE_NONE][LF_UDP] = RTE_PTYPE_L3_IPV6 | RTE_PTYPE_L4_UDP, 132d0d65498SPavan Nikhilesh [LC_IPV6][LE_NONE][LF_GRE] = RTE_PTYPE_L3_IPV6 | RTE_PTYPE_TUNNEL_GRE, 133d0d65498SPavan Nikhilesh [LC_IPV6][LE_NONE][LF_UDP_GENEVE] = 134d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV6 | RTE_PTYPE_TUNNEL_GENEVE, 135d0d65498SPavan Nikhilesh [LC_IPV6][LE_NONE][LF_UDP_VXLAN] = 136d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV6 | RTE_PTYPE_TUNNEL_VXLAN, 137d0d65498SPavan Nikhilesh [LC_IPV6][LE_NONE][LF_NVGRE] = 138d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV4 | RTE_PTYPE_TUNNEL_NVGRE, 139d0d65498SPavan Nikhilesh [LC_IPV6_OPT][LE_NONE][LF_NONE] = 140d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV6_EXT | RTE_PTYPE_UNKNOWN, 141d0d65498SPavan Nikhilesh [LC_IPV6_OPT][LE_NONE][LF_IPSEC_ESP] = 142d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV6_EXT | RTE_PTYPE_L3_IPV4, 143d0d65498SPavan Nikhilesh [LC_IPV6_OPT][LE_NONE][LF_IPFRAG] = 144d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV6_EXT | RTE_PTYPE_L4_FRAG, 145d0d65498SPavan Nikhilesh [LC_IPV6_OPT][LE_NONE][LF_IPCOMP] = 146d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV6_EXT | RTE_PTYPE_UNKNOWN, 147d0d65498SPavan Nikhilesh [LC_IPV6_OPT][LE_NONE][LF_TCP] = 148d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV6_EXT | RTE_PTYPE_L4_TCP, 149d0d65498SPavan Nikhilesh [LC_IPV6_OPT][LE_NONE][LF_UDP] = 150d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV6_EXT | RTE_PTYPE_L4_UDP, 151d0d65498SPavan Nikhilesh [LC_IPV6_OPT][LE_NONE][LF_GRE] = 152d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV6_EXT | RTE_PTYPE_TUNNEL_GRE, 153d0d65498SPavan Nikhilesh [LC_IPV6_OPT][LE_NONE][LF_UDP_GENEVE] = 154d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV6_EXT | RTE_PTYPE_TUNNEL_GENEVE, 155d0d65498SPavan Nikhilesh [LC_IPV6_OPT][LE_NONE][LF_UDP_VXLAN] = 156d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV6_EXT | RTE_PTYPE_TUNNEL_VXLAN, 157d0d65498SPavan Nikhilesh [LC_IPV6_OPT][LE_NONE][LF_NVGRE] = 158d0d65498SPavan Nikhilesh RTE_PTYPE_L3_IPV6_EXT | RTE_PTYPE_TUNNEL_NVGRE, 159d0d65498SPavan Nikhilesh 160d0d65498SPavan Nikhilesh }; 161d0d65498SPavan Nikhilesh 1627f4116bdSHarman Kalra 1635cbe1848SHarman Kalra static __rte_always_inline uint64_t 1649eb5cb3bSHarman Kalra octeontx_pktmbuf_detach(struct rte_mbuf *m, struct rte_mbuf **m_tofree) 1655cbe1848SHarman Kalra { 1665cbe1848SHarman Kalra struct rte_mempool *mp = m->pool; 1675cbe1848SHarman Kalra uint32_t mbuf_size, buf_len; 1685cbe1848SHarman Kalra struct rte_mbuf *md; 1695cbe1848SHarman Kalra uint16_t priv_size; 1705cbe1848SHarman Kalra uint16_t refcount; 1715cbe1848SHarman Kalra 1725cbe1848SHarman Kalra /* Update refcount of direct mbuf */ 1735cbe1848SHarman Kalra md = rte_mbuf_from_indirect(m); 1749eb5cb3bSHarman Kalra /* The real data will be in the direct buffer, inform callers this */ 1759eb5cb3bSHarman Kalra *m_tofree = md; 1765cbe1848SHarman Kalra refcount = rte_mbuf_refcnt_update(md, -1); 1775cbe1848SHarman Kalra 1785cbe1848SHarman Kalra priv_size = rte_pktmbuf_priv_size(mp); 1795cbe1848SHarman Kalra mbuf_size = (uint32_t)(sizeof(struct rte_mbuf) + priv_size); 1805cbe1848SHarman Kalra buf_len = rte_pktmbuf_data_room_size(mp); 1815cbe1848SHarman Kalra 1825cbe1848SHarman Kalra m->priv_size = priv_size; 1835cbe1848SHarman Kalra m->buf_addr = (char *)m + mbuf_size; 1845cbe1848SHarman Kalra m->buf_iova = rte_mempool_virt2iova(m) + mbuf_size; 1855cbe1848SHarman Kalra m->buf_len = (uint16_t)buf_len; 1865cbe1848SHarman Kalra rte_pktmbuf_reset_headroom(m); 1875cbe1848SHarman Kalra m->data_len = 0; 1885cbe1848SHarman Kalra m->ol_flags = 0; 1895cbe1848SHarman Kalra m->next = NULL; 1905cbe1848SHarman Kalra m->nb_segs = 1; 1915cbe1848SHarman Kalra 1925cbe1848SHarman Kalra /* Now indirect mbuf is safe to free */ 1935cbe1848SHarman Kalra rte_pktmbuf_free(m); 1945cbe1848SHarman Kalra 1955cbe1848SHarman Kalra if (refcount == 0) { 1965cbe1848SHarman Kalra rte_mbuf_refcnt_set(md, 1); 1975cbe1848SHarman Kalra md->data_len = 0; 1985cbe1848SHarman Kalra md->ol_flags = 0; 1995cbe1848SHarman Kalra md->next = NULL; 2005cbe1848SHarman Kalra md->nb_segs = 1; 2015cbe1848SHarman Kalra return 0; 2025cbe1848SHarman Kalra } else { 2035cbe1848SHarman Kalra return 1; 2045cbe1848SHarman Kalra } 2055cbe1848SHarman Kalra } 2065cbe1848SHarman Kalra 2075cbe1848SHarman Kalra static __rte_always_inline uint64_t 2089eb5cb3bSHarman Kalra octeontx_prefree_seg(struct rte_mbuf *m, struct rte_mbuf **m_tofree) 2095cbe1848SHarman Kalra { 2105cbe1848SHarman Kalra if (likely(rte_mbuf_refcnt_read(m) == 1)) { 2115cbe1848SHarman Kalra if (!RTE_MBUF_DIRECT(m)) 2129eb5cb3bSHarman Kalra return octeontx_pktmbuf_detach(m, m_tofree); 2135cbe1848SHarman Kalra 2145cbe1848SHarman Kalra m->next = NULL; 2155cbe1848SHarman Kalra m->nb_segs = 1; 2165cbe1848SHarman Kalra return 0; 2175cbe1848SHarman Kalra } else if (rte_mbuf_refcnt_update(m, -1) == 0) { 2185cbe1848SHarman Kalra if (!RTE_MBUF_DIRECT(m)) 2199eb5cb3bSHarman Kalra return octeontx_pktmbuf_detach(m, m_tofree); 2205cbe1848SHarman Kalra 2215cbe1848SHarman Kalra rte_mbuf_refcnt_set(m, 1); 2225cbe1848SHarman Kalra m->next = NULL; 2235cbe1848SHarman Kalra m->nb_segs = 1; 2245cbe1848SHarman Kalra return 0; 2255cbe1848SHarman Kalra } 2265cbe1848SHarman Kalra 2275cbe1848SHarman Kalra /* Mbuf is having refcount more than 1 so need not to be freed */ 2285cbe1848SHarman Kalra return 1; 2295cbe1848SHarman Kalra } 2305cbe1848SHarman Kalra 231100f6992SHarman Kalra static __rte_always_inline void 232100f6992SHarman Kalra octeontx_tx_checksum_offload(uint64_t *cmd_buf, const uint16_t flags, 233100f6992SHarman Kalra struct rte_mbuf *m) 234100f6992SHarman Kalra { 235100f6992SHarman Kalra struct octeontx_send_hdr_s *send_hdr = 236100f6992SHarman Kalra (struct octeontx_send_hdr_s *)cmd_buf; 237100f6992SHarman Kalra uint64_t ol_flags = m->ol_flags; 238100f6992SHarman Kalra 239100f6992SHarman Kalra /* PKO Checksum L4 Algorithm Enumeration 240100f6992SHarman Kalra * 0x0 - No checksum 241100f6992SHarman Kalra * 0x1 - UDP L4 checksum 242100f6992SHarman Kalra * 0x2 - TCP L4 checksum 243100f6992SHarman Kalra * 0x3 - SCTP L4 checksum 244100f6992SHarman Kalra */ 245*daa02b5cSOlivier Matz const uint8_t csum = (!(((ol_flags ^ RTE_MBUF_F_TX_UDP_CKSUM) >> 52) & 0x3) + 246*daa02b5cSOlivier Matz (!(((ol_flags ^ RTE_MBUF_F_TX_TCP_CKSUM) >> 52) & 0x3) * 2) + 247*daa02b5cSOlivier Matz (!(((ol_flags ^ RTE_MBUF_F_TX_SCTP_CKSUM) >> 52) & 0x3) * 3)); 248100f6992SHarman Kalra 249*daa02b5cSOlivier Matz const uint8_t is_tunnel_parsed = (!!(ol_flags & RTE_MBUF_F_TX_TUNNEL_GTP) || 250*daa02b5cSOlivier Matz !!(ol_flags & RTE_MBUF_F_TX_TUNNEL_VXLAN_GPE) || 251*daa02b5cSOlivier Matz !!(ol_flags & RTE_MBUF_F_TX_TUNNEL_VXLAN) || 252*daa02b5cSOlivier Matz !!(ol_flags & RTE_MBUF_F_TX_TUNNEL_GRE) || 253*daa02b5cSOlivier Matz !!(ol_flags & RTE_MBUF_F_TX_TUNNEL_GENEVE) || 254*daa02b5cSOlivier Matz !!(ol_flags & RTE_MBUF_F_TX_TUNNEL_IP) || 255*daa02b5cSOlivier Matz !!(ol_flags & RTE_MBUF_F_TX_TUNNEL_IPIP)); 256100f6992SHarman Kalra 257*daa02b5cSOlivier Matz const uint8_t csum_outer = (!!(ol_flags & RTE_MBUF_F_TX_OUTER_UDP_CKSUM) || 258*daa02b5cSOlivier Matz !!(ol_flags & RTE_MBUF_F_TX_TUNNEL_UDP)); 259100f6992SHarman Kalra const uint8_t outer_l2_len = m->outer_l2_len; 260100f6992SHarman Kalra const uint8_t l2_len = m->l2_len; 261100f6992SHarman Kalra 262100f6992SHarman Kalra if ((flags & OCCTX_TX_OFFLOAD_OL3_OL4_CSUM_F) && 263100f6992SHarman Kalra (flags & OCCTX_TX_OFFLOAD_L3_L4_CSUM_F)) { 264100f6992SHarman Kalra if (is_tunnel_parsed) { 265100f6992SHarman Kalra /* Outer L3 */ 266100f6992SHarman Kalra send_hdr->w0.l3ptr = outer_l2_len; 267100f6992SHarman Kalra send_hdr->w0.l4ptr = outer_l2_len + m->outer_l3_len; 268100f6992SHarman Kalra /* Set clk3 for PKO to calculate IPV4 header checksum */ 269*daa02b5cSOlivier Matz send_hdr->w0.ckl3 = !!(ol_flags & RTE_MBUF_F_TX_OUTER_IPV4); 270100f6992SHarman Kalra 271100f6992SHarman Kalra /* Outer L4 */ 272100f6992SHarman Kalra send_hdr->w0.ckl4 = csum_outer; 273100f6992SHarman Kalra 274100f6992SHarman Kalra /* Inner L3 */ 275100f6992SHarman Kalra send_hdr->w1.leptr = send_hdr->w0.l4ptr + l2_len; 276100f6992SHarman Kalra send_hdr->w1.lfptr = send_hdr->w1.leptr + m->l3_len; 277100f6992SHarman Kalra /* Set clke for PKO to calculate inner IPV4 header 278100f6992SHarman Kalra * checksum. 279100f6992SHarman Kalra */ 280*daa02b5cSOlivier Matz send_hdr->w0.ckle = !!(ol_flags & RTE_MBUF_F_TX_IPV4); 281100f6992SHarman Kalra 282100f6992SHarman Kalra /* Inner L4 */ 283100f6992SHarman Kalra send_hdr->w0.cklf = csum; 284100f6992SHarman Kalra } else { 285100f6992SHarman Kalra /* Inner L3 */ 286100f6992SHarman Kalra send_hdr->w0.l3ptr = l2_len; 287100f6992SHarman Kalra send_hdr->w0.l4ptr = l2_len + m->l3_len; 288100f6992SHarman Kalra /* Set clk3 for PKO to calculate IPV4 header checksum */ 289*daa02b5cSOlivier Matz send_hdr->w0.ckl3 = !!(ol_flags & RTE_MBUF_F_TX_IPV4); 290100f6992SHarman Kalra 291100f6992SHarman Kalra /* Inner L4 */ 292100f6992SHarman Kalra send_hdr->w0.ckl4 = csum; 293100f6992SHarman Kalra } 294100f6992SHarman Kalra } else if (flags & OCCTX_TX_OFFLOAD_OL3_OL4_CSUM_F) { 295100f6992SHarman Kalra /* Outer L3 */ 296100f6992SHarman Kalra send_hdr->w0.l3ptr = outer_l2_len; 297100f6992SHarman Kalra send_hdr->w0.l4ptr = outer_l2_len + m->outer_l3_len; 298100f6992SHarman Kalra /* Set clk3 for PKO to calculate IPV4 header checksum */ 299*daa02b5cSOlivier Matz send_hdr->w0.ckl3 = !!(ol_flags & RTE_MBUF_F_TX_OUTER_IPV4); 300100f6992SHarman Kalra 301100f6992SHarman Kalra /* Outer L4 */ 302100f6992SHarman Kalra send_hdr->w0.ckl4 = csum_outer; 303100f6992SHarman Kalra } else if (flags & OCCTX_TX_OFFLOAD_L3_L4_CSUM_F) { 304100f6992SHarman Kalra /* Inner L3 */ 305100f6992SHarman Kalra send_hdr->w0.l3ptr = l2_len; 306100f6992SHarman Kalra send_hdr->w0.l4ptr = l2_len + m->l3_len; 307100f6992SHarman Kalra /* Set clk3 for PKO to calculate IPV4 header checksum */ 308*daa02b5cSOlivier Matz send_hdr->w0.ckl3 = !!(ol_flags & RTE_MBUF_F_TX_IPV4); 309100f6992SHarman Kalra 310100f6992SHarman Kalra /* Inner L4 */ 311100f6992SHarman Kalra send_hdr->w0.ckl4 = csum; 312100f6992SHarman Kalra } 313100f6992SHarman Kalra } 314100f6992SHarman Kalra 3157f4116bdSHarman Kalra static __rte_always_inline uint16_t 3167f4116bdSHarman Kalra __octeontx_xmit_prepare(struct rte_mbuf *tx_pkt, uint64_t *cmd_buf, 3175cbe1848SHarman Kalra const uint16_t flag) 3181dedffebSPavan Nikhilesh { 3197f4116bdSHarman Kalra uint16_t gaura_id, nb_desc = 0; 3209eb5cb3bSHarman Kalra struct rte_mbuf *m_tofree; 3219eb5cb3bSHarman Kalra rte_iova_t iova; 3229eb5cb3bSHarman Kalra uint16_t data_len; 3239eb5cb3bSHarman Kalra 3249eb5cb3bSHarman Kalra m_tofree = tx_pkt; 3259eb5cb3bSHarman Kalra 3269eb5cb3bSHarman Kalra data_len = tx_pkt->data_len; 3279eb5cb3bSHarman Kalra iova = rte_mbuf_data_iova(tx_pkt); 3281dedffebSPavan Nikhilesh 32985221a0cSHarman Kalra /* Setup PKO_SEND_HDR_S */ 33085221a0cSHarman Kalra cmd_buf[nb_desc++] = tx_pkt->data_len & 0xffff; 33185221a0cSHarman Kalra cmd_buf[nb_desc++] = 0x0; 33285221a0cSHarman Kalra 333100f6992SHarman Kalra /* Enable tx checksum offload */ 334100f6992SHarman Kalra if ((flag & OCCTX_TX_OFFLOAD_OL3_OL4_CSUM_F) || 335100f6992SHarman Kalra (flag & OCCTX_TX_OFFLOAD_L3_L4_CSUM_F)) 336100f6992SHarman Kalra octeontx_tx_checksum_offload(cmd_buf, flag, tx_pkt); 337100f6992SHarman Kalra 3385cbe1848SHarman Kalra /* SEND_HDR[DF] bit controls if buffer is to be freed or 3395cbe1848SHarman Kalra * not, as SG_DESC[I] and SEND_HDR[II] are clear. 3405cbe1848SHarman Kalra */ 3415cbe1848SHarman Kalra if (flag & OCCTX_TX_OFFLOAD_MBUF_NOFF_F) 3429eb5cb3bSHarman Kalra cmd_buf[0] |= (octeontx_prefree_seg(tx_pkt, &m_tofree) << 3435cbe1848SHarman Kalra 58); 3445cbe1848SHarman Kalra 34585221a0cSHarman Kalra /* Mark mempool object as "put" since it is freed by PKO */ 34685221a0cSHarman Kalra if (!(cmd_buf[0] & (1ULL << 58))) 347ad276d5cSAndrew Rybchenko RTE_MEMPOOL_CHECK_COOKIES(m_tofree->pool, (void **)&m_tofree, 34885221a0cSHarman Kalra 1, 0); 34985221a0cSHarman Kalra /* Get the gaura Id */ 3509eb5cb3bSHarman Kalra gaura_id = 3519eb5cb3bSHarman Kalra octeontx_fpa_bufpool_gaura((uintptr_t)m_tofree->pool->pool_id); 35285221a0cSHarman Kalra 35385221a0cSHarman Kalra /* Setup PKO_SEND_BUFLINK_S */ 35485221a0cSHarman Kalra cmd_buf[nb_desc++] = PKO_SEND_BUFLINK_SUBDC | 35585221a0cSHarman Kalra PKO_SEND_BUFLINK_LDTYPE(0x1ull) | 35685221a0cSHarman Kalra PKO_SEND_BUFLINK_GAUAR((long)gaura_id) | 3579eb5cb3bSHarman Kalra data_len; 3589eb5cb3bSHarman Kalra cmd_buf[nb_desc++] = iova; 3591dedffebSPavan Nikhilesh 3607f4116bdSHarman Kalra return nb_desc; 3611dedffebSPavan Nikhilesh } 3621dedffebSPavan Nikhilesh 3637f4116bdSHarman Kalra static __rte_always_inline uint16_t 3647f4116bdSHarman Kalra __octeontx_xmit_mseg_prepare(struct rte_mbuf *tx_pkt, uint64_t *cmd_buf, 3655cbe1848SHarman Kalra const uint16_t flag) 3667f4116bdSHarman Kalra { 3677f4116bdSHarman Kalra uint16_t nb_segs, nb_desc = 0; 3687f4116bdSHarman Kalra uint16_t gaura_id, len = 0; 3699eb5cb3bSHarman Kalra struct rte_mbuf *m_next = NULL, *m_tofree; 3709eb5cb3bSHarman Kalra rte_iova_t iova; 3719eb5cb3bSHarman Kalra uint16_t data_len; 3729e747589SJerin Jacob 3737f4116bdSHarman Kalra nb_segs = tx_pkt->nb_segs; 3747f4116bdSHarman Kalra /* Setup PKO_SEND_HDR_S */ 3757f4116bdSHarman Kalra cmd_buf[nb_desc++] = tx_pkt->pkt_len & 0xffff; 3767f4116bdSHarman Kalra cmd_buf[nb_desc++] = 0x0; 3777f4116bdSHarman Kalra 378100f6992SHarman Kalra /* Enable tx checksum offload */ 379100f6992SHarman Kalra if ((flag & OCCTX_TX_OFFLOAD_OL3_OL4_CSUM_F) || 380100f6992SHarman Kalra (flag & OCCTX_TX_OFFLOAD_L3_L4_CSUM_F)) 381100f6992SHarman Kalra octeontx_tx_checksum_offload(cmd_buf, flag, tx_pkt); 382100f6992SHarman Kalra 3837f4116bdSHarman Kalra do { 3847f4116bdSHarman Kalra m_next = tx_pkt->next; 3859eb5cb3bSHarman Kalra /* Get TX parameters up front, octeontx_prefree_seg might change 3869eb5cb3bSHarman Kalra * them 3877f4116bdSHarman Kalra */ 3889eb5cb3bSHarman Kalra m_tofree = tx_pkt; 3899eb5cb3bSHarman Kalra data_len = tx_pkt->data_len; 3909eb5cb3bSHarman Kalra iova = rte_mbuf_data_iova(tx_pkt); 3917f4116bdSHarman Kalra 3927f4116bdSHarman Kalra /* Setup PKO_SEND_GATHER_S */ 3939eb5cb3bSHarman Kalra cmd_buf[nb_desc] = 0; 3947f4116bdSHarman Kalra 3955cbe1848SHarman Kalra /* SG_DESC[I] bit controls if buffer is to be freed or 3965cbe1848SHarman Kalra * not, as SEND_HDR[DF] and SEND_HDR[II] are clear. 3975cbe1848SHarman Kalra */ 3985cbe1848SHarman Kalra if (flag & OCCTX_TX_OFFLOAD_MBUF_NOFF_F) { 3995cbe1848SHarman Kalra cmd_buf[nb_desc] |= 4009eb5cb3bSHarman Kalra (octeontx_prefree_seg(tx_pkt, &m_tofree) << 57); 4015cbe1848SHarman Kalra } 4025cbe1848SHarman Kalra 4039eb5cb3bSHarman Kalra /* To handle case where mbufs belong to diff pools, like 4049eb5cb3bSHarman Kalra * fragmentation 4059eb5cb3bSHarman Kalra */ 4069eb5cb3bSHarman Kalra gaura_id = octeontx_fpa_bufpool_gaura((uintptr_t) 4079eb5cb3bSHarman Kalra m_tofree->pool->pool_id); 4089eb5cb3bSHarman Kalra 4099eb5cb3bSHarman Kalra /* Setup PKO_SEND_GATHER_S */ 4109eb5cb3bSHarman Kalra cmd_buf[nb_desc] |= PKO_SEND_GATHER_SUBDC | 4119eb5cb3bSHarman Kalra PKO_SEND_GATHER_LDTYPE(0x1ull) | 4129eb5cb3bSHarman Kalra PKO_SEND_GATHER_GAUAR((long)gaura_id) | 4139eb5cb3bSHarman Kalra data_len; 4149eb5cb3bSHarman Kalra 4157f4116bdSHarman Kalra /* Mark mempool object as "put" since it is freed by 4167f4116bdSHarman Kalra * PKO. 4177f4116bdSHarman Kalra */ 4187f4116bdSHarman Kalra if (!(cmd_buf[nb_desc] & (1ULL << 57))) { 4197f4116bdSHarman Kalra tx_pkt->next = NULL; 420ad276d5cSAndrew Rybchenko RTE_MEMPOOL_CHECK_COOKIES(m_tofree->pool, 4219eb5cb3bSHarman Kalra (void **)&m_tofree, 1, 0); 4227f4116bdSHarman Kalra } 4237f4116bdSHarman Kalra nb_desc++; 4247f4116bdSHarman Kalra 4259eb5cb3bSHarman Kalra cmd_buf[nb_desc++] = iova; 4267f4116bdSHarman Kalra 4277f4116bdSHarman Kalra nb_segs--; 4289eb5cb3bSHarman Kalra len += data_len; 4297f4116bdSHarman Kalra tx_pkt = m_next; 4307f4116bdSHarman Kalra } while (nb_segs); 4317f4116bdSHarman Kalra 4327f4116bdSHarman Kalra return nb_desc; 4337f4116bdSHarman Kalra } 4347f4116bdSHarman Kalra 4357f4116bdSHarman Kalra static __rte_always_inline uint16_t 4367f4116bdSHarman Kalra __octeontx_xmit_pkts(void *tx_queue, struct rte_mbuf **tx_pkts, 4377f4116bdSHarman Kalra uint16_t nb_pkts, uint64_t *cmd_buf, 4387f4116bdSHarman Kalra const uint16_t flags) 4397f4116bdSHarman Kalra { 4407f4116bdSHarman Kalra struct octeontx_txq *txq = tx_queue; 4417f4116bdSHarman Kalra octeontx_dq_t *dq = &txq->dq; 4427f4116bdSHarman Kalra uint16_t count = 0, nb_desc; 443f0f5d844SPhil Yang rte_io_wmb(); 4447f4116bdSHarman Kalra 4457f4116bdSHarman Kalra while (count < nb_pkts) { 4467f4116bdSHarman Kalra if (unlikely(*((volatile int64_t *)dq->fc_status_va) < 0)) 4477f4116bdSHarman Kalra break; 4487f4116bdSHarman Kalra 4497f4116bdSHarman Kalra if (flags & OCCTX_TX_MULTI_SEG_F) { 4507f4116bdSHarman Kalra nb_desc = __octeontx_xmit_mseg_prepare(tx_pkts[count], 4517f4116bdSHarman Kalra cmd_buf, flags); 4527f4116bdSHarman Kalra } else { 4537f4116bdSHarman Kalra nb_desc = __octeontx_xmit_prepare(tx_pkts[count], 4547f4116bdSHarman Kalra cmd_buf, flags); 4557f4116bdSHarman Kalra } 4567f4116bdSHarman Kalra 4577f4116bdSHarman Kalra octeontx_reg_lmtst(dq->lmtline_va, dq->ioreg_va, cmd_buf, 4587f4116bdSHarman Kalra nb_desc); 4597f4116bdSHarman Kalra 4607f4116bdSHarman Kalra count++; 4617f4116bdSHarman Kalra } 4627f4116bdSHarman Kalra return count; 4637f4116bdSHarman Kalra } 46485221a0cSHarman Kalra 46585221a0cSHarman Kalra uint16_t 4662d2c7918SJerin Jacob octeontx_recv_pkts(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t nb_pkts); 4679e747589SJerin Jacob 468100f6992SHarman Kalra #define L3L4CSUM_F OCCTX_TX_OFFLOAD_L3_L4_CSUM_F 469100f6992SHarman Kalra #define OL3OL4CSUM_F OCCTX_TX_OFFLOAD_OL3_OL4_CSUM_F 4705cbe1848SHarman Kalra #define NOFF_F OCCTX_TX_OFFLOAD_MBUF_NOFF_F 4717f4116bdSHarman Kalra #define MULT_F OCCTX_TX_MULTI_SEG_F 472100f6992SHarman Kalra 473100f6992SHarman Kalra /* [L3L4CSUM_F] [OL3OL4CSUM_F] [NOFF] [MULTI_SEG] */ 4747f4116bdSHarman Kalra #define OCCTX_TX_FASTPATH_MODES \ 475100f6992SHarman Kalra T(no_offload, 0, 0, 0, 0, 4, \ 476100f6992SHarman Kalra OCCTX_TX_OFFLOAD_NONE) \ 477100f6992SHarman Kalra T(mseg, 0, 0, 0, 1, 14, \ 478100f6992SHarman Kalra MULT_F) \ 479100f6992SHarman Kalra T(l3l4csum, 0, 0, 1, 0, 4, \ 480100f6992SHarman Kalra L3L4CSUM_F) \ 481100f6992SHarman Kalra T(l3l4csum_mseg, 0, 0, 1, 1, 14, \ 482100f6992SHarman Kalra L3L4CSUM_F | MULT_F) \ 483100f6992SHarman Kalra T(ol3ol4csum, 0, 1, 0, 0, 4, \ 484100f6992SHarman Kalra OL3OL4CSUM_F) \ 485100f6992SHarman Kalra T(ol3l4csum_mseg, 0, 1, 0, 1, 14, \ 486100f6992SHarman Kalra OL3OL4CSUM_F | MULT_F) \ 487100f6992SHarman Kalra T(ol3l4csum_l3l4csum, 0, 1, 1, 0, 4, \ 488100f6992SHarman Kalra OL3OL4CSUM_F | L3L4CSUM_F) \ 489100f6992SHarman Kalra T(ol3l4csum_l3l4csum_mseg, 0, 1, 1, 1, 14, \ 490100f6992SHarman Kalra OL3OL4CSUM_F | L3L4CSUM_F | MULT_F) \ 491100f6992SHarman Kalra T(noff, 1, 0, 0, 0, 4, \ 492100f6992SHarman Kalra NOFF_F) \ 493100f6992SHarman Kalra T(noff_mseg, 1, 0, 0, 1, 14, \ 494100f6992SHarman Kalra NOFF_F | MULT_F) \ 495100f6992SHarman Kalra T(noff_l3l4csum, 1, 0, 1, 0, 4, \ 496100f6992SHarman Kalra NOFF_F | L3L4CSUM_F) \ 497100f6992SHarman Kalra T(noff_l3l4csum_mseg, 1, 0, 1, 1, 14, \ 498100f6992SHarman Kalra NOFF_F | L3L4CSUM_F | MULT_F) \ 499100f6992SHarman Kalra T(noff_ol3ol4csum, 1, 1, 0, 0, 4, \ 500100f6992SHarman Kalra NOFF_F | OL3OL4CSUM_F) \ 501100f6992SHarman Kalra T(noff_ol3ol4csum_mseg, 1, 1, 0, 1, 14, \ 502100f6992SHarman Kalra NOFF_F | OL3OL4CSUM_F | MULT_F) \ 503100f6992SHarman Kalra T(noff_ol3ol4csum_l3l4csum, 1, 1, 1, 0, 4, \ 504100f6992SHarman Kalra NOFF_F | OL3OL4CSUM_F | L3L4CSUM_F) \ 505100f6992SHarman Kalra T(noff_ol3ol4csum_l3l4csum_mseg, 1, 1, 1, 1, 14, \ 506100f6992SHarman Kalra NOFF_F | OL3OL4CSUM_F | L3L4CSUM_F | \ 507100f6992SHarman Kalra MULT_F) 5087f4116bdSHarman Kalra 50956a96aa4SHarman Kalra /* RX offload macros */ 51045231cc6SVamsi Attunuru #define VLAN_FLTR_F OCCTX_RX_VLAN_FLTR_F 511cf55f04aSHarman Kalra #define CSUM_F OCCTX_RX_OFFLOAD_CSUM_F 51256a96aa4SHarman Kalra #define MULT_RX_F OCCTX_RX_MULTI_SEG_F 513cf55f04aSHarman Kalra 514cf55f04aSHarman Kalra /* [VLAN_FLTR] [CSUM_F] [MULTI_SEG] */ 51556a96aa4SHarman Kalra #define OCCTX_RX_FASTPATH_MODES \ 516cf55f04aSHarman Kalra R(no_offload, 0, 0, 0, OCCTX_RX_OFFLOAD_NONE) \ 517cf55f04aSHarman Kalra R(mseg, 0, 0, 1, MULT_RX_F) \ 518cf55f04aSHarman Kalra R(csum, 0, 1, 0, CSUM_F) \ 519cf55f04aSHarman Kalra R(csum_mseg, 0, 1, 1, CSUM_F | MULT_RX_F) \ 520cf55f04aSHarman Kalra R(vlan, 1, 0, 0, VLAN_FLTR_F) \ 521cf55f04aSHarman Kalra R(vlan_mseg, 1, 0, 1, VLAN_FLTR_F | MULT_RX_F) \ 522cf55f04aSHarman Kalra R(vlan_csum, 1, 1, 0, VLAN_FLTR_F | CSUM_F) \ 523cf55f04aSHarman Kalra R(vlan_csum_mseg, 1, 1, 1, CSUM_F | VLAN_FLTR_F | \ 524cf55f04aSHarman Kalra MULT_RX_F) 52556a96aa4SHarman Kalra 5269e747589SJerin Jacob #endif /* __OCTEONTX_RXTX_H__ */ 527