ksz884x.c (e98bdb3059cbf2b1cd4261e126b08429f64466c3) ksz884x.c (03671057c3b769c0adbf9212bf695481d3f59279)
1/**
2 * drivers/net/ethernet/micrel/ksx884x.c - Micrel KSZ8841/2 PCI Ethernet driver
3 *
4 * Copyright (c) 2009-2010 Micrel, Inc.
5 * Tristram Ha <Tristram.Ha@micrel.com>
6 *
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License version 2 as

--- 1237 unchanged lines hidden (view full) ---

1246 * @intr_blocked: Interrupt blocked.
1247 * @rx_desc_info: Receive descriptor information.
1248 * @tx_desc_info: Transmit descriptor information.
1249 * @tx_int_cnt: Transmit interrupt count. Used for TX optimization.
1250 * @tx_int_mask: Transmit interrupt mask. Used for TX optimization.
1251 * @tx_size: Transmit data size. Used for TX optimization.
1252 * The maximum is defined by MAX_TX_HELD_SIZE.
1253 * @perm_addr: Permanent MAC address.
1/**
2 * drivers/net/ethernet/micrel/ksx884x.c - Micrel KSZ8841/2 PCI Ethernet driver
3 *
4 * Copyright (c) 2009-2010 Micrel, Inc.
5 * Tristram Ha <Tristram.Ha@micrel.com>
6 *
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License version 2 as

--- 1237 unchanged lines hidden (view full) ---

1246 * @intr_blocked: Interrupt blocked.
1247 * @rx_desc_info: Receive descriptor information.
1248 * @tx_desc_info: Transmit descriptor information.
1249 * @tx_int_cnt: Transmit interrupt count. Used for TX optimization.
1250 * @tx_int_mask: Transmit interrupt mask. Used for TX optimization.
1251 * @tx_size: Transmit data size. Used for TX optimization.
1252 * The maximum is defined by MAX_TX_HELD_SIZE.
1253 * @perm_addr: Permanent MAC address.
1254 * @override_addr: Overrided MAC address.
1254 * @override_addr: Overridden MAC address.
1255 * @address: Additional MAC address entries.
1256 * @addr_list_size: Additional MAC address list size.
1255 * @address: Additional MAC address entries.
1256 * @addr_list_size: Additional MAC address list size.
1257 * @mac_override: Indication of MAC address overrided.
1257 * @mac_override: Indication of MAC address overridden.
1258 * @promiscuous: Counter to keep track of promiscuous mode set.
1259 * @all_multi: Counter to keep track of all multicast mode set.
1260 * @multi_list: Multicast address entries.
1261 * @multi_bits: Cached multicast hash table settings.
1262 * @multi_list_size: Multicast address list size.
1263 * @enabled: Indication of hardware enabled.
1264 * @rx_stop: Indication of receive process stop.
1265 * @features: Hardware features to enable.

--- 2771 unchanged lines hidden (view full) ---

4037 return 0 == *addr1 && 0 == *addr2;
4038}
4039
4040/**
4041 * hw_set_addr - set MAC address
4042 * @hw: The hardware instance.
4043 *
4044 * This routine programs the MAC address of the hardware when the address is
1258 * @promiscuous: Counter to keep track of promiscuous mode set.
1259 * @all_multi: Counter to keep track of all multicast mode set.
1260 * @multi_list: Multicast address entries.
1261 * @multi_bits: Cached multicast hash table settings.
1262 * @multi_list_size: Multicast address list size.
1263 * @enabled: Indication of hardware enabled.
1264 * @rx_stop: Indication of receive process stop.
1265 * @features: Hardware features to enable.

--- 2771 unchanged lines hidden (view full) ---

4037 return 0 == *addr1 && 0 == *addr2;
4038}
4039
4040/**
4041 * hw_set_addr - set MAC address
4042 * @hw: The hardware instance.
4043 *
4044 * This routine programs the MAC address of the hardware when the address is
4045 * overrided.
4045 * overridden.
4046 */
4047static void hw_set_addr(struct ksz_hw *hw)
4048{
4049 int i;
4050
4051 for (i = 0; i < ETH_ALEN; i++)
4052 writeb(hw->override_addr[MAC_ADDR_ORDER(i)],
4053 hw->io + KS884X_ADDR_0_OFFSET + i);

--- 1885 unchanged lines hidden (view full) ---

5939 (ADVERTISED_10baseT_Half | \
5940 ADVERTISED_10baseT_Full | \
5941 ADVERTISED_100baseT_Half | \
5942 ADVERTISED_100baseT_Full)
5943
5944/* These functions use the MII functions in mii.c. */
5945
5946/**
4046 */
4047static void hw_set_addr(struct ksz_hw *hw)
4048{
4049 int i;
4050
4051 for (i = 0; i < ETH_ALEN; i++)
4052 writeb(hw->override_addr[MAC_ADDR_ORDER(i)],
4053 hw->io + KS884X_ADDR_0_OFFSET + i);

--- 1885 unchanged lines hidden (view full) ---

5939 (ADVERTISED_10baseT_Half | \
5940 ADVERTISED_10baseT_Full | \
5941 ADVERTISED_100baseT_Half | \
5942 ADVERTISED_100baseT_Full)
5943
5944/* These functions use the MII functions in mii.c. */
5945
5946/**
5947 * netdev_get_settings - get network device settings
5947 * netdev_get_link_ksettings - get network device settings
5948 * @dev: Network device.
5949 * @cmd: Ethtool command.
5950 *
5951 * This function queries the PHY and returns its state in the ethtool command.
5952 *
5953 * Return 0 if successful; otherwise an error code.
5954 */
5948 * @dev: Network device.
5949 * @cmd: Ethtool command.
5950 *
5951 * This function queries the PHY and returns its state in the ethtool command.
5952 *
5953 * Return 0 if successful; otherwise an error code.
5954 */
5955static int netdev_get_settings(struct net_device *dev, struct ethtool_cmd *cmd)
5955static int netdev_get_link_ksettings(struct net_device *dev,
5956 struct ethtool_link_ksettings *cmd)
5956{
5957 struct dev_priv *priv = netdev_priv(dev);
5958 struct dev_info *hw_priv = priv->adapter;
5959
5960 mutex_lock(&hw_priv->lock);
5957{
5958 struct dev_priv *priv = netdev_priv(dev);
5959 struct dev_info *hw_priv = priv->adapter;
5960
5961 mutex_lock(&hw_priv->lock);
5961 mii_ethtool_gset(&priv->mii_if, cmd);
5962 cmd->advertising |= SUPPORTED_TP;
5962 mii_ethtool_get_link_ksettings(&priv->mii_if, cmd);
5963 ethtool_link_ksettings_add_link_mode(cmd, advertising, TP);
5963 mutex_unlock(&hw_priv->lock);
5964
5965 /* Save advertised settings for workaround in next function. */
5964 mutex_unlock(&hw_priv->lock);
5965
5966 /* Save advertised settings for workaround in next function. */
5966 priv->advertising = cmd->advertising;
5967 ethtool_convert_link_mode_to_legacy_u32(&priv->advertising,
5968 cmd->link_modes.advertising);
5969
5967 return 0;
5968}
5969
5970/**
5970 return 0;
5971}
5972
5973/**
5971 * netdev_set_settings - set network device settings
5974 * netdev_set_link_ksettings - set network device settings
5972 * @dev: Network device.
5973 * @cmd: Ethtool command.
5974 *
5975 * This function sets the PHY according to the ethtool command.
5976 *
5977 * Return 0 if successful; otherwise an error code.
5978 */
5975 * @dev: Network device.
5976 * @cmd: Ethtool command.
5977 *
5978 * This function sets the PHY according to the ethtool command.
5979 *
5980 * Return 0 if successful; otherwise an error code.
5981 */
5979static int netdev_set_settings(struct net_device *dev, struct ethtool_cmd *cmd)
5982static int netdev_set_link_ksettings(struct net_device *dev,
5983 const struct ethtool_link_ksettings *cmd)
5980{
5981 struct dev_priv *priv = netdev_priv(dev);
5982 struct dev_info *hw_priv = priv->adapter;
5983 struct ksz_port *port = &priv->port;
5984{
5985 struct dev_priv *priv = netdev_priv(dev);
5986 struct dev_info *hw_priv = priv->adapter;
5987 struct ksz_port *port = &priv->port;
5984 u32 speed = ethtool_cmd_speed(cmd);
5988 struct ethtool_link_ksettings copy_cmd;
5989 u32 speed = cmd->base.speed;
5990 u32 advertising;
5985 int rc;
5986
5991 int rc;
5992
5993 ethtool_convert_link_mode_to_legacy_u32(&advertising,
5994 cmd->link_modes.advertising);
5995
5987 /*
5988 * ethtool utility does not change advertised setting if auto
5989 * negotiation is not specified explicitly.
5990 */
5996 /*
5997 * ethtool utility does not change advertised setting if auto
5998 * negotiation is not specified explicitly.
5999 */
5991 if (cmd->autoneg && priv->advertising == cmd->advertising) {
5992 cmd->advertising |= ADVERTISED_ALL;
6000 if (cmd->base.autoneg && priv->advertising == advertising) {
6001 advertising |= ADVERTISED_ALL;
5993 if (10 == speed)
6002 if (10 == speed)
5994 cmd->advertising &=
6003 advertising &=
5995 ~(ADVERTISED_100baseT_Full |
5996 ADVERTISED_100baseT_Half);
5997 else if (100 == speed)
6004 ~(ADVERTISED_100baseT_Full |
6005 ADVERTISED_100baseT_Half);
6006 else if (100 == speed)
5998 cmd->advertising &=
6007 advertising &=
5999 ~(ADVERTISED_10baseT_Full |
6000 ADVERTISED_10baseT_Half);
6008 ~(ADVERTISED_10baseT_Full |
6009 ADVERTISED_10baseT_Half);
6001 if (0 == cmd->duplex)
6002 cmd->advertising &=
6010 if (0 == cmd->base.duplex)
6011 advertising &=
6003 ~(ADVERTISED_100baseT_Full |
6004 ADVERTISED_10baseT_Full);
6012 ~(ADVERTISED_100baseT_Full |
6013 ADVERTISED_10baseT_Full);
6005 else if (1 == cmd->duplex)
6006 cmd->advertising &=
6014 else if (1 == cmd->base.duplex)
6015 advertising &=
6007 ~(ADVERTISED_100baseT_Half |
6008 ADVERTISED_10baseT_Half);
6009 }
6010 mutex_lock(&hw_priv->lock);
6016 ~(ADVERTISED_100baseT_Half |
6017 ADVERTISED_10baseT_Half);
6018 }
6019 mutex_lock(&hw_priv->lock);
6011 if (cmd->autoneg &&
6012 (cmd->advertising & ADVERTISED_ALL) ==
6013 ADVERTISED_ALL) {
6020 if (cmd->base.autoneg &&
6021 (advertising & ADVERTISED_ALL) == ADVERTISED_ALL) {
6014 port->duplex = 0;
6015 port->speed = 0;
6016 port->force_link = 0;
6017 } else {
6022 port->duplex = 0;
6023 port->speed = 0;
6024 port->force_link = 0;
6025 } else {
6018 port->duplex = cmd->duplex + 1;
6026 port->duplex = cmd->base.duplex + 1;
6019 if (1000 != speed)
6020 port->speed = speed;
6027 if (1000 != speed)
6028 port->speed = speed;
6021 if (cmd->autoneg)
6029 if (cmd->base.autoneg)
6022 port->force_link = 0;
6023 else
6024 port->force_link = 1;
6025 }
6030 port->force_link = 0;
6031 else
6032 port->force_link = 1;
6033 }
6026 rc = mii_ethtool_sset(&priv->mii_if, cmd);
6034
6035 memcpy(&copy_cmd, cmd, sizeof(copy_cmd));
6036 ethtool_convert_legacy_u32_to_link_mode(copy_cmd.link_modes.advertising,
6037 advertising);
6038 rc = mii_ethtool_set_link_ksettings(
6039 &priv->mii_if,
6040 (const struct ethtool_link_ksettings *)&copy_cmd);
6027 mutex_unlock(&hw_priv->lock);
6028 return rc;
6029}
6030
6031/**
6032 * netdev_nway_reset - restart auto-negotiation
6033 * @dev: Network device.
6034 *

--- 557 unchanged lines hidden (view full) ---

6592 writel(hw->rx_cfg, hw->io + KS_DMA_RX_CTRL);
6593
6594 mutex_unlock(&hw_priv->lock);
6595
6596 return 0;
6597}
6598
6599static const struct ethtool_ops netdev_ethtool_ops = {
6041 mutex_unlock(&hw_priv->lock);
6042 return rc;
6043}
6044
6045/**
6046 * netdev_nway_reset - restart auto-negotiation
6047 * @dev: Network device.
6048 *

--- 557 unchanged lines hidden (view full) ---

6606 writel(hw->rx_cfg, hw->io + KS_DMA_RX_CTRL);
6607
6608 mutex_unlock(&hw_priv->lock);
6609
6610 return 0;
6611}
6612
6613static const struct ethtool_ops netdev_ethtool_ops = {
6600 .get_settings = netdev_get_settings,
6601 .set_settings = netdev_set_settings,
6602 .nway_reset = netdev_nway_reset,
6603 .get_link = netdev_get_link,
6604 .get_drvinfo = netdev_get_drvinfo,
6605 .get_regs_len = netdev_get_regs_len,
6606 .get_regs = netdev_get_regs,
6607 .get_wol = netdev_get_wol,
6608 .set_wol = netdev_set_wol,
6609 .get_msglevel = netdev_get_msglevel,
6610 .set_msglevel = netdev_set_msglevel,
6611 .get_eeprom_len = netdev_get_eeprom_len,
6612 .get_eeprom = netdev_get_eeprom,
6613 .set_eeprom = netdev_set_eeprom,
6614 .get_pauseparam = netdev_get_pauseparam,
6615 .set_pauseparam = netdev_set_pauseparam,
6616 .get_ringparam = netdev_get_ringparam,
6617 .get_strings = netdev_get_strings,
6618 .get_sset_count = netdev_get_sset_count,
6619 .get_ethtool_stats = netdev_get_ethtool_stats,
6614 .nway_reset = netdev_nway_reset,
6615 .get_link = netdev_get_link,
6616 .get_drvinfo = netdev_get_drvinfo,
6617 .get_regs_len = netdev_get_regs_len,
6618 .get_regs = netdev_get_regs,
6619 .get_wol = netdev_get_wol,
6620 .set_wol = netdev_set_wol,
6621 .get_msglevel = netdev_get_msglevel,
6622 .set_msglevel = netdev_set_msglevel,
6623 .get_eeprom_len = netdev_get_eeprom_len,
6624 .get_eeprom = netdev_get_eeprom,
6625 .set_eeprom = netdev_set_eeprom,
6626 .get_pauseparam = netdev_get_pauseparam,
6627 .set_pauseparam = netdev_set_pauseparam,
6628 .get_ringparam = netdev_get_ringparam,
6629 .get_strings = netdev_get_strings,
6630 .get_sset_count = netdev_get_sset_count,
6631 .get_ethtool_stats = netdev_get_ethtool_stats,
6632 .get_link_ksettings = netdev_get_link_ksettings,
6633 .set_link_ksettings = netdev_set_link_ksettings,
6620};
6621
6622/*
6623 * Hardware monitoring
6624 */
6625
6626static void update_link(struct net_device *dev, struct dev_priv *priv,
6627 struct ksz_port *port)

--- 396 unchanged lines hidden (view full) ---

7024 mutex_init(&hw_priv->lock);
7025
7026 for (i = 0; i < TOTAL_PORT_NUM; i++)
7027 init_waitqueue_head(&hw_priv->counter[i].counter);
7028
7029 if (macaddr[0] != ':')
7030 get_mac_addr(hw_priv, macaddr, MAIN_PORT);
7031
6634};
6635
6636/*
6637 * Hardware monitoring
6638 */
6639
6640static void update_link(struct net_device *dev, struct dev_priv *priv,
6641 struct ksz_port *port)

--- 396 unchanged lines hidden (view full) ---

7038 mutex_init(&hw_priv->lock);
7039
7040 for (i = 0; i < TOTAL_PORT_NUM; i++)
7041 init_waitqueue_head(&hw_priv->counter[i].counter);
7042
7043 if (macaddr[0] != ':')
7044 get_mac_addr(hw_priv, macaddr, MAIN_PORT);
7045
7032 /* Read MAC address and initialize override address if not overrided. */
7046 /* Read MAC address and initialize override address if not overridden. */
7033 hw_read_addr(hw);
7034
7035 /* Multiple device interfaces mode requires a second MAC address. */
7036 if (hw->dev_count > 1) {
7037 memcpy(sw->other_addr, hw->override_addr, ETH_ALEN);
7038 read_other_addr(hw);
7039 if (mac1addr[0] != ':')
7040 get_mac_addr(hw_priv, mac1addr, OTHER_PORT);

--- 216 unchanged lines hidden ---
7047 hw_read_addr(hw);
7048
7049 /* Multiple device interfaces mode requires a second MAC address. */
7050 if (hw->dev_count > 1) {
7051 memcpy(sw->other_addr, hw->override_addr, ETH_ALEN);
7052 read_other_addr(hw);
7053 if (mac1addr[0] != ':')
7054 get_mac_addr(hw_priv, mac1addr, OTHER_PORT);

--- 216 unchanged lines hidden ---