mirror of
https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git
synced 2024-10-29 23:53:32 +00:00
net: hns: fix the bug about loopback
It will always be passed if the soc is tested the loopback cases. This patch will fix this bug. Signed-off-by: Kejian Yan <yankejian@huawei.com> Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
parent
81422e672f
commit
68c222a6bc
5 changed files with 65 additions and 1 deletions
|
@ -675,8 +675,12 @@ static int hns_ae_config_loopback(struct hnae_handle *handle,
|
||||||
{
|
{
|
||||||
int ret;
|
int ret;
|
||||||
struct hnae_vf_cb *vf_cb = hns_ae_get_vf_cb(handle);
|
struct hnae_vf_cb *vf_cb = hns_ae_get_vf_cb(handle);
|
||||||
|
struct hns_mac_cb *mac_cb = hns_get_mac_cb(handle);
|
||||||
|
|
||||||
switch (loop) {
|
switch (loop) {
|
||||||
|
case MAC_INTERNALLOOP_PHY:
|
||||||
|
ret = 0;
|
||||||
|
break;
|
||||||
case MAC_INTERNALLOOP_SERDES:
|
case MAC_INTERNALLOOP_SERDES:
|
||||||
ret = hns_mac_config_sds_loopback(vf_cb->mac_cb, en);
|
ret = hns_mac_config_sds_loopback(vf_cb->mac_cb, en);
|
||||||
break;
|
break;
|
||||||
|
@ -686,6 +690,10 @@ static int hns_ae_config_loopback(struct hnae_handle *handle,
|
||||||
default:
|
default:
|
||||||
ret = -EINVAL;
|
ret = -EINVAL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!ret)
|
||||||
|
hns_dsaf_set_inner_lb(mac_cb->dsaf_dev, mac_cb->mac_id, en);
|
||||||
|
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -230,6 +230,30 @@ static void hns_dsaf_mix_def_qid_cfg(struct dsaf_device *dsaf_dev)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void hns_dsaf_inner_qid_cfg(struct dsaf_device *dsaf_dev)
|
||||||
|
{
|
||||||
|
u16 max_q_per_vf, max_vfn;
|
||||||
|
u32 q_id, q_num_per_port;
|
||||||
|
u32 mac_id;
|
||||||
|
|
||||||
|
if (AE_IS_VER1(dsaf_dev->dsaf_ver))
|
||||||
|
return;
|
||||||
|
|
||||||
|
hns_rcb_get_queue_mode(dsaf_dev->dsaf_mode,
|
||||||
|
HNS_DSAF_COMM_SERVICE_NW_IDX,
|
||||||
|
&max_vfn, &max_q_per_vf);
|
||||||
|
q_num_per_port = max_vfn * max_q_per_vf;
|
||||||
|
|
||||||
|
for (mac_id = 0, q_id = 0; mac_id < DSAF_SERVICE_NW_NUM; mac_id++) {
|
||||||
|
dsaf_set_dev_field(dsaf_dev,
|
||||||
|
DSAFV2_SERDES_LBK_0_REG + 4 * mac_id,
|
||||||
|
DSAFV2_SERDES_LBK_QID_M,
|
||||||
|
DSAFV2_SERDES_LBK_QID_S,
|
||||||
|
q_id);
|
||||||
|
q_id += q_num_per_port;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* hns_dsaf_sw_port_type_cfg - cfg sw type
|
* hns_dsaf_sw_port_type_cfg - cfg sw type
|
||||||
* @dsaf_id: dsa fabric id
|
* @dsaf_id: dsa fabric id
|
||||||
|
@ -691,6 +715,16 @@ void hns_dsaf_set_promisc_mode(struct dsaf_device *dsaf_dev, u32 en)
|
||||||
dsaf_set_dev_bit(dsaf_dev, DSAF_CFG_0_REG, DSAF_CFG_MIX_MODE_S, !!en);
|
dsaf_set_dev_bit(dsaf_dev, DSAF_CFG_0_REG, DSAF_CFG_MIX_MODE_S, !!en);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void hns_dsaf_set_inner_lb(struct dsaf_device *dsaf_dev, u32 mac_id, u32 en)
|
||||||
|
{
|
||||||
|
if (AE_IS_VER1(dsaf_dev->dsaf_ver) ||
|
||||||
|
dsaf_dev->mac_cb[mac_id].mac_type == HNAE_PORT_DEBUG)
|
||||||
|
return;
|
||||||
|
|
||||||
|
dsaf_set_dev_bit(dsaf_dev, DSAFV2_SERDES_LBK_0_REG + 4 * mac_id,
|
||||||
|
DSAFV2_SERDES_LBK_EN_B, !!en);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* hns_dsaf_tbl_stat_en - tbl
|
* hns_dsaf_tbl_stat_en - tbl
|
||||||
* @dsaf_id: dsa fabric id
|
* @dsaf_id: dsa fabric id
|
||||||
|
@ -1022,6 +1056,9 @@ static void hns_dsaf_comm_init(struct dsaf_device *dsaf_dev)
|
||||||
/* set promisc def queue id */
|
/* set promisc def queue id */
|
||||||
hns_dsaf_mix_def_qid_cfg(dsaf_dev);
|
hns_dsaf_mix_def_qid_cfg(dsaf_dev);
|
||||||
|
|
||||||
|
/* set inner loopback queue id */
|
||||||
|
hns_dsaf_inner_qid_cfg(dsaf_dev);
|
||||||
|
|
||||||
/* in non switch mode, set all port to access mode */
|
/* in non switch mode, set all port to access mode */
|
||||||
hns_dsaf_sw_port_type_cfg(dsaf_dev, DSAF_SW_PORT_TYPE_NON_VLAN);
|
hns_dsaf_sw_port_type_cfg(dsaf_dev, DSAF_SW_PORT_TYPE_NON_VLAN);
|
||||||
|
|
||||||
|
|
|
@ -417,5 +417,6 @@ void hns_dsaf_get_strings(int stringset, u8 *data, int port);
|
||||||
void hns_dsaf_get_regs(struct dsaf_device *ddev, u32 port, void *data);
|
void hns_dsaf_get_regs(struct dsaf_device *ddev, u32 port, void *data);
|
||||||
int hns_dsaf_get_regs_count(void);
|
int hns_dsaf_get_regs_count(void);
|
||||||
void hns_dsaf_set_promisc_mode(struct dsaf_device *dsaf_dev, u32 en);
|
void hns_dsaf_set_promisc_mode(struct dsaf_device *dsaf_dev, u32 en);
|
||||||
|
void hns_dsaf_set_inner_lb(struct dsaf_device *dsaf_dev, u32 mac_id, u32 en);
|
||||||
|
|
||||||
#endif /* __HNS_DSAF_MAIN_H__ */
|
#endif /* __HNS_DSAF_MAIN_H__ */
|
||||||
|
|
|
@ -134,6 +134,7 @@
|
||||||
#define DSAF_XGE_INT_STS_0_REG 0x1C0
|
#define DSAF_XGE_INT_STS_0_REG 0x1C0
|
||||||
#define DSAF_PPE_INT_STS_0_REG 0x1E0
|
#define DSAF_PPE_INT_STS_0_REG 0x1E0
|
||||||
#define DSAF_ROCEE_INT_STS_0_REG 0x200
|
#define DSAF_ROCEE_INT_STS_0_REG 0x200
|
||||||
|
#define DSAFV2_SERDES_LBK_0_REG 0x220
|
||||||
#define DSAF_PPE_QID_CFG_0_REG 0x300
|
#define DSAF_PPE_QID_CFG_0_REG 0x300
|
||||||
#define DSAF_SW_PORT_TYPE_0_REG 0x320
|
#define DSAF_SW_PORT_TYPE_0_REG 0x320
|
||||||
#define DSAF_STP_PORT_TYPE_0_REG 0x340
|
#define DSAF_STP_PORT_TYPE_0_REG 0x340
|
||||||
|
@ -857,6 +858,10 @@
|
||||||
#define PPEV2_CFG_RSS_TBL_4N3_S 24
|
#define PPEV2_CFG_RSS_TBL_4N3_S 24
|
||||||
#define PPEV2_CFG_RSS_TBL_4N3_M (((1UL << 5) - 1) << PPEV2_CFG_RSS_TBL_4N3_S)
|
#define PPEV2_CFG_RSS_TBL_4N3_M (((1UL << 5) - 1) << PPEV2_CFG_RSS_TBL_4N3_S)
|
||||||
|
|
||||||
|
#define DSAFV2_SERDES_LBK_EN_B 8
|
||||||
|
#define DSAFV2_SERDES_LBK_QID_S 0
|
||||||
|
#define DSAFV2_SERDES_LBK_QID_M (((1UL << 8) - 1) << DSAFV2_SERDES_LBK_QID_S)
|
||||||
|
|
||||||
#define PPE_CNT_CLR_CE_B 0
|
#define PPE_CNT_CLR_CE_B 0
|
||||||
#define PPE_CNT_CLR_SNAP_EN_B 1
|
#define PPE_CNT_CLR_SNAP_EN_B 1
|
||||||
|
|
||||||
|
|
|
@ -295,8 +295,10 @@ static int __lb_setup(struct net_device *ndev,
|
||||||
|
|
||||||
switch (loop) {
|
switch (loop) {
|
||||||
case MAC_INTERNALLOOP_PHY:
|
case MAC_INTERNALLOOP_PHY:
|
||||||
if ((phy_dev) && (!phy_dev->is_c45))
|
if ((phy_dev) && (!phy_dev->is_c45)) {
|
||||||
ret = hns_nic_config_phy_loopback(phy_dev, 0x1);
|
ret = hns_nic_config_phy_loopback(phy_dev, 0x1);
|
||||||
|
ret |= h->dev->ops->set_loopback(h, loop, 0x1);
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
case MAC_INTERNALLOOP_MAC:
|
case MAC_INTERNALLOOP_MAC:
|
||||||
if ((h->dev->ops->set_loopback) &&
|
if ((h->dev->ops->set_loopback) &&
|
||||||
|
@ -376,6 +378,7 @@ static void __lb_other_process(struct hns_nic_ring_data *ring_data,
|
||||||
struct sk_buff *skb)
|
struct sk_buff *skb)
|
||||||
{
|
{
|
||||||
struct net_device *ndev;
|
struct net_device *ndev;
|
||||||
|
struct hns_nic_priv *priv;
|
||||||
struct hnae_ring *ring;
|
struct hnae_ring *ring;
|
||||||
struct netdev_queue *dev_queue;
|
struct netdev_queue *dev_queue;
|
||||||
struct sk_buff *new_skb;
|
struct sk_buff *new_skb;
|
||||||
|
@ -385,8 +388,17 @@ static void __lb_other_process(struct hns_nic_ring_data *ring_data,
|
||||||
char buff[33]; /* 32B data and the last character '\0' */
|
char buff[33]; /* 32B data and the last character '\0' */
|
||||||
|
|
||||||
if (!ring_data) { /* Just for doing create frame*/
|
if (!ring_data) { /* Just for doing create frame*/
|
||||||
|
ndev = skb->dev;
|
||||||
|
priv = netdev_priv(ndev);
|
||||||
|
|
||||||
frame_size = skb->len;
|
frame_size = skb->len;
|
||||||
memset(skb->data, 0xFF, frame_size);
|
memset(skb->data, 0xFF, frame_size);
|
||||||
|
if ((!AE_IS_VER1(priv->enet_ver)) &&
|
||||||
|
(priv->ae_handle->port_type == HNAE_PORT_SERVICE)) {
|
||||||
|
memcpy(skb->data, ndev->dev_addr, 6);
|
||||||
|
skb->data[5] += 0x1f;
|
||||||
|
}
|
||||||
|
|
||||||
frame_size &= ~1ul;
|
frame_size &= ~1ul;
|
||||||
memset(&skb->data[frame_size / 2], 0xAA, frame_size / 2 - 1);
|
memset(&skb->data[frame_size / 2], 0xAA, frame_size / 2 - 1);
|
||||||
memset(&skb->data[frame_size / 2 + 10], 0xBE,
|
memset(&skb->data[frame_size / 2 + 10], 0xBE,
|
||||||
|
@ -486,6 +498,7 @@ static int __lb_run_test(struct net_device *ndev,
|
||||||
|
|
||||||
/* place data into test skb */
|
/* place data into test skb */
|
||||||
(void)skb_put(skb, size);
|
(void)skb_put(skb, size);
|
||||||
|
skb->dev = ndev;
|
||||||
__lb_other_process(NULL, skb);
|
__lb_other_process(NULL, skb);
|
||||||
skb->queue_mapping = NIC_LB_TEST_RING_ID;
|
skb->queue_mapping = NIC_LB_TEST_RING_ID;
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue