clear-pkgs-linux-iot-lts2018/0436-ASoC-Intel-Fix-race-co...

57 lines
2.1 KiB
Diff

From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
From: "Lewandowski, Gustaw" <gustaw.lewandowski@intel.com>
Date: Wed, 11 Jul 2018 13:52:39 +0200
Subject: [PATCH] ASoC: Intel: Fix race condition in IPC rx list
Since there are multiple IPCs being sent in a short span of time, there
is a possibility of more than one message being on the Rx list after
receiving response from firmware. In such cases, when the first
notification of interrupt from firmware is received, driver retrieves
the message from the Rx list but does not delete it from the list till
the next lock. In the meantime, when another interrupt is received from
the firmware, driver is reading the previous message again since the
previous message has not been removed from the list.
Change-Id: I3d85cce7b0e9632a73e286d7d42a2627c1431d6e
Reviewed-on:
Tested-by: Lewandowski, Gustaw <gustaw.lewandowski@intel.com>
Reviewed-by: Wasko, Michal <michal.wasko@intel.com>
---
sound/soc/intel/skylake/skl-sst-ipc.c | 5 ++---
1 file changed, 2 insertions(+), 3 deletions(-)
diff --git a/sound/soc/intel/skylake/skl-sst-ipc.c b/sound/soc/intel/skylake/skl-sst-ipc.c
index 9370c474c618..0e7b5ce64b9e 100644
--- a/sound/soc/intel/skylake/skl-sst-ipc.c
+++ b/sound/soc/intel/skylake/skl-sst-ipc.c
@@ -420,6 +420,7 @@ static struct ipc_message *skl_ipc_reply_get_msg(struct sst_generic_ipc *ipc,
msg = list_first_entry(&ipc->rx_list, struct ipc_message, list);
+ list_del(&msg->list);
out:
return msg;
@@ -707,8 +708,8 @@ void skl_ipc_process_reply(struct sst_generic_ipc *ipc,
spin_lock_irqsave(&ipc->dsp->spinlock, flags);
msg = skl_ipc_reply_get_msg(ipc, *ipc_header);
- spin_unlock_irqrestore(&ipc->dsp->spinlock, flags);
if (msg == NULL) {
+ spin_unlock_irqrestore(&ipc->dsp->spinlock, flags);
dev_dbg(ipc->dev, "ipc: rx list is empty\n");
return;
}
@@ -753,8 +754,6 @@ void skl_ipc_process_reply(struct sst_generic_ipc *ipc,
}
}
- spin_lock_irqsave(&ipc->dsp->spinlock, flags);
- list_del(&msg->list);
sst_ipc_tx_msg_reply_complete(ipc, msg);
spin_unlock_irqrestore(&ipc->dsp->spinlock, flags);
}
--
https://clearlinux.org