be2net: Program secondary UC MAC address into MAC filter
Signed-off-by: Ajit Khaparde <ajit.khaparde@emulex.com> Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
Родитель
4762f6cec4
Коммит
fbc13f018c
|
@ -309,6 +309,8 @@ struct be_vf_cfg {
|
|||
|
||||
#define BE_FLAGS_LINK_STATUS_INIT 1
|
||||
#define BE_FLAGS_WORKER_SCHEDULED (1 << 3)
|
||||
#define BE_UC_PMAC_COUNT 30
|
||||
#define BE_VF_UC_PMAC_COUNT 2
|
||||
|
||||
struct be_adapter {
|
||||
struct pci_dev *pdev;
|
||||
|
@ -361,7 +363,7 @@ struct be_adapter {
|
|||
/* Ethtool knobs and info */
|
||||
char fw_ver[FW_VER_LEN];
|
||||
int if_handle; /* Used to configure filtering */
|
||||
u32 pmac_id; /* MAC addr handle used by BE card */
|
||||
u32 *pmac_id; /* MAC addr handle used by BE card */
|
||||
u32 beacon_state; /* for set_phys_id */
|
||||
|
||||
bool eeh_err;
|
||||
|
@ -391,6 +393,8 @@ struct be_adapter {
|
|||
u16 pvid;
|
||||
u8 wol_cap;
|
||||
bool wol;
|
||||
u32 max_pmac_cnt; /* Max secondary UC MACs programmable */
|
||||
u32 uc_macs; /* Count of secondary UC MAC programmed */
|
||||
};
|
||||
|
||||
#define be_physfn(adapter) (!adapter->is_virtfn)
|
||||
|
|
|
@ -235,7 +235,7 @@ static int be_mac_addr_set(struct net_device *netdev, void *p)
|
|||
struct sockaddr *addr = p;
|
||||
int status = 0;
|
||||
u8 current_mac[ETH_ALEN];
|
||||
u32 pmac_id = adapter->pmac_id;
|
||||
u32 pmac_id = adapter->pmac_id[0];
|
||||
|
||||
if (!is_valid_ether_addr(addr->sa_data))
|
||||
return -EADDRNOTAVAIL;
|
||||
|
@ -248,7 +248,7 @@ static int be_mac_addr_set(struct net_device *netdev, void *p)
|
|||
|
||||
if (memcmp(addr->sa_data, current_mac, ETH_ALEN)) {
|
||||
status = be_cmd_pmac_add(adapter, (u8 *)addr->sa_data,
|
||||
adapter->if_handle, &adapter->pmac_id, 0);
|
||||
adapter->if_handle, &adapter->pmac_id[0], 0);
|
||||
if (status)
|
||||
goto err;
|
||||
|
||||
|
@ -885,6 +885,29 @@ static void be_set_rx_mode(struct net_device *netdev)
|
|||
goto done;
|
||||
}
|
||||
|
||||
if (netdev_uc_count(netdev) != adapter->uc_macs) {
|
||||
struct netdev_hw_addr *ha;
|
||||
int i = 1; /* First slot is claimed by the Primary MAC */
|
||||
|
||||
for (; adapter->uc_macs > 0; adapter->uc_macs--, i++) {
|
||||
be_cmd_pmac_del(adapter, adapter->if_handle,
|
||||
adapter->pmac_id[i], 0);
|
||||
}
|
||||
|
||||
if (netdev_uc_count(netdev) > adapter->max_pmac_cnt) {
|
||||
be_cmd_rx_filter(adapter, IFF_PROMISC, ON);
|
||||
adapter->promiscuous = true;
|
||||
goto done;
|
||||
}
|
||||
|
||||
netdev_for_each_uc_addr(ha, adapter->netdev) {
|
||||
adapter->uc_macs++; /* First slot is for Primary MAC */
|
||||
be_cmd_pmac_add(adapter, (u8 *)ha->addr,
|
||||
adapter->if_handle,
|
||||
&adapter->pmac_id[adapter->uc_macs], 0);
|
||||
}
|
||||
}
|
||||
|
||||
be_cmd_rx_filter(adapter, IFF_MULTICAST, ON);
|
||||
done:
|
||||
return;
|
||||
|
@ -2458,6 +2481,8 @@ static void be_vf_clear(struct be_adapter *adapter)
|
|||
|
||||
static int be_clear(struct be_adapter *adapter)
|
||||
{
|
||||
int i = 1;
|
||||
|
||||
if (adapter->flags & BE_FLAGS_WORKER_SCHEDULED) {
|
||||
cancel_delayed_work_sync(&adapter->work);
|
||||
adapter->flags &= ~BE_FLAGS_WORKER_SCHEDULED;
|
||||
|
@ -2466,6 +2491,10 @@ static int be_clear(struct be_adapter *adapter)
|
|||
if (sriov_enabled(adapter))
|
||||
be_vf_clear(adapter);
|
||||
|
||||
for (; adapter->uc_macs > 0; adapter->uc_macs--, i++)
|
||||
be_cmd_pmac_del(adapter, adapter->if_handle,
|
||||
adapter->pmac_id[i], 0);
|
||||
|
||||
be_cmd_if_destroy(adapter, adapter->if_handle, 0);
|
||||
|
||||
be_mcc_queues_destroy(adapter);
|
||||
|
@ -2477,6 +2506,7 @@ static int be_clear(struct be_adapter *adapter)
|
|||
be_cmd_fw_clean(adapter);
|
||||
|
||||
be_msix_disable(adapter);
|
||||
kfree(adapter->pmac_id);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -2552,10 +2582,10 @@ static int be_add_mac_from_list(struct be_adapter *adapter, u8 *mac)
|
|||
false, adapter->if_handle, pmac_id);
|
||||
|
||||
if (!status)
|
||||
adapter->pmac_id = pmac_id;
|
||||
adapter->pmac_id[0] = pmac_id;
|
||||
} else {
|
||||
status = be_cmd_pmac_add(adapter, mac,
|
||||
adapter->if_handle, &adapter->pmac_id, 0);
|
||||
adapter->if_handle, &adapter->pmac_id[0], 0);
|
||||
}
|
||||
do_none:
|
||||
return status;
|
||||
|
@ -2610,7 +2640,7 @@ static int be_setup(struct be_adapter *adapter)
|
|||
}
|
||||
status = be_cmd_if_create(adapter, cap_flags, en_flags,
|
||||
netdev->dev_addr, &adapter->if_handle,
|
||||
&adapter->pmac_id, 0);
|
||||
&adapter->pmac_id[0], 0);
|
||||
if (status != 0)
|
||||
goto err;
|
||||
|
||||
|
@ -3059,6 +3089,8 @@ static void be_netdev_init(struct net_device *netdev)
|
|||
netdev->vlan_features |= NETIF_F_SG | NETIF_F_TSO | NETIF_F_TSO6 |
|
||||
NETIF_F_IP_CSUM | NETIF_F_IPV6_CSUM;
|
||||
|
||||
netdev->priv_flags |= IFF_UNICAST_FLT;
|
||||
|
||||
netdev->flags |= IFF_MULTICAST;
|
||||
|
||||
netif_set_gso_max_size(netdev, 65535);
|
||||
|
@ -3264,6 +3296,17 @@ static int be_get_config(struct be_adapter *adapter)
|
|||
else
|
||||
adapter->max_vlans = BE_NUM_VLANS_SUPPORTED;
|
||||
|
||||
if (be_physfn(adapter))
|
||||
adapter->max_pmac_cnt = BE_UC_PMAC_COUNT;
|
||||
else
|
||||
adapter->max_pmac_cnt = BE_VF_UC_PMAC_COUNT;
|
||||
|
||||
/* primary mac needs 1 pmac entry */
|
||||
adapter->pmac_id = kcalloc(adapter->max_pmac_cnt + 1,
|
||||
sizeof(u32), GFP_KERNEL);
|
||||
if (!adapter->pmac_id)
|
||||
return -ENOMEM;
|
||||
|
||||
status = be_cmd_get_cntl_attributes(adapter);
|
||||
if (status)
|
||||
return status;
|
||||
|
|
Загрузка…
Ссылка в новой задаче