diff options
| author | Pravin B Shelar <pshelar@nicira.com> | 2013-06-13 14:11:44 -0400 |
|---|---|---|
| committer | Jesse Gross <jesse@nicira.com> | 2013-06-14 18:09:12 -0400 |
| commit | b34df5e805a6e98cae0bc5bc80c1b52d9ff811de (patch) | |
| tree | cc8d94ee92741fe21380180aeff3a6f12bb44adb | |
| parent | 45bfa52e36ef016b789eca73c7847db3f7b4742d (diff) | |
openvswitch: make skb->csum consistent with rest of networking stack.
Following patch keeps skb->csum correct across ovs.
Signed-off-by: Pravin B Shelar <pshelar@nicira.com>
Signed-off-by: Jesse Gross <jesse@nicira.com>
| -rw-r--r-- | net/openvswitch/actions.c | 4 | ||||
| -rw-r--r-- | net/openvswitch/flow.c | 3 | ||||
| -rw-r--r-- | net/openvswitch/vport-internal_dev.c | 1 | ||||
| -rw-r--r-- | net/openvswitch/vport-netdev.c | 2 | ||||
| -rw-r--r-- | net/openvswitch/vport.h | 7 |
5 files changed, 17 insertions, 0 deletions
diff --git a/net/openvswitch/actions.c b/net/openvswitch/actions.c index 894b6cbdd929..596d6373399d 100644 --- a/net/openvswitch/actions.c +++ b/net/openvswitch/actions.c | |||
| @@ -130,9 +130,13 @@ static int set_eth_addr(struct sk_buff *skb, | |||
| 130 | if (unlikely(err)) | 130 | if (unlikely(err)) |
| 131 | return err; | 131 | return err; |
| 132 | 132 | ||
| 133 | skb_postpull_rcsum(skb, eth_hdr(skb), ETH_ALEN * 2); | ||
| 134 | |||
| 133 | memcpy(eth_hdr(skb)->h_source, eth_key->eth_src, ETH_ALEN); | 135 | memcpy(eth_hdr(skb)->h_source, eth_key->eth_src, ETH_ALEN); |
| 134 | memcpy(eth_hdr(skb)->h_dest, eth_key->eth_dst, ETH_ALEN); | 136 | memcpy(eth_hdr(skb)->h_dest, eth_key->eth_dst, ETH_ALEN); |
| 135 | 137 | ||
| 138 | ovs_skb_postpush_rcsum(skb, eth_hdr(skb), ETH_ALEN * 2); | ||
| 139 | |||
| 136 | return 0; | 140 | return 0; |
| 137 | } | 141 | } |
| 138 | 142 | ||
diff --git a/net/openvswitch/flow.c b/net/openvswitch/flow.c index 33df0913358d..fca483360ce2 100644 --- a/net/openvswitch/flow.c +++ b/net/openvswitch/flow.c | |||
| @@ -618,6 +618,9 @@ int ovs_flow_extract(struct sk_buff *skb, u16 in_port, struct sw_flow_key *key, | |||
| 618 | memcpy(key->eth.dst, eth->h_dest, ETH_ALEN); | 618 | memcpy(key->eth.dst, eth->h_dest, ETH_ALEN); |
| 619 | 619 | ||
| 620 | __skb_pull(skb, 2 * ETH_ALEN); | 620 | __skb_pull(skb, 2 * ETH_ALEN); |
| 621 | /* We are going to push all headers that we pull, so no need to | ||
| 622 | * update skb->csum here. | ||
| 623 | */ | ||
| 621 | 624 | ||
| 622 | if (vlan_tx_tag_present(skb)) | 625 | if (vlan_tx_tag_present(skb)) |
| 623 | key->eth.tci = htons(skb->vlan_tci); | 626 | key->eth.tci = htons(skb->vlan_tci); |
diff --git a/net/openvswitch/vport-internal_dev.c b/net/openvswitch/vport-internal_dev.c index 84e0a0379186..e284c7e1fec4 100644 --- a/net/openvswitch/vport-internal_dev.c +++ b/net/openvswitch/vport-internal_dev.c | |||
| @@ -221,6 +221,7 @@ static int internal_dev_recv(struct vport *vport, struct sk_buff *skb) | |||
| 221 | skb->dev = netdev; | 221 | skb->dev = netdev; |
| 222 | skb->pkt_type = PACKET_HOST; | 222 | skb->pkt_type = PACKET_HOST; |
| 223 | skb->protocol = eth_type_trans(skb, netdev); | 223 | skb->protocol = eth_type_trans(skb, netdev); |
| 224 | skb_postpull_rcsum(skb, eth_hdr(skb), ETH_HLEN); | ||
| 224 | 225 | ||
| 225 | netif_rx(skb); | 226 | netif_rx(skb); |
| 226 | 227 | ||
diff --git a/net/openvswitch/vport-netdev.c b/net/openvswitch/vport-netdev.c index 43712217a372..40de815b4213 100644 --- a/net/openvswitch/vport-netdev.c +++ b/net/openvswitch/vport-netdev.c | |||
| @@ -49,6 +49,8 @@ static void netdev_port_receive(struct vport *vport, struct sk_buff *skb) | |||
| 49 | return; | 49 | return; |
| 50 | 50 | ||
| 51 | skb_push(skb, ETH_HLEN); | 51 | skb_push(skb, ETH_HLEN); |
| 52 | ovs_skb_postpush_rcsum(skb, skb->data, ETH_HLEN); | ||
| 53 | |||
| 52 | ovs_vport_receive(vport, skb); | 54 | ovs_vport_receive(vport, skb); |
| 53 | return; | 55 | return; |
| 54 | 56 | ||
diff --git a/net/openvswitch/vport.h b/net/openvswitch/vport.h index 1cef5cd3be47..293278c4c2df 100644 --- a/net/openvswitch/vport.h +++ b/net/openvswitch/vport.h | |||
| @@ -192,4 +192,11 @@ void ovs_vport_record_error(struct vport *, enum vport_err_type err_type); | |||
| 192 | extern const struct vport_ops ovs_netdev_vport_ops; | 192 | extern const struct vport_ops ovs_netdev_vport_ops; |
| 193 | extern const struct vport_ops ovs_internal_vport_ops; | 193 | extern const struct vport_ops ovs_internal_vport_ops; |
| 194 | 194 | ||
| 195 | static inline void ovs_skb_postpush_rcsum(struct sk_buff *skb, | ||
| 196 | const void *start, unsigned int len) | ||
| 197 | { | ||
| 198 | if (skb->ip_summed == CHECKSUM_COMPLETE) | ||
| 199 | skb->csum = csum_add(skb->csum, csum_partial(start, len, 0)); | ||
| 200 | } | ||
| 201 | |||
| 195 | #endif /* vport.h */ | 202 | #endif /* vport.h */ |
