|
|
@@ -206,12 +206,15 @@ static void ish_remove(struct pci_dev *pdev)
|
|
|
#ifdef CONFIG_PM
|
|
|
static struct device *ish_resume_device;
|
|
|
|
|
|
+/* 50ms to get resume response */
|
|
|
+#define WAIT_FOR_RESUME_ACK_MS 50
|
|
|
+
|
|
|
/**
|
|
|
* ish_resume_handler() - Work function to complete resume
|
|
|
* @work: work struct
|
|
|
*
|
|
|
* The resume work function to complete resume function asynchronously.
|
|
|
- * There are two types of platforms, one where ISH is not powered off,
|
|
|
+ * There are two resume paths, one where ISH is not powered off,
|
|
|
* in that case a simple resume message is enough, others we need
|
|
|
* a reset sequence.
|
|
|
*/
|
|
|
@@ -219,20 +222,31 @@ static void ish_resume_handler(struct work_struct *work)
|
|
|
{
|
|
|
struct pci_dev *pdev = to_pci_dev(ish_resume_device);
|
|
|
struct ishtp_device *dev = pci_get_drvdata(pdev);
|
|
|
+ uint32_t fwsts;
|
|
|
int ret;
|
|
|
|
|
|
- ishtp_send_resume(dev);
|
|
|
+ /* Get ISH FW status */
|
|
|
+ fwsts = IPC_GET_ISH_FWSTS(dev->ops->get_fw_status(dev));
|
|
|
|
|
|
- /* 50 ms to get resume response */
|
|
|
- if (dev->resume_flag)
|
|
|
- ret = wait_event_interruptible_timeout(dev->resume_wait,
|
|
|
- !dev->resume_flag,
|
|
|
- msecs_to_jiffies(50));
|
|
|
+ /*
|
|
|
+ * If currently, in ISH FW, sensor app is loaded or beyond that,
|
|
|
+ * it means ISH isn't powered off, in this case, send a resume message.
|
|
|
+ */
|
|
|
+ if (fwsts >= FWSTS_SENSOR_APP_LOADED) {
|
|
|
+ ishtp_send_resume(dev);
|
|
|
+
|
|
|
+ /* Waiting to get resume response */
|
|
|
+ if (dev->resume_flag)
|
|
|
+ ret = wait_event_interruptible_timeout(dev->resume_wait,
|
|
|
+ !dev->resume_flag,
|
|
|
+ msecs_to_jiffies(WAIT_FOR_RESUME_ACK_MS));
|
|
|
+ }
|
|
|
|
|
|
/*
|
|
|
- * If no resume response. This platform is not S0ix compatible
|
|
|
- * So on resume full reboot of ISH processor will happen, so
|
|
|
- * need to go through init sequence again
|
|
|
+ * If in ISH FW, sensor app isn't loaded yet, or no resume response.
|
|
|
+ * That means this platform is not S0ix compatible, or something is
|
|
|
+ * wrong with ISH FW. So on resume, full reboot of ISH processor will
|
|
|
+ * happen, so need to go through init sequence again.
|
|
|
*/
|
|
|
if (dev->resume_flag)
|
|
|
ish_init(dev);
|