public inbox for linux-watchdog@vger.kernel.org
 help / color / mirror / Atom feed
From: "Yang, Wenyou" <wenyou.yang@atmel.com>
To: Timo Kokkonen <timo.kokkonen@offcode.fi>,
	<linux-arm-kernel@lists.infradead.org>,
	<linux-watchdog@vger.kernel.org>,
	<boris.brezillon@free-electrons.com>, <nicolas.ferre@atmel.com>,
	<alexandre.belloni@free-electrons.com>
Subject: Re: [PATCHv5 2/4] watchdog: Allow watchdog to reset device at early boot
Date: Mon, 13 Apr 2015 15:56:16 +0800	[thread overview]
Message-ID: <552B76A0.5050307@atmel.com> (raw)
In-Reply-To: <1428671199-5562-3-git-send-email-timo.kokkonen@offcode.fi>



On 2015/4/10 21:06, Timo Kokkonen wrote:
> Historically the watchdogs have always been stopped before user space
> opens and takes over the device. This is not good on many production
> systems where any crash, in kernel or user space, must always result
> in a device reset.
>
> Add a new early_timeout_sec parameter to the watchdog that gives user
> space certain amount of time to set up itself and take over the
> watchdog. Until this timeout has been reached the watchdog core takes
> care of petting the watchdog HW. If there is any crash in kernel or
> user space, reboot is guaranteed as watchdog hardware is never
> stopped.
>
> There is also mode of supplying zero seconds for the early_timeout_sec
> parameter. In this mode the worker is not scheduled, so the watchdog
> timer is not touched nor is the HW petted until user space takes over
> it.
>
> Signed-off-by: Timo Kokkonen <timo.kokkonen@offcode.fi>
> ---
>   drivers/watchdog/watchdog_core.c | 39 ++++++++++++++++++++++++++++++---------
>   include/linux/watchdog.h         |  1 +
>   2 files changed, 31 insertions(+), 9 deletions(-)
>
> diff --git a/drivers/watchdog/watchdog_core.c b/drivers/watchdog/watchdog_core.c
> index 8e7d08d..d6bedf7 100644
> --- a/drivers/watchdog/watchdog_core.c
> +++ b/drivers/watchdog/watchdog_core.c
> @@ -111,12 +111,18 @@ EXPORT_SYMBOL_GPL(watchdog_init_timeout);
>    */
>   int watchdog_init_params(struct watchdog_device *wdd, struct device *dev)
>   {
> +	unsigned int t = 0;
>   	int ret = 0;
>   
>   	ret = watchdog_init_timeout(wdd, wdd->timeout, dev);
>   	if (ret < 0)
>   		return ret;
>   
> +	if (!of_property_read_u32(dev->of_node, "early-timeout-sec", &t))
> +		wdd->early_timeout_sec = t;
> +	else
> +		wdd->early_timeout_sec = -1;
> +
>   	/*
>   	 * Max HW timeout needs to be set so that core knows when to
>   	 * use a kernel worker to support longer watchdog timeouts
> @@ -139,6 +145,7 @@ static void watchdog_worker(struct work_struct *work)
>   	}
>   
>   	if ((!watchdog_active(wdd) && !watchdog_is_stoppable(wdd)) ||
> +		(!watchdog_active(wdd) && wdd->early_timeout_sec >= 0) ||
>   		(watchdog_active(wdd) &&
>   			wdd->hw_max_timeout < wdd->timeout * HZ)) {
>   		if (wdd->ops->ping)
> @@ -152,17 +159,31 @@ static void watchdog_worker(struct work_struct *work)
>   
>   static int prepare_watchdog(struct watchdog_device *wdd)
>   {
> -	/* Stop the watchdog now before user space opens the device */
> -	if (wdd->hw_features & WDOG_HW_IS_STOPPABLE &&
> -		wdd->hw_features & WDOG_HW_RUNNING_AT_BOOT) {
> -		wdd->ops->stop(wdd);
> -
> -	} else if (!(wdd->hw_features & WDOG_HW_IS_STOPPABLE)) {
> +	if (wdd->early_timeout_sec >= 0) {
>   		/*
> -		 * Can't stop it, use a kernel timer to tick
> -		 * it until it's open by user space
> +		 * early timeout, if set, ensures that watchdog will
> +		 * reset the device unless user space opens the
> +		 * watchdog device within the given interval.
>   		 */
> -		schedule_delayed_work(&wdd->work, wdd->hw_heartbeat);
> +		if (!(wdd->hw_features & WDOG_HW_RUNNING_AT_BOOT))
> +			wdd->ops->start(wdd);
> +
> +		if (wdd->early_timeout_sec > 0) {
> +			schedule_delayed_work(&wdd->work,  wdd->hw_heartbeat);
> +		}

This bracket is unnecessary.

> +	} else {
> +		/* Stop the watchdog now before user space opens the device */
> +		if (wdd->hw_features & WDOG_HW_IS_STOPPABLE &&
> +			wdd->hw_features & WDOG_HW_RUNNING_AT_BOOT) {
> +			wdd->ops->stop(wdd);
> +
> +		} else if (!(wdd->hw_features & WDOG_HW_IS_STOPPABLE)) {
> +			/*
> +			 * Can't stop it, use a kernel timer to tick
> +			 * it until it's open by user space
> +			 */
> +			schedule_delayed_work(&wdd->work, wdd->hw_heartbeat);
> +		}
>   	}
>   	return 0;
>   }
> diff --git a/include/linux/watchdog.h b/include/linux/watchdog.h
> index c16c921..6f868b6 100644
> --- a/include/linux/watchdog.h
> +++ b/include/linux/watchdog.h
> @@ -94,6 +94,7 @@ struct watchdog_device {
>   	unsigned int hw_max_timeout; /* in jiffies */
>   	unsigned int hw_heartbeat; /* in jiffies */
>   	unsigned long int expires; /* for soft timer */
> +	unsigned int early_timeout_sec;
>   	void *driver_data;
>   	struct mutex lock;
>   	struct delayed_work work;
Best Regards,
Wenyou Yang


  reply	other threads:[~2015-04-13  7:56 UTC|newest]

Thread overview: 14+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2015-04-10 13:06 [PATCHv5 0/4] watchdog: Extend kernel API and add early_timeout_sec feature Timo Kokkonen
2015-04-10 13:06 ` [PATCHv5 1/4] watchdog: Extend kernel API to know about HW limitations Timo Kokkonen
2015-04-13  7:56   ` Yang, Wenyou
2015-04-13  9:29   ` Yang, Wenyou
2015-04-13 11:00     ` Timo Kokkonen
2015-04-14  2:39       ` Yang, Wenyou
2015-04-14  5:31         ` Timo Kokkonen
2015-04-14  5:44           ` Yang, Wenyou
2015-04-10 13:06 ` [PATCHv5 2/4] watchdog: Allow watchdog to reset device at early boot Timo Kokkonen
2015-04-13  7:56   ` Yang, Wenyou [this message]
2015-04-10 13:06 ` [PATCHv5 3/4] devicetree: Document generic watchdog properties Timo Kokkonen
2015-04-10 13:06 ` [PATCHv5 4/4] watchdog: at91sam9_wdt: Convert to use new watchdog core extensions Timo Kokkonen
2015-04-13  7:55 ` [PATCHv5 0/4] watchdog: Extend kernel API and add early_timeout_sec feature Yang, Wenyou
2015-04-13  8:19   ` Timo Kokkonen

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=552B76A0.5050307@atmel.com \
    --to=wenyou.yang@atmel.com \
    --cc=alexandre.belloni@free-electrons.com \
    --cc=boris.brezillon@free-electrons.com \
    --cc=linux-arm-kernel@lists.infradead.org \
    --cc=linux-watchdog@vger.kernel.org \
    --cc=nicolas.ferre@atmel.com \
    --cc=timo.kokkonen@offcode.fi \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox