Revert "IPoIB: fix mcast_dev_flush/mcast_restart_task race"
authorRoland Dreier <roland@purestorage.com>
Fri, 30 Jan 2015 23:39:11 +0000 (15:39 -0800)
committerRoland Dreier <roland@purestorage.com>
Fri, 30 Jan 2015 23:39:11 +0000 (15:39 -0800)
This reverts commit e5d1dcf1b0951f4ba00d93653942dda6196109d8.

The series of IPoIB bug fixes that went into 3.19-rc1 introduce
regressions, and after trying to sort things out, we decided to revert
to 3.18's IPoIB driver and get things right for 3.20.

Signed-off-by: Roland Dreier <roland@purestorage.com>
drivers/infiniband/ulp/ipoib/ipoib_multicast.c

index 41325960e4e0410ab91c0f982e9a654fecfc0f1a..a52c9f3f7e420d733b2ca165f84dad6bf8750485 100644 (file)
@@ -802,10 +802,7 @@ void ipoib_mcast_dev_flush(struct net_device *dev)
 
        spin_unlock_irqrestore(&priv->lock, flags);
 
-       /*
-        * make sure the in-flight joins have finished before we attempt
-        * to leave
-        */
+       /* seperate between the wait to the leave*/
        list_for_each_entry_safe(mcast, tmcast, &remove_list, list)
                if (test_bit(IPOIB_MCAST_FLAG_BUSY, &mcast->flags))
                        wait_for_completion(&mcast->done);
@@ -926,38 +923,14 @@ void ipoib_mcast_restart_task(struct work_struct *work)
        netif_addr_unlock(dev);
        local_irq_restore(flags);
 
-       /*
-        * make sure the in-flight joins have finished before we attempt
-        * to leave
-        */
-       list_for_each_entry_safe(mcast, tmcast, &remove_list, list)
-               if (test_bit(IPOIB_MCAST_FLAG_BUSY, &mcast->flags))
-                       wait_for_completion(&mcast->done);
-
-       /*
-        * We have to cancel outside of the spinlock, but we have to
-        * take the rtnl lock or else we race with the removal of
-        * entries from the remove list in mcast_dev_flush as part
-        * of ipoib_stop() which will call mcast_stop_thread with
-        * flush == 1 while holding the rtnl lock, and the
-        * flush_workqueue won't complete until this restart_mcast_task
-        * completes.  So do like the carrier on task and attempt to
-        * take the rtnl lock, but if we can't before the ADMIN_UP flag
-        * goes away, then just return and know that the remove list will
-        * get flushed later by mcast_dev_flush.
-        */
-       while (!rtnl_trylock()) {
-               if (!test_bit(IPOIB_FLAG_ADMIN_UP, &priv->flags))
-                       return;
-               else
-                       msleep(20);
-       }
+       /* We have to cancel outside of the spinlock */
        list_for_each_entry_safe(mcast, tmcast, &remove_list, list) {
                ipoib_mcast_leave(mcast->dev, mcast);
                ipoib_mcast_free(mcast);
        }
-       ipoib_mcast_start_thread(dev);
-       rtnl_unlock();
+
+       if (test_bit(IPOIB_FLAG_ADMIN_UP, &priv->flags))
+               ipoib_mcast_start_thread(dev);
 }
 
 #ifdef CONFIG_INFINIBAND_IPOIB_DEBUG