Skip to content

Commit

Permalink
remoteproc: stm32: wakeup the system by wdg irq
Browse files Browse the repository at this point in the history
If the device node defines the 'wakeup-source' property, use the WDG
exti IRQ as a wakeup source of the system.

Signed-off-by: Fabien Dessenne <fabien.dessenne@st.com>
Link: https://lore.kernel.org/r/1566833923-16718-3-git-send-email-fabien.dessenne@st.com
[bjorn: Replace ifdef with __maybe_unused for suspend/resume functions]
Signed-off-by: Bjorn Andersson <bjorn.andersson@linaro.org>
  • Loading branch information
Fabien Dessenne authored and andersson committed Nov 15, 2019
1 parent 14ea1d0 commit 410119e
Showing 1 changed file with 45 additions and 0 deletions.
45 changes: 45 additions & 0 deletions drivers/remoteproc/stm32_rproc.c
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
#include <linux/of_address.h>
#include <linux/of_device.h>
#include <linux/of_reserved_mem.h>
#include <linux/pm_wakeirq.h>
#include <linux/regmap.h>
#include <linux/remoteproc.h>
#include <linux/reset.h>
Expand Down Expand Up @@ -69,6 +70,7 @@ struct stm32_rproc {
struct reset_control *rst;
struct stm32_syscon hold_boot;
struct stm32_syscon pdds;
int wdg_irq;
u32 nb_rmems;
struct stm32_rproc_mem *rmems;
struct stm32_mbox mb[MBOX_NB_MBX];
Expand Down Expand Up @@ -546,6 +548,13 @@ static int stm32_rproc_parse_dt(struct platform_device *pdev)
return err;
}

ddata->wdg_irq = irq;

if (of_property_read_bool(np, "wakeup-source")) {
device_init_wakeup(dev, true);
dev_pm_set_wake_irq(dev, irq);
}

dev_info(dev, "wdg irq registered\n");
}

Expand Down Expand Up @@ -633,6 +642,10 @@ static int stm32_rproc_probe(struct platform_device *pdev)
free_wkq:
destroy_workqueue(ddata->workqueue);
free_rproc:
if (device_may_wakeup(dev)) {
dev_pm_clear_wake_irq(dev);
device_init_wakeup(dev, false);
}
rproc_free(rproc);
return ret;
}
Expand All @@ -641,23 +654,55 @@ static int stm32_rproc_remove(struct platform_device *pdev)
{
struct rproc *rproc = platform_get_drvdata(pdev);
struct stm32_rproc *ddata = rproc->priv;
struct device *dev = &pdev->dev;

if (atomic_read(&rproc->power) > 0)
rproc_shutdown(rproc);

rproc_del(rproc);
stm32_rproc_free_mbox(rproc);
destroy_workqueue(ddata->workqueue);

if (device_may_wakeup(dev)) {
dev_pm_clear_wake_irq(dev);
device_init_wakeup(dev, false);
}
rproc_free(rproc);

return 0;
}

static int __maybe_unused stm32_rproc_suspend(struct device *dev)
{
struct rproc *rproc = dev_get_drvdata(dev);
struct stm32_rproc *ddata = rproc->priv;

if (device_may_wakeup(dev))
return enable_irq_wake(ddata->wdg_irq);

return 0;
}

static int __maybe_unused stm32_rproc_resume(struct device *dev)
{
struct rproc *rproc = dev_get_drvdata(dev);
struct stm32_rproc *ddata = rproc->priv;

if (device_may_wakeup(dev))
return disable_irq_wake(ddata->wdg_irq);

return 0;
}

static SIMPLE_DEV_PM_OPS(stm32_rproc_pm_ops,
stm32_rproc_suspend, stm32_rproc_resume);

static struct platform_driver stm32_rproc_driver = {
.probe = stm32_rproc_probe,
.remove = stm32_rproc_remove,
.driver = {
.name = "stm32-rproc",
.pm = &stm32_rproc_pm_ops,
.of_match_table = of_match_ptr(stm32_rproc_match),
},
};
Expand Down

0 comments on commit 410119e

Please sign in to comment.