| 2782 | } |
| 2783 | |
| 2784 | static __rte_always_inline void |
| 2785 | vhost_dequeue_offload(struct virtio_net *dev, struct virtio_net_hdr *hdr, |
| 2786 | struct rte_mbuf *m, bool legacy_ol_flags) |
| 2787 | { |
| 2788 | struct rte_net_hdr_lens hdr_lens; |
| 2789 | int l4_supported = 0; |
| 2790 | uint32_t ptype; |
| 2791 | |
| 2792 | if (hdr->flags == 0 && hdr->gso_type == VIRTIO_NET_HDR_GSO_NONE) |
| 2793 | return; |
| 2794 | |
| 2795 | if (legacy_ol_flags) { |
| 2796 | vhost_dequeue_offload_legacy(dev, hdr, m); |
| 2797 | return; |
| 2798 | } |
| 2799 | |
| 2800 | m->ol_flags |= RTE_MBUF_F_RX_IP_CKSUM_UNKNOWN; |
| 2801 | |
| 2802 | ptype = rte_net_get_ptype(m, &hdr_lens, RTE_PTYPE_ALL_MASK); |
| 2803 | m->packet_type = ptype; |
| 2804 | if ((ptype & RTE_PTYPE_L4_MASK) == RTE_PTYPE_L4_TCP || |
| 2805 | (ptype & RTE_PTYPE_L4_MASK) == RTE_PTYPE_L4_UDP || |
| 2806 | (ptype & RTE_PTYPE_L4_MASK) == RTE_PTYPE_L4_SCTP) |
| 2807 | l4_supported = 1; |
| 2808 | |
| 2809 | /* According to Virtio 1.1 spec, the device only needs to look at |
| 2810 | * VIRTIO_NET_HDR_F_NEEDS_CSUM in the packet transmission path. |
| 2811 | * This differs from the processing incoming packets path where the |
| 2812 | * driver could rely on VIRTIO_NET_HDR_F_DATA_VALID flag set by the |
| 2813 | * device. |
| 2814 | * |
| 2815 | * 5.1.6.2.1 Driver Requirements: Packet Transmission |
| 2816 | * The driver MUST NOT set the VIRTIO_NET_HDR_F_DATA_VALID and |
| 2817 | * VIRTIO_NET_HDR_F_RSC_INFO bits in flags. |
| 2818 | * |
| 2819 | * 5.1.6.2.2 Device Requirements: Packet Transmission |
| 2820 | * The device MUST ignore flag bits that it does not recognize. |
| 2821 | */ |
| 2822 | if (hdr->flags & VIRTIO_NET_HDR_F_NEEDS_CSUM) { |
| 2823 | uint32_t hdrlen; |
| 2824 | |
| 2825 | hdrlen = hdr_lens.l2_len + hdr_lens.l3_len + hdr_lens.l4_len; |
| 2826 | if (hdr->csum_start <= hdrlen && l4_supported != 0) { |
| 2827 | m->ol_flags |= RTE_MBUF_F_RX_L4_CKSUM_NONE; |
| 2828 | } else { |
| 2829 | /* Unknown proto or tunnel, do sw cksum. We can assume |
| 2830 | * the cksum field is in the first segment since the |
| 2831 | * buffers we provided to the host are large enough. |
| 2832 | * In case of SCTP, this will be wrong since it's a CRC |
| 2833 | * but there's nothing we can do. |
| 2834 | */ |
| 2835 | uint16_t csum = 0, off; |
| 2836 | |
| 2837 | if (hdr->csum_start >= rte_pktmbuf_pkt_len(m)) |
| 2838 | return; |
| 2839 | |
| 2840 | if (rte_raw_cksum_mbuf(m, hdr->csum_start, |
| 2841 | rte_pktmbuf_pkt_len(m) - hdr->csum_start, &csum) < 0) |
no test coverage detected