datapath: Add support for Linux 3.12
[sliver-openvswitch.git] / datapath / linux / compat / gso.h
1 #ifndef __LINUX_GSO_WRAPPER_H
2 #define __LINUX_GSO_WRAPPER_H
3
4 #include <linux/version.h>
5 #if LINUX_VERSION_CODE < KERNEL_VERSION(3,12,0)
6
7 #include <linux/skbuff.h>
8 #include <net/protocol.h>
9
10 #include "datapath.h"
11
12 struct ovs_gso_cb {
13         struct ovs_skb_cb dp_cb;
14         sk_buff_data_t  inner_network_header;
15         sk_buff_data_t  inner_mac_header;
16         void (*fix_segment)(struct sk_buff *);
17 };
18 #define OVS_GSO_CB(skb) ((struct ovs_gso_cb *)(skb)->cb)
19
20 #define skb_inner_network_header rpl_skb_inner_network_header
21
22 #ifdef NET_SKBUFF_DATA_USES_OFFSET
23 #define skb_inner_network_header rpl_skb_inner_network_header
24 static inline unsigned char *skb_inner_network_header(const struct sk_buff *skb)
25 {
26         return skb->head + OVS_GSO_CB(skb)->inner_network_header;
27 }
28
29 #define skb_inner_mac_header rpl_skb_inner_mac_header
30 static inline unsigned char *skb_inner_mac_header(const struct sk_buff *skb)
31 {
32         return skb->head + OVS_GSO_CB(skb)->inner_mac_header;
33 }
34
35 #else
36
37 #define skb_inner_network_header rpl_skb_inner_network_header
38 static inline unsigned char *skb_inner_network_header(const struct sk_buff *skb)
39 {
40         return OVS_GSO_CB(skb)->inner_network_header;
41 }
42
43 #define skb_inner_mac_header rpl_skb_inner_mac_header
44 static inline unsigned char *skb_inner_mac_header(const struct sk_buff *skb)
45 {
46         return OVS_GSO_CB(skb)->inner_mac_header;
47 }
48
49 #endif
50
51 #define skb_inner_network_offset rpl_skb_inner_network_offset
52 static inline int skb_inner_network_offset(const struct sk_buff *skb)
53 {
54         return skb_inner_network_header(skb) - skb->data;
55 }
56
57 #define skb_inner_mac_offset rpl_skb_inner_mac_offset
58 static inline int skb_inner_mac_offset(const struct sk_buff *skb)
59 {
60         return skb_inner_mac_header(skb) - skb->data;
61 }
62
63 #define skb_reset_inner_headers rpl_skb_reset_inner_headers
64 static inline void skb_reset_inner_headers(struct sk_buff *skb)
65 {
66         BUILD_BUG_ON(sizeof(struct ovs_gso_cb) > FIELD_SIZEOF(struct sk_buff, cb));
67         OVS_GSO_CB(skb)->inner_network_header = skb->network_header;
68         OVS_GSO_CB(skb)->inner_mac_header = skb->mac_header;
69
70         OVS_GSO_CB(skb)->fix_segment = NULL;
71 }
72
73 #define ip_local_out rpl_ip_local_out
74 int ip_local_out(struct sk_buff *skb);
75
76 #endif /* 3.12 */
77 #endif