Commit b241115b authored by Jian Shen's avatar Jian Shen Committed by Yang Yingliang
Browse files

net: hns3: add support for modify VLAN filter state

mainline inclusion
from mainline-v5.14-rc1
commit 2ba30662
category: feature
bugzilla: NA
CVE: NA

Reference: https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=2ba306627f59



----------------------------------------------------------------------

Previously, with hardware limitation, the port VLAN filter are
effective for both PF and its VFs simultaneously, so a single
function is not able to enable/disable separately, and the VLAN
filter state is default enabled. Now some device supports each
function to bypass port VLAN filter, then each function can
switch VLAN filter separately. Add capability flag to check
whether the device supports modify VLAN filter state. If flag
on, user will be able to modify the VLAN filter state by ethtool
-K.

Furtherly, the default VLAN filter state is also changed
according to whether non-zero VLAN used. Then the device can
receive packet with any VLAN tag if only VLAN 0 used.

The function hclge_need_enable_vport_vlan_filter() is used to
help implement above changes. And the VLAN filter handle for
promisc mode can also be simplified by this function.

Signed-off-by: default avatarJian Shen <shenjian15@huawei.com>
Signed-off-by: default avatarHuazhong Tan <tanhuazhong@huawei.com>
Signed-off-by: default avatarJakub Kicinski <kuba@kernel.org>
Signed-off-by: default avatarJunxin Chen <chenjunxin1@huawei.com>
Reviewed-by: default avatarJunxin Chen <chenjunxin1@huawei.com>
Signed-off-by: default avatarYang Yingliang <yangyingliang@huawei.com>
parent 79549957
Loading
Loading
Loading
Loading
+5 −1
Original line number Diff line number Diff line
@@ -58,6 +58,7 @@
#define HNAE3_ROCE_CLIENT_INITED_B		0x5
#define HNAE3_DEV_SUPPORT_FD_B			0x6
#define HNAE3_DEV_SUPPORT_GRO_B			0x7
#define HNAE3_DEV_SUPPORT_VLAN_FLTR_MDF_B	0x8

#define HNAE3_DEV_SUPPORT_ROCE_DCB_BITS (BIT(HNAE3_DEV_SUPPORT_DCB_B) |\
		BIT(HNAE3_DEV_SUPPORT_ROCE_B))
@@ -74,6 +75,9 @@
#define hnae3_dev_gro_supported(hdev) \
	hnae3_get_bit((hdev)->ae_dev->flag, HNAE3_DEV_SUPPORT_GRO_B)

#define hnae3_dev_vlan_fltr_mdf_supported(hdev) \
	hnae3_get_bit((hdev)->ae_dev->flag, HNAE3_DEV_SUPPORT_VLAN_FLTR_MDF_B)

#define ring_ptr_move_fw(ring, p) \
	((ring)->p = ((ring)->p + 1) % (ring)->desc_num)
#define ring_ptr_move_bw(ring, p) \
@@ -543,7 +547,7 @@ struct hnae3_ae_ops {
	void (*get_mdix_mode)(struct hnae3_handle *handle,
			      u8 *tp_mdix_ctrl, u8 *tp_mdix);

	void (*enable_vlan_filter)(struct hnae3_handle *handle, bool enable);
	int (*enable_vlan_filter)(struct hnae3_handle *handle, bool enable);
	int (*set_vlan_filter)(struct hnae3_handle *handle, __be16 proto,
			       u16 vlan_id, bool is_kill);
	int (*set_vf_vlan_filter)(struct hnae3_handle *handle, int vfid,
+10 −24
Original line number Diff line number Diff line
@@ -585,13 +585,10 @@ static u8 hns3_get_netdev_flags(struct net_device *netdev)
{
	u8 flags = 0;

	if (netdev->flags & IFF_PROMISC) {
	if (netdev->flags & IFF_PROMISC)
		flags = HNAE3_USER_UPE | HNAE3_USER_MPE | HNAE3_BPE;
	} else {
		flags |= HNAE3_VLAN_FLTR;
		if (netdev->flags & IFF_ALLMULTI)
			flags |= HNAE3_USER_MPE;
	}
	else if (netdev->flags & IFF_ALLMULTI)
		flags = HNAE3_USER_MPE;

	return flags;
}
@@ -621,23 +618,6 @@ void hns3_request_update_promisc_mode(struct hnae3_handle *handle)
		ops->request_update_promisc_mode(handle);
}

void hns3_enable_vlan_filter(struct net_device *netdev, bool enable)
{
	struct hns3_nic_priv *priv = netdev_priv(netdev);
	struct hnae3_handle *h = priv->ae_handle;
	bool last_state;

	if (h->pdev->revision >= 0x21 && h->ae_algo->ops->enable_vlan_filter) {
		last_state = h->netdev_flags & HNAE3_VLAN_FLTR ? true : false;
		if (enable != last_state) {
			netdev_info(netdev,
				    "%s vlan filter\n",
				    enable ? "enable" : "disable");
			h->ae_algo->ops->enable_vlan_filter(h, enable);
		}
	}
}

static int hns3_set_tso(struct sk_buff *skb, u32 *paylen,
			u16 *mss, u32 *type_cs_vlan_tso, u32 *send_bytes)
{
@@ -1619,7 +1599,9 @@ static int hns3_nic_set_features(struct net_device *netdev,
	if ((changed & NETIF_F_HW_VLAN_CTAG_FILTER) &&
	    h->ae_algo->ops->enable_vlan_filter) {
		enable = !!(features & NETIF_F_HW_VLAN_CTAG_FILTER);
		h->ae_algo->ops->enable_vlan_filter(h, enable);
		ret = h->ae_algo->ops->enable_vlan_filter(h, enable);
		if (ret)
			return ret;
	}

	if ((changed & NETIF_F_HW_VLAN_CTAG_RX) &&
@@ -2409,6 +2391,7 @@ static void hns3_set_default_feature(struct net_device *netdev)
{
	struct hnae3_handle *h = hns3_get_handle(netdev);
	struct pci_dev *pdev = h->pdev;
	struct hnae3_ae_dev *ae_dev = pci_get_drvdata(pdev);

	netdev->priv_flags |= IFF_UNICAST_FLT;

@@ -2460,6 +2443,9 @@ static void hns3_set_default_feature(struct net_device *netdev)
			netdev->features |= NETIF_F_NTUPLE;
		}
	}

	if (hnae3_get_bit(ae_dev->flag, HNAE3_DEV_SUPPORT_VLAN_FLTR_MDF_B))
		netdev->hw_features |= NETIF_F_HW_VLAN_CTAG_FILTER;
}

static int hns3_alloc_buffer(struct hns3_enet_ring *ring,
+0 −1
Original line number Diff line number Diff line
@@ -650,7 +650,6 @@ void hns3_set_vector_coalesce_tx_gl(struct hns3_enet_tqp_vector *tqp_vector,
void hns3_set_vector_coalesce_rl(struct hns3_enet_tqp_vector *tqp_vector,
				 u32 rl_value);

void hns3_enable_vlan_filter(struct net_device *netdev, bool enable);
void hns3_request_update_promisc_mode(struct hnae3_handle *handle);

#ifdef CONFIG_HNS3_DCB
+2 −6
Original line number Diff line number Diff line
@@ -83,7 +83,6 @@ static const struct hns3_stats hns3_rxq_stats[] = {
static int hns3_lp_setup(struct net_device *ndev, enum hnae3_loop loop, bool en)
{
	struct hnae3_handle *h = hns3_get_handle(ndev);
	bool vlan_filter_enable;
	int ret;

	if (!h->ae_algo->ops->set_loopback ||
@@ -105,14 +104,11 @@ static int hns3_lp_setup(struct net_device *ndev, enum hnae3_loop loop, bool en)
	if (ret || h->pdev->revision >= 0x21)
		return ret;

	if (en) {
	if (en)
		h->ae_algo->ops->set_promisc_mode(h, true, true);
	} else {
	else
		/* recover promisc mode before loopback test */
		hns3_request_update_promisc_mode(h);
		vlan_filter_enable = ndev->flags & IFF_PROMISC ? false : true;
		hns3_enable_vlan_filter(ndev, vlan_filter_enable);
	}

	return ret;
}
+10 −0
Original line number Diff line number Diff line
@@ -498,6 +498,8 @@ struct hclge_pf_res_cmd {
#define HCLGE_CFG_RSS_SIZE_M	GENMASK(31, 24)
#define HCLGE_CFG_SPEED_ABILITY_S	0
#define HCLGE_CFG_SPEED_ABILITY_M	GENMASK(7, 0)
#define HCLGE_CFG_VLAN_FLTR_CAP_S	8
#define HCLGE_CFG_VLAN_FLTR_CAP_M	GENMASK(9, 8)
#define HCLGE_CFG_UMV_TBL_SPACE_S	16
#define HCLGE_CFG_UMV_TBL_SPACE_M	GENMASK(31, 16)

@@ -791,6 +793,14 @@ struct hclge_vlan_filter_vf_cfg_cmd {
	u8  vf_bitmap[HCLGE_MAX_VF_BYTES];
};

#define HCLGE_INGRESS_BYPASS_B		0
struct hclge_port_vlan_filter_bypass_cmd {
	u8 bypass_state;
	u8 rsv1[3];
	u8 vf_id;
	u8 rsv2[19];
};

#define HCLGE_SWITCH_ANTI_SPOOF_B	0U
#define HCLGE_SWITCH_ALW_LPBK_B		1U
#define HCLGE_SWITCH_ALW_LCL_LPBK_B	2U
Loading