diff options
| author | David S. Miller <davem@davemloft.net> | 2017-03-28 07:11:50 +0300 |
|---|---|---|
| committer | David S. Miller <davem@davemloft.net> | 2017-03-28 07:11:50 +0300 |
| commit | 95ed0edd833fa07299d4ff38116c0496ce766364 (patch) | |
| tree | 20269c62b0a9d0ff31acb4421f54fedd9f2291cc /include | |
| parent | 205ed44ec0676099fc17ba6d3195e48bea947147 (diff) | |
| parent | e292dcae1648cd5b5c80031a154f594aa590667f (diff) | |
| download | linux-95ed0edd833fa07299d4ff38116c0496ce766364.tar.xz | |
Merge branch 'bond-link-status-fixes'
Mahesh Bandewar says:
====================
link-status fixes for mii-monitoring
The mii monitoring is divided into two phases - inspect and commit. The
inspect phase technically should not make any changes to the state and
defer it to the commit phase. However detected link state inconsistencies
on several machines and discovered that it's the result of some
inconsistent update to link states and assumption that you *always* get
rtnl-mutex. In reality when trylock() fails to acquire rtnl-mutex, the
commit phase is postponed until next mii-mon run. At the next round
because of the state change performed in the previous inspect-run, this
round does not detect any changes and would skip calling commit phase.
This would result in an inconsistent state until next link event happens
(if it ever happens).
During the the commit phase, it's always assumed that speed and duplex
fetch is always successful, but that's always not the case. However the
slave state is marked UP irrespective of speed / duplex fetch operation.
If the speed / duplex fetch operation results in insane values for either
of these two fields, then keeping internal link state UP is not going to
provide fruitful results either.
Please see into individual patches for more details.
====================
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'include')
| -rw-r--r-- | include/net/bonding.h | 22 |
1 files changed, 17 insertions, 5 deletions
diff --git a/include/net/bonding.h b/include/net/bonding.h index 3c857778a6ca..fb2dd97857c4 100644 --- a/include/net/bonding.h +++ b/include/net/bonding.h @@ -153,7 +153,8 @@ struct slave { unsigned long last_link_up; unsigned long last_rx; unsigned long target_last_arp_rx[BOND_MAX_ARP_TARGETS]; - s8 link; /* one of BOND_LINK_XXXX */ + s8 link; /* one of BOND_LINK_XXXX */ + s8 link_new_state; /* one of BOND_LINK_XXXX */ s8 new_link; u8 backup:1, /* indicates backup slave. Value corresponds with BOND_STATE_ACTIVE and BOND_STATE_BACKUP */ @@ -504,13 +505,17 @@ static inline bool bond_is_slave_inactive(struct slave *slave) return slave->inactive; } -static inline void bond_set_slave_link_state(struct slave *slave, int state, - bool notify) +static inline void bond_propose_link_state(struct slave *slave, int state) +{ + slave->link_new_state = state; +} + +static inline void bond_commit_link_state(struct slave *slave, bool notify) { - if (slave->link == state) + if (slave->link == slave->link_new_state) return; - slave->link = state; + slave->link = slave->link_new_state; if (notify) { bond_queue_slave_event(slave); bond_lower_state_changed(slave); @@ -523,6 +528,13 @@ static inline void bond_set_slave_link_state(struct slave *slave, int state, } } +static inline void bond_set_slave_link_state(struct slave *slave, int state, + bool notify) +{ + bond_propose_link_state(slave, state); + bond_commit_link_state(slave, notify); +} + static inline void bond_slave_link_notify(struct bonding *bond) { struct list_head *iter; |
