Branch data Line data Source code
1 : : /* SPDX-License-Identifier: BSD-3-Clause 2 : : * Copyright(c) 2017 Intel Corporation 3 : : */ 4 : : 5 : : #include <errno.h> 6 : : 7 : : #include <rte_log.h> 8 : : #include <rte_ethdev.h> 9 : : 10 : : #include "rte_gso.h" 11 : : #include "gso_common.h" 12 : : #include "gso_tcp4.h" 13 : : #include "gso_tunnel_tcp4.h" 14 : : #include "gso_tunnel_udp4.h" 15 : : #include "gso_udp4.h" 16 : : 17 : : #define ILLEGAL_UDP_GSO_CTX(ctx) \ 18 : : ((((ctx)->gso_types & RTE_ETH_TX_OFFLOAD_UDP_TSO) == 0) || \ 19 : : (ctx)->gso_size < RTE_GSO_UDP_SEG_SIZE_MIN) 20 : : 21 : : #define ILLEGAL_TCP_GSO_CTX(ctx) \ 22 : : ((((ctx)->gso_types & (RTE_ETH_TX_OFFLOAD_TCP_TSO | \ 23 : : RTE_ETH_TX_OFFLOAD_VXLAN_TNL_TSO | \ 24 : : RTE_ETH_TX_OFFLOAD_GRE_TNL_TSO)) == 0) || \ 25 : : (ctx)->gso_size < RTE_GSO_SEG_SIZE_MIN) 26 : : 27 : : int 28 : 0 : rte_gso_segment(struct rte_mbuf *pkt, 29 : : const struct rte_gso_ctx *gso_ctx, 30 : : struct rte_mbuf **pkts_out, 31 : : uint16_t nb_pkts_out) 32 : : { 33 : : struct rte_mempool *direct_pool, *indirect_pool; 34 : : uint64_t ol_flags; 35 : : uint16_t gso_size; 36 : : uint8_t ipid_delta; 37 : : int ret = 1; 38 : : 39 [ # # ]: 0 : if (pkt == NULL || pkts_out == NULL || gso_ctx == NULL || 40 [ # # ]: 0 : nb_pkts_out < 1 || 41 [ # # # # : 0 : (ILLEGAL_UDP_GSO_CTX(gso_ctx) && # # ] 42 [ # # ]: 0 : ILLEGAL_TCP_GSO_CTX(gso_ctx))) 43 : : return -EINVAL; 44 : : 45 [ # # ]: 0 : if (gso_ctx->gso_size >= pkt->pkt_len) { 46 : 0 : pkt->ol_flags &= (~(RTE_MBUF_F_TX_TCP_SEG | RTE_MBUF_F_TX_UDP_SEG)); 47 : 0 : return 0; 48 : : } 49 : : 50 : 0 : direct_pool = gso_ctx->direct_pool; 51 : 0 : indirect_pool = gso_ctx->indirect_pool; 52 : : gso_size = gso_ctx->gso_size; 53 : 0 : ipid_delta = (gso_ctx->flag != RTE_GSO_FLAG_IPID_FIXED); 54 : 0 : ol_flags = pkt->ol_flags; 55 : : 56 [ # # # # ]: 0 : if ((IS_IPV4_VXLAN_TCP4(pkt->ol_flags) && 57 [ # # ]: 0 : (gso_ctx->gso_types & RTE_ETH_TX_OFFLOAD_VXLAN_TNL_TSO)) || 58 [ # # ]: 0 : ((IS_IPV4_GRE_TCP4(pkt->ol_flags) && 59 : : (gso_ctx->gso_types & RTE_ETH_TX_OFFLOAD_GRE_TNL_TSO)))) { 60 : 0 : pkt->ol_flags &= (~RTE_MBUF_F_TX_TCP_SEG); 61 : 0 : ret = gso_tunnel_tcp4_segment(pkt, gso_size, ipid_delta, 62 : : direct_pool, indirect_pool, 63 : : pkts_out, nb_pkts_out); 64 [ # # ]: 0 : } else if (IS_IPV4_VXLAN_UDP4(pkt->ol_flags) && 65 [ # # ]: 0 : (gso_ctx->gso_types & RTE_ETH_TX_OFFLOAD_VXLAN_TNL_TSO) && 66 : : (gso_ctx->gso_types & RTE_ETH_TX_OFFLOAD_UDP_TSO)) { 67 : 0 : pkt->ol_flags &= (~RTE_MBUF_F_TX_UDP_SEG); 68 : 0 : ret = gso_tunnel_udp4_segment(pkt, gso_size, 69 : : direct_pool, indirect_pool, 70 : : pkts_out, nb_pkts_out); 71 [ # # # # ]: 0 : } else if (IS_IPV4_TCP(pkt->ol_flags) && 72 : : (gso_ctx->gso_types & RTE_ETH_TX_OFFLOAD_TCP_TSO)) { 73 : 0 : pkt->ol_flags &= (~RTE_MBUF_F_TX_TCP_SEG); 74 : 0 : ret = gso_tcp4_segment(pkt, gso_size, ipid_delta, 75 : : direct_pool, indirect_pool, 76 : : pkts_out, nb_pkts_out); 77 [ # # # # ]: 0 : } else if (IS_IPV4_UDP(pkt->ol_flags) && 78 : : (gso_ctx->gso_types & RTE_ETH_TX_OFFLOAD_UDP_TSO)) { 79 : 0 : pkt->ol_flags &= (~RTE_MBUF_F_TX_UDP_SEG); 80 : 0 : ret = gso_udp4_segment(pkt, gso_size, direct_pool, 81 : : indirect_pool, pkts_out, nb_pkts_out); 82 : : } else { 83 : : ret = -ENOTSUP; /* only UDP or TCP allowed */ 84 : : } 85 : : 86 [ # # ]: 0 : if (ret < 0) { 87 : : /* Revert the ol_flags in the event of failure. */ 88 : 0 : pkt->ol_flags = ol_flags; 89 : : } 90 : : 91 : : return ret; 92 : : }