]> Pileus Git - ~andy/linux/commitdiff
bonding: fix locking in enslave failure path
authornikolay@redhat.com <nikolay@redhat.com>
Mon, 22 Apr 2013 08:12:22 +0000 (08:12 +0000)
committerDavid S. Miller <davem@davemloft.net>
Thu, 25 Apr 2013 08:03:21 +0000 (04:03 -0400)
In commit 3c5913b53fefc9d9e15a2d0f93042766658d9f3f ("bonding:
primary_slave & curr_active_slave are not cleaned on enslave failure")
I didn't account for the use of curr_active_slave without curr_slave_lock
and since there are such users, we should hold bond->lock for writing while
setting it to NULL (in the NULL case we don't need the curr_slave_lock).
Keeping the bond lock as to avoid the extra release/acquire cycle.

Signed-off-by: Nikolay Aleksandrov <nikolay@redhat.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
drivers/net/bonding/bond_main.c

index dbbea0eec134f1b2f0225161a33111264450f48e..7db40de1b41f441690589a4d0793e092c9d3c898 100644 (file)
@@ -1915,14 +1915,16 @@ err_detach:
        bond_detach_slave(bond, new_slave);
        if (bond->primary_slave == new_slave)
                bond->primary_slave = NULL;
-       write_unlock_bh(&bond->lock);
        if (bond->curr_active_slave == new_slave) {
+               bond_change_active_slave(bond, NULL);
+               write_unlock_bh(&bond->lock);
                read_lock(&bond->lock);
                write_lock_bh(&bond->curr_slave_lock);
-               bond_change_active_slave(bond, NULL);
                bond_select_active_slave(bond);
                write_unlock_bh(&bond->curr_slave_lock);
                read_unlock(&bond->lock);
+       } else {
+               write_unlock_bh(&bond->lock);
        }
        slave_disable_netpoll(new_slave);