Unverified Commit f89b6bb5 authored by openeuler-ci-bot's avatar openeuler-ci-bot Committed by Gitee
Browse files

!7732 HNS3: Fixed a deadlock issue caused by concurrent VF deactivation and PF reset

Merge Pull Request from: @mufengyan 
 
driver inclusion
category: bugfix
bugzilla: https://gitee.com/openeuler/kernel/issues/I9R48E


CVE: NA
    
---------------------------------------------------------------------
    
When the VF is deactivated and PF reset concurrently, the fastpath
process holds the rtnl_lock and enters the infinite loop of the
network port down. As a result, the rtnl_lock can not be obtained
during subsequent reset and ethtool operations, and the timeout
calltrace message is displayed.
    
Now the rtnl_lock function is moved to the fastpath function, and
the reset status judgment is added to ensure that the fastpath operation
does not work concurrently with the reset operation. This prevents
exceptions caused by unmatched operations on the protocol stack.
    
Signed-off-by: default avatarYixi Shen <shenyixi@huawei.com>
 
Link:https://gitee.com/openeuler/kernel/pulls/7732

 

Reviewed-by: default avatarLin Yunsheng <linyunsheng@huawei.com>
Signed-off-by: default avatarJialin Zhang <zhangjialin11@huawei.com>
parents 8a5173f7 426f0a71
Loading
Loading
Loading
Loading
+0 −2
Original line number Diff line number Diff line
@@ -3463,9 +3463,7 @@ static int hns3_fastpath_configure(struct pci_dev *pdev, bool fastpath_en)
	if (!hnae3_dev_udma_supported(ae_dev) || !ae_dev->ops->set_fastpath)
		return 0;

	rtnl_lock();
	ret = ae_dev->ops->set_fastpath(ae_dev, fastpath_en);
	rtnl_unlock();

	return ret;
}
+11 −2
Original line number Diff line number Diff line
@@ -12445,13 +12445,21 @@ static int hclge_set_fastpath(struct hnae3_ae_dev *ae_dev, bool fastpath_en)
	int last_bad_ret = 0;
	int ret;

	while (test_bit(HCLGE_STATE_RST_HANDLING, &hdev->state))
		msleep(HCLGE_WAIT_RESET_DONE);

	rtnl_lock();
	ret = hclge_notify_client(hdev, HNAE3_DOWN_CLIENT);
	if (ret)
	if (ret) {
		rtnl_unlock();
		return ret;
	}

	ret = hclge_tm_flush_cfg(hdev, true);
	if (ret)
	if (ret) {
		rtnl_unlock();
		return ret;
	}

	ret = hclge_set_fastpath_cmd(ae_dev, fastpath_en);
	if (ret) {
@@ -12468,6 +12476,7 @@ static int hclge_set_fastpath(struct hnae3_ae_dev *ae_dev, bool fastpath_en)
	if (ret)
		last_bad_ret = ret;

	rtnl_unlock();
	return last_bad_ret;
}
#endif