Skip to content

Commit 055db69

Browse files
jay-vosburghdavem330
authored andcommitted
bonding: fix slave stuck in BOND_LINK_FAIL state
The bonding miimon logic has a flaw, in that a failure of the rtnl_trylock can cause a slave to become permanently stuck in BOND_LINK_FAIL state. The sequence of events to cause this is as follows: 1) bond_miimon_inspect finds that a slave's link is down, and so calls bond_propose_link_state, setting slave->new_link_state to BOND_LINK_FAIL, then sets slave->new_link to BOND_LINK_DOWN and returns non-zero. 2) In bond_mii_monitor, the rtnl_trylock fails, and the timer is rescheduled. No change is committed. 3) bond_miimon_inspect is called again, but this time the slave from step 1 has recovered. slave->new_link is reset to NOCHANGE, and, as slave->link was never changed, the switch enters the BOND_LINK_UP case, and does nothing. The pending BOND_LINK_FAIL state from step 1 remains pending, as new_link_state is not reset. 4) The state from step 3 persists until another slave changes link state and causes bond_miimon_inspect to return non-zero. At this point, the BOND_LINK_FAIL state change on the slave from steps 1-3 is committed, and the slave will remain stuck in BOND_LINK_FAIL state even though it is actually link up. The remedy for this is to initialize new_link_state on each entry to bond_miimon_inspect, as is already done with new_link. Fixes: fb9eb89 ("bonding: handle link transition from FAIL to UP correctly") Reported-by: Alex Sidorenko <alexandre.sidorenko@hpe.com> Reviewed-by: Jarod Wilson <jarod@redhat.com> Signed-off-by: Jay Vosburgh <jay.vosburgh@canonical.com> Acked-by: Mahesh Bandewar <maheshb@google.com> Signed-off-by: David S. Miller <davem@davemloft.net>
1 parent b7e732f commit 055db69

1 file changed

Lines changed: 1 addition & 0 deletions

File tree

drivers/net/bonding/bond_main.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2042,6 +2042,7 @@ static int bond_miimon_inspect(struct bonding *bond)
20422042

20432043
bond_for_each_slave_rcu(bond, slave, iter) {
20442044
slave->new_link = BOND_LINK_NOCHANGE;
2045+
slave->link_new_state = slave->link;
20452046

20462047
link_state = bond_check_dev_link(bond, slave->dev, 0);
20472048

0 commit comments

Comments
 (0)