Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 79a25852 authored by Ido Shamay's avatar Ido Shamay Committed by David S. Miller
Browse files

net/mlx4_en: Fix wrong csum complete report when rxvlan offload is disabled



The check_csum() function relied on hwtstamp_rx_filter to know if rxvlan
offload is disabled. This is wrong since rxvlan offload can be switched
on/off regardless of hwtstamp_rx_filter.

Also moved check_csum to query CQE information to identify VLAN packets
and removed the check of IP packets, since it has been validated before.

Fixes: f8c6455b ('net/mlx4_en: Extend checksum offloading by CHECKSUM COMPLETE')
Signed-off-by: default avatarIdo Shamay <idos@mellanox.com>
Signed-off-by: default avatarOr Gerlitz <ogerlitz@mellanox.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 488a9b48
Loading
Loading
Loading
Loading
+6 −11
Original line number Diff line number Diff line
@@ -718,7 +718,7 @@ static int get_fixed_ipv6_csum(__wsum hw_checksum, struct sk_buff *skb,
}
#endif
static int check_csum(struct mlx4_cqe *cqe, struct sk_buff *skb, void *va,
		      int hwtstamp_rx_filter)
		      netdev_features_t dev_features)
{
	__wsum hw_checksum = 0;

@@ -726,14 +726,8 @@ static int check_csum(struct mlx4_cqe *cqe, struct sk_buff *skb, void *va,

	hw_checksum = csum_unfold((__force __sum16)cqe->checksum);

	if (((struct ethhdr *)va)->h_proto == htons(ETH_P_8021Q) &&
	    hwtstamp_rx_filter != HWTSTAMP_FILTER_NONE) {
		/* next protocol non IPv4 or IPv6 */
		if (((struct vlan_hdr *)hdr)->h_vlan_encapsulated_proto
		    != htons(ETH_P_IP) &&
		    ((struct vlan_hdr *)hdr)->h_vlan_encapsulated_proto
		    != htons(ETH_P_IPV6))
			return -1;
	if (cqe->vlan_my_qpn & cpu_to_be32(MLX4_CQE_VLAN_PRESENT_MASK) &&
	    !(dev_features & NETIF_F_HW_VLAN_CTAG_RX)) {
		hw_checksum = get_fixed_vlan_csum(hw_checksum, hdr);
		hdr += sizeof(struct vlan_hdr);
	}
@@ -896,7 +890,8 @@ int mlx4_en_process_rx_cq(struct net_device *dev, struct mlx4_en_cq *cq, int bud

			if (ip_summed == CHECKSUM_COMPLETE) {
				void *va = skb_frag_address(skb_shinfo(gro_skb)->frags);
				if (check_csum(cqe, gro_skb, va, ring->hwtstamp_rx_filter)) {
				if (check_csum(cqe, gro_skb, va,
					       dev->features)) {
					ip_summed = CHECKSUM_NONE;
					ring->csum_none++;
					ring->csum_complete--;
@@ -951,7 +946,7 @@ int mlx4_en_process_rx_cq(struct net_device *dev, struct mlx4_en_cq *cq, int bud
		}

		if (ip_summed == CHECKSUM_COMPLETE) {
			if (check_csum(cqe, skb, skb->data, ring->hwtstamp_rx_filter)) {
			if (check_csum(cqe, skb, skb->data, dev->features)) {
				ip_summed = CHECKSUM_NONE;
				ring->csum_complete--;
				ring->csum_none++;