From 1d6133123fb2626499e0e0a9d62e39bcdc5e593b Mon Sep 17 00:00:00 2001
From: Marco Chiappero <marco.chiappero@intel.com>
Date: Wed, 17 Nov 2021 14:30:43 +0000
Subject: [PATCH] crypto: qat - handle retries due to collisions in
 adf_iov_putmsg()
Git-commit: 1d6133123fb2626499e0e0a9d62e39bcdc5e593b
Patch-mainline: v5.17-rc1
References: jsc#PED-1073

Rework __adf_iov_putmsg() to handle retries due to collisions
internally, removing the need for an external retry loop.
The functions __adf_iov_putmsg() and adf_iov_putmsg() have been merged
together maintaining the adf_iov_putmsg() name.

This will allow to use this function only for GEN2 devices, since
collision are peculiar of this generation and therefore should be
confined to the actual implementation of the transport/medium access.

Note that now adf_iov_putmsg() will retry to send a message only in case
of collisions and will now fail if an ACK is not received from the
remote function.

Signed-off-by: Marco Chiappero <marco.chiappero@intel.com>
Co-developed-by: Giovanni Cabiddu <giovanni.cabiddu@intel.com>
Signed-off-by: Giovanni Cabiddu <giovanni.cabiddu@intel.com>
Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>
Signed-off-by: Torsten Duwe <duwe@suse.de>

---
 drivers/crypto/qat/qat_common/adf_pf2vf_msg.c | 52 +++++++------------
 1 file changed, 19 insertions(+), 33 deletions(-)

diff --git a/drivers/crypto/qat/qat_common/adf_pf2vf_msg.c b/drivers/crypto/qat/qat_common/adf_pf2vf_msg.c
index 201744825e23a..d98e3639c9d28 100644
--- a/drivers/crypto/qat/qat_common/adf_pf2vf_msg.c
+++ b/drivers/crypto/qat/qat_common/adf_pf2vf_msg.c
@@ -14,7 +14,7 @@
 					 ADF_PFVF_MSG_ACK_MAX_RETRY + \
 					 ADF_PFVF_MSG_COLLISION_DETECT_DELAY)
 
-static int __adf_iov_putmsg(struct adf_accel_dev *accel_dev, u32 msg, u8 vf_nr)
+static int adf_iov_putmsg(struct adf_accel_dev *accel_dev, u32 msg, u8 vf_nr)
 {
 	struct adf_accel_pci *pci_info = &accel_dev->accel_pci_dev;
 	struct adf_hw_device_data *hw_data = accel_dev->hw_device;
@@ -24,8 +24,9 @@ static int __adf_iov_putmsg(struct adf_accel_dev *accel_dev, u32 msg, u8 vf_nr)
 	u32 local_in_use_mask, local_in_use_pattern;
 	u32 remote_in_use_mask, remote_in_use_pattern;
 	struct mutex *lock;	/* lock preventing concurrent acces of CSR */
+	unsigned int retries = ADF_PFVF_MSG_MAX_RETRIES;
 	u32 int_bit;
-	int ret = 0;
+	int ret;
 
 	if (accel_dev->is_vf) {
 		pf2vf_offset = hw_data->get_pf2vf_offset(0);
@@ -45,20 +46,22 @@ static int __adf_iov_putmsg(struct adf_accel_dev *accel_dev, u32 msg, u8 vf_nr)
 		int_bit = ADF_PF2VF_INT;
 	}
 
+	msg &= ~local_in_use_mask;
+	msg |= local_in_use_pattern;
+
 	mutex_lock(lock);
 
+start:
+	ret = 0;
+
 	/* Check if the PFVF CSR is in use by remote function */
 	val = ADF_CSR_RD(pmisc_bar_addr, pf2vf_offset);
 	if ((val & remote_in_use_mask) == remote_in_use_pattern) {
 		dev_dbg(&GET_DEV(accel_dev),
 			"PFVF CSR in use by remote function\n");
-		ret = -EBUSY;
-		goto out;
+		goto retry;
 	}
 
-	msg &= ~local_in_use_mask;
-	msg |= local_in_use_pattern;
-
 	/* Attempt to get ownership of the PFVF CSR */
 	ADF_CSR_WR(pmisc_bar_addr, pf2vf_offset, msg | int_bit);
 
@@ -77,8 +80,7 @@ static int __adf_iov_putmsg(struct adf_accel_dev *accel_dev, u32 msg, u8 vf_nr)
 	if (val != msg) {
 		dev_dbg(&GET_DEV(accel_dev),
 			"Collision - PFVF CSR overwritten by remote function\n");
-		ret = -EIO;
-		goto out;
+		goto retry;
 	}
 
 	/* Finished with the PFVF CSR; relinquish it and leave msg in CSR */
@@ -86,31 +88,15 @@ static int __adf_iov_putmsg(struct adf_accel_dev *accel_dev, u32 msg, u8 vf_nr)
 out:
 	mutex_unlock(lock);
 	return ret;
-}
 
-/**
- * adf_iov_putmsg() - send PFVF message
- * @accel_dev:  Pointer to acceleration device.
- * @msg:	Message to send
- * @vf_nr:	VF number to which the message will be sent if on PF, ignored
- *		otherwise
- *
- * Function sends a message through the PFVF channel
- *
- * Return: 0 on success, error code otherwise.
- */
-static int adf_iov_putmsg(struct adf_accel_dev *accel_dev, u32 msg, u8 vf_nr)
-{
-	u32 count = 0;
-	int ret;
-
-	do {
-		ret = __adf_iov_putmsg(accel_dev, msg, vf_nr);
-		if (ret)
-			msleep(ADF_PFVF_MSG_RETRY_DELAY);
-	} while (ret && (count++ < ADF_PFVF_MSG_MAX_RETRIES));
-
-	return ret;
+retry:
+	if (--retries) {
+		msleep(ADF_PFVF_MSG_RETRY_DELAY);
+		goto start;
+	} else {
+		ret = -EBUSY;
+		goto out;
+	}
 }
 
 /**
-- 
2.35.3

