Commit 492a1d98 authored by Mintz, Yuval's avatar Mintz, Yuval Committed by David S. Miller

qede: Don't use an internal MAC field

Driver maintains its primary MAC in a private field which
gets updated when ndo_dev_set_mac() gets called.

However, there are flows where the primary MAC of the device can change
without said NDO being called [bond device in TLB mode configuring
slaves' addresses], resulting in a configuration where there's a mismatch
between what's apparent to user [the netdevice's value] and what's
configured in the HW [the private value].

As we don't have any real motivation of maintaining this
private field, simply remove it and start using the netdevice's
field instead.
Signed-off-by: default avatarYuval Mintz <Yuval.Mintz@cavium.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 71851ea5
...@@ -197,7 +197,6 @@ struct qede_dev { ...@@ -197,7 +197,6 @@ struct qede_dev {
#define QEDE_TSS_COUNT(edev) ((edev)->num_queues - (edev)->fp_num_rx) #define QEDE_TSS_COUNT(edev) ((edev)->num_queues - (edev)->fp_num_rx)
struct qed_int_info int_info; struct qed_int_info int_info;
unsigned char primary_mac[ETH_ALEN];
/* Smaller private varaiant of the RTNL lock */ /* Smaller private varaiant of the RTNL lock */
struct mutex qede_lock; struct mutex qede_lock;
......
...@@ -495,12 +495,16 @@ void qede_force_mac(void *dev, u8 *mac, bool forced) ...@@ -495,12 +495,16 @@ void qede_force_mac(void *dev, u8 *mac, bool forced)
{ {
struct qede_dev *edev = dev; struct qede_dev *edev = dev;
__qede_lock(edev);
/* MAC hints take effect only if we haven't set one already */ /* MAC hints take effect only if we haven't set one already */
if (is_valid_ether_addr(edev->ndev->dev_addr) && !forced) if (is_valid_ether_addr(edev->ndev->dev_addr) && !forced) {
__qede_unlock(edev);
return; return;
}
ether_addr_copy(edev->ndev->dev_addr, mac); ether_addr_copy(edev->ndev->dev_addr, mac);
ether_addr_copy(edev->primary_mac, mac); __qede_unlock(edev);
} }
void qede_fill_rss_params(struct qede_dev *edev, void qede_fill_rss_params(struct qede_dev *edev,
...@@ -1061,41 +1065,51 @@ int qede_set_mac_addr(struct net_device *ndev, void *p) ...@@ -1061,41 +1065,51 @@ int qede_set_mac_addr(struct net_device *ndev, void *p)
{ {
struct qede_dev *edev = netdev_priv(ndev); struct qede_dev *edev = netdev_priv(ndev);
struct sockaddr *addr = p; struct sockaddr *addr = p;
int rc; int rc = 0;
ASSERT_RTNL(); /* @@@TBD To be removed */
DP_INFO(edev, "Set_mac_addr called\n"); /* Make sure the state doesn't transition while changing the MAC.
* Also, all flows accessing the dev_addr field are doing that under
* this lock.
*/
__qede_lock(edev);
if (!is_valid_ether_addr(addr->sa_data)) { if (!is_valid_ether_addr(addr->sa_data)) {
DP_NOTICE(edev, "The MAC address is not valid\n"); DP_NOTICE(edev, "The MAC address is not valid\n");
return -EFAULT; rc = -EFAULT;
goto out;
} }
if (!edev->ops->check_mac(edev->cdev, addr->sa_data)) { if (!edev->ops->check_mac(edev->cdev, addr->sa_data)) {
DP_NOTICE(edev, "qed prevents setting MAC\n"); DP_NOTICE(edev, "qed prevents setting MAC %pM\n",
return -EINVAL; addr->sa_data);
rc = -EINVAL;
goto out;
}
if (edev->state == QEDE_STATE_OPEN) {
/* Remove the previous primary mac */
rc = qede_set_ucast_rx_mac(edev, QED_FILTER_XCAST_TYPE_DEL,
ndev->dev_addr);
if (rc)
goto out;
} }
ether_addr_copy(ndev->dev_addr, addr->sa_data); ether_addr_copy(ndev->dev_addr, addr->sa_data);
DP_INFO(edev, "Setting device MAC to %pM\n", addr->sa_data);
if (!netif_running(ndev)) { if (edev->state != QEDE_STATE_OPEN) {
DP_NOTICE(edev, "The device is currently down\n"); DP_VERBOSE(edev, NETIF_MSG_IFDOWN,
return 0; "The device is currently down\n");
goto out;
} }
/* Remove the previous primary mac */ edev->ops->common->update_mac(edev->cdev, ndev->dev_addr);
rc = qede_set_ucast_rx_mac(edev, QED_FILTER_XCAST_TYPE_DEL,
edev->primary_mac);
if (rc)
return rc;
edev->ops->common->update_mac(edev->cdev, addr->sa_data);
/* Add MAC filter according to the new unicast HW MAC address */ rc = qede_set_ucast_rx_mac(edev, QED_FILTER_XCAST_TYPE_ADD,
ether_addr_copy(edev->primary_mac, ndev->dev_addr); ndev->dev_addr);
return qede_set_ucast_rx_mac(edev, QED_FILTER_XCAST_TYPE_ADD, out:
edev->primary_mac); __qede_unlock(edev);
return rc;
} }
static int static int
...@@ -1200,7 +1214,7 @@ void qede_config_rx_mode(struct net_device *ndev) ...@@ -1200,7 +1214,7 @@ void qede_config_rx_mode(struct net_device *ndev)
* (configrue / leave the primary mac) * (configrue / leave the primary mac)
*/ */
rc = qede_set_ucast_rx_mac(edev, QED_FILTER_XCAST_TYPE_REPLACE, rc = qede_set_ucast_rx_mac(edev, QED_FILTER_XCAST_TYPE_REPLACE,
edev->primary_mac); edev->ndev->dev_addr);
if (rc) if (rc)
goto out; goto out;
......
...@@ -1997,9 +1997,6 @@ static int qede_load(struct qede_dev *edev, enum qede_load_mode mode, ...@@ -1997,9 +1997,6 @@ static int qede_load(struct qede_dev *edev, enum qede_load_mode mode,
goto err4; goto err4;
DP_INFO(edev, "Start VPORT, RXQ and TXQ succeeded\n"); DP_INFO(edev, "Start VPORT, RXQ and TXQ succeeded\n");
/* Add primary mac and set Rx filters */
ether_addr_copy(edev->primary_mac, edev->ndev->dev_addr);
/* Program un-configured VLANs */ /* Program un-configured VLANs */
qede_configure_vlan_filters(edev); qede_configure_vlan_filters(edev);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment