Merge "master" into "wdp".
[sliver-openvswitch.git] / lib / netdev.c
index 09c00af..58f6ceb 100644 (file)
@@ -304,7 +304,6 @@ create_device(struct netdev_options *options, struct netdev_dev **netdev_devp)
  * If the 'may_open' flag is set then the call will succeed even if another
  * caller has already opened it.  It may be to false if the device should not
  * currently be open. */
-
 int
 netdev_open(struct netdev_options *options, struct netdev **netdevp)
 {
@@ -371,6 +370,14 @@ netdev_open_default(const char *name, struct netdev **netdevp)
     return netdev_open(&options, netdevp);
 }
 
+/* Increments the reference count on 'netdev'.  Returns 'netdev'. */
+struct netdev *
+netdev_reopen(struct netdev *netdev)
+{
+    netdev->ref_cnt++;
+    return netdev;
+}
+
 /* Reconfigures the device 'netdev' with 'args'.  'args' may be empty
  * or NULL if none are needed. */
 int
@@ -396,11 +403,13 @@ netdev_reconfigure(struct netdev *netdev, const struct shash *args)
     return 0;
 }
 
-/* Closes and destroys 'netdev'. */
+/* Decrements the reference count on 'netdev'.  If the reference count reaches
+ * zero, closes and destroys 'netdev'. */
 void
 netdev_close(struct netdev *netdev)
 {
-    if (netdev) {
+    assert(!netdev || netdev->ref_cnt > 0);
+    if (netdev && !--netdev->ref_cnt) {
         struct netdev_dev *netdev_dev = netdev_get_dev(netdev);
 
         assert(netdev_dev->ref_cnt);
@@ -1132,6 +1141,7 @@ netdev_init(struct netdev *netdev, struct netdev_dev *netdev_dev)
 {
     memset(netdev, 0, sizeof *netdev);
     netdev->netdev_dev = netdev_dev;
+    netdev->ref_cnt = 1;
     list_push_back(&netdev_list, &netdev->node);
 }
 
@@ -1139,7 +1149,7 @@ netdev_init(struct netdev *netdev, struct netdev_dev *netdev_dev)
  *
  * Normally this function only needs to be called from netdev_close().
  * However, it may be called by providers due to an error on opening
- * that occurs after initialization.  It this case netdev_close() would
+ * that occurs after initialization.  In this case netdev_close() would
  * never be called. */
 void
 netdev_uninit(struct netdev *netdev, bool close)