Skip to content

Commit 681ec39

Browse files
Yunsheng Lindavem330
authored andcommitted
net: hns3: fix for vlan table lost problem when resetting
The vlan table in hardware is clear after PF/Core/IMP/Global reset, which will cause vlan tagged packets not being received problem. This patch fixes it by restoring the vlan table after reset. Signed-off-by: Yunsheng Lin <linyunsheng@huawei.com> Signed-off-by: Peng Li <lipeng321@huawei.com> Signed-off-by: David S. Miller <davem@davemloft.net>
1 parent 1a426f8 commit 681ec39

File tree

2 files changed

+29
-0
lines changed

2 files changed

+29
-0
lines changed

drivers/net/ethernet/hisilicon/hns3/hns3_enet.c

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1404,26 +1404,48 @@ static int hns3_vlan_rx_add_vid(struct net_device *netdev,
14041404
__be16 proto, u16 vid)
14051405
{
14061406
struct hnae3_handle *h = hns3_get_handle(netdev);
1407+
struct hns3_nic_priv *priv = netdev_priv(netdev);
14071408
int ret = -EIO;
14081409

14091410
if (h->ae_algo->ops->set_vlan_filter)
14101411
ret = h->ae_algo->ops->set_vlan_filter(h, proto, vid, false);
14111412

1413+
if (!ret)
1414+
set_bit(vid, priv->active_vlans);
1415+
14121416
return ret;
14131417
}
14141418

14151419
static int hns3_vlan_rx_kill_vid(struct net_device *netdev,
14161420
__be16 proto, u16 vid)
14171421
{
14181422
struct hnae3_handle *h = hns3_get_handle(netdev);
1423+
struct hns3_nic_priv *priv = netdev_priv(netdev);
14191424
int ret = -EIO;
14201425

14211426
if (h->ae_algo->ops->set_vlan_filter)
14221427
ret = h->ae_algo->ops->set_vlan_filter(h, proto, vid, true);
14231428

1429+
if (!ret)
1430+
clear_bit(vid, priv->active_vlans);
1431+
14241432
return ret;
14251433
}
14261434

1435+
static void hns3_restore_vlan(struct net_device *netdev)
1436+
{
1437+
struct hns3_nic_priv *priv = netdev_priv(netdev);
1438+
u16 vid;
1439+
int ret;
1440+
1441+
for_each_set_bit(vid, priv->active_vlans, VLAN_N_VID) {
1442+
ret = hns3_vlan_rx_add_vid(netdev, htons(ETH_P_8021Q), vid);
1443+
if (ret)
1444+
netdev_warn(netdev, "Restore vlan: %d filter, ret:%d\n",
1445+
vid, ret);
1446+
}
1447+
}
1448+
14271449
static int hns3_ndo_set_vf_vlan(struct net_device *netdev, int vf, u16 vlan,
14281450
u8 qos, __be16 vlan_proto)
14291451
{
@@ -3341,6 +3363,10 @@ static int hns3_reset_notify_init_enet(struct hnae3_handle *handle)
33413363
hns3_nic_set_rx_mode(netdev);
33423364
hns3_recover_hw_addr(netdev);
33433365

3366+
/* Hardware table is only clear when pf resets */
3367+
if (!(handle->flags & HNAE3_SUPPORT_VF))
3368+
hns3_restore_vlan(netdev);
3369+
33443370
/* Carrier off reporting is important to ethtool even BEFORE open */
33453371
netif_carrier_off(netdev);
33463372

drivers/net/ethernet/hisilicon/hns3/hns3_enet.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,8 @@
1010
#ifndef __HNS3_ENET_H
1111
#define __HNS3_ENET_H
1212

13+
#include <linux/if_vlan.h>
14+
1315
#include "hnae3.h"
1416

1517
extern const char hns3_driver_version[];
@@ -539,6 +541,7 @@ struct hns3_nic_priv {
539541
struct notifier_block notifier_block;
540542
/* Vxlan/Geneve information */
541543
struct hns3_udp_tunnel udp_tnl[HNS3_UDP_TNL_MAX];
544+
unsigned long active_vlans[BITS_TO_LONGS(VLAN_N_VID)];
542545
};
543546

544547
union l3_hdr_info {

0 commit comments

Comments
 (0)