mac-learning: Change mac_learning_set_flood_vlans() to not take ownership.
authorBen Pfaff <blp@nicira.com>
Wed, 6 Apr 2011 22:31:22 +0000 (15:31 -0700)
committerBen Pfaff <blp@nicira.com>
Tue, 26 Apr 2011 00:11:29 +0000 (17:11 -0700)
These new semantics are less efficient in the case where the flood_vlans
actually changed, but that should be very rare.

There are no advantages to this change on its own, but upcoming commits
will add multiple layers between the code supplying the flood_vlans and
actually calling mac_learning_set_flood_vlans().  Consistency in this
multilayered interface seems valuable, and the rest of it does not transfer
ownership from the caller to the callee.

lib/bitmap.h
lib/mac-learning.c
lib/mac-learning.h
lib/vlan-bitmap.h
vswitchd/bridge.c

index fd05d3da135457356e2e347f377059b67638831d..f6feff0859d99392f218740c2aba8f1588234103 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 2009, 2010 Nicira Networks.
+ * Copyright (c) 2008, 2009, 2010, 2011 Nicira Networks.
  *
  * Licensed under the Apache License, Version 2.0 (the "License");
  * you may not use this file except in compliance with the License.
@@ -53,6 +53,12 @@ bitmap_allocate(size_t n_bits)
     return xzalloc(bitmap_n_bytes(n_bits));
 }
 
+static inline unsigned long *
+bitmap_clone(const unsigned long *bitmap, size_t n_bits)
+{
+    return xmemdup(bitmap, bitmap_n_bytes(n_bits));
+}
+
 static inline void
 bitmap_free(unsigned long *bitmap)
 {
index a57bbc7599f93210c533cd74ab9308aeab5c543e..981578d8aa688ae9a547b9c3bc3729dd07cf3423 100644 (file)
@@ -139,17 +139,19 @@ mac_learning_destroy(struct mac_learning *ml)
 }
 
 /* Provides a bitmap of VLANs which have learning disabled, that is, VLANs on
- * which all packets are flooded.  It takes ownership of the bitmap.  Returns
- * true if the set has changed from the previous value. */
+ * which all packets are flooded.  Returns true if the set has changed from the
+ * previous value. */
 bool
-mac_learning_set_flood_vlans(struct mac_learning *ml, unsigned long *bitmap)
+mac_learning_set_flood_vlans(struct mac_learning *ml,
+                             const unsigned long *bitmap)
 {
-    bool ret = vlan_bitmap_equal(ml->flood_vlans, bitmap);
-
-    bitmap_free(ml->flood_vlans);
-    ml->flood_vlans = bitmap;
-
-    return ret;
+    if (vlan_bitmap_equal(ml->flood_vlans, bitmap)) {
+        return false;
+    } else {
+        bitmap_free(ml->flood_vlans);
+        ml->flood_vlans = vlan_bitmap_clone(bitmap);
+        return true;
+    }
 }
 
 static bool
index 51a7ac7380afb4488ca57e7df54b02d06fca6ea8..d9fa433cde662429cc758d461fb17293513335d1 100644 (file)
@@ -96,7 +96,7 @@ void mac_learning_wait(struct mac_learning *);
 
 /* Configuration. */
 bool mac_learning_set_flood_vlans(struct mac_learning *,
-                                  unsigned long *bitmap);
+                                  const unsigned long *bitmap);
 
 /* Learning. */
 bool mac_learning_may_learn(const struct mac_learning *,
index eca42fea9cf01c63ff730134b19265bc9c30fff0..6d74d4008b30c2a115b90d7b5f168a2bc444ee3f 100644 (file)
@@ -37,4 +37,11 @@ vlan_bitmap_contains(const unsigned long *vlans, uint16_t vid)
     return !vlans || bitmap_is_set(vlans, vid);
 }
 
+/* Returns a new copy of 'vlans'. */
+static inline unsigned long *
+vlan_bitmap_clone(const unsigned long *vlans)
+{
+    return vlans ? bitmap_clone(vlans, 4096) : NULL;
+}
+
 #endif /* lib/vlan-bitmap.h */
index e3e5a4c717a25ef9ed57e7dd5724267c6360f3e3..9e9566cc3ea17368abb7e9362a241dd113f101dc 100644 (file)
@@ -3621,6 +3621,7 @@ mirror_reconfigure(struct bridge *br)
         bridge_flush(br);
         mac_learning_flush(br->ml);
     }
+    free(rspan_vlans);
 }
 
 static void