Skip to content

Commit

Permalink
tg3: adapt tg3 to use reworked PCI PM code
Browse files Browse the repository at this point in the history
Adapt the tg3 driver to use the reworked PCI PM and make it use the
exported PCI PM core functions instead of accessing the PCI PM registers
directly by itself.

Signed-off-by: Rafael J. Wysocki <rjw@sisk.pl>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: David S. Miller <davem@davemloft.net>
  • Loading branch information
Rafael J. Wysocki authored and David S. Miller committed Jul 30, 2008
1 parent 849e8ca commit 12dac07
Showing 1 changed file with 28 additions and 39 deletions.
67 changes: 28 additions & 39 deletions drivers/net/tg3.c
Original file line number Diff line number Diff line change
Expand Up @@ -1982,8 +1982,6 @@ static void tg3_power_down_phy(struct tg3 *tp)
static int tg3_set_power_state(struct tg3 *tp, pci_power_t state)
{
u32 misc_host_ctrl;
u16 power_control, power_caps;
int pm = tp->pm_cap;

/* Make sure register accesses (indirect or otherwise)
* will function correctly.
Expand All @@ -1992,18 +1990,10 @@ static int tg3_set_power_state(struct tg3 *tp, pci_power_t state)
TG3PCI_MISC_HOST_CTRL,
tp->misc_host_ctrl);

pci_read_config_word(tp->pdev,
pm + PCI_PM_CTRL,
&power_control);
power_control |= PCI_PM_CTRL_PME_STATUS;
power_control &= ~(PCI_PM_CTRL_STATE_MASK);
switch (state) {
case PCI_D0:
power_control |= 0;
pci_write_config_word(tp->pdev,
pm + PCI_PM_CTRL,
power_control);
udelay(100); /* Delay after power state change */
pci_enable_wake(tp->pdev, state, false);
pci_set_power_state(tp->pdev, PCI_D0);

/* Switch out of Vaux if it is a NIC */
if (tp->tg3_flags2 & TG3_FLG2_IS_NIC)
Expand All @@ -2012,26 +2002,15 @@ static int tg3_set_power_state(struct tg3 *tp, pci_power_t state)
return 0;

case PCI_D1:
power_control |= 1;
break;

case PCI_D2:
power_control |= 2;
break;

case PCI_D3hot:
power_control |= 3;
break;

default:
printk(KERN_WARNING PFX "%s: Invalid power state (%d) "
"requested.\n",
tp->dev->name, state);
printk(KERN_ERR PFX "%s: Invalid power state (D%d) requested\n",
tp->dev->name, state);
return -EINVAL;
}

power_control |= PCI_PM_CTRL_PME_ENABLE;

misc_host_ctrl = tr32(TG3PCI_MISC_HOST_CTRL);
tw32(TG3PCI_MISC_HOST_CTRL,
misc_host_ctrl | MISC_HOST_CTRL_MASK_PCI_INT);
Expand Down Expand Up @@ -2109,8 +2088,6 @@ static int tg3_set_power_state(struct tg3 *tp, pci_power_t state)
WOL_DRV_WOL |
WOL_SET_MAGIC_PKT);

pci_read_config_word(tp->pdev, pm + PCI_PM_PMC, &power_caps);

if (tp->tg3_flags & TG3_FLAG_WOL_ENABLE) {
u32 mac_mode;

Expand Down Expand Up @@ -2143,8 +2120,8 @@ static int tg3_set_power_state(struct tg3 *tp, pci_power_t state)
if (!(tp->tg3_flags2 & TG3_FLG2_5750_PLUS))
tw32(MAC_LED_CTRL, tp->led_ctrl);

if (((power_caps & PCI_PM_CAP_PME_D3cold) &&
(tp->tg3_flags & TG3_FLAG_WOL_ENABLE)))
if (pci_pme_capable(tp->pdev, state) &&
(tp->tg3_flags & TG3_FLAG_WOL_ENABLE))
mac_mode |= MAC_MODE_MAGIC_PKT_ENABLE;

tw32_f(MAC_MODE, mac_mode);
Expand Down Expand Up @@ -2236,9 +2213,11 @@ static int tg3_set_power_state(struct tg3 *tp, pci_power_t state)

tg3_write_sig_post_reset(tp, RESET_KIND_SHUTDOWN);

if (tp->tg3_flags & TG3_FLAG_WOL_ENABLE)
pci_enable_wake(tp->pdev, state, true);

/* Finally, set the new power state. */
pci_write_config_word(tp->pdev, pm + PCI_PM_CTRL, power_control);
udelay(100); /* Delay after power state change */
pci_set_power_state(tp->pdev, state);

return 0;
}
Expand Down Expand Up @@ -9065,7 +9044,8 @@ static void tg3_get_wol(struct net_device *dev, struct ethtool_wolinfo *wol)
{
struct tg3 *tp = netdev_priv(dev);

if (tp->tg3_flags & TG3_FLAG_WOL_CAP)
if ((tp->tg3_flags & TG3_FLAG_WOL_CAP) &&
device_can_wakeup(&tp->pdev->dev))
wol->supported = WAKE_MAGIC;
else
wol->supported = 0;
Expand All @@ -9078,18 +9058,22 @@ static void tg3_get_wol(struct net_device *dev, struct ethtool_wolinfo *wol)
static int tg3_set_wol(struct net_device *dev, struct ethtool_wolinfo *wol)
{
struct tg3 *tp = netdev_priv(dev);
struct device *dp = &tp->pdev->dev;

if (wol->wolopts & ~WAKE_MAGIC)
return -EINVAL;
if ((wol->wolopts & WAKE_MAGIC) &&
!(tp->tg3_flags & TG3_FLAG_WOL_CAP))
!((tp->tg3_flags & TG3_FLAG_WOL_CAP) && device_can_wakeup(dp)))
return -EINVAL;

spin_lock_bh(&tp->lock);
if (wol->wolopts & WAKE_MAGIC)
if (wol->wolopts & WAKE_MAGIC) {
tp->tg3_flags |= TG3_FLAG_WOL_ENABLE;
else
device_set_wakeup_enable(dp, true);
} else {
tp->tg3_flags &= ~TG3_FLAG_WOL_ENABLE;
device_set_wakeup_enable(dp, false);
}
spin_unlock_bh(&tp->lock);

return 0;
Expand Down Expand Up @@ -11296,7 +11280,8 @@ static void __devinit tg3_get_eeprom_hw_cfg(struct tg3 *tp)
if (val & VCPU_CFGSHDW_ASPM_DBNC)
tp->tg3_flags |= TG3_FLAG_ASPM_WORKAROUND;
if ((val & VCPU_CFGSHDW_WOL_ENABLE) &&
(val & VCPU_CFGSHDW_WOL_MAGPKT))
(val & VCPU_CFGSHDW_WOL_MAGPKT) &&
device_may_wakeup(&tp->pdev->dev))
tp->tg3_flags |= TG3_FLAG_WOL_ENABLE;
return;
}
Expand Down Expand Up @@ -11426,8 +11411,9 @@ static void __devinit tg3_get_eeprom_hw_cfg(struct tg3 *tp)
!(nic_cfg & NIC_SRAM_DATA_CFG_FIBER_WOL))
tp->tg3_flags &= ~TG3_FLAG_WOL_CAP;

if (tp->tg3_flags & TG3_FLAG_WOL_CAP &&
nic_cfg & NIC_SRAM_DATA_CFG_WOL_ENABLE)
if ((tp->tg3_flags & TG3_FLAG_WOL_CAP) &&
(nic_cfg & NIC_SRAM_DATA_CFG_WOL_ENABLE) &&
device_may_wakeup(&tp->pdev->dev))
tp->tg3_flags |= TG3_FLAG_WOL_ENABLE;

if (cfg2 & (1 << 17))
Expand Down Expand Up @@ -13613,6 +13599,7 @@ static int tg3_suspend(struct pci_dev *pdev, pm_message_t state)
{
struct net_device *dev = pci_get_drvdata(pdev);
struct tg3 *tp = netdev_priv(dev);
pci_power_t target_state;
int err;

/* PCI register 4 needs to be saved whether netif_running() or not.
Expand Down Expand Up @@ -13641,7 +13628,9 @@ static int tg3_suspend(struct pci_dev *pdev, pm_message_t state)
tp->tg3_flags &= ~TG3_FLAG_INIT_COMPLETE;
tg3_full_unlock(tp);

err = tg3_set_power_state(tp, pci_choose_state(pdev, state));
target_state = pdev->pm_cap ? pci_target_state(pdev) : PCI_D3hot;

err = tg3_set_power_state(tp, target_state);
if (err) {
int err2;

Expand Down

0 comments on commit 12dac07

Please sign in to comment.