Skip to content

Commit ed68411

Browse files
scosugregkh
authored andcommitted
serial: 8250: omap: Support wakeup pinctrl state on suspend
UART can be used as a wakeup source for am62 from suspend to ram states. To enable wakeup from UART am62 requires a wakeup flag being set in the pinctrl. If the device is marked as wakeup enabled, select the 'wakeup' pinctrl state on suspend and restore the default pinctrl state on resume. Signed-off-by: Markus Schneider-Pargmann <msp@baylibre.com> Signed-off-by: Kendall Willis <k-willis@ti.com> Link: https://lore.kernel.org/r/20250910-uart-daisy-chain-8250-omap-v2-2-e90d44c1a9ac@ti.com Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
1 parent 49fce07 commit ed68411

1 file changed

Lines changed: 36 additions & 0 deletions

File tree

drivers/tty/serial/8250/8250_omap.c

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,8 @@
2727
#include <linux/pm_wakeirq.h>
2828
#include <linux/dma-mapping.h>
2929
#include <linux/sys_soc.h>
30+
#include <linux/reboot.h>
31+
#include <linux/pinctrl/consumer.h>
3032

3133
#include "8250.h"
3234

@@ -145,6 +147,9 @@ struct omap8250_priv {
145147
spinlock_t rx_dma_lock;
146148
bool rx_dma_broken;
147149
bool throttled;
150+
151+
struct pinctrl *pinctrl;
152+
struct pinctrl_state *pinctrl_wakeup;
148153
};
149154

150155
struct omap8250_dma_params {
@@ -1349,6 +1354,18 @@ static int omap8250_no_handle_irq(struct uart_port *port)
13491354
return 0;
13501355
}
13511356

1357+
static int omap8250_select_wakeup_pinctrl(struct device *dev,
1358+
struct omap8250_priv *priv)
1359+
{
1360+
if (IS_ERR_OR_NULL(priv->pinctrl_wakeup))
1361+
return 0;
1362+
1363+
if (!device_may_wakeup(dev))
1364+
return 0;
1365+
1366+
return pinctrl_select_state(priv->pinctrl, priv->pinctrl_wakeup);
1367+
}
1368+
13521369
static struct omap8250_dma_params am654_dma = {
13531370
.rx_size = SZ_2K,
13541371
.rx_trigger = 1,
@@ -1573,6 +1590,11 @@ static int omap8250_probe(struct platform_device *pdev)
15731590
priv->line = ret;
15741591
pm_runtime_mark_last_busy(&pdev->dev);
15751592
pm_runtime_put_autosuspend(&pdev->dev);
1593+
1594+
priv->pinctrl = devm_pinctrl_get(&pdev->dev);
1595+
if (!IS_ERR_OR_NULL(priv->pinctrl))
1596+
priv->pinctrl_wakeup = pinctrl_lookup_state(priv->pinctrl, "wakeup");
1597+
15761598
return 0;
15771599
err:
15781600
pm_runtime_dont_use_autosuspend(&pdev->dev);
@@ -1630,6 +1652,13 @@ static int omap8250_suspend(struct device *dev)
16301652
struct uart_8250_port *up = serial8250_get_port(priv->line);
16311653
int err = 0;
16321654

1655+
err = omap8250_select_wakeup_pinctrl(dev, priv);
1656+
if (err) {
1657+
dev_err(dev, "Failed to select wakeup pinctrl, aborting suspend %pe\n",
1658+
ERR_PTR(err));
1659+
return err;
1660+
}
1661+
16331662
serial8250_suspend_port(priv->line);
16341663

16351664
err = pm_runtime_resume_and_get(dev);
@@ -1651,6 +1680,13 @@ static int omap8250_resume(struct device *dev)
16511680
struct uart_8250_port *up = serial8250_get_port(priv->line);
16521681
int err;
16531682

1683+
err = pinctrl_select_default_state(dev);
1684+
if (err) {
1685+
dev_err(dev, "Failed to select default pinctrl state on resume: %pe\n",
1686+
ERR_PTR(err));
1687+
return err;
1688+
}
1689+
16541690
if (uart_console(&up->port) && console_suspend_enabled) {
16551691
err = pm_runtime_force_resume(dev);
16561692
if (err)

0 commit comments

Comments
 (0)