datapath: Add support for kernel 3.14.
[sliver-openvswitch.git] / datapath / vport.h
index 2cf2b18..cfaea09 100644 (file)
@@ -23,6 +23,7 @@
 #include <linux/list.h>
 #include <linux/netlink.h>
 #include <linux/openvswitch.h>
+#include <linux/reciprocal_div.h>
 #include <linux/skbuff.h>
 #include <linux/spinlock.h>
 #include <linux/u64_stats_sync.h>
@@ -50,6 +51,10 @@ void ovs_vport_get_stats(struct vport *, struct ovs_vport_stats *);
 int ovs_vport_set_options(struct vport *, struct nlattr *options);
 int ovs_vport_get_options(const struct vport *, struct sk_buff *);
 
+int ovs_vport_set_upcall_portids(struct vport *, struct nlattr *pids);
+int ovs_vport_get_upcall_portids(const struct vport *, struct sk_buff *);
+u32 ovs_vport_find_upcall_portid(const struct vport *, struct sk_buff *);
+
 int ovs_vport_send(struct vport *, struct sk_buff *);
 
 /* The following definitions are for implementers of vport devices: */
@@ -60,13 +65,27 @@ struct vport_err_stats {
        u64 tx_dropped;
        u64 tx_errors;
 };
+/**
+ * struct vport_portids - array of netlink portids of a vport.
+ *                        must be protected by rcu.
+ * @rn_ids: The reciprocal value of @n_ids.
+ * @rcu: RCU callback head for deferred destruction.
+ * @n_ids: Size of @ids array.
+ * @ids: Array storing the Netlink socket pids to be used for packets received
+ * on this port that miss the flow table.
+ */
+struct vport_portids {
+       struct reciprocal_value rn_ids;
+       struct rcu_head rcu;
+       u32 n_ids;
+       u32 ids[];
+};
 
 /**
  * struct vport - one port within a datapath
  * @rcu: RCU callback head for deferred destruction.
  * @dp: Datapath to which this port belongs.
- * @upcall_portid: The Netlink port to use for packets received on this port that
- * miss the flow table.
+ * @upcall_portids: RCU protected 'struct vport_portids'.
  * @port_no: Index into @dp's @ports array.
  * @hash_node: Element in @dev_table hash table in vport.c.
  * @dp_hash_node: Element in @datapath->ports hash table in datapath.c.
@@ -80,14 +99,14 @@ struct vport_err_stats {
 struct vport {
        struct rcu_head rcu;
        struct datapath *dp;
-       u32 upcall_portid;
+       struct vport_portids __rcu *upcall_portids;
        u16 port_no;
 
        struct hlist_node hash_node;
        struct hlist_node dp_hash_node;
        const struct vport_ops *ops;
 
-       struct pcpu_tstats __percpu *percpu_stats;
+       struct pcpu_sw_netstats __percpu *percpu_stats;
 
        spinlock_t stats_lock;
        struct vport_err_stats err_stats;
@@ -112,7 +131,7 @@ struct vport_parms {
        /* For ovs_vport_alloc(). */
        struct datapath *dp;
        u16 port_no;
-       u32 upcall_portid;
+       struct nlattr *upcall_portids;
 };
 
 /**
@@ -173,7 +192,7 @@ void ovs_vport_deferred_free(struct vport *vport);
  */
 static inline void *vport_priv(const struct vport *vport)
 {
-       return (u8 *)vport + ALIGN(sizeof(struct vport), VPORT_ALIGN);
+       return (u8 *)(uintptr_t)vport + ALIGN(sizeof(struct vport), VPORT_ALIGN);
 }
 
 /**
@@ -186,9 +205,9 @@ static inline void *vport_priv(const struct vport *vport)
  * the result of a hash table lookup.  @priv must point to the start of the
  * private data area.
  */
-static inline struct vport *vport_from_priv(const void *priv)
+static inline struct vport *vport_from_priv(void *priv)
 {
-       return (struct vport *)(priv - ALIGN(sizeof(struct vport), VPORT_ALIGN));
+       return (struct vport *)((u8 *)priv - ALIGN(sizeof(struct vport), VPORT_ALIGN));
 }
 
 void ovs_vport_receive(struct vport *, struct sk_buff *,