* [RFC PATCH 14/17] lxt973: Clean up fixed-mode fiber PHY handling
From: Kyle Moffett @ 2011-10-20 21:00 UTC (permalink / raw)
To: linux-kernel, netdev; +Cc: Kyle Moffett
In-Reply-To: <1319144425-15547-1-git-send-email-Kyle.D.Moffett@boeing.com>
The LXT973 driver does not need to detect fiber/copper PHY modes in the
phy ->probe() method, it can instead check the register directly from
the ->config_aneg() method.
Furthermore, the driver should not manually poke the registers, but
instead adjust the PHY state variables and allow genphy_config_aneg() to
do the rest of the work.
NOTE: Needs testing by somebody with the hardware.
Signed-off-by: Kyle Moffett <Kyle.D.Moffett@boeing.com>
---
drivers/net/phy/lxt.c | 33 +++++++++++++--------------------
1 files changed, 13 insertions(+), 20 deletions(-)
diff --git a/drivers/net/phy/lxt.c b/drivers/net/phy/lxt.c
index 902d2d1..186dc94 100644
--- a/drivers/net/phy/lxt.c
+++ b/drivers/net/phy/lxt.c
@@ -122,31 +122,25 @@ static int lxt971_config_intr(struct phy_device *phydev)
return err;
}
-static int lxt973_probe(struct phy_device *phydev)
+static int lxt973_config_aneg(struct phy_device *phydev)
{
int val = phy_read(phydev, MII_LXT973_PCR);
+ if (val < 0)
+ return val;
+ /*
+ * If the PHY is in fiber-only mode then ignore the ethtool settings
+ * and force the required 100Base-FX mode.
+ */
if (val & PCR_FIBER_SELECT) {
- /*
- * If fiber is selected, then the only correct setting
- * is 100Mbps, full duplex, and auto negotiation off.
- */
- val = phy_read(phydev, MII_BMCR);
- val |= (BMCR_SPEED100 | BMCR_FULLDPLX);
- val &= ~BMCR_ANENABLE;
- phy_write(phydev, MII_BMCR, val);
- /* Remember that the port is in fiber mode. */
- phydev->priv = lxt973_probe;
- } else {
- phydev->priv = NULL;
+ phydev->supported = ADVERTISED_FIBRE|ADVERTISED_100baseT_Full;
+ phydev->advertising = phydev->supported;
+ phydev->autoneg = AUTONEG_DISABLE;
+ phydev->speed = SPEED_100;
+ phydev->duplex = DUPLEX_FULL;
}
- return 0;
-}
-static int lxt973_config_aneg(struct phy_device *phydev)
-{
- /* Do nothing if port is in fiber mode. */
- return phydev->priv ? 0 : genphy_config_aneg(phydev);
+ return genphy_config_aneg(phydev);
}
static struct phy_driver lxt_drivers[] = { {
@@ -174,7 +168,6 @@ static struct phy_driver lxt_drivers[] = { {
.phy_id_mask = 0xfffffff0,
.features = PHY_BASIC_FEATURES,
.flags = 0,
- .probe = lxt973_probe,
.config_aneg = lxt973_config_aneg,
.driver = { .owner = THIS_MODULE,},
} };
--
1.7.2.5
^ permalink raw reply related
* [RFC PATCH 13/17] mpc836x: Move board-specific bcm5481 fixup out of the PHY driver
From: Kyle Moffett @ 2011-10-20 21:00 UTC (permalink / raw)
To: linux-kernel, netdev; +Cc: linuxppc-dev, Paul Mackerras, Kyle Moffett
In-Reply-To: <1319144425-15547-1-git-send-email-Kyle.D.Moffett@boeing.com>
By comparing the BCM5481 registers modified in the ->config_aneg()
method with the datasheet I have for the BCM5482, it appears that the
register writes are adjusting signal timing to work around a known
trace-length issue on the PCB.
Such hardware workarounds don't belong in the generic driver, and should
instead be placed in a board-specific PHY fixup.
NOTE: Needs testing by somebody with the hardware.
Signed-off-by: Kyle Moffett <Kyle.D.Moffett@boeing.com>
---
arch/powerpc/platforms/83xx/mpc836x_rdk.c | 35 ++++++++++++++++++++++++++++
drivers/net/phy/broadcom.c | 36 -----------------------------
2 files changed, 35 insertions(+), 36 deletions(-)
diff --git a/arch/powerpc/platforms/83xx/mpc836x_rdk.c b/arch/powerpc/platforms/83xx/mpc836x_rdk.c
index b0090aa..b7cc607 100644
--- a/arch/powerpc/platforms/83xx/mpc836x_rdk.c
+++ b/arch/powerpc/platforms/83xx/mpc836x_rdk.c
@@ -14,6 +14,7 @@
#include <linux/kernel.h>
#include <linux/pci.h>
+#include <linux/phy.h>
#include <linux/of_platform.h>
#include <linux/io.h>
#include <asm/prom.h>
@@ -38,6 +39,36 @@ static int __init mpc836x_rdk_declare_of_platform_devices(void)
}
machine_device_initcall(mpc836x_rdk, mpc836x_rdk_declare_of_platform_devices);
+static int mpc836x_rdk_bcm5481_fixup(struct phy_device *phydev)
+{
+ int reg;
+
+ if (phydev->interface != PHY_INTERFACE_MODE_RGMII_RXID)
+ return;
+
+ /*
+ * There is no BCM5481 specification available, so down
+ * here is everything we know about "register 0x18". This
+ * at least helps BCM5481 to successfuly receive packets
+ * on MPC8360E-RDK board. Peter Barada <peterb@logicpd.com>
+ * says: "This sets delay between the RXD and RXC signals
+ * instead of using trace lengths to achieve timing".
+ */
+
+ /* Set RDX clk delay. */
+ reg = 0x7 | (0x7 << 12);
+ phy_write(phydev, 0x18, reg);
+ reg = phy_read(phydev, 0x18);
+ if (reg < 0)
+ return reg;
+
+ /* Set RDX-RXC skew. */
+ reg |= (1 << 8);
+ /* Write bits 14:0. */
+ reg |= (1 << 15);
+ return phy_write(phydev, 0x18, reg);
+}
+
static void __init mpc836x_rdk_setup_arch(void)
{
#ifdef CONFIG_PCI
@@ -54,6 +85,10 @@ static void __init mpc836x_rdk_setup_arch(void)
#ifdef CONFIG_QUICC_ENGINE
qe_reset();
#endif
+#ifdef CONFIG_BROADCOM_PHY
+ phy_register_fixup_for_uid(0x0143bca0, 0xfffffff0,
+ &mpc836x_rdk_bcm5481_phy_fixup);
+#endif
}
static void __init mpc836x_rdk_init_IRQ(void)
diff --git a/drivers/net/phy/broadcom.c b/drivers/net/phy/broadcom.c
index 1b83f75..8c03ebc 100644
--- a/drivers/net/phy/broadcom.c
+++ b/drivers/net/phy/broadcom.c
@@ -539,41 +539,6 @@ static int bcm54xx_config_intr(struct phy_device *phydev)
return err;
}
-static int bcm5481_config_aneg(struct phy_device *phydev)
-{
- int ret;
-
- /* Aneg firsly. */
- ret = genphy_config_aneg(phydev);
-
- /* Then we can set up the delay. */
- if (phydev->interface == PHY_INTERFACE_MODE_RGMII_RXID) {
- u16 reg;
-
- /*
- * There is no BCM5481 specification available, so down
- * here is everything we know about "register 0x18". This
- * at least helps BCM5481 to successfuly receive packets
- * on MPC8360E-RDK board. Peter Barada <peterb@logicpd.com>
- * says: "This sets delay between the RXD and RXC signals
- * instead of using trace lengths to achieve timing".
- */
-
- /* Set RDX clk delay. */
- reg = 0x7 | (0x7 << 12);
- phy_write(phydev, 0x18, reg);
-
- reg = phy_read(phydev, 0x18);
- /* Set RDX-RXC skew. */
- reg |= (1 << 8);
- /* Write bits 14:0. */
- reg |= (1 << 15);
- phy_write(phydev, 0x18, reg);
- }
-
- return ret;
-}
-
static int brcm_phy_setbits(struct phy_device *phydev, int reg, int set)
{
int val;
@@ -736,7 +701,6 @@ static struct phy_driver broadcom_drivers[] = { {
SUPPORTED_Pause | SUPPORTED_Asym_Pause,
.flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT,
.config_init = bcm54xx_config_init,
- .config_aneg = bcm5481_config_aneg,
.ack_interrupt = bcm54xx_ack_interrupt,
.config_intr = bcm54xx_config_intr,
.driver = { .owner = THIS_MODULE },
--
1.7.2.5
^ permalink raw reply related
* [RFC PATCH 12/17] tc35815: Use standard phy_init_hw() instead of BMCR_RESET bit
From: Kyle Moffett @ 2011-10-20 21:00 UTC (permalink / raw)
To: linux-kernel, netdev; +Cc: Kyle Moffett, Lucas De Marchi, Paul
In-Reply-To: <1319144425-15547-1-git-send-email-Kyle.D.Moffett@boeing.com>
The PHY should not be manually reset with the BMCR, as that will undo
board-specific PHY fixups and driver-specific phy->drv->config_init().
Instead, the PHY should be reset using phy_init_hw().
NOTE: Depends on earlier phy_init_hw() patch.
Not-yet-Signed-off-by: Kyle Moffett <Kyle.D.Moffett@boeing.com>
---
drivers/net/tc35815.c | 15 ++-------------
1 files changed, 2 insertions(+), 13 deletions(-)
diff --git a/drivers/net/tc35815.c b/drivers/net/tc35815.c
index 4a55a16..c3422f8 100644
--- a/drivers/net/tc35815.c
+++ b/drivers/net/tc35815.c
@@ -1175,19 +1175,8 @@ static void tc35815_restart(struct net_device *dev)
{
struct tc35815_local *lp = netdev_priv(dev);
- if (lp->phy_dev) {
- int timeout;
-
- phy_write(lp->phy_dev, MII_BMCR, BMCR_RESET);
- timeout = 100;
- while (--timeout) {
- if (!(phy_read(lp->phy_dev, MII_BMCR) & BMCR_RESET))
- break;
- udelay(1);
- }
- if (!timeout)
- printk(KERN_ERR "%s: BMCR reset failed.\n", dev->name);
- }
+ if (lp->phy_dev)
+ phy_init_hw(lp->phy_dev);
spin_lock_bh(&lp->rx_lock);
spin_lock_irq(&lp->lock);
--
1.7.2.5
^ permalink raw reply related
* [RFC PATCH 11/17] sh_eth: Don't unnecessarily reset the PHY
From: Kyle Moffett @ 2011-10-20 21:00 UTC (permalink / raw)
To: linux-kernel, netdev
Cc: Kyle Moffett, David S. Miller, Yoshihiro Shimoda,
Nobuhiro Iwamatsu, Kuninori Morimoto
In-Reply-To: <1319144425-15547-1-git-send-email-Kyle.D.Moffett@boeing.com>
The PHY is already reset during driver probing, and this manual reset
afterwards will wipe out board-specific PHY fixups and driver-specific
phy->drv->config_init() register tweaks.
Signed-off-by: Kyle Moffett <Kyle.D.Moffett@boeing.com>
---
drivers/net/sh_eth.c | 19 +------------------
1 files changed, 1 insertions(+), 18 deletions(-)
diff --git a/drivers/net/sh_eth.c b/drivers/net/sh_eth.c
index 1c1666e..7ef4378 100644
--- a/drivers/net/sh_eth.c
+++ b/drivers/net/sh_eth.c
@@ -1235,23 +1235,6 @@ static int sh_eth_phy_init(struct net_device *ndev)
return 0;
}
-/* PHY control start function */
-static int sh_eth_phy_start(struct net_device *ndev)
-{
- struct sh_eth_private *mdp = netdev_priv(ndev);
- int ret;
-
- ret = sh_eth_phy_init(ndev);
- if (ret)
- return ret;
-
- /* reset phy - this also wakes it from PDOWN */
- phy_write(mdp->phydev, MII_BMCR, BMCR_RESET);
- phy_start(mdp->phydev);
-
- return 0;
-}
-
static int sh_eth_get_settings(struct net_device *ndev,
struct ethtool_cmd *ecmd)
{
@@ -1410,7 +1393,7 @@ static int sh_eth_open(struct net_device *ndev)
goto out_free_irq;
/* PHY control start*/
- ret = sh_eth_phy_start(ndev);
+ ret = sh_eth_phy_init(ndev);
if (ret)
goto out_free_irq;
--
1.7.2.5
^ permalink raw reply related
* [RFC PATCH 10/17] pxa186_eth: Use standardized phy_init_hw() for PHY reset
From: Kyle Moffett @ 2011-10-20 21:00 UTC (permalink / raw)
To: linux-kernel, netdev
Cc: Kyle Moffett, David S. Miller, Richard Cochran, Joe Perches,
Jon Mason
In-Reply-To: <1319144425-15547-1-git-send-email-Kyle.D.Moffett@boeing.com>
The PHY does not need to be reset immediately before phy_attach(), as
that function will call phy_init_hw() properly on its own. Furthermore,
the PHY should not be manually reset, as that will undo board-specific
PHY fixups and driver-specific phy->drv->config_init() register tweaks.
NOTE: Depends on earlier phy_init_hw() patch.
Not-yet-Signed-off-by: Kyle Moffett <Kyle.D.Moffett@boeing.com>
---
drivers/net/pxa168_eth.c | 21 +--------------------
1 files changed, 1 insertions(+), 20 deletions(-)
diff --git a/drivers/net/pxa168_eth.c b/drivers/net/pxa168_eth.c
index d17d062..ab3bca9 100644
--- a/drivers/net/pxa168_eth.c
+++ b/drivers/net/pxa168_eth.c
@@ -323,23 +323,6 @@ static void ethernet_phy_set_addr(struct pxa168_eth_private *pep, int phy_addr)
wrl(pep, PHY_ADDRESS, reg_data);
}
-static void ethernet_phy_reset(struct pxa168_eth_private *pep)
-{
- int data;
-
- data = phy_read(pep->phy, MII_BMCR);
- if (data < 0)
- return;
-
- data |= BMCR_RESET;
- if (phy_write(pep->phy, MII_BMCR, data) < 0)
- return;
-
- do {
- data = phy_read(pep->phy, MII_BMCR);
- } while (data >= 0 && data & BMCR_RESET);
-}
-
static void rxq_refill(struct net_device *dev)
{
struct pxa168_eth_private *pep = netdev_priv(dev);
@@ -647,7 +630,7 @@ static void eth_port_start(struct net_device *dev)
struct ethtool_cmd cmd;
pxa168_get_settings(pep->dev, &cmd);
- ethernet_phy_reset(pep);
+ phy_init_hw(pep->phy);
pxa168_set_settings(pep->dev, &cmd);
}
@@ -1393,8 +1376,6 @@ static struct phy_device *phy_scan(struct pxa168_eth_private *pep, int phy_addr)
static void phy_init(struct pxa168_eth_private *pep, int speed, int duplex)
{
struct phy_device *phy = pep->phy;
- ethernet_phy_reset(pep);
-
phy_attach(pep->dev, dev_name(&phy->dev), 0, PHY_INTERFACE_MODE_MII);
if (speed == 0) {
--
1.7.2.5
^ permalink raw reply related
* [RFC PATCH 09/17] mv643xx_eth: Use standardized phy_init_hw() for PHY reset
From: Kyle Moffett @ 2011-10-20 21:00 UTC (permalink / raw)
To: linux-kernel, netdev; +Cc: Kyle Moffett, Lennert Buytenhek
In-Reply-To: <1319144425-15547-1-git-send-email-Kyle.D.Moffett@boeing.com>
The PHY does not need to be reset immediately before phy_attach(), as
that function will call phy_init_hw() properly on its own. Furthermore,
the PHY should not be manually reset, as that will undo board-specific
PHY fixups and driver-specific phy->drv->config_init() register tweaks.
NOTE: Depends on earlier phy_init_hw() patch.
Not-yet-Signed-off-by: Kyle Moffett <Kyle.D.Moffett@boeing.com>
---
drivers/net/mv643xx_eth.c | 22 +---------------------
1 files changed, 1 insertions(+), 21 deletions(-)
diff --git a/drivers/net/mv643xx_eth.c b/drivers/net/mv643xx_eth.c
index 2596999..d3e223c 100644
--- a/drivers/net/mv643xx_eth.c
+++ b/drivers/net/mv643xx_eth.c
@@ -2188,23 +2188,6 @@ static inline void oom_timer_wrapper(unsigned long data)
napi_schedule(&mp->napi);
}
-static void phy_reset(struct mv643xx_eth_private *mp)
-{
- int data;
-
- data = phy_read(mp->phy, MII_BMCR);
- if (data < 0)
- return;
-
- data |= BMCR_RESET;
- if (phy_write(mp->phy, MII_BMCR, data) < 0)
- return;
-
- do {
- data = phy_read(mp->phy, MII_BMCR);
- } while (data >= 0 && data & BMCR_RESET);
-}
-
static void port_start(struct mv643xx_eth_private *mp)
{
u32 pscr;
@@ -2217,7 +2200,7 @@ static void port_start(struct mv643xx_eth_private *mp)
struct ethtool_cmd cmd;
mv643xx_eth_get_settings(mp->dev, &cmd);
- phy_reset(mp);
+ phy_init_hw(mp->phy);
mv643xx_eth_set_settings(mp->dev, &cmd);
}
@@ -2779,9 +2762,6 @@ static struct phy_device *phy_scan(struct mv643xx_eth_private *mp,
static void phy_init(struct mv643xx_eth_private *mp, int speed, int duplex)
{
struct phy_device *phy = mp->phy;
-
- phy_reset(mp);
-
phy_attach(mp->dev, dev_name(&phy->dev), 0, PHY_INTERFACE_MODE_GMII);
if (speed == 0) {
--
1.7.2.5
^ permalink raw reply related
* [RFC PATCH 08/17] drivers/net/bfin_mac: Don't unnecessarily reset the PHY
From: Kyle Moffett @ 2011-10-20 21:00 UTC (permalink / raw)
To: linux-kernel, netdev
Cc: Kyle Moffett, David S. Miller, Mike Frysinger, Sonic Zhang,
Tobias Klauser, uclinux-dist-devel
In-Reply-To: <1319144425-15547-1-git-send-email-Kyle.D.Moffett@boeing.com>
The PHY is already reset during driver probing, and this manual reset
afterwards will wipe out board-specific PHY fixups and driver-specific
phy->drv->config_init() register tweaks.
Signed-off-by: Kyle Moffett <Kyle.D.Moffett@boeing.com>
---
drivers/net/bfin_mac.c | 1 -
1 files changed, 0 insertions(+), 1 deletions(-)
diff --git a/drivers/net/bfin_mac.c b/drivers/net/bfin_mac.c
index 6c019e1..1427ec3 100644
--- a/drivers/net/bfin_mac.c
+++ b/drivers/net/bfin_mac.c
@@ -1402,7 +1402,6 @@ static int bfin_mac_open(struct net_device *dev)
return ret;
phy_start(lp->phydev);
- phy_write(lp->phydev, MII_BMCR, BMCR_RESET);
setup_system_regs(dev);
setup_mac_addr(dev->dev_addr);
--
1.7.2.5
^ permalink raw reply related
* [RFC PATCH 07/17] phy: Unify PHY reset, initialization, and fixup handling
From: Kyle Moffett @ 2011-10-20 21:00 UTC (permalink / raw)
To: linux-kernel, netdev
Cc: Kyle Moffett, Randy Dunlap, Stephen Hemminger, David S. Miller,
David Decotigny, Andrew Morton, Lucas De Marchi,
Marc Kleine-Budde, Mike Frysinger, linux-doc
In-Reply-To: <1319144425-15547-1-git-send-email-Kyle.D.Moffett@boeing.com>
Whenever the BMCR_RESET bit is set (in the MII_BMCR register), the
IEEE standards say we MUST poll until it is cleared, which may take up
to 0.5s. Failing to do so may result in MDIO bus errors or ignored
register writes. Furthermore, some chips require a little extra time
*after* the bit is cleared before they will work correctly.
This modifies the phy_init_hw() helper function to perform the necessary
full-reset followed by scans of board-specific and driver-specific fixups,
then ensures that phy_init_hw() is called everywhere necessary.
Since some of the fixups must be the first thing run after reset, all
ethernet drivers should call phy_init_hw() to set things up instead of
setting BMCR_RESET by hand.
NOTE: I'm pretty sure the locking is wrong here, it's on my TODO list.
Not-yet-Signed-off-by: Kyle Moffett <Kyle.D.Moffett@boeing.com>
---
Documentation/networking/phy.txt | 5 +-
drivers/net/phy/phy.c | 20 ++++--
drivers/net/phy/phy_device.c | 132 +++++++++++++++++++++++++++-----------
include/linux/phy.h | 1 -
4 files changed, 111 insertions(+), 47 deletions(-)
diff --git a/Documentation/networking/phy.txt b/Documentation/networking/phy.txt
index 62f890e..0db8c81 100644
--- a/Documentation/networking/phy.txt
+++ b/Documentation/networking/phy.txt
@@ -251,15 +251,16 @@ Writing a PHY driver
Each driver consists of a number of function pointers:
+ probe: Allocate phy->priv, optionally refuse to bind.
+ PHY may not have been reset or had fixups run yet.
config_init: configures PHY into a sane state after a reset.
For instance, a Davicom PHY requires descrambling disabled.
- probe: Does any setup needed by the driver
suspend/resume: power management
config_aneg: Changes the speed/duplex/negotiation settings
read_status: Reads the current speed/duplex/negotiation settings
ack_interrupt: Clear a pending interrupt
config_intr: Enable or disable interrupts
- remove: Does any driver take-down
+ remove: Free phy->priv and clean up driver state
All of these functions are optional. It is strongly preferred to use the
generic phy driver's versions of these two functions if at all possible:
diff --git a/drivers/net/phy/phy.c b/drivers/net/phy/phy.c
index cc7f353..c378f91 100644
--- a/drivers/net/phy/phy.c
+++ b/drivers/net/phy/phy.c
@@ -354,14 +354,20 @@ int phy_mii_ioctl(struct phy_device *phydev,
}
mdiobus_write(phydev->bus, mii_data->phy_id,
- mii_data->reg_num, val);
+ mii_data->reg_num, val);
+
+ /*
+ * If they wanted to reset the PHY, then this needs to also
+ * wait for the reset to complete. or later MDIO cycles may
+ * fail with errors.
+ *
+ * NOTE: This interface is for debug only, and therefore it
+ * will NOT rerun board or driver initialization.
+ */
+ if ((mii_data->reg_num == MII_BMCR) && (val & BMCR_RESET)
+ && (mii_data->phy_id == phydev->addr))
+ phy_poll_reset(phydev);
- if (mii_data->reg_num == MII_BMCR &&
- val & BMCR_RESET &&
- phydev->drv->config_init) {
- phy_scan_fixups(phydev);
- phydev->drv->config_init(phydev);
- }
break;
case SIOCSHWTSTAMP:
diff --git a/drivers/net/phy/phy_device.c b/drivers/net/phy/phy_device.c
index 8990e87..fc0f315 100644
--- a/drivers/net/phy/phy_device.c
+++ b/drivers/net/phy/phy_device.c
@@ -125,30 +125,6 @@ static int phy_needs_fixup(struct phy_device *phydev, struct phy_fixup *fixup)
return 1;
}
-/* Runs any matching fixups for this phydev */
-int phy_scan_fixups(struct phy_device *phydev)
-{
- struct phy_fixup *fixup;
-
- mutex_lock(&phy_fixup_lock);
- list_for_each_entry(fixup, &phy_fixup_list, list) {
- if (phy_needs_fixup(phydev, fixup)) {
- int err;
-
- err = fixup->run(phydev);
-
- if (err < 0) {
- mutex_unlock(&phy_fixup_lock);
- return err;
- }
- }
- }
- mutex_unlock(&phy_fixup_lock);
-
- return 0;
-}
-EXPORT_SYMBOL(phy_scan_fixups);
-
static struct phy_device* phy_device_create(struct mii_bus *bus,
int addr, int phy_id)
{
@@ -274,12 +250,18 @@ int phy_device_register(struct phy_device *phydev)
return -EINVAL;
phydev->bus->phy_map[phydev->addr] = phydev;
- /* Run all of the fixups for this PHY */
- phy_scan_fixups(phydev);
+ /* Reset and reinitialize the PHY */
+ err = phy_init_hw(phydev);
+ if (err) {
+ dev_err(phydev->dev.parent, "phy %d failed to init: %d\n",
+ phydev->addr, err);
+ goto out;
+ }
err = device_register(&phydev->dev);
if (err) {
- pr_err("phy %d failed to register\n", phydev->addr);
+ dev_err(phydev->dev.parent, "phy %d failed to register: %d\n",
+ phydev->addr, err);
goto out;
}
@@ -380,7 +362,7 @@ struct phy_device * phy_connect(struct net_device *dev, const char *bus_id,
* PHY with the requested name */
d = bus_find_device_by_name(&mdio_bus_type, NULL, bus_id);
if (!d) {
- pr_err("PHY %s not found\n", bus_id);
+ dev_err(&dev->dev, "PHY %s not found\n", bus_id);
return ERR_PTR(-ENODEV);
}
phydev = to_phy_device(d);
@@ -410,19 +392,93 @@ void phy_disconnect(struct phy_device *phydev)
}
EXPORT_SYMBOL(phy_disconnect);
-int phy_init_hw(struct phy_device *phydev)
+/**
+ * phy_poll_reset - Safely wait until a PHY reset has properly completed
+ * @phydev: The PHY device to poll
+ *
+ * Description: According to IEEE 802.3, Section 2, Subsection 22.2.4.1.1, as
+ * published in 2008, a PHY reset may take up to 0.5 seconds. The MII BMCR
+ * register must be polled until the BMCR_RESET bit clears.
+ *
+ * Furthermore, any attempts to write to PHY registers may have no effect
+ * or even generate MDIO bus errors until this is complete.
+ *
+ * Some PHYs (such as the Marvell 88E1111) don't entirely conform to the
+ * standard and do not fully reset after the BMCR_RESET bit is set, and may
+ * even *REQUIRE* a soft-reset to properly restart autonegotiation. In an
+ * effort to support such broken PHYs, this function is separate from the
+ * standard phy_init_hw() which will zero all the other bits in the BMCR
+ * and reapply all driver-specific and board-specific fixups.
+ */
+int phy_poll_reset(struct phy_device *phydev)
{
+ /* Poll until the reset bit clears (50ms per retry == 0.6 sec) */
+ unsigned int retries = 12;
int ret;
+ do {
+ msleep(50);
+ ret = phy_read(phydev, MII_BMCR);
+ if (ret < 0)
+ return ret;
+ } while (ret & BMCR_RESET && --retries);
+ if (ret & BMCR_RESET)
+ return -ETIMEDOUT;
+
+ /*
+ * Some chips (smsc911x) may still need up to another 1ms after the
+ * BMCR_RESET bit is cleared before they are usable.
+ */
+ msleep(1);
+ return 0;
+}
- if (!phydev->drv || !phydev->drv->config_init)
- return 0;
+/**
+ * phy_init_hw - Fully reinitialize a PHY and apply board and driver fixups
+ * @phydev: the PHY device to reset
+ *
+ * Description: Reset the specified PHY using the BMCR_RESET bit, clearing
+ * all of the other bits in the BMCR. On standards-compliant PHYs this
+ * should also restore all other registers to power-on defaults.
+ *
+ * In addition, this will automatically run any board-specific and
+ * driver-specific fixups.
+ */
+int phy_init_hw(struct phy_device *phydev)
+{
+ struct phy_fixup *fixup;
- ret = phy_scan_fixups(phydev);
+ /* Always perform a reset first */
+ int ret = phy_write(phydev, MII_BMCR, BMCR_RESET);
if (ret < 0)
return ret;
- return phydev->drv->config_init(phydev);
+ /* Now wait for the reset to complete */
+ ret = phy_poll_reset(phydev);
+ if (ret < 0)
+ return ret;
+
+ /* Scan board-specific PHY fixups */
+ mutex_lock(&phy_fixup_lock);
+ list_for_each_entry(fixup, &phy_fixup_list, list) {
+ if (!phy_needs_fixup(phydev, fixup))
+ continue;
+
+ ret = fixup->run(phydev);
+ if (ret < 0)
+ break;
+ }
+ mutex_unlock(&phy_fixup_lock);
+ if (ret < 0)
+ return ret;
+
+ /* Now driver-specific initialization */
+ ret = 0;
+ if (phydev->drv && phydev->drv->config_init)
+ ret = phydev->drv->config_init(phydev);
+
+ return ret;
}
+EXPORT_SYMBOL(phy_init_hw);
/**
* phy_attach_direct - attach a network device to a given PHY device pointer
@@ -471,9 +527,11 @@ static int phy_attach_direct(struct net_device *dev, struct phy_device *phydev,
phydev->state = PHY_READY;
- /* Do initial configuration here, now that
- * we have certain key parameters
- * (dev_flags and interface) */
+ /*
+ * The PHY was already reset and initialize when it was first probed,
+ * but we just set the dev_flags and interface fields, so the driver
+ * may need to re-initialize things again to take those into account.
+ */
err = phy_init_hw(phydev);
if (err)
phy_detach(phydev);
@@ -503,7 +561,7 @@ struct phy_device *phy_attach(struct net_device *dev,
* PHY with the requested name */
d = bus_find_device_by_name(bus, NULL, bus_id);
if (!d) {
- pr_err("PHY %s not found\n", bus_id);
+ dev_err(&dev->dev, "PHY %s not found\n", bus_id);
return ERR_PTR(-ENODEV);
}
phydev = to_phy_device(d);
diff --git a/include/linux/phy.h b/include/linux/phy.h
index c6bbb38..f07fc1c 100644
--- a/include/linux/phy.h
+++ b/include/linux/phy.h
@@ -526,7 +526,6 @@ int phy_register_fixup_for_id(const char *bus_id,
int (*run)(struct phy_device *));
int phy_register_fixup_for_uid(u32 phy_uid, u32 phy_uid_mask,
int (*run)(struct phy_device *));
-int phy_scan_fixups(struct phy_device *phydev);
int __init mdio_bus_init(void);
void mdio_bus_exit(void);
--
1.7.2.5
^ permalink raw reply related
* [RFC PATCH 05/17] phy_driver: Make .read_status()/.config_aneg() optional
From: Kyle Moffett @ 2011-10-20 21:00 UTC (permalink / raw)
To: linux-kernel, netdev
Cc: Kyle Moffett, Randy Dunlap, Stephen Hemminger, David S. Miller,
Greg Dietsche, Giuseppe Cavallaro, David Daney, Arnaud Patard,
Grant Likely, Baruch Siach, Thorsten Schubert, David Decotigny,
Andrew Morton, Lucas De Marchi, Marc Kleine-Budde, Mike Frysinger,
linux-doc
In-Reply-To: <1319144425-15547-1-git-send-email-Kyle.D.Moffett@boeing.com>
Approximately 90% of the PHY drivers follow the PHY layer docs and
simply use &genphy_read_status and &genphy_config_aneg. There would
seem to be little point in requiring them all to manually specify those
functions.
This patch makes it much easier for subsequent patches to split and
refactor the functionality of the .config_aneg() method.
Signed-off-by: Kyle Moffett <Kyle.D.Moffett@boeing.com>
---
Documentation/networking/phy.txt | 13 +++++--------
drivers/net/phy/bcm63xx.c | 4 ----
drivers/net/phy/broadcom.c | 20 --------------------
drivers/net/phy/cicada.c | 4 ----
drivers/net/phy/davicom.c | 4 ----
drivers/net/phy/icplus.c | 2 --
drivers/net/phy/lxt.c | 5 -----
drivers/net/phy/marvell.c | 6 ------
drivers/net/phy/micrel.c | 10 ----------
drivers/net/phy/national.c | 2 --
drivers/net/phy/phy.c | 5 ++++-
drivers/net/phy/phy_device.c | 2 --
drivers/net/phy/qsemi.c | 2 --
drivers/net/phy/realtek.c | 2 --
drivers/net/phy/smsc.c | 10 ----------
drivers/net/phy/ste10Xp.c | 4 ----
drivers/net/phy/vitesse.c | 4 ----
include/linux/phy.h | 8 +++++---
18 files changed, 14 insertions(+), 93 deletions(-)
diff --git a/Documentation/networking/phy.txt b/Documentation/networking/phy.txt
index 9eb1ba5..62f890e 100644
--- a/Documentation/networking/phy.txt
+++ b/Documentation/networking/phy.txt
@@ -261,14 +261,11 @@ Writing a PHY driver
config_intr: Enable or disable interrupts
remove: Does any driver take-down
- Of these, only config_aneg and read_status are required to be
- assigned by the driver code. The rest are optional. Also, it is
- preferred to use the generic phy driver's versions of these two
- functions if at all possible: genphy_read_status and
- genphy_config_aneg. If this is not possible, it is likely that
- you only need to perform some actions before and after invoking
- these functions, and so your functions will wrap the generic
- ones.
+ All of these functions are optional. It is strongly preferred to use the
+ generic phy driver's versions of these two functions if at all possible:
+ genphy_read_status and genphy_config_aneg. If this is not possible, it is
+ likely that you only need to perform some actions before and after invoking
+ these functions, and so your functions will wrap the generic ones.
Feel free to look at the Marvell, Cicada, and Davicom drivers in
drivers/net/phy/ for examples (the lxt and qsemi drivers have
diff --git a/drivers/net/phy/bcm63xx.c b/drivers/net/phy/bcm63xx.c
index e16f98c..c455f02 100644
--- a/drivers/net/phy/bcm63xx.c
+++ b/drivers/net/phy/bcm63xx.c
@@ -82,8 +82,6 @@ static struct phy_driver bcm63xx_1_driver = {
.features = (PHY_BASIC_FEATURES | SUPPORTED_Pause),
.flags = PHY_HAS_INTERRUPT,
.config_init = bcm63xx_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = bcm63xx_ack_interrupt,
.config_intr = bcm63xx_config_intr,
.driver = { .owner = THIS_MODULE },
@@ -97,8 +95,6 @@ static struct phy_driver bcm63xx_2_driver = {
.features = (PHY_BASIC_FEATURES | SUPPORTED_Pause),
.flags = PHY_HAS_INTERRUPT,
.config_init = bcm63xx_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = bcm63xx_ack_interrupt,
.config_intr = bcm63xx_config_intr,
.driver = { .owner = THIS_MODULE },
diff --git a/drivers/net/phy/broadcom.c b/drivers/net/phy/broadcom.c
index d84c422..f220264 100644
--- a/drivers/net/phy/broadcom.c
+++ b/drivers/net/phy/broadcom.c
@@ -692,8 +692,6 @@ static struct phy_driver bcm5411_driver = {
SUPPORTED_Pause | SUPPORTED_Asym_Pause,
.flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT,
.config_init = bcm54xx_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = bcm54xx_ack_interrupt,
.config_intr = bcm54xx_config_intr,
.driver = { .owner = THIS_MODULE },
@@ -707,8 +705,6 @@ static struct phy_driver bcm5421_driver = {
SUPPORTED_Pause | SUPPORTED_Asym_Pause,
.flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT,
.config_init = bcm54xx_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = bcm54xx_ack_interrupt,
.config_intr = bcm54xx_config_intr,
.driver = { .owner = THIS_MODULE },
@@ -722,8 +718,6 @@ static struct phy_driver bcm5461_driver = {
SUPPORTED_Pause | SUPPORTED_Asym_Pause,
.flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT,
.config_init = bcm54xx_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = bcm54xx_ack_interrupt,
.config_intr = bcm54xx_config_intr,
.driver = { .owner = THIS_MODULE },
@@ -737,8 +731,6 @@ static struct phy_driver bcm5464_driver = {
SUPPORTED_Pause | SUPPORTED_Asym_Pause,
.flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT,
.config_init = bcm54xx_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = bcm54xx_ack_interrupt,
.config_intr = bcm54xx_config_intr,
.driver = { .owner = THIS_MODULE },
@@ -753,7 +745,6 @@ static struct phy_driver bcm5481_driver = {
.flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT,
.config_init = bcm54xx_config_init,
.config_aneg = bcm5481_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = bcm54xx_ack_interrupt,
.config_intr = bcm54xx_config_intr,
.driver = { .owner = THIS_MODULE },
@@ -767,7 +758,6 @@ static struct phy_driver bcm5482_driver = {
SUPPORTED_Pause | SUPPORTED_Asym_Pause,
.flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT,
.config_init = bcm5482_config_init,
- .config_aneg = genphy_config_aneg,
.read_status = bcm5482_read_status,
.ack_interrupt = bcm54xx_ack_interrupt,
.config_intr = bcm54xx_config_intr,
@@ -782,8 +772,6 @@ static struct phy_driver bcm50610_driver = {
SUPPORTED_Pause | SUPPORTED_Asym_Pause,
.flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT,
.config_init = bcm54xx_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = bcm54xx_ack_interrupt,
.config_intr = bcm54xx_config_intr,
.driver = { .owner = THIS_MODULE },
@@ -797,8 +785,6 @@ static struct phy_driver bcm50610m_driver = {
SUPPORTED_Pause | SUPPORTED_Asym_Pause,
.flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT,
.config_init = bcm54xx_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = bcm54xx_ack_interrupt,
.config_intr = bcm54xx_config_intr,
.driver = { .owner = THIS_MODULE },
@@ -812,8 +798,6 @@ static struct phy_driver bcm57780_driver = {
SUPPORTED_Pause | SUPPORTED_Asym_Pause,
.flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT,
.config_init = bcm54xx_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = bcm54xx_ack_interrupt,
.config_intr = bcm54xx_config_intr,
.driver = { .owner = THIS_MODULE },
@@ -827,8 +811,6 @@ static struct phy_driver bcmac131_driver = {
SUPPORTED_Pause | SUPPORTED_Asym_Pause,
.flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT,
.config_init = brcm_fet_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = brcm_fet_ack_interrupt,
.config_intr = brcm_fet_config_intr,
.driver = { .owner = THIS_MODULE },
@@ -842,8 +824,6 @@ static struct phy_driver bcm5241_driver = {
SUPPORTED_Pause | SUPPORTED_Asym_Pause,
.flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT,
.config_init = brcm_fet_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = brcm_fet_ack_interrupt,
.config_intr = brcm_fet_config_intr,
.driver = { .owner = THIS_MODULE },
diff --git a/drivers/net/phy/cicada.c b/drivers/net/phy/cicada.c
index d281731..c409ca2 100644
--- a/drivers/net/phy/cicada.c
+++ b/drivers/net/phy/cicada.c
@@ -109,8 +109,6 @@ static struct phy_driver cis8201_driver = {
.features = PHY_GBIT_FEATURES,
.flags = PHY_HAS_INTERRUPT,
.config_init = &cis820x_config_init,
- .config_aneg = &genphy_config_aneg,
- .read_status = &genphy_read_status,
.ack_interrupt = &cis820x_ack_interrupt,
.config_intr = &cis820x_config_intr,
.driver = { .owner = THIS_MODULE,},
@@ -124,8 +122,6 @@ static struct phy_driver cis8204_driver = {
.features = PHY_GBIT_FEATURES,
.flags = PHY_HAS_INTERRUPT,
.config_init = &cis820x_config_init,
- .config_aneg = &genphy_config_aneg,
- .read_status = &genphy_read_status,
.ack_interrupt = &cis820x_ack_interrupt,
.config_intr = &cis820x_config_intr,
.driver = { .owner = THIS_MODULE,},
diff --git a/drivers/net/phy/davicom.c b/drivers/net/phy/davicom.c
index 2f774ac..5249e1e 100644
--- a/drivers/net/phy/davicom.c
+++ b/drivers/net/phy/davicom.c
@@ -156,7 +156,6 @@ static struct phy_driver dm9161e_driver = {
.features = PHY_BASIC_FEATURES,
.config_init = dm9161_config_init,
.config_aneg = dm9161_config_aneg,
- .read_status = genphy_read_status,
.driver = { .owner = THIS_MODULE,},
};
@@ -167,7 +166,6 @@ static struct phy_driver dm9161a_driver = {
.features = PHY_BASIC_FEATURES,
.config_init = dm9161_config_init,
.config_aneg = dm9161_config_aneg,
- .read_status = genphy_read_status,
.driver = { .owner = THIS_MODULE,},
};
@@ -177,8 +175,6 @@ static struct phy_driver dm9131_driver = {
.phy_id_mask = 0x0ffffff0,
.features = PHY_BASIC_FEATURES,
.flags = PHY_HAS_INTERRUPT,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = dm9161_ack_interrupt,
.config_intr = dm9161_config_intr,
.driver = { .owner = THIS_MODULE,},
diff --git a/drivers/net/phy/icplus.c b/drivers/net/phy/icplus.c
index 2969dac..28a190e 100644
--- a/drivers/net/phy/icplus.c
+++ b/drivers/net/phy/icplus.c
@@ -151,8 +151,6 @@ static struct phy_driver ip1001_driver = {
.features = PHY_GBIT_FEATURES | SUPPORTED_Pause |
SUPPORTED_Asym_Pause,
.config_init = &ip1001_config_init,
- .config_aneg = &genphy_config_aneg,
- .read_status = &genphy_read_status,
.suspend = genphy_suspend,
.resume = genphy_resume,
.driver = { .owner = THIS_MODULE,},
diff --git a/drivers/net/phy/lxt.c b/drivers/net/phy/lxt.c
index 6f6e8b6..0ed7e51 100644
--- a/drivers/net/phy/lxt.c
+++ b/drivers/net/phy/lxt.c
@@ -156,8 +156,6 @@ static struct phy_driver lxt970_driver = {
.features = PHY_BASIC_FEATURES,
.flags = PHY_HAS_INTERRUPT,
.config_init = lxt970_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = lxt970_ack_interrupt,
.config_intr = lxt970_config_intr,
.driver = { .owner = THIS_MODULE,},
@@ -169,8 +167,6 @@ static struct phy_driver lxt971_driver = {
.phy_id_mask = 0xfffffff0,
.features = PHY_BASIC_FEATURES,
.flags = PHY_HAS_INTERRUPT,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = lxt971_ack_interrupt,
.config_intr = lxt971_config_intr,
.driver = { .owner = THIS_MODULE,},
@@ -184,7 +180,6 @@ static struct phy_driver lxt973_driver = {
.flags = 0,
.probe = lxt973_probe,
.config_aneg = lxt973_config_aneg,
- .read_status = genphy_read_status,
.driver = { .owner = THIS_MODULE,},
};
diff --git a/drivers/net/phy/marvell.c b/drivers/net/phy/marvell.c
index e8b9c53..e4beb96 100644
--- a/drivers/net/phy/marvell.c
+++ b/drivers/net/phy/marvell.c
@@ -725,7 +725,6 @@ static struct phy_driver marvell_drivers[] = {
.features = PHY_GBIT_FEATURES,
.flags = PHY_HAS_INTERRUPT,
.config_aneg = &marvell_config_aneg,
- .read_status = &genphy_read_status,
.ack_interrupt = &marvell_ack_interrupt,
.config_intr = &marvell_config_intr,
.driver = { .owner = THIS_MODULE },
@@ -738,7 +737,6 @@ static struct phy_driver marvell_drivers[] = {
.flags = PHY_HAS_INTERRUPT,
.config_init = &m88e1111_config_init,
.config_aneg = &marvell_config_aneg,
- .read_status = &genphy_read_status,
.ack_interrupt = &marvell_ack_interrupt,
.config_intr = &marvell_config_intr,
.driver = { .owner = THIS_MODULE },
@@ -764,7 +762,6 @@ static struct phy_driver marvell_drivers[] = {
.flags = PHY_HAS_INTERRUPT,
.config_init = &m88e1118_config_init,
.config_aneg = &m88e1118_config_aneg,
- .read_status = &genphy_read_status,
.ack_interrupt = &marvell_ack_interrupt,
.config_intr = &marvell_config_intr,
.driver = {.owner = THIS_MODULE,},
@@ -803,7 +800,6 @@ static struct phy_driver marvell_drivers[] = {
.flags = PHY_HAS_INTERRUPT,
.config_init = &m88e1145_config_init,
.config_aneg = &marvell_config_aneg,
- .read_status = &genphy_read_status,
.ack_interrupt = &marvell_ack_interrupt,
.config_intr = &marvell_config_intr,
.driver = { .owner = THIS_MODULE },
@@ -816,7 +812,6 @@ static struct phy_driver marvell_drivers[] = {
.flags = PHY_HAS_INTERRUPT,
.config_init = &m88e1149_config_init,
.config_aneg = &m88e1118_config_aneg,
- .read_status = &genphy_read_status,
.ack_interrupt = &marvell_ack_interrupt,
.config_intr = &marvell_config_intr,
.driver = { .owner = THIS_MODULE },
@@ -829,7 +824,6 @@ static struct phy_driver marvell_drivers[] = {
.flags = PHY_HAS_INTERRUPT,
.config_init = &m88e1111_config_init,
.config_aneg = &marvell_config_aneg,
- .read_status = &genphy_read_status,
.ack_interrupt = &marvell_ack_interrupt,
.config_intr = &marvell_config_intr,
.driver = { .owner = THIS_MODULE },
diff --git a/drivers/net/phy/micrel.c b/drivers/net/phy/micrel.c
index 590f902..1404b3c 100644
--- a/drivers/net/phy/micrel.c
+++ b/drivers/net/phy/micrel.c
@@ -121,8 +121,6 @@ static struct phy_driver ks8737_driver = {
.features = (PHY_BASIC_FEATURES | SUPPORTED_Pause),
.flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT,
.config_init = kszphy_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = kszphy_ack_interrupt,
.config_intr = ks8737_config_intr,
.driver = { .owner = THIS_MODULE,},
@@ -136,8 +134,6 @@ static struct phy_driver ks8041_driver = {
| SUPPORTED_Asym_Pause),
.flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT,
.config_init = kszphy_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = kszphy_ack_interrupt,
.config_intr = kszphy_config_intr,
.driver = { .owner = THIS_MODULE,},
@@ -151,8 +147,6 @@ static struct phy_driver ks8051_driver = {
| SUPPORTED_Asym_Pause),
.flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT,
.config_init = ks8051_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = kszphy_ack_interrupt,
.config_intr = kszphy_config_intr,
.driver = { .owner = THIS_MODULE,},
@@ -165,8 +159,6 @@ static struct phy_driver ks8001_driver = {
.features = (PHY_BASIC_FEATURES | SUPPORTED_Pause),
.flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT,
.config_init = kszphy_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = kszphy_ack_interrupt,
.config_intr = kszphy_config_intr,
.driver = { .owner = THIS_MODULE,},
@@ -180,8 +172,6 @@ static struct phy_driver ksz9021_driver = {
| SUPPORTED_Asym_Pause),
.flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT,
.config_init = kszphy_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = kszphy_ack_interrupt,
.config_intr = ksz9021_config_intr,
.driver = { .owner = THIS_MODULE, },
diff --git a/drivers/net/phy/national.c b/drivers/net/phy/national.c
index 04bb8fc..9eca50e 100644
--- a/drivers/net/phy/national.c
+++ b/drivers/net/phy/national.c
@@ -132,8 +132,6 @@ static struct phy_driver dp83865_driver = {
.features = PHY_GBIT_FEATURES | SUPPORTED_Pause | SUPPORTED_Asym_Pause,
.flags = PHY_HAS_INTERRUPT,
.config_init = ns_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = ns_ack_interrupt,
.config_intr = ns_config_intr,
.driver = {.owner = THIS_MODULE,}
diff --git a/drivers/net/phy/phy.c b/drivers/net/phy/phy.c
index 3cbda08..cc7f353 100644
--- a/drivers/net/phy/phy.c
+++ b/drivers/net/phy/phy.c
@@ -395,7 +395,10 @@ int phy_start_aneg(struct phy_device *phydev)
if (AUTONEG_DISABLE == phydev->autoneg)
phy_sanitize_settings(phydev);
- err = phydev->drv->config_aneg(phydev);
+ if (phydev->drv->config_aneg)
+ err = phydev->drv->config_aneg(phydev);
+ else
+ err = genphy_config_aneg(phydev);
if (err < 0)
goto out_unlock;
diff --git a/drivers/net/phy/phy_device.c b/drivers/net/phy/phy_device.c
index ff109fe..f1d8352 100644
--- a/drivers/net/phy/phy_device.c
+++ b/drivers/net/phy/phy_device.c
@@ -1018,8 +1018,6 @@ static struct phy_driver genphy_driver = {
.name = "Generic PHY",
.config_init = genphy_config_init,
.features = 0,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.suspend = genphy_suspend,
.resume = genphy_resume,
.driver = {.owner= THIS_MODULE, },
diff --git a/drivers/net/phy/qsemi.c b/drivers/net/phy/qsemi.c
index fe0d0a1..5a120a8c 100644
--- a/drivers/net/phy/qsemi.c
+++ b/drivers/net/phy/qsemi.c
@@ -118,8 +118,6 @@ static struct phy_driver qs6612_driver = {
.features = PHY_BASIC_FEATURES,
.flags = PHY_HAS_INTERRUPT,
.config_init = qs6612_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = qs6612_ack_interrupt,
.config_intr = qs6612_config_intr,
.driver = { .owner = THIS_MODULE,},
diff --git a/drivers/net/phy/realtek.c b/drivers/net/phy/realtek.c
index a4eae75..1a00deb 100644
--- a/drivers/net/phy/realtek.c
+++ b/drivers/net/phy/realtek.c
@@ -55,8 +55,6 @@ static struct phy_driver rtl821x_driver = {
.phy_id_mask = 0x001fffff,
.features = PHY_GBIT_FEATURES,
.flags = PHY_HAS_INTERRUPT,
- .config_aneg = &genphy_config_aneg,
- .read_status = &genphy_read_status,
.ack_interrupt = &rtl821x_ack_interrupt,
.config_intr = &rtl821x_config_intr,
.driver = { .owner = THIS_MODULE,},
diff --git a/drivers/net/phy/smsc.c b/drivers/net/phy/smsc.c
index 342505c..a8aa088 100644
--- a/drivers/net/phy/smsc.c
+++ b/drivers/net/phy/smsc.c
@@ -90,8 +90,6 @@ static struct phy_driver lan83c185_driver = {
.flags = PHY_HAS_INTERRUPT | PHY_HAS_MAGICANEG,
/* basic functions */
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.config_init = smsc_phy_config_init,
/* IRQ related */
@@ -114,8 +112,6 @@ static struct phy_driver lan8187_driver = {
.flags = PHY_HAS_INTERRUPT | PHY_HAS_MAGICANEG,
/* basic functions */
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.config_init = smsc_phy_config_init,
/* IRQ related */
@@ -138,8 +134,6 @@ static struct phy_driver lan8700_driver = {
.flags = PHY_HAS_INTERRUPT | PHY_HAS_MAGICANEG,
/* basic functions */
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.config_init = smsc_phy_config_init,
/* IRQ related */
@@ -162,8 +156,6 @@ static struct phy_driver lan911x_int_driver = {
.flags = PHY_HAS_INTERRUPT | PHY_HAS_MAGICANEG,
/* basic functions */
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.config_init = lan911x_config_init,
/* IRQ related */
@@ -186,8 +178,6 @@ static struct phy_driver lan8710_driver = {
.flags = PHY_HAS_INTERRUPT | PHY_HAS_MAGICANEG,
/* basic functions */
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.config_init = smsc_phy_config_init,
/* IRQ related */
diff --git a/drivers/net/phy/ste10Xp.c b/drivers/net/phy/ste10Xp.c
index 187a2fa..45cde8f 100644
--- a/drivers/net/phy/ste10Xp.c
+++ b/drivers/net/phy/ste10Xp.c
@@ -88,8 +88,6 @@ static struct phy_driver ste101p_pdriver = {
.features = PHY_BASIC_FEATURES | SUPPORTED_Pause,
.flags = PHY_HAS_INTERRUPT,
.config_init = ste10Xp_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = ste10Xp_ack_interrupt,
.config_intr = ste10Xp_config_intr,
.suspend = genphy_suspend,
@@ -104,8 +102,6 @@ static struct phy_driver ste100p_pdriver = {
.features = PHY_BASIC_FEATURES | SUPPORTED_Pause,
.flags = PHY_HAS_INTERRUPT,
.config_init = ste10Xp_config_init,
- .config_aneg = genphy_config_aneg,
- .read_status = genphy_read_status,
.ack_interrupt = ste10Xp_ack_interrupt,
.config_intr = ste10Xp_config_intr,
.suspend = genphy_suspend,
diff --git a/drivers/net/phy/vitesse.c b/drivers/net/phy/vitesse.c
index 5d8f6e1..20ea438 100644
--- a/drivers/net/phy/vitesse.c
+++ b/drivers/net/phy/vitesse.c
@@ -136,8 +136,6 @@ static struct phy_driver vsc8244_driver = {
.features = PHY_GBIT_FEATURES,
.flags = PHY_HAS_INTERRUPT,
.config_init = &vsc824x_config_init,
- .config_aneg = &genphy_config_aneg,
- .read_status = &genphy_read_status,
.ack_interrupt = &vsc824x_ack_interrupt,
.config_intr = &vsc82xx_config_intr,
.driver = { .owner = THIS_MODULE,},
@@ -163,8 +161,6 @@ static struct phy_driver vsc8221_driver = {
.features = PHY_GBIT_FEATURES,
.flags = PHY_HAS_INTERRUPT,
.config_init = &vsc8221_config_init,
- .config_aneg = &genphy_config_aneg,
- .read_status = &genphy_read_status,
.ack_interrupt = &vsc824x_ack_interrupt,
.config_intr = &vsc82xx_config_intr,
.driver = { .owner = THIS_MODULE,},
diff --git a/include/linux/phy.h b/include/linux/phy.h
index 54fc413..a55a6c4 100644
--- a/include/linux/phy.h
+++ b/include/linux/phy.h
@@ -349,8 +349,7 @@ struct phy_device {
* flags: A bitfield defining certain other features this PHY
* supports (like interrupts)
*
- * The drivers must implement config_aneg and read_status. All
- * other functions are optional. Note that none of these
+ * All functions are optional. Note that none of these
* functions should be called from interrupt time. The goal is
* for the bus read/write functions to be able to block when the
* bus transaction is happening, and be freed up by an interrupt
@@ -493,7 +492,10 @@ int phy_start_aneg(struct phy_device *phydev);
int phy_stop_interrupts(struct phy_device *phydev);
static inline int phy_read_status(struct phy_device *phydev) {
- return phydev->drv->read_status(phydev);
+ if (phydev->drv->read_status)
+ return phydev->drv->read_status(phydev);
+ else
+ return genphy_read_status(phydev);
}
int genphy_restart_aneg(struct phy_device *phydev);
--
1.7.2.5
^ permalink raw reply related
* [RFC PATCH 04/17] phy/icplus: Fix read_status/config_aneg error handling
From: Kyle Moffett @ 2011-10-20 21:00 UTC (permalink / raw)
To: linux-kernel, netdev
Cc: Kyle Moffett, David S. Miller, Greg Dietsche, Giuseppe Cavallaro
In-Reply-To: <1319144425-15547-1-git-send-email-Kyle.D.Moffett@boeing.com>
Fixes the icplus PHY driver to propagate the return values of the
functions genphy_read_status() and genphy_config_aneg() instead of
ignoring them.
NOTE: Completely untested. Needs somebody with hardware to try it out.
Signed-off-by: Kyle Moffett <Kyle.D.Moffett@boeing.com>
---
drivers/net/phy/icplus.c | 10 +++++-----
1 files changed, 5 insertions(+), 5 deletions(-)
diff --git a/drivers/net/phy/icplus.c b/drivers/net/phy/icplus.c
index d4cbc29..2969dac 100644
--- a/drivers/net/phy/icplus.c
+++ b/drivers/net/phy/icplus.c
@@ -115,19 +115,19 @@ static int ip1001_config_init(struct phy_device *phydev)
static int ip175c_read_status(struct phy_device *phydev)
{
if (phydev->addr == 4) /* WAN port */
- genphy_read_status(phydev);
- else
- /* Don't need to read status for switch ports */
- phydev->irq = PHY_IGNORE_INTERRUPT;
+ return genphy_read_status(phydev);
+ /* Don't need to read status for switch ports */
+ phydev->irq = PHY_IGNORE_INTERRUPT;
return 0;
}
static int ip175c_config_aneg(struct phy_device *phydev)
{
if (phydev->addr == 4) /* WAN port */
- genphy_config_aneg(phydev);
+ return genphy_config_aneg(phydev);
+ /* Don't need to do anything for switch ports */
return 0;
}
--
1.7.2.5
^ permalink raw reply related
* [RFC PATCH 03/17] greth: Allow PHYs to override ->read_status
From: Kyle Moffett @ 2011-10-20 21:00 UTC (permalink / raw)
To: linux-kernel, netdev; +Cc: Kyle Moffett, Kristoffer Glembo
In-Reply-To: <1319144425-15547-1-git-send-email-Kyle.D.Moffett@boeing.com>
Instead of manually calling genphy_read_status(), the greth driver
should call phy_read_status() to allow the PHY driver to override the
read_status method with its own version.
NOTE: Completely untested. Needs somebody with hardware to try it out.
Signed-off-by: Kyle Moffett <Kyle.D.Moffett@boeing.com>
---
drivers/net/greth.c | 2 +-
1 files changed, 1 insertions(+), 1 deletions(-)
diff --git a/drivers/net/greth.c b/drivers/net/greth.c
index 52a3900..e7f268f 100644
--- a/drivers/net/greth.c
+++ b/drivers/net/greth.c
@@ -1367,7 +1367,7 @@ static int greth_mdio_init(struct greth_private *greth)
timeout = jiffies + 6*HZ;
while (!phy_aneg_done(greth->phy) && time_before(jiffies, timeout)) {
}
- genphy_read_status(greth->phy);
+ phy_read_status(greth->phy);
greth_link_change(greth->netdev);
}
--
1.7.2.5
^ permalink raw reply related
* [RFC PATCH 02/17] of_mdio: Don't phy_scan_fixups() twice
From: Kyle Moffett @ 2011-10-20 21:00 UTC (permalink / raw)
To: linux-kernel, netdev; +Cc: Kyle Moffett, Grant Likely, devicetree-discuss
In-Reply-To: <1319144425-15547-1-git-send-email-Kyle.D.Moffett@boeing.com>
The "phy_device_register()" call 5 lines down already calls
phy_scan_fixups(), there's no need to do it a second time.
Signed-off-by: Kyle Moffett <Kyle.D.Moffett@boeing.com>
---
drivers/of/of_mdio.c | 1 -
1 files changed, 0 insertions(+), 1 deletions(-)
diff --git a/drivers/of/of_mdio.c b/drivers/of/of_mdio.c
index d35e300..980c079 100644
--- a/drivers/of/of_mdio.c
+++ b/drivers/of/of_mdio.c
@@ -83,7 +83,6 @@ int of_mdiobus_register(struct mii_bus *mdio, struct device_node *np)
addr);
continue;
}
- phy_scan_fixups(phy);
/* Associate the OF node with the device structure so it
* can be looked up later */
--
1.7.2.5
^ permalink raw reply related
* [RFC PATCH 01/17] et1011c: Replaced PHY driver by a small dm646x board fixup
From: Kyle Moffett @ 2011-10-20 21:00 UTC (permalink / raw)
To: linux-kernel, netdev
Cc: Kevin Hilman, Russell King, Sekhar Nori, David S. Miller,
H Hartley Sweeten, John Stultz, Kyle Moffett, Florian Fainelli,
Giuseppe Cavallaro, Richard Cochran, linux-arm-kernel
In-Reply-To: <1319144425-15547-1-git-send-email-Kyle.D.Moffett@boeing.com>
The et1011c PHY driver has several noticeable code smells:
(1) It uses a "static int speed" variable to see if the speed changed
between calls to et1011c_read_status(). This obviously breaks if
more than one PHY is present in a system.
(2) The "GMII_INTERFACE" and "SYS_CLK_EN" bits should be properly set
at reset-time by hardwired pins on the ET1011C chip, as they are
specific to the wiring on the board. They should NOT be set by a
generic PHY driver, and at best belong in a board-specific fixup.
(3) The FIFO bits are "changed" to the default reset value specified
in the datasheet.
(4) The driver does not appear to contain code anywhere which undoes
any of the above changes if the interface drops from 1000BaseT to
100BaseTX without a chip reset. Instead it appears to perform an
extraneous BMCR_RESET in its ->config_aneg() method, which would
wipe out any settings applied by phy_register_fixup() and friends.
This PHY should be handled entirely by the genphy driver with only a
minimal board-specific "phy_register_fixup()" in the DM646x code.
NOTE: Completely untested. Needs somebody with hardware to try it out.
Signed-off-by: Kyle Moffett <Kyle.D.Moffett@boeing.com>
---
arch/arm/mach-davinci/dm646x.c | 24 ++++++++
drivers/net/phy/Kconfig | 5 --
drivers/net/phy/Makefile | 1 -
drivers/net/phy/et1011c.c | 119 ----------------------------------------
4 files changed, 24 insertions(+), 125 deletions(-)
delete mode 100644 drivers/net/phy/et1011c.c
diff --git a/arch/arm/mach-davinci/dm646x.c b/arch/arm/mach-davinci/dm646x.c
index 1802e71..afcdf37 100644
--- a/arch/arm/mach-davinci/dm646x.c
+++ b/arch/arm/mach-davinci/dm646x.c
@@ -14,6 +14,7 @@
#include <linux/serial_8250.h>
#include <linux/platform_device.h>
#include <linux/gpio.h>
+#include <linux/phy.h>
#include <asm/mach/map.h>
@@ -908,6 +909,27 @@ void __init dm646x_init(void)
davinci_common_init(&davinci_soc_info_dm646x);
}
+/* Apparently the PHY bootstrap pin wiring on the board is wrong */
+#define ET1011C_CONFIG_REG (0x16)
+#define ET1011C_TX_FIFO_MASK (0x3000)
+#define ET1011C_TX_FIFO_DEPTH_16 (0x1000)
+#define ET1011C_SYS_CLK_EN (0x0010)
+#define ET1011C_INTERFACE_MASK (0x0007)
+#define ET1011C_INTERFACE_GMII_GTX_CLK (0x0002)
+static int dm646x_et1011c_phy_fixup(struct phy_device *phydev)
+{
+ int val = phy_read(phydev, ET1011C_CONFIG_REG);
+ if (val < 0)
+ return val;
+
+ val &= ~ET1011C_TX_FIFO_MASK;
+ val |= ET1011C_TX_FIFO_DEPTH_16;
+ val |= ET1011C_SYS_CLK_EN;
+ val &= ~ET1011C_INTERFACE_MASK
+ val |= ET1011C_INTERFACE_GMII_GTX_CLK;
+ return phy_write(phydev, ET1011C_CONFIG_REG, val);
+}
+
static int __init dm646x_init_devices(void)
{
if (!cpu_is_davinci_dm646x())
@@ -917,6 +939,8 @@ static int __init dm646x_init_devices(void)
platform_device_register(&dm646x_emac_device);
clk_add_alias(NULL, dev_name(&dm646x_mdio_device.dev),
NULL, &dm646x_emac_device.dev);
+ phy_register_fixup_for_uid(0x0282f014, 0xfffffff0,
+ &dm646x_et1011c_phy_fixup);
return 0;
}
diff --git a/drivers/net/phy/Kconfig b/drivers/net/phy/Kconfig
index a702443..fdd2ace 100644
--- a/drivers/net/phy/Kconfig
+++ b/drivers/net/phy/Kconfig
@@ -82,11 +82,6 @@ config STE10XP
---help---
This is the driver for the STe100p and STe101p PHYs.
-config LSI_ET1011C_PHY
- tristate "Driver for LSI ET1011C PHY"
- ---help---
- Supports the LSI ET1011C PHY.
-
config MICREL_PHY
tristate "Driver for Micrel PHYs"
---help---
diff --git a/drivers/net/phy/Makefile b/drivers/net/phy/Makefile
index 2333215..d4c0bd0 100644
--- a/drivers/net/phy/Makefile
+++ b/drivers/net/phy/Makefile
@@ -14,7 +14,6 @@ obj-$(CONFIG_BROADCOM_PHY) += broadcom.o
obj-$(CONFIG_BCM63XX_PHY) += bcm63xx.o
obj-$(CONFIG_ICPLUS_PHY) += icplus.o
obj-$(CONFIG_REALTEK_PHY) += realtek.o
-obj-$(CONFIG_LSI_ET1011C_PHY) += et1011c.o
obj-$(CONFIG_FIXED_PHY) += fixed.o
obj-$(CONFIG_MDIO_BITBANG) += mdio-bitbang.o
obj-$(CONFIG_MDIO_GPIO) += mdio-gpio.o
diff --git a/drivers/net/phy/et1011c.c b/drivers/net/phy/et1011c.c
deleted file mode 100644
index a8eb19e..0000000
--- a/drivers/net/phy/et1011c.c
+++ /dev/null
@@ -1,119 +0,0 @@
-/*
- * drivers/net/phy/et1011c.c
- *
- * Driver for LSI ET1011C PHYs
- *
- * Author: Chaithrika U S
- *
- * Copyright (c) 2008 Texas Instruments
- *
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by the
- * Free Software Foundation; either version 2 of the License, or (at your
- * option) any later version.
- *
- */
-#include <linux/kernel.h>
-#include <linux/string.h>
-#include <linux/errno.h>
-#include <linux/unistd.h>
-#include <linux/interrupt.h>
-#include <linux/init.h>
-#include <linux/delay.h>
-#include <linux/netdevice.h>
-#include <linux/etherdevice.h>
-#include <linux/skbuff.h>
-#include <linux/spinlock.h>
-#include <linux/mm.h>
-#include <linux/module.h>
-#include <linux/mii.h>
-#include <linux/ethtool.h>
-#include <linux/phy.h>
-#include <linux/io.h>
-#include <linux/uaccess.h>
-#include <asm/irq.h>
-
-#define ET1011C_STATUS_REG (0x1A)
-#define ET1011C_CONFIG_REG (0x16)
-#define ET1011C_SPEED_MASK (0x0300)
-#define ET1011C_GIGABIT_SPEED (0x0200)
-#define ET1011C_TX_FIFO_MASK (0x3000)
-#define ET1011C_TX_FIFO_DEPTH_8 (0x0000)
-#define ET1011C_TX_FIFO_DEPTH_16 (0x1000)
-#define ET1011C_INTERFACE_MASK (0x0007)
-#define ET1011C_GMII_INTERFACE (0x0002)
-#define ET1011C_SYS_CLK_EN (0x01 << 4)
-
-
-MODULE_DESCRIPTION("LSI ET1011C PHY driver");
-MODULE_AUTHOR("Chaithrika U S");
-MODULE_LICENSE("GPL");
-
-static int et1011c_config_aneg(struct phy_device *phydev)
-{
- int ctl = 0;
- ctl = phy_read(phydev, MII_BMCR);
- if (ctl < 0)
- return ctl;
- ctl &= ~(BMCR_FULLDPLX | BMCR_SPEED100 | BMCR_SPEED1000 |
- BMCR_ANENABLE);
- /* First clear the PHY */
- phy_write(phydev, MII_BMCR, ctl | BMCR_RESET);
-
- return genphy_config_aneg(phydev);
-}
-
-static int et1011c_read_status(struct phy_device *phydev)
-{
- int ret;
- u32 val;
- static int speed;
- ret = genphy_read_status(phydev);
-
- if (speed != phydev->speed) {
- speed = phydev->speed;
- val = phy_read(phydev, ET1011C_STATUS_REG);
- if ((val & ET1011C_SPEED_MASK) ==
- ET1011C_GIGABIT_SPEED) {
- val = phy_read(phydev, ET1011C_CONFIG_REG);
- val &= ~ET1011C_TX_FIFO_MASK;
- phy_write(phydev, ET1011C_CONFIG_REG, val\
- | ET1011C_GMII_INTERFACE\
- | ET1011C_SYS_CLK_EN\
- | ET1011C_TX_FIFO_DEPTH_16);
-
- }
- }
- return ret;
-}
-
-static struct phy_driver et1011c_driver = {
- .phy_id = 0x0282f014,
- .name = "ET1011C",
- .phy_id_mask = 0xfffffff0,
- .features = (PHY_BASIC_FEATURES | SUPPORTED_1000baseT_Full),
- .flags = PHY_POLL,
- .config_aneg = et1011c_config_aneg,
- .read_status = et1011c_read_status,
- .driver = { .owner = THIS_MODULE,},
-};
-
-static int __init et1011c_init(void)
-{
- return phy_driver_register(&et1011c_driver);
-}
-
-static void __exit et1011c_exit(void)
-{
- phy_driver_unregister(&et1011c_driver);
-}
-
-module_init(et1011c_init);
-module_exit(et1011c_exit);
-
-static struct mdio_device_id __maybe_unused et1011c_tbl[] = {
- { 0x0282f014, 0xfffffff0 },
- { }
-};
-
-MODULE_DEVICE_TABLE(mdio, et1011c_tbl);
--
1.7.2.5
^ permalink raw reply related
* Re: [PATCH net-next] myri10ge: fix truesize underestimation
From: Eric Dumazet @ 2011-10-20 20:59 UTC (permalink / raw)
To: Andrew Gallatin; +Cc: Jon Mason, David Miller, netdev
In-Reply-To: <4EA0885A.9010009@myri.com>
Le jeudi 20 octobre 2011 à 16:45 -0400, Andrew Gallatin a écrit :
> On 10/20/11 16:44, Eric Dumazet wrote:
> > Le jeudi 20 octobre 2011 à 15:33 -0500, Jon Mason a écrit :
> >> On Thu, Oct 20, 2011 at 3:10 PM, Eric Dumazet<eric.dumazet@gmail.com> wrote:
> >>> skb->truesize must account for allocated memory, not the used part of
> >>> it. Doing this work is important to avoid unexpected OOM situations.
> >>>
> >>> Signed-off-by: Eric Dumazet<eric.dumazet@gmail.com>
> >>
> >> Acked-by: Jon Mason<mason@myri.com>
> >
> > Thanks for reviewing Jon !
> >
> >
>
> Please wait a second.. I think the patch is incorrect.
>
> There is already code in myri10ge_rx_skb_build() which
> attempts to set the truesize. However, it sets it to
> the used, rather than the allocated size so it is apparently
> incorrect.
>
> I'd prefer we fix that code.
Well, I believe I did exactly that :)
truesize of initial skb is fine.
Then for everay frag added, you must add to skb-truesize the allocated
memory for this frag.
You add frags of a given size (small or big)
In the end, its truesize += bytes * number_of_frags
(bytes being small_size or big_size)
^ permalink raw reply
* Re: [PATCH 07/10] RDMA/cxgb4: DB Drop Recovery for RDMA and LLD queues.
From: David Miller @ 2011-10-20 20:57 UTC (permalink / raw)
To: swise-7bPotxP6k4+P2YhJcF5u+vpXobYPEAuW
Cc: roland-BHEL68pLQRGGvPXPguhicg, vipul-ut6Up61K2wZBDgjK7y7TUQ,
linux-rdma-u79uwXL29TY76Z2rM5mHXA, netdev-u79uwXL29TY76Z2rM5mHXA,
divy-ut6Up61K2wZBDgjK7y7TUQ, dm-ut6Up61K2wZBDgjK7y7TUQ,
kumaras-ut6Up61K2wZBDgjK7y7TUQ
In-Reply-To: <4EA05A27.9090605-7bPotxP6k4+P2YhJcF5u+vpXobYPEAuW@public.gmane.org>
From: Steve Wise <swise-7bPotxP6k4+P2YhJcF5u+vpXobYPEAuW@public.gmane.org>
Date: Thu, 20 Oct 2011 12:28:07 -0500
> On 10/20/2011 12:17 PM, Roland Dreier wrote:
>>> I believe 5 and 7 have build dependencies.
>> Right, missed that one too.
>>
>> But it seems 4,6,8,9,10 are independent of the rest of the series?
>>
>> ie I can trivially apply them and then worry about working out
>> the drivers/net / drivers/infiniband interdependency a bit later?
>>
>
> Some of these might be dependent on prior patches the series. But if
> they aren't, yes, you could do that.
So, how do you guys want to do this? If you give me a list of which
patches I should put into net-next and leave the rest to the infiniband
tree, that'd work fine for me as long as net-next is left in a working
state independent of the infiniband tree.
--
To unsubscribe from this list: send the line "unsubscribe linux-rdma" in
the body of a message to majordomo-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
^ permalink raw reply
* Re: [patch] pktgen: bug when calling ndelay in x86 architectures
From: Eric Dumazet @ 2011-10-20 20:55 UTC (permalink / raw)
To: David Miller
Cc: bhutchings, daniel.turull, netdev, robert, voravit, jens.laas
In-Reply-To: <20111020.162444.559487256559727633.davem@davemloft.net>
Le jeudi 20 octobre 2011 à 16:24 -0400, David Miller a écrit :
> From: Eric Dumazet <eric.dumazet@gmail.com>
> Date: Tue, 18 Oct 2011 16:47:44 +0200
>
> > Le mardi 18 octobre 2011 à 15:00 +0100, Ben Hutchings a écrit :
> >
> >> AIUI, the reason for limits on delays is not that it's bad practice to
> >> spin for so long, but that the delay calculations may overflow or
> >> otherwise become inaccurate.
> >
> > OK, I can understand that, then a more appropriate patch would be :
>
> I think doing the udelay/ndelay thing is the way to go for 'net' and
> -stable. We can do something sophisticated with ktime et al. in
> 'net-next'.
>
Well, I am not sure a patch is needed for net, since there is no bug,
but maybe small inaccuracies ? Correct me if I misunderstood Daniel !
> Eric, could you please formally submit this patch with proper
> changelog etc.?
Sure !
[PATCH net-next] pktgen: remove ndelay() call
Daniel Turull reported inaccuracies in pktgen when using low packet
rates, because we call ndelay(val) with values bigger than 20000.
Instead of calling ndelay() for delays < 100us, we can instead loop
calling ktime_now() only.
Reported-by: Daniel Turull <daniel.turull@gmail.com>
Signed-off-by: Eric Dumazet <eric.dumazet@gmail.com>
---
net/core/pktgen.c | 11 +++++++----
1 file changed, 7 insertions(+), 4 deletions(-)
diff --git a/net/core/pktgen.c b/net/core/pktgen.c
index 6bbf008..0001c24 100644
--- a/net/core/pktgen.c
+++ b/net/core/pktgen.c
@@ -2145,9 +2145,12 @@ static void spin(struct pktgen_dev *pkt_dev, ktime_t spin_until)
}
start_time = ktime_now();
- if (remaining < 100000)
- ndelay(remaining); /* really small just spin */
- else {
+ if (remaining < 100000) {
+ /* for small delays (<100us), just loop until limit is reached */
+ do {
+ end_time = ktime_now();
+ } while (ktime_lt(end_time, spin_until));
+ } else {
/* see do_nanosleep */
hrtimer_init_sleeper(&t, current);
do {
@@ -2162,8 +2165,8 @@ static void spin(struct pktgen_dev *pkt_dev, ktime_t spin_until)
hrtimer_cancel(&t.timer);
} while (t.task && pkt_dev->running && !signal_pending(current));
__set_current_state(TASK_RUNNING);
+ end_time = ktime_now();
}
- end_time = ktime_now();
pkt_dev->idle_acc += ktime_to_ns(ktime_sub(end_time, start_time));
pkt_dev->next_tx = ktime_add_ns(spin_until, pkt_dev->delay);
^ permalink raw reply related
* Re: [PATCH v2 net-next] tcp: use TCP_DEFAULT_INIT_RCVWND in tcp_fixup_rcvbuf()
From: David Miller @ 2011-10-20 20:54 UTC (permalink / raw)
To: eric.dumazet; +Cc: netdev
In-Reply-To: <1319143281.2854.25.camel@edumazet-laptop>
From: Eric Dumazet <eric.dumazet@gmail.com>
Date: Thu, 20 Oct 2011 22:41:21 +0200
> Since commit 356f039822b (TCP: increase default initial receive
> window.), we allow sender to send 10 (TCP_DEFAULT_INIT_RCVWND) segments.
>
> Change tcp_fixup_rcvbuf() to reflect this change, even if no real change
> is expected, since sysctl_tcp_rmem[1] = 87380 and this value
> is bigger than tcp_fixup_rcvbuf() computed rcvmem (~23720)
>
> Note: Since commit 356f039822b limited default window to maximum of
> 10*1460 and 2*MSS, we use same heuristic in this patch.
>
> Signed-off-by: Eric Dumazet <eric.dumazet@gmail.com>
Applied, thanks a lot Eric.
^ permalink raw reply
* RE: [net-next-2.6 PATCH 0/8 RFC v2] macvlan: MAC Address filtering support for passthru mode
From: Rose, Gregory V @ 2011-10-20 20:47 UTC (permalink / raw)
To: Rose, Gregory V, Roopa Prabhu, netdev@vger.kernel.org
Cc: sri@us.ibm.com, dragos.tatulea@gmail.com, arnd@arndb.de,
kvm@vger.kernel.org, mst@redhat.com, davem@davemloft.net,
mchan@broadcom.com, dwang2@cisco.com, shemminger@vyatta.com,
eric.dumazet@gmail.com, kaber@trash.net, benve@cisco.com
In-Reply-To: <43F901BD926A4E43B106BF17856F075501A19FF1D8@orsmsx508.amr.corp.intel.com>
> -----Original Message-----
> From: netdev-owner@vger.kernel.org [mailto:netdev-owner@vger.kernel.org]
> On Behalf Of Rose, Gregory V
> Sent: Thursday, October 20, 2011 1:44 PM
> To: Roopa Prabhu; netdev@vger.kernel.org
> Cc: sri@us.ibm.com; dragos.tatulea@gmail.com; arnd@arndb.de;
> kvm@vger.kernel.org; mst@redhat.com; davem@davemloft.net;
> mchan@broadcom.com; dwang2@cisco.com; shemminger@vyatta.com;
> eric.dumazet@gmail.com; kaber@trash.net; benve@cisco.com
> Subject: RE: [net-next-2.6 PATCH 0/8 RFC v2] macvlan: MAC Address
> filtering support for passthru mode
>
> > -----Original Message-----
> > From: Roopa Prabhu [mailto:roprabhu@cisco.com]
> > Sent: Wednesday, October 19, 2011 3:30 PM
> > To: Rose, Gregory V; netdev@vger.kernel.org
> > Cc: sri@us.ibm.com; dragos.tatulea@gmail.com; arnd@arndb.de;
> > kvm@vger.kernel.org; mst@redhat.com; davem@davemloft.net;
> > mchan@broadcom.com; dwang2@cisco.com; shemminger@vyatta.com;
> > eric.dumazet@gmail.com; kaber@trash.net; benve@cisco.com
> > Subject: Re: [net-next-2.6 PATCH 0/8 RFC v2] macvlan: MAC Address
> > filtering support for passthru mode
> >
> >
> >
> >
> > On 10/19/11 2:06 PM, "Rose, Gregory V" <gregory.v.rose@intel.com> wrote:
> >
> > >> -----Original Message-----
> > >> From: netdev-owner@vger.kernel.org [mailto:netdev-
> > owner@vger.kernel.org]
> > >> On Behalf Of Roopa Prabhu
> > >> Sent: Tuesday, October 18, 2011 11:26 PM
> > >> To: netdev@vger.kernel.org
> > >> Cc: sri@us.ibm.com; dragos.tatulea@gmail.com; arnd@arndb.de;
> > >> kvm@vger.kernel.org; mst@redhat.com; davem@davemloft.net;
> > >> mchan@broadcom.com; dwang2@cisco.com; shemminger@vyatta.com;
> > >> eric.dumazet@gmail.com; kaber@trash.net; benve@cisco.com
> > >> Subject: [net-next-2.6 PATCH 0/8 RFC v2] macvlan: MAC Address
> filtering
> > >> support for passthru mode
> > >>
> > >
> > > [snip...]
> > >
> > >>
> > >>
> > >> Note: The choice of rtnl_link_ops was because I saw the use case for
> > >> this in virtual devices that need to do filtering in sw like macvlan
> > >> and tun. Hw devices usually have filtering in hw with netdev->uc and
> > >> mc lists to indicate active filters. But I can move from
> rtnl_link_ops
> > >> to netdev_ops if that is the preferred way to go and if there is a
> > >> need to support this interface on all kinds of interfaces.
> > >> Please suggest.
> > >
> > > I'm still digesting the rest of the RFC patches but I did want to
> > quickly jump
> > > in and push for adding this support in netdev_ops. I would like to
> see
> > these
> > > features available in more devices than just macvtap and macvlan. I
> can
> > > conceive
> > > of use cases for multiple HW MAC and VLAN filters for a VF device that
> > isn't
> > > owned by a macvlan/macvtap interface and only has netdev_ops support.
> > In this
> > > case it would be necessary to program the filters directly to the VF
> > device
> > > interface or PF interface (or lowerdev as you refer to it) instead of
> > going
> > > through macvlan/macvtap.
> > >
> > > This work dovetails nicely with some work I've been doing and I'd be
> > very
> > > interested
> > > in helping move this forward if we could work out the details that
> would
> > allow
> > > support
> > > of the features we (and the community) require.
> >
> > Great. Thanks. I will definitely be interested to get this patch working
> > for
> > any other use case you have.
> >
> > Moving the ops to netdev should be trivial. You probably want the ops to
> > work on the VF via the PF, like the existing ndo_set_vf_mac etc.
>
> That is correct, so we would need to add some way to pass the VF number to
> the op.
> In addition, there are use cases for multiple MAC address filters for the
> Physical
> Function (PF) so we would like to be able to identify to the netdev op
> that it is
> supposed to perform the action on the PF filters instead of a VF.
>
> An example of this would be when an administrator has created some number of VFs
> for a given PF but is also running the PF in bridged (i.e. promiscuous)mode so
> that it can support purely SW emulated network connections in some VMs that have
> low network latency and bandwidth requirements while reserving the VFs for VMs that
^^^
That should be "no", not low...
- Greg
^ permalink raw reply
* Re: [PATCH net-next] myri10ge: fix truesize underestimation
From: Andrew Gallatin @ 2011-10-20 20:45 UTC (permalink / raw)
To: Eric Dumazet; +Cc: Jon Mason, David Miller, netdev
In-Reply-To: <1319143442.2854.26.camel@edumazet-laptop>
On 10/20/11 16:44, Eric Dumazet wrote:
> Le jeudi 20 octobre 2011 à 15:33 -0500, Jon Mason a écrit :
>> On Thu, Oct 20, 2011 at 3:10 PM, Eric Dumazet<eric.dumazet@gmail.com> wrote:
>>> skb->truesize must account for allocated memory, not the used part of
>>> it. Doing this work is important to avoid unexpected OOM situations.
>>>
>>> Signed-off-by: Eric Dumazet<eric.dumazet@gmail.com>
>>
>> Acked-by: Jon Mason<mason@myri.com>
>
> Thanks for reviewing Jon !
>
>
Please wait a second.. I think the patch is incorrect.
There is already code in myri10ge_rx_skb_build() which
attempts to set the truesize. However, it sets it to
the used, rather than the allocated size so it is apparently
incorrect.
I'd prefer we fix that code.
Thanks,
Drew
^ permalink raw reply
* Re: [PATCH net-next] myri10ge: fix truesize underestimation
From: Eric Dumazet @ 2011-10-20 20:44 UTC (permalink / raw)
To: Jon Mason; +Cc: David Miller, netdev, Andrew Gallatin
In-Reply-To: <CAMaF-rN8K3hDiwwqh_eGQ0nrxskn+7r9Rn_yDJ46aesKR77nbg@mail.gmail.com>
Le jeudi 20 octobre 2011 à 15:33 -0500, Jon Mason a écrit :
> On Thu, Oct 20, 2011 at 3:10 PM, Eric Dumazet <eric.dumazet@gmail.com> wrote:
> > skb->truesize must account for allocated memory, not the used part of
> > it. Doing this work is important to avoid unexpected OOM situations.
> >
> > Signed-off-by: Eric Dumazet <eric.dumazet@gmail.com>
>
> Acked-by: Jon Mason <mason@myri.com>
Thanks for reviewing Jon !
^ permalink raw reply
* RE: [net-next-2.6 PATCH 0/8 RFC v2] macvlan: MAC Address filtering support for passthru mode
From: Rose, Gregory V @ 2011-10-20 20:43 UTC (permalink / raw)
To: Roopa Prabhu, netdev@vger.kernel.org
Cc: sri@us.ibm.com, dragos.tatulea@gmail.com, arnd@arndb.de,
kvm@vger.kernel.org, mst@redhat.com, davem@davemloft.net,
mchan@broadcom.com, dwang2@cisco.com, shemminger@vyatta.com,
eric.dumazet@gmail.com, kaber@trash.net, benve@cisco.com
In-Reply-To: <CAC49D8A.374FB%roprabhu@cisco.com>
> -----Original Message-----
> From: Roopa Prabhu [mailto:roprabhu@cisco.com]
> Sent: Wednesday, October 19, 2011 3:30 PM
> To: Rose, Gregory V; netdev@vger.kernel.org
> Cc: sri@us.ibm.com; dragos.tatulea@gmail.com; arnd@arndb.de;
> kvm@vger.kernel.org; mst@redhat.com; davem@davemloft.net;
> mchan@broadcom.com; dwang2@cisco.com; shemminger@vyatta.com;
> eric.dumazet@gmail.com; kaber@trash.net; benve@cisco.com
> Subject: Re: [net-next-2.6 PATCH 0/8 RFC v2] macvlan: MAC Address
> filtering support for passthru mode
>
>
>
>
> On 10/19/11 2:06 PM, "Rose, Gregory V" <gregory.v.rose@intel.com> wrote:
>
> >> -----Original Message-----
> >> From: netdev-owner@vger.kernel.org [mailto:netdev-
> owner@vger.kernel.org]
> >> On Behalf Of Roopa Prabhu
> >> Sent: Tuesday, October 18, 2011 11:26 PM
> >> To: netdev@vger.kernel.org
> >> Cc: sri@us.ibm.com; dragos.tatulea@gmail.com; arnd@arndb.de;
> >> kvm@vger.kernel.org; mst@redhat.com; davem@davemloft.net;
> >> mchan@broadcom.com; dwang2@cisco.com; shemminger@vyatta.com;
> >> eric.dumazet@gmail.com; kaber@trash.net; benve@cisco.com
> >> Subject: [net-next-2.6 PATCH 0/8 RFC v2] macvlan: MAC Address filtering
> >> support for passthru mode
> >>
> >
> > [snip...]
> >
> >>
> >>
> >> Note: The choice of rtnl_link_ops was because I saw the use case for
> >> this in virtual devices that need to do filtering in sw like macvlan
> >> and tun. Hw devices usually have filtering in hw with netdev->uc and
> >> mc lists to indicate active filters. But I can move from rtnl_link_ops
> >> to netdev_ops if that is the preferred way to go and if there is a
> >> need to support this interface on all kinds of interfaces.
> >> Please suggest.
> >
> > I'm still digesting the rest of the RFC patches but I did want to
> quickly jump
> > in and push for adding this support in netdev_ops. I would like to see
> these
> > features available in more devices than just macvtap and macvlan. I can
> > conceive
> > of use cases for multiple HW MAC and VLAN filters for a VF device that
> isn't
> > owned by a macvlan/macvtap interface and only has netdev_ops support.
> In this
> > case it would be necessary to program the filters directly to the VF
> device
> > interface or PF interface (or lowerdev as you refer to it) instead of
> going
> > through macvlan/macvtap.
> >
> > This work dovetails nicely with some work I've been doing and I'd be
> very
> > interested
> > in helping move this forward if we could work out the details that would
> allow
> > support
> > of the features we (and the community) require.
>
> Great. Thanks. I will definitely be interested to get this patch working
> for
> any other use case you have.
>
> Moving the ops to netdev should be trivial. You probably want the ops to
> work on the VF via the PF, like the existing ndo_set_vf_mac etc.
That is correct, so we would need to add some way to pass the VF number to the op.
In addition, there are use cases for multiple MAC address filters for the Physical
Function (PF) so we would like to be able to identify to the netdev op that it is
supposed to perform the action on the PF filters instead of a VF.
An example of this would be when an administrator has created some number of VFs
for a given PF but is also running the PF in bridged (i.e. promiscuous) mode so that it
can support purely SW emulated network connections in some VMs that have low network
latency and bandwidth requirements while reserving the VFs for VMs that require the low latency, high throughput that directly assigned VFs can provide. In this case an
emulated SW interface in a VM is unable to properly communicate with VFs on the same
PF because the emulated SW interface's MAC address isn't programmed into the HW filters
on the PF. If we could use this op to program the MAC address and VLAN filters of
the emulated SW interfaces into the PF HW a VF could then properly communicate across
the NIC's internal VEB to the emulated SW interfaces.
> Yes, lets work out the details and I can move this to netdev->ops. Let me
> know.
I think essentially if you could add some parameter to the ops to specify whether it
is addressing a VF or the PF and then if it is a VF further specify the VF number we
would be very close to addressing the requirements of many valuable use cases in
addition to the ones you have identified in your RFC.
Does that sound reasonable?
Thanks,
- Greg
^ permalink raw reply
* [PATCH v2 net-next] tcp: use TCP_DEFAULT_INIT_RCVWND in tcp_fixup_rcvbuf()
From: Eric Dumazet @ 2011-10-20 20:41 UTC (permalink / raw)
To: David Miller; +Cc: netdev
In-Reply-To: <20111020.161356.2120784879469409197.davem@davemloft.net>
Since commit 356f039822b (TCP: increase default initial receive
window.), we allow sender to send 10 (TCP_DEFAULT_INIT_RCVWND) segments.
Change tcp_fixup_rcvbuf() to reflect this change, even if no real change
is expected, since sysctl_tcp_rmem[1] = 87380 and this value
is bigger than tcp_fixup_rcvbuf() computed rcvmem (~23720)
Note: Since commit 356f039822b limited default window to maximum of
10*1460 and 2*MSS, we use same heuristic in this patch.
Signed-off-by: Eric Dumazet <eric.dumazet@gmail.com>
---
net/ipv4/tcp_input.c | 23 +++++++++++++++--------
1 file changed, 15 insertions(+), 8 deletions(-)
diff --git a/net/ipv4/tcp_input.c b/net/ipv4/tcp_input.c
index 1e848b2..e8e6d49 100644
--- a/net/ipv4/tcp_input.c
+++ b/net/ipv4/tcp_input.c
@@ -345,17 +345,24 @@ static void tcp_grow_window(struct sock *sk, struct sk_buff *skb)
static void tcp_fixup_rcvbuf(struct sock *sk)
{
- struct tcp_sock *tp = tcp_sk(sk);
- int rcvmem = SKB_TRUESIZE(tp->advmss + MAX_TCP_HEADER);
+ u32 mss = tcp_sk(sk)->advmss;
+ u32 icwnd = TCP_DEFAULT_INIT_RCVWND;
+ int rcvmem;
- /* Try to select rcvbuf so that 4 mss-sized segments
- * will fit to window and corresponding skbs will fit to our rcvbuf.
- * (was 3; 4 is minimum to allow fast retransmit to work.)
+ /* Limit to 10 segments if mss <= 1460,
+ * or 14600/mss segments, with a minimum of two segments.
*/
- while (tcp_win_from_space(rcvmem) < tp->advmss)
+ if (mss > 1460)
+ icwnd = max_t(u32, (1460 * TCP_DEFAULT_INIT_RCVWND) / mss, 2);
+
+ rcvmem = SKB_TRUESIZE(mss + MAX_TCP_HEADER);
+ while (tcp_win_from_space(rcvmem) < mss)
rcvmem += 128;
- if (sk->sk_rcvbuf < 4 * rcvmem)
- sk->sk_rcvbuf = min(4 * rcvmem, sysctl_tcp_rmem[2]);
+
+ rcvmem *= icwnd;
+
+ if (sk->sk_rcvbuf < rcvmem)
+ sk->sk_rcvbuf = min(rcvmem, sysctl_tcp_rmem[2]);
}
/* 4. Try to fixup all. It is made immediately after connection enters
^ permalink raw reply related
* Re: Kernel panic from tg3 net driver
From: Ari Savolainen @ 2011-10-20 20:37 UTC (permalink / raw)
To: Eric Dumazet; +Cc: David Miller, richardcochran, netdev, linux-kernel
In-Reply-To: <1319141867.2854.19.camel@edumazet-laptop>
That's right. I tried the patch and it didn't help.
Ari
2011/10/20 Eric Dumazet <eric.dumazet@gmail.com>:
> Le jeudi 20 octobre 2011 à 16:11 -0400, David Miller a écrit :
>> From: Eric Dumazet <eric.dumazet@gmail.com>
>> Date: Thu, 20 Oct 2011 22:05:25 +0200
>>
>> > And I think this was fixed yesterday ?
>> >
>> > De: roy.qing.li@gmail.com
>> > À: ari.m.savolainen@gmail.com, netdev@vger.kernel.org
>> > Sujet: [PATCH net-next] neigh: fix rcu splat in neigh_update()
>> > Date: Tue, 18 Oct 2011 16:32:42 +0800 (18/10/2011 10:32:42)
>> >
>>
>> Good catch, it seems to be this bug.
>
> Oh well, sorry, it seems it was one bug hit during bisection, but maybe
> its completely unrelated to the real problem.
>
>
>
>
^ permalink raw reply
* Re: [PATCH net-next] myri10ge: fix truesize underestimation
From: Jon Mason @ 2011-10-20 20:33 UTC (permalink / raw)
To: Eric Dumazet; +Cc: David Miller, netdev, Andrew Gallatin
In-Reply-To: <1319141403.2854.17.camel@edumazet-laptop>
On Thu, Oct 20, 2011 at 3:10 PM, Eric Dumazet <eric.dumazet@gmail.com> wrote:
> skb->truesize must account for allocated memory, not the used part of
> it. Doing this work is important to avoid unexpected OOM situations.
>
> Signed-off-by: Eric Dumazet <eric.dumazet@gmail.com>
Acked-by: Jon Mason <mason@myri.com>
> CC: Jon Mason <mason@myri.com>
> ---
> drivers/net/ethernet/myricom/myri10ge/myri10ge.c | 3 ++-
> 1 file changed, 2 insertions(+), 1 deletion(-)
>
> diff --git a/drivers/net/ethernet/myricom/myri10ge/myri10ge.c b/drivers/net/ethernet/myricom/myri10ge/myri10ge.c
> index c970a48..0778edc 100644
> --- a/drivers/net/ethernet/myricom/myri10ge/myri10ge.c
> +++ b/drivers/net/ethernet/myricom/myri10ge/myri10ge.c
> @@ -1210,7 +1210,6 @@ myri10ge_rx_skb_build(struct sk_buff *skb, u8 * va,
> struct skb_frag_struct *skb_frags;
>
> skb->len = skb->data_len = len;
> - skb->truesize = len + sizeof(struct sk_buff);
> /* attach the page(s) */
>
> skb_frags = skb_shinfo(skb)->frags;
> @@ -1385,6 +1384,8 @@ myri10ge_rx_done(struct myri10ge_slice_state *ss, int len, __wsum csum,
> if (skb_frag_size(&skb_shinfo(skb)->frags[0]) <= 0) {
> skb_frag_unref(skb, 0);
> skb_shinfo(skb)->nr_frags = 0;
> + } else {
> + skb->truesize += bytes * skb_shinfo(skb)->nr_frags;
> }
> skb->protocol = eth_type_trans(skb, dev);
> skb_record_rx_queue(skb, ss - &mgp->ss[0]);
>
>
>
^ permalink raw reply
* Re: [patch net-next]alx: Atheros AR8131/AR8151/AR8152/AR8161 Ethernet driver
From: Luis R. Rodriguez @ 2011-10-20 20:33 UTC (permalink / raw)
To: Ren, Cloud
Cc: David Miller, netdev@vger.kernel.org,
linux-kernel@vger.kernel.org
In-Reply-To: <6349D7A510622448B1BA0967850A8438011CC2A0@nasanexd02d.na.qualcomm.com>
On Thu, Oct 20, 2011 at 2:48 AM, Ren, Cloud <cjren@qca.qualcomm.com> wrote:
>
>>From: "Ren, Cloud" <cjren@qca.qualcomm.com>
>>Date: Thu, 20 Oct 2011 09:23:07 +0000
>>
>>> As you saw, should I do the two following steps?
>>> 1. I firstly try to submit code to linux-staging.git.
>>> 2. After the driver have been accepted by linux-staging.git, I submit to net-
>>next.git again.
>>
>>You submit and get it into staging so that it can sit there for some time and get
>>reviewed and improved by others.
>>
>>One doesn't submit directly to net-next right after it gets into staging, staging
>>is a place where your driver lives while it still smelly funky and needs more
>>work.
>
> The driver will support the next generation NICs of Atheros. Meanwhile, the driver can
> also have better optimization for AR8131 and AR8151 than atl1c. For some reason, we
> don't plan to patch atl1c driver to support our new NIC, such as AR8161. So I hope the driver
> can stay in net-next in the end. Of course, I will be responsible for modify source code and
> let it match kernel requirements.
Cloud,
If you want to skip staging (which I recommend) then you need to
address all upstream concerns expressed. Given that you indicate that
you will be working on following up with the driver until its
acceptable upstream my recommendation is either to clean up the driver
very well and review it internally at Atheros prior to a public
submission *or* just dump into staging and get the benefit of
community cleanup and eventually wait until it is ready for proper
upstream. If you want internal private review at Atheros you can use
the internal private ath9k-devel list.
Also are you going to maintain the older atlx drivers? While at it can
you clear up who maintains what as far as Atheros is concerned for
Ethernet?
Luis
^ permalink raw reply
page: next (older) | prev (newer) | latest
- recent:[subjects (threaded)|topics (new)|topics (active)]
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox