Signed-off-by: Pravin B Shelar <pshe...@nicira.com>
---
 datapath/datapath.c                           |   50 ++++++++++++-------------
 datapath/linux/compat/include/linux/netlink.h |    6 +++
 datapath/linux/compat/include/net/genetlink.h |    8 ++++
 datapath/tunnel.c                             |   35 +++++++++--------
 datapath/vport-capwap.c                       |    5 ++-
 5 files changed, 63 insertions(+), 41 deletions(-)

diff --git a/datapath/datapath.c b/datapath/datapath.c
index 65f4dc8..a28096e 100644
--- a/datapath/datapath.c
+++ b/datapath/datapath.c
@@ -61,8 +61,8 @@
 #include "vport-internal_dev.h"
 
 #if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,18) || \
-    LINUX_VERSION_CODE >= KERNEL_VERSION(3,6,0)
-#error Kernels before 2.6.18 or after 3.5 are not supported by this version of 
Open vSwitch.
+    LINUX_VERSION_CODE >= KERNEL_VERSION(3,7,0)
+#error Kernels before 2.6.18 or after 3.6 are not supported by this version of 
Open vSwitch.
 #endif
 
 #define REHASH_FLOW_INTERVAL (10 * 60 * HZ)
@@ -1080,7 +1080,7 @@ static int ovs_flow_cmd_new_or_set(struct sk_buff *skb, 
struct genl_info *info)
                /* Put flow in bucket. */
                ovs_flow_tbl_insert(table, flow, &key, key_len);
 
-               reply = ovs_flow_cmd_build_info(flow, dp, info->snd_pid,
+               reply = ovs_flow_cmd_build_info(flow, dp, 
genl_info_port_id(info),
                                                info->snd_seq,
                                                OVS_FLOW_CMD_NEW);
        } else {
@@ -1118,7 +1118,7 @@ static int ovs_flow_cmd_new_or_set(struct sk_buff *skb, 
struct genl_info *info)
                        ovs_flow_deferred_free_acts(old_acts);
                }
 
-               reply = ovs_flow_cmd_build_info(flow, dp, info->snd_pid,
+               reply = ovs_flow_cmd_build_info(flow, dp, 
genl_info_port_id(info),
                                               info->snd_seq, OVS_FLOW_CMD_NEW);
 
                /* Clear stats. */
@@ -1130,7 +1130,7 @@ static int ovs_flow_cmd_new_or_set(struct sk_buff *skb, 
struct genl_info *info)
        }
 
        if (!IS_ERR(reply))
-               genl_notify(reply, genl_info_net(info), info->snd_pid,
+               genl_notify(reply, genl_info_net(info), genl_info_port_id(info),
                           ovs_dp_flow_multicast_group.id, info->nlhdr,
                           GFP_KERNEL);
        else
@@ -1171,7 +1171,7 @@ static int ovs_flow_cmd_get(struct sk_buff *skb, struct 
genl_info *info)
        if (!flow)
                return -ENOENT;
 
-       reply = ovs_flow_cmd_build_info(flow, dp, info->snd_pid,
+       reply = ovs_flow_cmd_build_info(flow, dp, genl_info_port_id(info),
                                        info->snd_seq, OVS_FLOW_CMD_NEW);
        if (IS_ERR(reply))
                return PTR_ERR(reply);
@@ -1213,13 +1213,13 @@ static int ovs_flow_cmd_del(struct sk_buff *skb, struct 
genl_info *info)
 
        ovs_flow_tbl_remove(table, flow);
 
-       err = ovs_flow_cmd_fill_info(flow, dp, reply, info->snd_pid,
+       err = ovs_flow_cmd_fill_info(flow, dp, reply, genl_info_port_id(info),
                                     info->snd_seq, 0, OVS_FLOW_CMD_DEL);
        BUG_ON(err < 0);
 
        ovs_flow_deferred_free(flow);
 
-       genl_notify(reply, genl_info_net(info), info->snd_pid,
+       genl_notify(reply, genl_info_net(info), genl_info_port_id(info),
                    ovs_dp_flow_multicast_group.id, info->nlhdr, GFP_KERNEL);
        return 0;
 }
@@ -1247,7 +1247,7 @@ static int ovs_flow_cmd_dump(struct sk_buff *skb, struct 
netlink_callback *cb)
                        break;
 
                if (ovs_flow_cmd_fill_info(flow, dp, skb,
-                                          NETLINK_CB(cb->skb).pid,
+                                          NETLINK_CB_PORT_ID(cb->skb),
                                           cb->nlh->nlmsg_seq, NLM_F_MULTI,
                                           OVS_FLOW_CMD_NEW) < 0)
                        break;
@@ -1448,7 +1448,7 @@ static int ovs_dp_cmd_new(struct sk_buff *skb, struct 
genl_info *info)
                goto err_destroy_ports_array;
        }
 
-       reply = ovs_dp_cmd_build_info(dp, info->snd_pid,
+       reply = ovs_dp_cmd_build_info(dp, genl_info_port_id(info),
                                      info->snd_seq, OVS_DP_CMD_NEW);
        err = PTR_ERR(reply);
        if (IS_ERR(reply))
@@ -1460,7 +1460,7 @@ static int ovs_dp_cmd_new(struct sk_buff *skb, struct 
genl_info *info)
 
        rtnl_unlock();
 
-       genl_notify(reply, genl_info_net(info), info->snd_pid,
+       genl_notify(reply, genl_info_net(info), genl_info_port_id(info),
                    ovs_dp_datapath_multicast_group.id, info->nlhdr,
                    GFP_KERNEL);
        return 0;
@@ -1527,7 +1527,7 @@ static int ovs_dp_cmd_del(struct sk_buff *skb, struct 
genl_info *info)
        if (IS_ERR(dp))
                return err;
 
-       reply = ovs_dp_cmd_build_info(dp, info->snd_pid,
+       reply = ovs_dp_cmd_build_info(dp, genl_info_port_id(info),
                                      info->snd_seq, OVS_DP_CMD_DEL);
        err = PTR_ERR(reply);
        if (IS_ERR(reply))
@@ -1535,7 +1535,7 @@ static int ovs_dp_cmd_del(struct sk_buff *skb, struct 
genl_info *info)
 
        __dp_destroy(dp);
 
-       genl_notify(reply, genl_info_net(info), info->snd_pid,
+       genl_notify(reply, genl_info_net(info), genl_info_port_id(info),
                    ovs_dp_datapath_multicast_group.id, info->nlhdr,
                    GFP_KERNEL);
 
@@ -1556,7 +1556,7 @@ static int ovs_dp_cmd_set(struct sk_buff *skb, struct 
genl_info *info)
        if (IS_ERR(dp))
                return PTR_ERR(dp);
 
-       reply = ovs_dp_cmd_build_info(dp, info->snd_pid,
+       reply = ovs_dp_cmd_build_info(dp, genl_info_port_id(info),
                                      info->snd_seq, OVS_DP_CMD_NEW);
        if (IS_ERR(reply)) {
                err = PTR_ERR(reply);
@@ -1565,7 +1565,7 @@ static int ovs_dp_cmd_set(struct sk_buff *skb, struct 
genl_info *info)
                return 0;
        }
 
-       genl_notify(reply, genl_info_net(info), info->snd_pid,
+       genl_notify(reply, genl_info_net(info), genl_info_port_id(info),
                    ovs_dp_datapath_multicast_group.id, info->nlhdr,
                    GFP_KERNEL);
 
@@ -1586,7 +1586,7 @@ static int ovs_dp_cmd_get(struct sk_buff *skb, struct 
genl_info *info)
        if (IS_ERR(dp))
                return PTR_ERR(dp);
 
-       reply = ovs_dp_cmd_build_info(dp, info->snd_pid,
+       reply = ovs_dp_cmd_build_info(dp, genl_info_port_id(info),
                                      info->snd_seq, OVS_DP_CMD_NEW);
        if (IS_ERR(reply))
                return PTR_ERR(reply);
@@ -1603,7 +1603,7 @@ static int ovs_dp_cmd_dump(struct sk_buff *skb, struct 
netlink_callback *cb)
 
        list_for_each_entry(dp, &ovs_net->dps, list_node) {
                if (i >= skip &&
-                   ovs_dp_cmd_fill_info(dp, skb, NETLINK_CB(cb->skb).pid,
+                   ovs_dp_cmd_fill_info(dp, skb, NETLINK_CB_PORT_ID(cb->skb),
                                         cb->nlh->nlmsg_seq, NLM_F_MULTI,
                                         OVS_DP_CMD_NEW) < 0)
                        break;
@@ -1848,7 +1848,7 @@ static int ovs_vport_cmd_new(struct sk_buff *skb, struct 
genl_info *info)
 
        err = change_vport(vport, a);
        if (!err) {
-               reply = ovs_vport_cmd_build_info(vport, info->snd_pid,
+               reply = ovs_vport_cmd_build_info(vport, genl_info_port_id(info),
                                                 info->snd_seq,
                                                 OVS_VPORT_CMD_NEW);
                if (IS_ERR(reply))
@@ -1858,7 +1858,7 @@ static int ovs_vport_cmd_new(struct sk_buff *skb, struct 
genl_info *info)
                ovs_dp_detach_port(vport);
                goto exit_unlock;
        }
-       genl_notify(reply, genl_info_net(info), info->snd_pid,
+       genl_notify(reply, genl_info_net(info), genl_info_port_id(info),
                    ovs_dp_vport_multicast_group.id, info->nlhdr, GFP_KERNEL);
 
 exit_unlock:
@@ -1898,7 +1898,7 @@ static int ovs_vport_cmd_set(struct sk_buff *skb, struct 
genl_info *info)
        if (!err && a[OVS_VPORT_ATTR_UPCALL_PID])
                vport->upcall_pid = nla_get_u32(a[OVS_VPORT_ATTR_UPCALL_PID]);
 
-       reply = ovs_vport_cmd_build_info(vport, info->snd_pid, info->snd_seq,
+       reply = ovs_vport_cmd_build_info(vport, genl_info_port_id(info), 
info->snd_seq,
                                         OVS_VPORT_CMD_NEW);
        if (IS_ERR(reply)) {
                netlink_set_err(GENL_SOCK(sock_net(skb->sk)), 0,
@@ -1906,7 +1906,7 @@ static int ovs_vport_cmd_set(struct sk_buff *skb, struct 
genl_info *info)
                goto exit_unlock;
        }
 
-       genl_notify(reply, genl_info_net(info), info->snd_pid,
+       genl_notify(reply, genl_info_net(info), genl_info_port_id(info),
                    ovs_dp_vport_multicast_group.id, info->nlhdr, GFP_KERNEL);
 
 exit_unlock:
@@ -1937,7 +1937,7 @@ static int ovs_vport_cmd_del(struct sk_buff *skb, struct 
genl_info *info)
                goto exit_unlock;
        }
 
-       reply = ovs_vport_cmd_build_info(vport, info->snd_pid, info->snd_seq,
+       reply = ovs_vport_cmd_build_info(vport, genl_info_port_id(info), 
info->snd_seq,
                                         OVS_VPORT_CMD_DEL);
        err = PTR_ERR(reply);
        if (IS_ERR(reply))
@@ -1945,7 +1945,7 @@ static int ovs_vport_cmd_del(struct sk_buff *skb, struct 
genl_info *info)
 
        ovs_dp_detach_port(vport);
 
-       genl_notify(reply, genl_info_net(info), info->snd_pid,
+       genl_notify(reply, genl_info_net(info), genl_info_port_id(info),
                    ovs_dp_vport_multicast_group.id, info->nlhdr, GFP_KERNEL);
 
 exit_unlock:
@@ -1972,7 +1972,7 @@ static int ovs_vport_cmd_get(struct sk_buff *skb, struct 
genl_info *info)
        if (IS_ERR(vport))
                goto exit_unlock;
 
-       reply = ovs_vport_cmd_build_info(vport, info->snd_pid, info->snd_seq,
+       reply = ovs_vport_cmd_build_info(vport, genl_info_port_id(info), 
info->snd_seq,
                                         OVS_VPORT_CMD_NEW);
        err = PTR_ERR(reply);
        if (IS_ERR(reply))
@@ -2008,7 +2008,7 @@ static int ovs_vport_cmd_dump(struct sk_buff *skb, struct 
netlink_callback *cb)
                hlist_for_each_entry_rcu(vport, n, &dp->ports[i], dp_hash_node) 
{
                        if (j >= skip &&
                            ovs_vport_cmd_fill_info(vport, skb,
-                                                   NETLINK_CB(cb->skb).pid,
+                                                   NETLINK_CB_PORT_ID(cb->skb),
                                                    cb->nlh->nlmsg_seq,
                                                    NLM_F_MULTI,
                                                    OVS_VPORT_CMD_NEW) < 0)
diff --git a/datapath/linux/compat/include/linux/netlink.h 
b/datapath/linux/compat/include/linux/netlink.h
index 44a2073..73af1cb 100644
--- a/datapath/linux/compat/include/linux/netlink.h
+++ b/datapath/linux/compat/include/linux/netlink.h
@@ -32,4 +32,10 @@ static inline struct nlmsghdr *nlmsg_hdr(const struct 
sk_buff *skb)
 }
 #endif
 
+#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,6,0)
+#define NETLINK_CB_PORT_ID(skb) (NETLINK_CB((skb)).portid)
+#else
+#define NETLINK_CB_PORT_ID(skb) (NETLINK_CB((skb)).pid)
+#endif
+
 #endif
diff --git a/datapath/linux/compat/include/net/genetlink.h 
b/datapath/linux/compat/include/net/genetlink.h
index af7d5fd..a4fc431 100644
--- a/datapath/linux/compat/include/net/genetlink.h
+++ b/datapath/linux/compat/include/net/genetlink.h
@@ -171,6 +171,14 @@ static inline struct net *genl_info_net(struct genl_info 
*info)
 }
 #endif
 
+static inline u32 genl_info_port_id(struct genl_info *info)
+{
+#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,6,0)
+       return info->snd_portid;
+#else
+       return info->snd_pid;
+#endif
+}
 #if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,32)
 #define genlmsg_unicast(ignore_net, skb, pid)   genlmsg_unicast(skb, pid)
 #endif
diff --git a/datapath/tunnel.c b/datapath/tunnel.c
index 5b74877..04ff55f 100644
--- a/datapath/tunnel.c
+++ b/datapath/tunnel.c
@@ -701,32 +701,35 @@ static bool check_mtu(struct sk_buff *skb,
        return true;
 }
 
-static struct rtable *find_route(const struct tnl_mutable_config *mutable,
-                                  __be32 saddr, __be32 daddr, u8 ipproto,
-                                  u8 tos)
+static struct rtable *find_route(struct net *net,
+               __be32 *saddr, __be32 daddr, u8 ipproto,
+               u8 tos)
 {
+       struct rtable *rt;
        /* Tunnel configuration keeps DSCP part of TOS bits, But Linux
         * router expect RT_TOS bits only. */
 
 #if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,39)
        struct flowi fl = { .nl_u = { .ip4_u = {
                                        .daddr = daddr,
-                                       .saddr = saddr,
+                                       .saddr = *saddr,
                                        .tos   = RT_TOS(tos) } },
                                        .proto = ipproto };
-       struct rtable *rt;
 
-       if (unlikely(ip_route_output_key(port_key_get_net(&mutable->key), &rt, 
&fl)))
+       if (unlikely(ip_route_output_key(net, &rt, &fl)))
                return ERR_PTR(-EADDRNOTAVAIL);
-
+       *saddr = fl.nl_u.ip4_u.saddr;
        return rt;
 #else
        struct flowi4 fl = { .daddr = daddr,
-                            .saddr = saddr,
+                            .saddr = *saddr,
                             .flowi4_tos = RT_TOS(tos),
                             .flowi4_proto = ipproto };
 
-       return ip_route_output_key(port_key_get_net(&mutable->key), &fl);
+       rt = ip_route_output_key(net, &fl);
+       if (!IS_ERR(rt))
+               *saddr = fl.saddr;
+       return rt;
 #endif
 }
 
@@ -947,7 +950,8 @@ int ovs_tnl_send(struct vport *vport, struct sk_buff *skb)
        }
 
        /* Route lookup */
-       rt = find_route(mutable, saddr, daddr, tnl_vport->tnl_ops->ipproto, 
tos);
+       rt = find_route(port_key_get_net(&mutable->key), &saddr, daddr,
+                         tnl_vport->tnl_ops->ipproto, tos);
        if (IS_ERR(rt))
                goto error_free;
 
@@ -1007,10 +1011,9 @@ int ovs_tnl_send(struct vport *vport, struct sk_buff 
*skb)
                iph = ip_hdr(skb);
                iph->version    = 4;
                iph->ihl        = sizeof(struct iphdr) >> 2;
-               iph->frag_off   = htons(IP_DF);
                iph->protocol   = tnl_vport->tnl_ops->ipproto;
-               iph->daddr      = rt->rt_dst;
-               iph->saddr      = rt->rt_src;
+               iph->daddr      = daddr;
+               iph->saddr      = saddr;
                iph->tos        = tos;
                iph->ttl        = ttl;
                iph->frag_off   = frag_off;
@@ -1106,9 +1109,11 @@ static int tnl_set_config(struct net *net, struct nlattr 
*options,
        if (ipv4_is_multicast(mutable->key.daddr)) {
                struct net_device *dev;
                struct rtable *rt;
+               __be32 saddr = mutable->key.saddr;
 
-               rt = find_route(mutable, mutable->key.saddr, mutable->key.daddr,
-                                 tnl_ops->ipproto, mutable->tos);
+               rt = find_route(port_key_get_net(&mutable->key),
+                            &saddr, mutable->key.daddr,
+                            tnl_ops->ipproto, mutable->tos);
                if (IS_ERR(rt))
                        return -EADDRNOTAVAIL;
                dev = rt_dst(rt).dev;
diff --git a/datapath/vport-capwap.c b/datapath/vport-capwap.c
index e466323..83c4b03 100644
--- a/datapath/vport-capwap.c
+++ b/datapath/vport-capwap.c
@@ -791,8 +791,11 @@ static struct sk_buff *defrag(struct sk_buff *skb, bool 
frag_last)
        struct frag_queue *fq;
 
        if (atomic_read(&ns_frag_state->mem) > ns_frag_state->high_thresh)
+#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,6,0)
+               inet_frag_evictor(ns_frag_state, &frag_state, true);
+#else
                inet_frag_evictor(ns_frag_state, &frag_state);
-
+#endif
        match.daddr = iph->daddr;
        match.saddr = iph->saddr;
        match.id = cwh->frag_id;
-- 
1.7.10

_______________________________________________
dev mailing list
dev@openvswitch.org
http://openvswitch.org/mailman/listinfo/dev

Reply via email to