diff options
author | Linux Build Service Account <lnxbuild@quicinc.com> | 2017-04-26 06:33:45 -0700 |
---|---|---|
committer | Gerrit - the friendly Code Review server <code-review@localhost> | 2017-04-26 06:33:44 -0700 |
commit | f4300126c72e799687753ef561840b937f50fa90 (patch) | |
tree | aa9335b051244a6fbc2dcd251af2c2da64267502 /drivers | |
parent | d8af252b938a3a60527e346d5dd200adb7facb3e (diff) | |
parent | bf1e13f6f726b9d5d5c3a8b6086f56684f969ef5 (diff) |
Merge "Revert "spi: spi_qsd: Check device state during set_cs call""
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/spi/spi_qsd.c | 55 |
1 files changed, 38 insertions, 17 deletions
diff --git a/drivers/spi/spi_qsd.c b/drivers/spi/spi_qsd.c index 8efe18dcc98f..548efd11e856 100644 --- a/drivers/spi/spi_qsd.c +++ b/drivers/spi/spi_qsd.c @@ -1496,9 +1496,9 @@ static inline void msm_spi_set_cs(struct spi_device *spi, bool set_flag) u32 spi_ioc_orig; int rc; - if (dd->suspended) { - dev_err(dd->dev, "%s: SPI operational state not valid %d\n", - __func__, dd->suspended); + rc = pm_runtime_get_sync(dd->dev); + if (rc < 0) { + dev_err(dd->dev, "Failure during runtime get"); return; } @@ -1524,6 +1524,8 @@ static inline void msm_spi_set_cs(struct spi_device *spi, bool set_flag) writel_relaxed(spi_ioc, dd->base + SPI_IO_CONTROL); if (dd->pdata->is_shared) put_local_resources(dd); + pm_runtime_mark_last_busy(dd->dev); + pm_runtime_put_autosuspend(dd->dev); } static void reset_core(struct msm_spi *dd) @@ -1707,16 +1709,23 @@ static int msm_spi_prepare_transfer_hardware(struct spi_master *master) struct msm_spi *dd = spi_master_get_devdata(master); int resume_state = 0; - if (!pm_runtime_enabled(dd->dev)) { - dev_err(dd->dev, "Runtime PM not available\n"); - resume_state = -EBUSY; - goto spi_finalize; - } - resume_state = pm_runtime_get_sync(dd->dev); if (resume_state < 0) goto spi_finalize; + /* + * Counter-part of system-suspend when runtime-pm is not enabled. + * This way, resume can be left empty and device will be put in + * active mode only if client requests anything on the bus + */ + if (!pm_runtime_enabled(dd->dev)) + resume_state = msm_spi_pm_resume_runtime(dd->dev); + if (resume_state < 0) + goto spi_finalize; + if (dd->suspended) { + resume_state = -EBUSY; + goto spi_finalize; + } return 0; spi_finalize: @@ -1728,11 +1737,6 @@ static int msm_spi_unprepare_transfer_hardware(struct spi_master *master) { struct msm_spi *dd = spi_master_get_devdata(master); - if (!pm_runtime_enabled(dd->dev)) { - dev_err(dd->dev, "Runtime PM not available\n"); - return -EBUSY; - } - pm_runtime_mark_last_busy(dd->dev); pm_runtime_put_autosuspend(dd->dev); return 0; @@ -2672,10 +2676,27 @@ resume_exit: #ifdef CONFIG_PM_SLEEP static int msm_spi_suspend(struct device *device) { - if (!pm_runtime_status_suspended(device)) { - dev_err(device, "Runtime not suspended, deny sys suspend"); - return -EBUSY; + if (!pm_runtime_enabled(device) || !pm_runtime_suspended(device)) { + struct platform_device *pdev = to_platform_device(device); + struct spi_master *master = platform_get_drvdata(pdev); + struct msm_spi *dd; + + dev_dbg(device, "system suspend"); + if (!master) + goto suspend_exit; + dd = spi_master_get_devdata(master); + if (!dd) + goto suspend_exit; + msm_spi_pm_suspend_runtime(device); + + /* + * set the device's runtime PM status to 'suspended' + */ + pm_runtime_disable(device); + pm_runtime_set_suspended(device); + pm_runtime_enable(device); } +suspend_exit: return 0; } |