ethtool: Call ethtool's get/set_settings callbacks with cleaned data

This makes sure that when a driver calls the ethtool's
get/set_settings() callback of another driver, the data passed to it
is clean. This guarantees that speed_hi will be zeroed correctly if
the called callback doesn't explicitely set it: we are sure we don't
get a corrupted speed from the underlying driver. We also take care of
setting the cmd field appropriately (ETHTOOL_GSET/SSET).

This applies to dev_ethtool_get_settings(), which now makes sure it
sets up that ethtool command parameter correctly before passing it to
drivers. This also means that whoever calls dev_ethtool_get_settings()
does not have to clean the ethtool command parameter. This function
also becomes an exported symbol instead of an inline.

All drivers visible to make allyesconfig under x86_64 have been
updated.

Signed-off-by: David Decotigny <decot@google.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
David Decotigny
2011-04-27 18:32:38 +00:00
committed by David S. Miller
parent 3650460543
commit 8ae6daca85
20 changed files with 117 additions and 89 deletions

View File

@@ -318,19 +318,15 @@ void __init tx4939_sio_init(unsigned int sclk, unsigned int cts_mask)
}
#if defined(CONFIG_TC35815) || defined(CONFIG_TC35815_MODULE)
static int tx4939_get_eth_speed(struct net_device *dev)
static u32 tx4939_get_eth_speed(struct net_device *dev)
{
struct ethtool_cmd cmd = { ETHTOOL_GSET };
int speed = 100; /* default 100Mbps */
int err;
if (!dev->ethtool_ops || !dev->ethtool_ops->get_settings)
return speed;
err = dev->ethtool_ops->get_settings(dev, &cmd);
if (err < 0)
return speed;
speed = cmd.speed == SPEED_100 ? 100 : 10;
return speed;
struct ethtool_cmd cmd;
if (dev_ethtool_get_settings(dev, &cmd))
return 100; /* default 100Mbps */
return ethtool_cmd_speed(&cmd);
}
static int tx4939_netdev_event(struct notifier_block *this,
unsigned long event,
void *ptr)
@@ -343,8 +339,7 @@ static int tx4939_netdev_event(struct notifier_block *this,
else if (dev->irq == TXX9_IRQ_BASE + TX4939_IR_ETH(1))
bit = TX4939_PCFG_SPEED1;
if (bit) {
int speed = tx4939_get_eth_speed(dev);
if (speed == 100)
if (tx4939_get_eth_speed(dev) == 100)
txx9_set64(&tx4939_ccfgptr->pcfg, bit);
else
txx9_clear64(&tx4939_ccfgptr->pcfg, bit);