ovs-controller: Avoid dereferencing NULL pointer when the switch acts as a hub
authorZhengLingyun <konghuarukhr@163.com>
Tue, 8 Oct 2013 15:52:40 +0000 (23:52 +0800)
committerBen Pfaff <blp@nicira.com>
Tue, 8 Oct 2013 17:02:13 +0000 (10:02 -0700)
Starting ovs-controller with '-H' option will lead to a segment fault problem.
Add a check, and adjust the indentation of the following code.

Signed-off-by: ZhengLingyun <konghuarukhr@163.com>
Signed-off-by: Ben Pfaff <blp@nicira.com>
lib/learning-switch.c

index 336257c..0459434 100644 (file)
@@ -475,19 +475,23 @@ lswitch_choose_destination(struct lswitch *sw, const struct flow *flow)
     ofp_port_t out_port;
 
     /* Learn the source MAC. */
-    ovs_rwlock_wrlock(&sw->ml->rwlock);
-    if (mac_learning_may_learn(sw->ml, flow->dl_src, 0)) {
-        struct mac_entry *mac = mac_learning_insert(sw->ml, flow->dl_src, 0);
-        if (mac->port.ofp_port != flow->in_port.ofp_port) {
-            VLOG_DBG_RL(&rl, "%016llx: learned that "ETH_ADDR_FMT" is on "
-                        "port %"PRIu16, sw->datapath_id,
-                        ETH_ADDR_ARGS(flow->dl_src), flow->in_port.ofp_port);
-
-            mac->port.ofp_port = flow->in_port.ofp_port;
-            mac_learning_changed(sw->ml);
+    if (sw->ml) {
+        ovs_rwlock_wrlock(&sw->ml->rwlock);
+        if (mac_learning_may_learn(sw->ml, flow->dl_src, 0)) {
+            struct mac_entry *mac = mac_learning_insert(sw->ml, flow->dl_src,
+                                                        0);
+            if (mac->port.ofp_port != flow->in_port.ofp_port) {
+                VLOG_DBG_RL(&rl, "%016llx: learned that "ETH_ADDR_FMT" is on "
+                            "port %"PRIu16, sw->datapath_id,
+                            ETH_ADDR_ARGS(flow->dl_src),
+                            flow->in_port.ofp_port);
+
+                mac->port.ofp_port = flow->in_port.ofp_port;
+                mac_learning_changed(sw->ml);
+            }
         }
+        ovs_rwlock_unlock(&sw->ml->rwlock);
     }
-    ovs_rwlock_unlock(&sw->ml->rwlock);
 
     /* Drop frames for reserved multicast addresses. */
     if (eth_addr_is_reserved(flow->dl_dst)) {