mail archive of the barebox mailing list
 help / color / mirror / Atom feed
* [PATCH 1/2] watchdog: i.MX: add soc_reset operation
@ 2017-01-19 15:03 Sascha Hauer
  2017-01-19 15:03 ` [PATCH 2/2] watchdog: i.MX: Fix internal/external reset Sascha Hauer
  2017-01-20  5:39 ` [PATCH 1/2] watchdog: i.MX: add soc_reset operation Sam Ravnborg
  0 siblings, 2 replies; 5+ messages in thread
From: Sascha Hauer @ 2017-01-19 15:03 UTC (permalink / raw)
  To: Barebox List

On i.MX21 watchdog type the reset operation is really different
from the watchdog enable/set timeout operation, so create an
extra callback for this instead of folding both things together.

Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
---
 drivers/watchdog/imxwd.c | 32 +++++++++++++++++++++-----------
 1 file changed, 21 insertions(+), 11 deletions(-)

diff --git a/drivers/watchdog/imxwd.c b/drivers/watchdog/imxwd.c
index 03e116ea2..c736fdaa3 100644
--- a/drivers/watchdog/imxwd.c
+++ b/drivers/watchdog/imxwd.c
@@ -26,6 +26,7 @@ struct imx_wd;
 
 struct imx_wd_ops {
 	int (*set_timeout)(struct imx_wd *, int);
+	void (*soc_reset)(struct imx_wd *);
 	int (*init)(struct imx_wd *);
 };
 
@@ -76,10 +77,7 @@ static int imx1_watchdog_set_timeout(struct imx_wd *priv, int timeout)
 		return 0;
 	}
 
-	if (timeout > 0)
-		val = (timeout * 2 - 1) << 8;
-	else
-		val = 0;
+	val = (timeout * 2 - 1) << 8;
 
 	writew(val, priv->base + IMX1_WDOG_WCR);
 	writew(IMX1_WDOG_WCR_WDE | val, priv->base + IMX1_WDOG_WCR);
@@ -91,6 +89,11 @@ static int imx1_watchdog_set_timeout(struct imx_wd *priv, int timeout)
 	return 0;
 }
 
+static void imx1_soc_reset(struct imx_wd *priv)
+{
+	writew(IMX1_WDOG_WCR_WDE, priv->base + IMX1_WDOG_WCR);
+}
+
 static int imx21_watchdog_set_timeout(struct imx_wd *priv, int timeout)
 {
 	u16 val;
@@ -103,13 +106,9 @@ static int imx21_watchdog_set_timeout(struct imx_wd *priv, int timeout)
 	if (timeout == 0) /* bit 2 (WDE) cannot be set to 0 again */
 		return -ENOSYS;
 
-	if (timeout > 0)
-		val = ((timeout * 2 - 1) << 8) | IMX21_WDOG_WCR_SRS |
-			IMX21_WDOG_WCR_WDA;
-	else
-		val = 0;
+	val = ((timeout * 2 - 1) << 8) | IMX21_WDOG_WCR_SRS |
+		IMX21_WDOG_WCR_WDA;
 
-	writew(val, priv->base + IMX21_WDOG_WCR);
 	writew(IMX21_WDOG_WCR_WDE | val, priv->base + IMX21_WDOG_WCR);
 
 	/* Write Service Sequence */
@@ -119,6 +118,15 @@ static int imx21_watchdog_set_timeout(struct imx_wd *priv, int timeout)
 	return 0;
 }
 
+static void imx21_soc_reset(struct imx_wd *priv)
+{
+	u16 val;
+
+	val = IMX21_WDOG_WCR_SRS | IMX21_WDOG_WCR_WDA;
+
+	writew(val, priv->base + IMX21_WDOG_WCR);
+}
+
 static int imx_watchdog_set_timeout(struct watchdog *wd, unsigned timeout)
 {
 	struct imx_wd *priv = (struct imx_wd *)to_imx_wd(wd);
@@ -130,7 +138,7 @@ static void __noreturn imxwd_force_soc_reset(struct restart_handler *rst)
 {
 	struct imx_wd *priv = container_of(rst, struct imx_wd, restart);
 
-	priv->ops->set_timeout(priv, -1);
+	priv->ops->soc_reset(priv);
 
 	mdelay(1000);
 
@@ -227,11 +235,13 @@ on_error:
 
 static const struct imx_wd_ops imx21_wd_ops = {
 	.set_timeout = imx21_watchdog_set_timeout,
+	.soc_reset = imx21_soc_reset,
 	.init = imx21_wd_init,
 };
 
 static const struct imx_wd_ops imx1_wd_ops = {
 	.set_timeout = imx1_watchdog_set_timeout,
+	.soc_reset = imx1_soc_reset,
 };
 
 static __maybe_unused struct of_device_id imx_wdt_dt_ids[] = {
-- 
2.11.0


_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 5+ messages in thread

* [PATCH 2/2] watchdog: i.MX: Fix internal/external reset
  2017-01-19 15:03 [PATCH 1/2] watchdog: i.MX: add soc_reset operation Sascha Hauer
@ 2017-01-19 15:03 ` Sascha Hauer
  2017-01-20  5:39 ` [PATCH 1/2] watchdog: i.MX: add soc_reset operation Sam Ravnborg
  1 sibling, 0 replies; 5+ messages in thread
From: Sascha Hauer @ 2017-01-19 15:03 UTC (permalink / raw)
  To: Barebox List

The watchdog can either reset only the SoC or assert the WDOG_B
output signal instead. On some boards it's necessary to use the
external WDOG_B output to make sure that external devices like the
PMIC are also properly resetted. This has been fixed in the Linux
driver which honours a fsl,ext-reset-output device tree property
to select between both ways. Do the same in the barebox driver.

Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
---
 drivers/watchdog/imxwd.c | 16 ++++++++++++++--
 1 file changed, 14 insertions(+), 2 deletions(-)

diff --git a/drivers/watchdog/imxwd.c b/drivers/watchdog/imxwd.c
index c736fdaa3..84dea802b 100644
--- a/drivers/watchdog/imxwd.c
+++ b/drivers/watchdog/imxwd.c
@@ -36,6 +36,7 @@ struct imx_wd {
 	struct device_d *dev;
 	const struct imx_wd_ops *ops;
 	struct restart_handler restart;
+	bool ext_reset;
 };
 
 #define to_imx_wd(h) container_of(h, struct imx_wd, wd)
@@ -51,6 +52,7 @@ struct imx_wd {
 #define IMX21_WDOG_WSTR	0x04 /* Watchdog Status Register  */
 #define IMX21_WDOG_WMCR	0x08 /* Misc Register */
 #define IMX21_WDOG_WCR_WDE	(1 << 2)
+#define IMX21_WDOG_WCR_WDT	(1 << 3)
 #define IMX21_WDOG_WCR_SRS	(1 << 4)
 #define IMX21_WDOG_WCR_WDA	(1 << 5)
 
@@ -109,6 +111,9 @@ static int imx21_watchdog_set_timeout(struct imx_wd *priv, int timeout)
 	val = ((timeout * 2 - 1) << 8) | IMX21_WDOG_WCR_SRS |
 		IMX21_WDOG_WCR_WDA;
 
+	if (priv->ext_reset)
+		val |= IMX21_WDOG_WCR_WDT;
+
 	writew(IMX21_WDOG_WCR_WDE | val, priv->base + IMX21_WDOG_WCR);
 
 	/* Write Service Sequence */
@@ -120,9 +125,13 @@ static int imx21_watchdog_set_timeout(struct imx_wd *priv, int timeout)
 
 static void imx21_soc_reset(struct imx_wd *priv)
 {
-	u16 val;
+	u16 val = 0;
 
-	val = IMX21_WDOG_WCR_SRS | IMX21_WDOG_WCR_WDA;
+	/* Use internal reset or external - not both */
+	if (priv->ext_reset)
+		val |= IMX21_WDOG_WCR_SRS; /* do not assert int reset */
+	else
+		val |= IMX21_WDOG_WCR_WDA; /* do not assert ext-reset */
 
 	writew(val, priv->base + IMX21_WDOG_WCR);
 }
@@ -202,6 +211,9 @@ static int imx_wd_probe(struct device_d *dev)
 	priv->wd.dev = dev;
 	priv->dev = dev;
 
+	priv->ext_reset = of_property_read_bool(dev->device_node,
+						"fsl,ext-reset-output");
+
 	if (IS_ENABLED(CONFIG_WATCHDOG_IMX)) {
 		ret = watchdog_register(&priv->wd);
 		if (ret)
-- 
2.11.0


_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: [PATCH 1/2] watchdog: i.MX: add soc_reset operation
  2017-01-19 15:03 [PATCH 1/2] watchdog: i.MX: add soc_reset operation Sascha Hauer
  2017-01-19 15:03 ` [PATCH 2/2] watchdog: i.MX: Fix internal/external reset Sascha Hauer
@ 2017-01-20  5:39 ` Sam Ravnborg
  2017-01-20  5:44   ` Sam Ravnborg
  1 sibling, 1 reply; 5+ messages in thread
From: Sam Ravnborg @ 2017-01-20  5:39 UTC (permalink / raw)
  To: Sascha Hauer; +Cc: Barebox List

On Thu, Jan 19, 2017 at 04:03:51PM +0100, Sascha Hauer wrote:
> On i.MX21 watchdog type the reset operation is really different
> from the watchdog enable/set timeout operation, so create an
> extra callback for this instead of folding both things together.
> 
> Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
> ---
>  drivers/watchdog/imxwd.c | 32 +++++++++++++++++++++-----------
>  1 file changed, 21 insertions(+), 11 deletions(-)
> 
> diff --git a/drivers/watchdog/imxwd.c b/drivers/watchdog/imxwd.c
> index 03e116ea2..c736fdaa3 100644
> --- a/drivers/watchdog/imxwd.c
> +++ b/drivers/watchdog/imxwd.c
> @@ -26,6 +26,7 @@ struct imx_wd;
>  
>  struct imx_wd_ops {
>  	int (*set_timeout)(struct imx_wd *, int);

With this change the timeout argument could be unsigned int.

> +	void (*soc_reset)(struct imx_wd *);
>  	int (*init)(struct imx_wd *);
>  };
>  
> @@ -76,10 +77,7 @@ static int imx1_watchdog_set_timeout(struct imx_wd *priv, int timeout)
>  		return 0;
>  	}
>  
> -	if (timeout > 0)
> -		val = (timeout * 2 - 1) << 8;
> -	else
> -		val = 0;
> +	val = (timeout * 2 - 1) << 8;
>  
>  	writew(val, priv->base + IMX1_WDOG_WCR);
>  	writew(IMX1_WDOG_WCR_WDE | val, priv->base + IMX1_WDOG_WCR);

Otherwise the timeout < 0 should somehow be handled here.

> @@ -91,6 +89,11 @@ static int imx1_watchdog_set_timeout(struct imx_wd *priv, int timeout)
>  	return 0;
>  }
>  
> +static void imx1_soc_reset(struct imx_wd *priv)
> +{
> +	writew(IMX1_WDOG_WCR_WDE, priv->base + IMX1_WDOG_WCR);
> +}
> +
>  static int imx21_watchdog_set_timeout(struct imx_wd *priv, int timeout)
>  {
>  	u16 val;
> @@ -103,13 +106,9 @@ static int imx21_watchdog_set_timeout(struct imx_wd *priv, int timeout)
>  	if (timeout == 0) /* bit 2 (WDE) cannot be set to 0 again */
>  		return -ENOSYS;
>  
> -	if (timeout > 0)
> -		val = ((timeout * 2 - 1) << 8) | IMX21_WDOG_WCR_SRS |
> -			IMX21_WDOG_WCR_WDA;
> -	else
> -		val = 0;
> +	val = ((timeout * 2 - 1) << 8) | IMX21_WDOG_WCR_SRS |
> +		IMX21_WDOG_WCR_WDA;
Likewise.

	Sam

_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: [PATCH 1/2] watchdog: i.MX: add soc_reset operation
  2017-01-20  5:39 ` [PATCH 1/2] watchdog: i.MX: add soc_reset operation Sam Ravnborg
@ 2017-01-20  5:44   ` Sam Ravnborg
  2017-01-20  8:10     ` Sascha Hauer
  0 siblings, 1 reply; 5+ messages in thread
From: Sam Ravnborg @ 2017-01-20  5:44 UTC (permalink / raw)
  To: Sascha Hauer; +Cc: Barebox List

On Fri, Jan 20, 2017 at 06:39:03AM +0100, Sam Ravnborg wrote:
> On Thu, Jan 19, 2017 at 04:03:51PM +0100, Sascha Hauer wrote:
> > On i.MX21 watchdog type the reset operation is really different
> > from the watchdog enable/set timeout operation, so create an
> > extra callback for this instead of folding both things together.
> > 
> > Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
> > ---
> >  drivers/watchdog/imxwd.c | 32 +++++++++++++++++++++-----------
> >  1 file changed, 21 insertions(+), 11 deletions(-)
> > 
> > diff --git a/drivers/watchdog/imxwd.c b/drivers/watchdog/imxwd.c
> > index 03e116ea2..c736fdaa3 100644
> > --- a/drivers/watchdog/imxwd.c
> > +++ b/drivers/watchdog/imxwd.c
> > @@ -26,6 +26,7 @@ struct imx_wd;
> >  
> >  struct imx_wd_ops {
> >  	int (*set_timeout)(struct imx_wd *, int);
> 
> With this change the timeout argument could be unsigned int.
> 
> > +	void (*soc_reset)(struct imx_wd *);
> >  	int (*init)(struct imx_wd *);
> >  };
> >  
> > @@ -76,10 +77,7 @@ static int imx1_watchdog_set_timeout(struct imx_wd *priv, int timeout)
> >  		return 0;
> >  	}
> >  
> > -	if (timeout > 0)
> > -		val = (timeout * 2 - 1) << 8;
> > -	else
> > -		val = 0;
> > +	val = (timeout * 2 - 1) << 8;
> >  
> >  	writew(val, priv->base + IMX1_WDOG_WCR);
> >  	writew(IMX1_WDOG_WCR_WDE | val, priv->base + IMX1_WDOG_WCR);
> 
> Otherwise the timeout < 0 should somehow be handled here.

Unless we do not bother because this is all local to the file
and we know the two call sites.

	Sam

_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: [PATCH 1/2] watchdog: i.MX: add soc_reset operation
  2017-01-20  5:44   ` Sam Ravnborg
@ 2017-01-20  8:10     ` Sascha Hauer
  0 siblings, 0 replies; 5+ messages in thread
From: Sascha Hauer @ 2017-01-20  8:10 UTC (permalink / raw)
  To: Sam Ravnborg; +Cc: Barebox List

Hi Sam,

On Fri, Jan 20, 2017 at 06:44:00AM +0100, Sam Ravnborg wrote:
> On Fri, Jan 20, 2017 at 06:39:03AM +0100, Sam Ravnborg wrote:
> > On Thu, Jan 19, 2017 at 04:03:51PM +0100, Sascha Hauer wrote:
> > > On i.MX21 watchdog type the reset operation is really different
> > > from the watchdog enable/set timeout operation, so create an
> > > extra callback for this instead of folding both things together.
> > > 
> > > Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
> > > ---
> > >  drivers/watchdog/imxwd.c | 32 +++++++++++++++++++++-----------
> > >  1 file changed, 21 insertions(+), 11 deletions(-)
> > > 
> > > diff --git a/drivers/watchdog/imxwd.c b/drivers/watchdog/imxwd.c
> > > index 03e116ea2..c736fdaa3 100644
> > > --- a/drivers/watchdog/imxwd.c
> > > +++ b/drivers/watchdog/imxwd.c
> > > @@ -26,6 +26,7 @@ struct imx_wd;
> > >  
> > >  struct imx_wd_ops {
> > >  	int (*set_timeout)(struct imx_wd *, int);
> > 
> > With this change the timeout argument could be unsigned int.
> > 
> > > +	void (*soc_reset)(struct imx_wd *);
> > >  	int (*init)(struct imx_wd *);
> > >  };
> > >  
> > > @@ -76,10 +77,7 @@ static int imx1_watchdog_set_timeout(struct imx_wd *priv, int timeout)
> > >  		return 0;
> > >  	}
> > >  
> > > -	if (timeout > 0)
> > > -		val = (timeout * 2 - 1) << 8;
> > > -	else
> > > -		val = 0;
> > > +	val = (timeout * 2 - 1) << 8;
> > >  
> > >  	writew(val, priv->base + IMX1_WDOG_WCR);
> > >  	writew(IMX1_WDOG_WCR_WDE | val, priv->base + IMX1_WDOG_WCR);
> > 
> > Otherwise the timeout < 0 should somehow be handled here.
> 
> Unless we do not bother because this is all local to the file
> and we know the two call sites.

I changed it to unsigned and also removed another check for negative
values.

Sascha

-- 
Pengutronix e.K.                           |                             |
Industrial Linux Solutions                 | http://www.pengutronix.de/  |
Peiner Str. 6-8, 31137 Hildesheim, Germany | Phone: +49-5121-206917-0    |
Amtsgericht Hildesheim, HRA 2686           | Fax:   +49-5121-206917-5555 |

_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 5+ messages in thread

end of thread, other threads:[~2017-01-20  8:12 UTC | newest]

Thread overview: 5+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2017-01-19 15:03 [PATCH 1/2] watchdog: i.MX: add soc_reset operation Sascha Hauer
2017-01-19 15:03 ` [PATCH 2/2] watchdog: i.MX: Fix internal/external reset Sascha Hauer
2017-01-20  5:39 ` [PATCH 1/2] watchdog: i.MX: add soc_reset operation Sam Ravnborg
2017-01-20  5:44   ` Sam Ravnborg
2017-01-20  8:10     ` Sascha Hauer

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox