Commit 426f0a71 authored by Yixi Shen's avatar Yixi Shen Committed by mufengyan
Browse files

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

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.

Fixes: dbd08c19 ("Support configuration of fastpath feature")
Signed-off-by: default avatarYixi Shen <shenyixi@huawei.com>
parent 80a0681e
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