Improve compatibility fallbacks for allocating multicast groups.
authorBen Pfaff <blp@nicira.com>
Sat, 3 Jan 2009 00:10:19 +0000 (16:10 -0800)
committerBen Pfaff <blp@nicira.com>
Sat, 3 Jan 2009 00:26:30 +0000 (16:26 -0800)
The linux-2.6 compatibility code for allocating multicast groups only
allocated a single multicast group per Generic Netlink family.  However,
OpenFlow performance is going to be better if we allocate one per OpenFlow
datapath (which are all in the same Generic Netlink family).  This commit
implements that.

Thanks to Justin for pointing out the issue.

datapath/linux-2.6/Modules.mk
datapath/linux-2.6/compat-2.6/genetlink-brcompat.c [new file with mode: 0644]
datapath/linux-2.6/compat-2.6/genetlink-openflow.c [new file with mode: 0644]
datapath/linux-2.6/compat-2.6/genetlink.c [deleted file]

index b3211c140a38a2722f5a3f70079ea480a5961fda..6f4f7a41d172b2d69ca7656709b9acc3c709030f 100644 (file)
@@ -1,7 +1,7 @@
 dist_modules += brcompat
 
 openflow_sources += \
-       linux-2.6/compat-2.6/genetlink.c \
+       linux-2.6/compat-2.6/genetlink-openflow.c \
        linux-2.6/compat-2.6/random32.c
 
 openflow_headers += \
@@ -22,7 +22,7 @@ openflow_headers += \
        linux-2.6/compat-2.6/include/net/genetlink.h
 
 brcompat_sources = \
-       linux-2.6/compat-2.6/genetlink.c \
+       linux-2.6/compat-2.6/genetlink-brcompat.c \
        brcompat.c 
 
 brcompat_headers = 
diff --git a/datapath/linux-2.6/compat-2.6/genetlink-brcompat.c b/datapath/linux-2.6/compat-2.6/genetlink-brcompat.c
new file mode 100644 (file)
index 0000000..f30996c
--- /dev/null
@@ -0,0 +1,20 @@
+#include "net/genetlink.h"
+
+#include <linux/version.h>
+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,23)
+
+/* We fix grp->id to 32 so that it doesn't collide with any of the multicast
+ * groups selected by openflow_mod, which uses groups 16 through 31.  Collision
+ * isn't fatal--multicast listeners should check that the family is the one
+ * that they want and discard others--but it wastes time and memory to receive
+ * unwanted messages. */
+int genl_register_mc_group(struct genl_family *family,
+                          struct genl_multicast_group *grp)
+{
+       grp->id = 32;
+       grp->family = family;
+
+       return 0;
+}
+
+#endif /* kernel < 2.6.23 */
diff --git a/datapath/linux-2.6/compat-2.6/genetlink-openflow.c b/datapath/linux-2.6/compat-2.6/genetlink-openflow.c
new file mode 100644 (file)
index 0000000..9e09215
--- /dev/null
@@ -0,0 +1,22 @@
+#include "net/genetlink.h"
+
+#include <linux/version.h>
+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,23)
+
+/* We use multicast groups 16 through 31 to avoid colliding with the multicast
+ * group selected by brcompat_mod, which uses groups 32.  Collision isn't
+ * fatal--multicast listeners should check that the family is the one that they
+ * want and discard others--but it wastes time and memory to receive unwanted
+ * messages. */
+int genl_register_mc_group(struct genl_family *family,
+                          struct genl_multicast_group *grp)
+{
+       /* This code is called single-threaded. */
+       static unsigned int next_id = 0;
+       grp->id = next_id++ % 16 + 16;
+       grp->family = family;
+
+       return 0;
+}
+
+#endif /* kernel < 2.6.23 */
diff --git a/datapath/linux-2.6/compat-2.6/genetlink.c b/datapath/linux-2.6/compat-2.6/genetlink.c
deleted file mode 100644 (file)
index a6fa073..0000000
+++ /dev/null
@@ -1,15 +0,0 @@
-#include "net/genetlink.h"
-
-#include <linux/version.h>
-#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,23)
-
-int genl_register_mc_group(struct genl_family *family,
-        struct genl_multicast_group *grp)
-{
-       grp->id = family->id;
-       grp->family = family;
-
-       return 0;
-}
-
-#endif /* kernel < 2.6.23 */