net: usb: ax88179_178a: wol optimizations
- Check if wol is supported on reset instead of everytime get_wol is called. - Save wolopts in private data instead of relying on the HW to save it. - Defer enabling WoL until suspend instead of enabling it everytime set_wol is called. Signed-off-by: Justin Chen <justinpopo6@gmail.com> Signed-off-by: Jakub Kicinski <kuba@kernel.org>
This commit is contained in:
parent
2bcbd3d8a7
commit
5050531610
@ -171,6 +171,8 @@ struct ax88179_data {
|
||||
u8 eee_active;
|
||||
u16 rxctl;
|
||||
u8 in_pm;
|
||||
u32 wol_supported;
|
||||
u32 wolopts;
|
||||
};
|
||||
|
||||
struct ax88179_int_data {
|
||||
@ -400,6 +402,7 @@ ax88179_phy_write_mmd_indirect(struct usbnet *dev, u16 prtad, u16 devad,
|
||||
static int ax88179_suspend(struct usb_interface *intf, pm_message_t message)
|
||||
{
|
||||
struct usbnet *dev = usb_get_intfdata(intf);
|
||||
struct ax88179_data *priv = dev->driver_priv;
|
||||
u16 tmp16;
|
||||
u8 tmp8;
|
||||
|
||||
@ -407,6 +410,19 @@ static int ax88179_suspend(struct usb_interface *intf, pm_message_t message)
|
||||
|
||||
usbnet_suspend(intf, message);
|
||||
|
||||
/* Enable WoL */
|
||||
if (priv->wolopts) {
|
||||
ax88179_read_cmd(dev, AX_ACCESS_MAC, AX_MONITOR_MOD,
|
||||
1, 1, &tmp8);
|
||||
if (priv->wolopts & WAKE_PHY)
|
||||
tmp8 |= AX_MONITOR_MODE_RWLC;
|
||||
if (priv->wolopts & WAKE_MAGIC)
|
||||
tmp8 |= AX_MONITOR_MODE_RWMP;
|
||||
|
||||
ax88179_write_cmd(dev, AX_ACCESS_MAC, AX_MONITOR_MOD,
|
||||
1, 1, &tmp8);
|
||||
}
|
||||
|
||||
/* Disable RX path */
|
||||
ax88179_read_cmd(dev, AX_ACCESS_MAC, AX_MEDIUM_STATUS_MODE,
|
||||
2, 2, &tmp16);
|
||||
@ -480,40 +496,22 @@ static void
|
||||
ax88179_get_wol(struct net_device *net, struct ethtool_wolinfo *wolinfo)
|
||||
{
|
||||
struct usbnet *dev = netdev_priv(net);
|
||||
u8 opt;
|
||||
struct ax88179_data *priv = dev->driver_priv;
|
||||
|
||||
if (ax88179_read_cmd(dev, AX_ACCESS_MAC, AX_MONITOR_MOD,
|
||||
1, 1, &opt) < 0) {
|
||||
wolinfo->supported = 0;
|
||||
wolinfo->wolopts = 0;
|
||||
return;
|
||||
}
|
||||
|
||||
wolinfo->supported = WAKE_PHY | WAKE_MAGIC;
|
||||
wolinfo->wolopts = 0;
|
||||
if (opt & AX_MONITOR_MODE_RWLC)
|
||||
wolinfo->wolopts |= WAKE_PHY;
|
||||
if (opt & AX_MONITOR_MODE_RWMP)
|
||||
wolinfo->wolopts |= WAKE_MAGIC;
|
||||
wolinfo->supported = priv->wol_supported;
|
||||
wolinfo->wolopts = priv->wolopts;
|
||||
}
|
||||
|
||||
static int
|
||||
ax88179_set_wol(struct net_device *net, struct ethtool_wolinfo *wolinfo)
|
||||
{
|
||||
struct usbnet *dev = netdev_priv(net);
|
||||
u8 opt = 0;
|
||||
struct ax88179_data *priv = dev->driver_priv;
|
||||
|
||||
if (wolinfo->wolopts & ~(WAKE_PHY | WAKE_MAGIC))
|
||||
if (wolinfo->wolopts & ~(priv->wol_supported))
|
||||
return -EINVAL;
|
||||
|
||||
if (wolinfo->wolopts & WAKE_PHY)
|
||||
opt |= AX_MONITOR_MODE_RWLC;
|
||||
if (wolinfo->wolopts & WAKE_MAGIC)
|
||||
opt |= AX_MONITOR_MODE_RWMP;
|
||||
|
||||
if (ax88179_write_cmd(dev, AX_ACCESS_MAC, AX_MONITOR_MOD,
|
||||
1, 1, &opt) < 0)
|
||||
return -EINVAL;
|
||||
priv->wolopts = wolinfo->wolopts;
|
||||
|
||||
return 0;
|
||||
}
|
||||
@ -1636,6 +1634,12 @@ static int ax88179_reset(struct usbnet *dev)
|
||||
ax88179_write_cmd(dev, AX_ACCESS_MAC, AX_MEDIUM_STATUS_MODE,
|
||||
2, 2, tmp16);
|
||||
|
||||
/* Check if WoL is supported */
|
||||
ax179_data->wol_supported = 0;
|
||||
if (ax88179_read_cmd(dev, AX_ACCESS_MAC, AX_MONITOR_MOD,
|
||||
1, 1, &tmp) > 0)
|
||||
ax179_data->wol_supported = WAKE_MAGIC | WAKE_PHY;
|
||||
|
||||
ax88179_led_setting(dev);
|
||||
|
||||
ax179_data->eee_enabled = 0;
|
||||
|
Loading…
Reference in New Issue
Block a user