Acked-by: Jarno Rajahalme <[email protected]>

> On Mar 2, 2017, at 7:29 PM, Joe Stringer <[email protected]> wrote:
> 
> From: Lance Richardson <[email protected]>
> 
> Upstream commit:
>    commit 75f01a4c9cc291ff5cb28ca1216adb163b7a20ee
>    Author: Lance Richardson <[email protected]>
>    Date: Thu Jan 12 19:33:18 2017 -0500
> 
>    openvswitch: maintain correct checksum state in conntrack actions
> 
>    When executing conntrack actions on skbuffs with checksum mode
>    CHECKSUM_COMPLETE, the checksum must be updated to account for
>    header pushes and pulls. Otherwise we get "hw csum failure"
>    logs similar to this (ICMP packet received on geneve tunnel
>    via ixgbe NIC):
> 
>    [  405.740065] genev_sys_6081: hw csum failure
>    [  405.740106] CPU: 3 PID: 0 Comm: swapper/3 Tainted: G          I     
> 4.10.0-rc3+ #1
>    [  405.740108] Call Trace:
>    [  405.740110]  <IRQ>
>    [  405.740113]  dump_stack+0x63/0x87
>    [  405.740116]  netdev_rx_csum_fault+0x3a/0x40
>    [  405.740118]  __skb_checksum_complete+0xcf/0xe0
>    [  405.740120]  nf_ip_checksum+0xc8/0xf0
>    [  405.740124]  icmp_error+0x1de/0x351 [nf_conntrack_ipv4]
>    [  405.740132]  nf_conntrack_in+0xe1/0x550 [nf_conntrack]
>    [  405.740137]  ? find_bucket.isra.2+0x62/0x70 [openvswitch]
>    [  405.740143]  __ovs_ct_lookup+0x95/0x980 [openvswitch]
>    [  405.740145]  ? netif_rx_internal+0x44/0x110
>    [  405.740149]  ovs_ct_execute+0x147/0x4b0 [openvswitch]
>    [  405.740153]  do_execute_actions+0x22e/0xa70 [openvswitch]
>    [  405.740157]  ovs_execute_actions+0x40/0x120 [openvswitch]
>    [  405.740161]  ovs_dp_process_packet+0x84/0x120 [openvswitch]
>    [  405.740166]  ovs_vport_receive+0x73/0xd0 [openvswitch]
>    [  405.740168]  ? udp_rcv+0x1a/0x20
>    [  405.740170]  ? ip_local_deliver_finish+0x93/0x1e0
>    [  405.740172]  ? ip_local_deliver+0x6f/0xe0
>    [  405.740174]  ? ip_rcv_finish+0x3a0/0x3a0
>    [  405.740176]  ? ip_rcv_finish+0xdb/0x3a0
>    [  405.740177]  ? ip_rcv+0x2a7/0x400
>    [  405.740180]  ? __netif_receive_skb_core+0x970/0xa00
>    [  405.740185]  netdev_frame_hook+0xd3/0x160 [openvswitch]
>    [  405.740187]  __netif_receive_skb_core+0x1dc/0xa00
>    [  405.740194]  ? ixgbe_clean_rx_irq+0x46d/0xa20 [ixgbe]
>    [  405.740197]  __netif_receive_skb+0x18/0x60
>    [  405.740199]  netif_receive_skb_internal+0x40/0xb0
>    [  405.740201]  napi_gro_receive+0xcd/0x120
>    [  405.740204]  gro_cell_poll+0x57/0x80 [geneve]
>    [  405.740206]  net_rx_action+0x260/0x3c0
>    [  405.740209]  __do_softirq+0xc9/0x28c
>    [  405.740211]  irq_exit+0xd9/0xf0
>    [  405.740213]  do_IRQ+0x51/0xd0
>    [  405.740215]  common_interrupt+0x93/0x93
> 
>    Fixes: 7f8a436eaa2c ("openvswitch: Add conntrack action")
>    Signed-off-by: Lance Richardson <[email protected]>
>    Acked-by: Pravin B Shelar <[email protected]>
>    Signed-off-by: David S. Miller <[email protected]>
> 
> Upstream: 75f01a4c9cc2 ("openvswitch: maintain correct checksum state in 
> conntrack actions")
> Signed-off-by: Joe Stringer <[email protected]>
> ---
> datapath/conntrack.c | 6 ++++--
> 1 file changed, 4 insertions(+), 2 deletions(-)
> 
> diff --git a/datapath/conntrack.c b/datapath/conntrack.c
> index e4e76b836805..36db32abbf63 100644
> --- a/datapath/conntrack.c
> +++ b/datapath/conntrack.c
> @@ -555,7 +555,7 @@ static int ovs_ct_nat_execute(struct sk_buff *skb, struct 
> nf_conn *ct,
>       int hooknum, nh_off, err = NF_ACCEPT;
> 
>       nh_off = skb_network_offset(skb);
> -     skb_pull(skb, nh_off);
> +     skb_pull_rcsum(skb, nh_off);
> 
>       /* See HOOK2MANIP(). */
>       if (maniptype == NF_NAT_MANIP_SRC)
> @@ -620,6 +620,7 @@ static int ovs_ct_nat_execute(struct sk_buff *skb, struct 
> nf_conn *ct,
>       err = nf_nat_packet(ct, ctinfo, hooknum, skb);
> push:
>       skb_push(skb, nh_off);
> +     skb_postpush_rcsum(skb, skb->data, nh_off);
> 
>       return err;
> }
> @@ -927,7 +928,7 @@ int ovs_ct_execute(struct net *net, struct sk_buff *skb,
> 
>       /* The conntrack module expects to be working at L3. */
>       nh_ofs = skb_network_offset(skb);
> -     skb_pull(skb, nh_ofs);
> +     skb_pull_rcsum(skb, nh_ofs);
> 
>       if (key->ip.frag != OVS_FRAG_TYPE_NONE) {
>               err = handle_fragments(net, key, info->zone.id, skb);
> @@ -941,6 +942,7 @@ int ovs_ct_execute(struct net *net, struct sk_buff *skb,
>               err = ovs_ct_lookup(net, key, info, skb);
> 
>       skb_push(skb, nh_ofs);
> +     skb_postpush_rcsum(skb, skb->data, nh_ofs);
>       if (err)
>               kfree_skb(skb);
>       return err;
> -- 
> 2.11.1
> 

_______________________________________________
dev mailing list
[email protected]
https://mail.openvswitch.org/mailman/listinfo/ovs-dev

Reply via email to