Patchwork [3.5.y.z,extended,stable] Patch "bonding: don't call update_speed_duplex() under spinlocks" has been added to staging queue

mail settings
Submitter Luis Henriques
Date March 25, 2013, 6:03 p.m.
Message ID <>
Download mbox | patch
Permalink /patch/230936/
State New
Headers show


Luis Henriques - March 25, 2013, 6:03 p.m.
This is a note to let you know that I have just added a patch titled

    bonding: don't call update_speed_duplex() under spinlocks

to the linux-3.5.y-queue branch of the 3.5.y.z extended stable tree 
which can be found at:;a=shortlog;h=refs/heads/linux-3.5.y-queue

If you, or anyone else, feels it should not be added to this tree, please 
reply to this email.

For more information about the 3.5.y.z tree, see



From 5e17fed1a4b7ed360faad7c8fb1006dd0ab4e711 Mon Sep 17 00:00:00 2001
From: Veaceslav Falico <>
Date: Tue, 12 Mar 2013 06:31:32 +0000
Subject: [PATCH] bonding: don't call update_speed_duplex() under spinlocks

commit 876254ae2758d50dcb08c7bd00caf6a806571178 upstream.

bond_update_speed_duplex() might sleep while calling underlying slave's
routines. Move it out of atomic context in bond_enslave() and remove it
from bond_miimon_commit() - it was introduced by commit 546add79, however
when the slave interfaces go up/change state it's their responsibility to
fire NETDEV_UP/NETDEV_CHANGE events so that bonding can properly update
their speed.

I've tested it on all combinations of ifup/ifdown, autoneg/speed/duplex
changes, remote-controlled and local, on (not) MII-based cards. All changes
are visible.

Signed-off-by: Veaceslav Falico <>
Signed-off-by: David S. Miller <>
Signed-off-by: Luis Henriques <>
 drivers/net/bonding/bond_main.c | 6 ++----
 1 file changed, 2 insertions(+), 4 deletions(-)



diff --git a/drivers/net/bonding/bond_main.c b/drivers/net/bonding/bond_main.c
index 2466847..a8406dc 100644
--- a/drivers/net/bonding/bond_main.c
+++ b/drivers/net/bonding/bond_main.c
@@ -1737,6 +1737,8 @@  int bond_enslave(struct net_device *bond_dev, struct net_device *slave_dev)


+	bond_update_speed_duplex(new_slave);

 	new_slave->last_arp_rx = jiffies -
@@ -1789,8 +1791,6 @@  int bond_enslave(struct net_device *bond_dev, struct net_device *slave_dev)
 		new_slave->link == BOND_LINK_DOWN ? "DOWN" :
 			(new_slave->link == BOND_LINK_UP ? "UP" : "BACK"));

-	bond_update_speed_duplex(new_slave);
 	if (USES_PRIMARY(bond->params.mode) && bond->params.primary[0]) {
 		/* if there is a primary slave, remember it */
 		if (strcmp(bond->params.primary, new_slave->dev->name) == 0) {
@@ -2471,8 +2471,6 @@  static void bond_miimon_commit(struct bonding *bond)

-			bond_update_speed_duplex(slave);
 			pr_info("%s: link status definitely up for interface %s, %u Mbps %s duplex.\n",
 				bond->dev->name, slave->dev->name,
 				slave->speed, slave->duplex ? "full" : "half");