Merge branch 'hns3-fixes'
Huazhong Tan says: ==================== net: hns3: fixes for -net There are some bugfixes for the HNS3 ethernet driver. ==================== Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
commit
2dc3bd74d7
|
@ -77,6 +77,7 @@
|
||||||
((ring)->p = ((ring)->p - 1 + (ring)->desc_num) % (ring)->desc_num)
|
((ring)->p = ((ring)->p - 1 + (ring)->desc_num) % (ring)->desc_num)
|
||||||
|
|
||||||
enum hns_desc_type {
|
enum hns_desc_type {
|
||||||
|
DESC_TYPE_UNKNOWN,
|
||||||
DESC_TYPE_SKB,
|
DESC_TYPE_SKB,
|
||||||
DESC_TYPE_FRAGLIST_SKB,
|
DESC_TYPE_FRAGLIST_SKB,
|
||||||
DESC_TYPE_PAGE,
|
DESC_TYPE_PAGE,
|
||||||
|
|
|
@ -1118,12 +1118,12 @@ static int hns3_fill_desc(struct hns3_enet_ring *ring, void *priv,
|
||||||
return -ENOMEM;
|
return -ENOMEM;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
desc_cb->priv = priv;
|
||||||
desc_cb->length = size;
|
desc_cb->length = size;
|
||||||
|
desc_cb->dma = dma;
|
||||||
|
desc_cb->type = type;
|
||||||
|
|
||||||
if (likely(size <= HNS3_MAX_BD_SIZE)) {
|
if (likely(size <= HNS3_MAX_BD_SIZE)) {
|
||||||
desc_cb->priv = priv;
|
|
||||||
desc_cb->dma = dma;
|
|
||||||
desc_cb->type = type;
|
|
||||||
desc->addr = cpu_to_le64(dma);
|
desc->addr = cpu_to_le64(dma);
|
||||||
desc->tx.send_size = cpu_to_le16(size);
|
desc->tx.send_size = cpu_to_le16(size);
|
||||||
desc->tx.bdtp_fe_sc_vld_ra_ri =
|
desc->tx.bdtp_fe_sc_vld_ra_ri =
|
||||||
|
@ -1135,18 +1135,11 @@ static int hns3_fill_desc(struct hns3_enet_ring *ring, void *priv,
|
||||||
}
|
}
|
||||||
|
|
||||||
frag_buf_num = hns3_tx_bd_count(size);
|
frag_buf_num = hns3_tx_bd_count(size);
|
||||||
sizeoflast = size & HNS3_TX_LAST_SIZE_M;
|
sizeoflast = size % HNS3_MAX_BD_SIZE;
|
||||||
sizeoflast = sizeoflast ? sizeoflast : HNS3_MAX_BD_SIZE;
|
sizeoflast = sizeoflast ? sizeoflast : HNS3_MAX_BD_SIZE;
|
||||||
|
|
||||||
/* When frag size is bigger than hardware limit, split this frag */
|
/* When frag size is bigger than hardware limit, split this frag */
|
||||||
for (k = 0; k < frag_buf_num; k++) {
|
for (k = 0; k < frag_buf_num; k++) {
|
||||||
/* The txbd's baseinfo of DESC_TYPE_PAGE & DESC_TYPE_SKB */
|
|
||||||
desc_cb->priv = priv;
|
|
||||||
desc_cb->dma = dma + HNS3_MAX_BD_SIZE * k;
|
|
||||||
desc_cb->type = ((type == DESC_TYPE_FRAGLIST_SKB ||
|
|
||||||
type == DESC_TYPE_SKB) && !k) ?
|
|
||||||
type : DESC_TYPE_PAGE;
|
|
||||||
|
|
||||||
/* now, fill the descriptor */
|
/* now, fill the descriptor */
|
||||||
desc->addr = cpu_to_le64(dma + HNS3_MAX_BD_SIZE * k);
|
desc->addr = cpu_to_le64(dma + HNS3_MAX_BD_SIZE * k);
|
||||||
desc->tx.send_size = cpu_to_le16((k == frag_buf_num - 1) ?
|
desc->tx.send_size = cpu_to_le16((k == frag_buf_num - 1) ?
|
||||||
|
@ -1158,7 +1151,6 @@ static int hns3_fill_desc(struct hns3_enet_ring *ring, void *priv,
|
||||||
/* move ring pointer to next */
|
/* move ring pointer to next */
|
||||||
ring_ptr_move_fw(ring, next_to_use);
|
ring_ptr_move_fw(ring, next_to_use);
|
||||||
|
|
||||||
desc_cb = &ring->desc_cb[ring->next_to_use];
|
|
||||||
desc = &ring->desc[ring->next_to_use];
|
desc = &ring->desc[ring->next_to_use];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1346,6 +1338,10 @@ static void hns3_clear_desc(struct hns3_enet_ring *ring, int next_to_use_orig)
|
||||||
unsigned int i;
|
unsigned int i;
|
||||||
|
|
||||||
for (i = 0; i < ring->desc_num; i++) {
|
for (i = 0; i < ring->desc_num; i++) {
|
||||||
|
struct hns3_desc *desc = &ring->desc[ring->next_to_use];
|
||||||
|
|
||||||
|
memset(desc, 0, sizeof(*desc));
|
||||||
|
|
||||||
/* check if this is where we started */
|
/* check if this is where we started */
|
||||||
if (ring->next_to_use == next_to_use_orig)
|
if (ring->next_to_use == next_to_use_orig)
|
||||||
break;
|
break;
|
||||||
|
@ -1353,6 +1349,9 @@ static void hns3_clear_desc(struct hns3_enet_ring *ring, int next_to_use_orig)
|
||||||
/* rollback one */
|
/* rollback one */
|
||||||
ring_ptr_move_bw(ring, next_to_use);
|
ring_ptr_move_bw(ring, next_to_use);
|
||||||
|
|
||||||
|
if (!ring->desc_cb[ring->next_to_use].dma)
|
||||||
|
continue;
|
||||||
|
|
||||||
/* unmap the descriptor dma address */
|
/* unmap the descriptor dma address */
|
||||||
if (ring->desc_cb[ring->next_to_use].type == DESC_TYPE_SKB ||
|
if (ring->desc_cb[ring->next_to_use].type == DESC_TYPE_SKB ||
|
||||||
ring->desc_cb[ring->next_to_use].type ==
|
ring->desc_cb[ring->next_to_use].type ==
|
||||||
|
@ -1369,6 +1368,7 @@ static void hns3_clear_desc(struct hns3_enet_ring *ring, int next_to_use_orig)
|
||||||
|
|
||||||
ring->desc_cb[ring->next_to_use].length = 0;
|
ring->desc_cb[ring->next_to_use].length = 0;
|
||||||
ring->desc_cb[ring->next_to_use].dma = 0;
|
ring->desc_cb[ring->next_to_use].dma = 0;
|
||||||
|
ring->desc_cb[ring->next_to_use].type = DESC_TYPE_UNKNOWN;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -165,8 +165,6 @@ enum hns3_nic_state {
|
||||||
#define HNS3_TXD_MSS_S 0
|
#define HNS3_TXD_MSS_S 0
|
||||||
#define HNS3_TXD_MSS_M (0x3fff << HNS3_TXD_MSS_S)
|
#define HNS3_TXD_MSS_M (0x3fff << HNS3_TXD_MSS_S)
|
||||||
|
|
||||||
#define HNS3_TX_LAST_SIZE_M 0xffff
|
|
||||||
|
|
||||||
#define HNS3_VECTOR_TX_IRQ BIT_ULL(0)
|
#define HNS3_VECTOR_TX_IRQ BIT_ULL(0)
|
||||||
#define HNS3_VECTOR_RX_IRQ BIT_ULL(1)
|
#define HNS3_VECTOR_RX_IRQ BIT_ULL(1)
|
||||||
|
|
||||||
|
|
|
@ -2673,11 +2673,10 @@ void hclge_task_schedule(struct hclge_dev *hdev, unsigned long delay_time)
|
||||||
delay_time);
|
delay_time);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int hclge_get_mac_link_status(struct hclge_dev *hdev)
|
static int hclge_get_mac_link_status(struct hclge_dev *hdev, int *link_status)
|
||||||
{
|
{
|
||||||
struct hclge_link_status_cmd *req;
|
struct hclge_link_status_cmd *req;
|
||||||
struct hclge_desc desc;
|
struct hclge_desc desc;
|
||||||
int link_status;
|
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
hclge_cmd_setup_basic_desc(&desc, HCLGE_OPC_QUERY_LINK_STATUS, true);
|
hclge_cmd_setup_basic_desc(&desc, HCLGE_OPC_QUERY_LINK_STATUS, true);
|
||||||
|
@ -2689,33 +2688,25 @@ static int hclge_get_mac_link_status(struct hclge_dev *hdev)
|
||||||
}
|
}
|
||||||
|
|
||||||
req = (struct hclge_link_status_cmd *)desc.data;
|
req = (struct hclge_link_status_cmd *)desc.data;
|
||||||
link_status = req->status & HCLGE_LINK_STATUS_UP_M;
|
*link_status = (req->status & HCLGE_LINK_STATUS_UP_M) > 0 ?
|
||||||
|
HCLGE_LINK_STATUS_UP : HCLGE_LINK_STATUS_DOWN;
|
||||||
|
|
||||||
return !!link_status;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int hclge_get_mac_phy_link(struct hclge_dev *hdev)
|
static int hclge_get_mac_phy_link(struct hclge_dev *hdev, int *link_status)
|
||||||
{
|
{
|
||||||
unsigned int mac_state;
|
struct phy_device *phydev = hdev->hw.mac.phydev;
|
||||||
int link_stat;
|
|
||||||
|
*link_status = HCLGE_LINK_STATUS_DOWN;
|
||||||
|
|
||||||
if (test_bit(HCLGE_STATE_DOWN, &hdev->state))
|
if (test_bit(HCLGE_STATE_DOWN, &hdev->state))
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
mac_state = hclge_get_mac_link_status(hdev);
|
if (phydev && (phydev->state != PHY_RUNNING || !phydev->link))
|
||||||
|
return 0;
|
||||||
|
|
||||||
if (hdev->hw.mac.phydev) {
|
return hclge_get_mac_link_status(hdev, link_status);
|
||||||
if (hdev->hw.mac.phydev->state == PHY_RUNNING)
|
|
||||||
link_stat = mac_state &
|
|
||||||
hdev->hw.mac.phydev->link;
|
|
||||||
else
|
|
||||||
link_stat = 0;
|
|
||||||
|
|
||||||
} else {
|
|
||||||
link_stat = mac_state;
|
|
||||||
}
|
|
||||||
|
|
||||||
return !!link_stat;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void hclge_update_link_status(struct hclge_dev *hdev)
|
static void hclge_update_link_status(struct hclge_dev *hdev)
|
||||||
|
@ -2725,6 +2716,7 @@ static void hclge_update_link_status(struct hclge_dev *hdev)
|
||||||
struct hnae3_handle *rhandle;
|
struct hnae3_handle *rhandle;
|
||||||
struct hnae3_handle *handle;
|
struct hnae3_handle *handle;
|
||||||
int state;
|
int state;
|
||||||
|
int ret;
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
if (!client)
|
if (!client)
|
||||||
|
@ -2733,7 +2725,12 @@ static void hclge_update_link_status(struct hclge_dev *hdev)
|
||||||
if (test_and_set_bit(HCLGE_STATE_LINK_UPDATING, &hdev->state))
|
if (test_and_set_bit(HCLGE_STATE_LINK_UPDATING, &hdev->state))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
state = hclge_get_mac_phy_link(hdev);
|
ret = hclge_get_mac_phy_link(hdev, &state);
|
||||||
|
if (ret) {
|
||||||
|
clear_bit(HCLGE_STATE_LINK_UPDATING, &hdev->state);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if (state != hdev->hw.mac.link) {
|
if (state != hdev->hw.mac.link) {
|
||||||
for (i = 0; i < hdev->num_vmdq_vport + 1; i++) {
|
for (i = 0; i < hdev->num_vmdq_vport + 1; i++) {
|
||||||
handle = &hdev->vport[i].nic;
|
handle = &hdev->vport[i].nic;
|
||||||
|
@ -6524,14 +6521,15 @@ static int hclge_mac_link_status_wait(struct hclge_dev *hdev, int link_ret)
|
||||||
{
|
{
|
||||||
#define HCLGE_MAC_LINK_STATUS_NUM 100
|
#define HCLGE_MAC_LINK_STATUS_NUM 100
|
||||||
|
|
||||||
|
int link_status;
|
||||||
int i = 0;
|
int i = 0;
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
do {
|
do {
|
||||||
ret = hclge_get_mac_link_status(hdev);
|
ret = hclge_get_mac_link_status(hdev, &link_status);
|
||||||
if (ret < 0)
|
if (ret)
|
||||||
return ret;
|
return ret;
|
||||||
else if (ret == link_ret)
|
if (link_status == link_ret)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
msleep(HCLGE_LINK_STATUS_MS);
|
msleep(HCLGE_LINK_STATUS_MS);
|
||||||
|
@ -6542,9 +6540,6 @@ static int hclge_mac_link_status_wait(struct hclge_dev *hdev, int link_ret)
|
||||||
static int hclge_mac_phy_link_status_wait(struct hclge_dev *hdev, bool en,
|
static int hclge_mac_phy_link_status_wait(struct hclge_dev *hdev, bool en,
|
||||||
bool is_phy)
|
bool is_phy)
|
||||||
{
|
{
|
||||||
#define HCLGE_LINK_STATUS_DOWN 0
|
|
||||||
#define HCLGE_LINK_STATUS_UP 1
|
|
||||||
|
|
||||||
int link_ret;
|
int link_ret;
|
||||||
|
|
||||||
link_ret = en ? HCLGE_LINK_STATUS_UP : HCLGE_LINK_STATUS_DOWN;
|
link_ret = en ? HCLGE_LINK_STATUS_UP : HCLGE_LINK_STATUS_DOWN;
|
||||||
|
|
|
@ -317,6 +317,9 @@ enum hclge_link_fail_code {
|
||||||
HCLGE_LF_XSFP_ABSENT,
|
HCLGE_LF_XSFP_ABSENT,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
#define HCLGE_LINK_STATUS_DOWN 0
|
||||||
|
#define HCLGE_LINK_STATUS_UP 1
|
||||||
|
|
||||||
#define HCLGE_PG_NUM 4
|
#define HCLGE_PG_NUM 4
|
||||||
#define HCLGE_SCH_MODE_SP 0
|
#define HCLGE_SCH_MODE_SP 0
|
||||||
#define HCLGE_SCH_MODE_DWRR 1
|
#define HCLGE_SCH_MODE_DWRR 1
|
||||||
|
|
Loading…
Reference in New Issue