i2c-msm-geni: Initialize completion variable before txfer request

During I2C GSI mode transfer scenario, there is a potential race between
initializing the completion variable and waiting for the completion.
After submitting the DMA transfer request, initializing the completion
may actually reset the received event as DMA could have complete the
transfer immediately before driver waits for the event. Then it can
never receive the completion and results in timeout.

This change initializes the completion variable before submitting the
DMA transfer request and then waits for the completion.

Change-Id: I537d1187a84171a0811862efd5e118c8d8b57fef
Signed-off-by: Mukesh Kumar Savaliya <msavaliy@codeaurora.org>
This commit is contained in:
Mukesh Kumar Savaliya 2020-12-23 21:14:23 +05:30
commit 20e81ac78a

View file

@ -695,11 +695,11 @@ static int geni_i2c_lock_bus(struct geni_i2c_dev *gi2c)
goto geni_i2c_err_lock_bus;
}
reinit_completion(&gi2c->xfer);
/* Issue TX */
tx_cookie = dmaengine_submit(gi2c->tx_desc);
dma_async_issue_pending(gi2c->tx_c);
reinit_completion(&gi2c->xfer);
timeout = wait_for_completion_timeout(&gi2c->xfer, HZ);
if (!timeout) {
GENI_SE_ERR(gi2c->ipcl, true, gi2c->dev,
@ -740,11 +740,11 @@ static void geni_i2c_unlock_bus(struct geni_i2c_dev *gi2c)
goto geni_i2c_err_unlock_bus;
}
reinit_completion(&gi2c->xfer);
/* Issue TX */
tx_cookie = dmaengine_submit(gi2c->tx_desc);
dma_async_issue_pending(gi2c->tx_c);
reinit_completion(&gi2c->xfer);
timeout = wait_for_completion_timeout(&gi2c->xfer, HZ);
if (!timeout) {
GENI_SE_ERR(gi2c->ipcl, true, gi2c->dev,