xref: /OK3568_Linux_fs/kernel/Documentation/watchdog/watchdog-kernel-api.rst (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1*4882a593Smuzhiyun===============================================
2*4882a593SmuzhiyunThe Linux WatchDog Timer Driver Core kernel API
3*4882a593Smuzhiyun===============================================
4*4882a593Smuzhiyun
5*4882a593SmuzhiyunLast reviewed: 12-Feb-2013
6*4882a593Smuzhiyun
7*4882a593SmuzhiyunWim Van Sebroeck <wim@iguana.be>
8*4882a593Smuzhiyun
9*4882a593SmuzhiyunIntroduction
10*4882a593Smuzhiyun------------
11*4882a593SmuzhiyunThis document does not describe what a WatchDog Timer (WDT) Driver or Device is.
12*4882a593SmuzhiyunIt also does not describe the API which can be used by user space to communicate
13*4882a593Smuzhiyunwith a WatchDog Timer. If you want to know this then please read the following
14*4882a593Smuzhiyunfile: Documentation/watchdog/watchdog-api.rst .
15*4882a593Smuzhiyun
16*4882a593SmuzhiyunSo what does this document describe? It describes the API that can be used by
17*4882a593SmuzhiyunWatchDog Timer Drivers that want to use the WatchDog Timer Driver Core
18*4882a593SmuzhiyunFramework. This framework provides all interfacing towards user space so that
19*4882a593Smuzhiyunthe same code does not have to be reproduced each time. This also means that
20*4882a593Smuzhiyuna watchdog timer driver then only needs to provide the different routines
21*4882a593Smuzhiyun(operations) that control the watchdog timer (WDT).
22*4882a593Smuzhiyun
23*4882a593SmuzhiyunThe API
24*4882a593Smuzhiyun-------
25*4882a593SmuzhiyunEach watchdog timer driver that wants to use the WatchDog Timer Driver Core
26*4882a593Smuzhiyunmust #include <linux/watchdog.h> (you would have to do this anyway when
27*4882a593Smuzhiyunwriting a watchdog device driver). This include file contains following
28*4882a593Smuzhiyunregister/unregister routines::
29*4882a593Smuzhiyun
30*4882a593Smuzhiyun	extern int watchdog_register_device(struct watchdog_device *);
31*4882a593Smuzhiyun	extern void watchdog_unregister_device(struct watchdog_device *);
32*4882a593Smuzhiyun
33*4882a593SmuzhiyunThe watchdog_register_device routine registers a watchdog timer device.
34*4882a593SmuzhiyunThe parameter of this routine is a pointer to a watchdog_device structure.
35*4882a593SmuzhiyunThis routine returns zero on success and a negative errno code for failure.
36*4882a593Smuzhiyun
37*4882a593SmuzhiyunThe watchdog_unregister_device routine deregisters a registered watchdog timer
38*4882a593Smuzhiyundevice. The parameter of this routine is the pointer to the registered
39*4882a593Smuzhiyunwatchdog_device structure.
40*4882a593Smuzhiyun
41*4882a593SmuzhiyunThe watchdog subsystem includes an registration deferral mechanism,
42*4882a593Smuzhiyunwhich allows you to register an watchdog as early as you wish during
43*4882a593Smuzhiyunthe boot process.
44*4882a593Smuzhiyun
45*4882a593SmuzhiyunThe watchdog device structure looks like this::
46*4882a593Smuzhiyun
47*4882a593Smuzhiyun  struct watchdog_device {
48*4882a593Smuzhiyun	int id;
49*4882a593Smuzhiyun	struct device *parent;
50*4882a593Smuzhiyun	const struct attribute_group **groups;
51*4882a593Smuzhiyun	const struct watchdog_info *info;
52*4882a593Smuzhiyun	const struct watchdog_ops *ops;
53*4882a593Smuzhiyun	const struct watchdog_governor *gov;
54*4882a593Smuzhiyun	unsigned int bootstatus;
55*4882a593Smuzhiyun	unsigned int timeout;
56*4882a593Smuzhiyun	unsigned int pretimeout;
57*4882a593Smuzhiyun	unsigned int min_timeout;
58*4882a593Smuzhiyun	unsigned int max_timeout;
59*4882a593Smuzhiyun	unsigned int min_hw_heartbeat_ms;
60*4882a593Smuzhiyun	unsigned int max_hw_heartbeat_ms;
61*4882a593Smuzhiyun	struct notifier_block reboot_nb;
62*4882a593Smuzhiyun	struct notifier_block restart_nb;
63*4882a593Smuzhiyun	void *driver_data;
64*4882a593Smuzhiyun	struct watchdog_core_data *wd_data;
65*4882a593Smuzhiyun	unsigned long status;
66*4882a593Smuzhiyun	struct list_head deferred;
67*4882a593Smuzhiyun  };
68*4882a593Smuzhiyun
69*4882a593SmuzhiyunIt contains following fields:
70*4882a593Smuzhiyun
71*4882a593Smuzhiyun* id: set by watchdog_register_device, id 0 is special. It has both a
72*4882a593Smuzhiyun  /dev/watchdog0 cdev (dynamic major, minor 0) as well as the old
73*4882a593Smuzhiyun  /dev/watchdog miscdev. The id is set automatically when calling
74*4882a593Smuzhiyun  watchdog_register_device.
75*4882a593Smuzhiyun* parent: set this to the parent device (or NULL) before calling
76*4882a593Smuzhiyun  watchdog_register_device.
77*4882a593Smuzhiyun* groups: List of sysfs attribute groups to create when creating the watchdog
78*4882a593Smuzhiyun  device.
79*4882a593Smuzhiyun* info: a pointer to a watchdog_info structure. This structure gives some
80*4882a593Smuzhiyun  additional information about the watchdog timer itself. (Like it's unique name)
81*4882a593Smuzhiyun* ops: a pointer to the list of watchdog operations that the watchdog supports.
82*4882a593Smuzhiyun* gov: a pointer to the assigned watchdog device pretimeout governor or NULL.
83*4882a593Smuzhiyun* timeout: the watchdog timer's timeout value (in seconds).
84*4882a593Smuzhiyun  This is the time after which the system will reboot if user space does
85*4882a593Smuzhiyun  not send a heartbeat request if WDOG_ACTIVE is set.
86*4882a593Smuzhiyun* pretimeout: the watchdog timer's pretimeout value (in seconds).
87*4882a593Smuzhiyun* min_timeout: the watchdog timer's minimum timeout value (in seconds).
88*4882a593Smuzhiyun  If set, the minimum configurable value for 'timeout'.
89*4882a593Smuzhiyun* max_timeout: the watchdog timer's maximum timeout value (in seconds),
90*4882a593Smuzhiyun  as seen from userspace. If set, the maximum configurable value for
91*4882a593Smuzhiyun  'timeout'. Not used if max_hw_heartbeat_ms is non-zero.
92*4882a593Smuzhiyun* min_hw_heartbeat_ms: Hardware limit for minimum time between heartbeats,
93*4882a593Smuzhiyun  in milli-seconds. This value is normally 0; it should only be provided
94*4882a593Smuzhiyun  if the hardware can not tolerate lower intervals between heartbeats.
95*4882a593Smuzhiyun* max_hw_heartbeat_ms: Maximum hardware heartbeat, in milli-seconds.
96*4882a593Smuzhiyun  If set, the infrastructure will send heartbeats to the watchdog driver
97*4882a593Smuzhiyun  if 'timeout' is larger than max_hw_heartbeat_ms, unless WDOG_ACTIVE
98*4882a593Smuzhiyun  is set and userspace failed to send a heartbeat for at least 'timeout'
99*4882a593Smuzhiyun  seconds. max_hw_heartbeat_ms must be set if a driver does not implement
100*4882a593Smuzhiyun  the stop function.
101*4882a593Smuzhiyun* reboot_nb: notifier block that is registered for reboot notifications, for
102*4882a593Smuzhiyun  internal use only. If the driver calls watchdog_stop_on_reboot, watchdog core
103*4882a593Smuzhiyun  will stop the watchdog on such notifications.
104*4882a593Smuzhiyun* restart_nb: notifier block that is registered for machine restart, for
105*4882a593Smuzhiyun  internal use only. If a watchdog is capable of restarting the machine, it
106*4882a593Smuzhiyun  should define ops->restart. Priority can be changed through
107*4882a593Smuzhiyun  watchdog_set_restart_priority.
108*4882a593Smuzhiyun* bootstatus: status of the device after booting (reported with watchdog
109*4882a593Smuzhiyun  WDIOF_* status bits).
110*4882a593Smuzhiyun* driver_data: a pointer to the drivers private data of a watchdog device.
111*4882a593Smuzhiyun  This data should only be accessed via the watchdog_set_drvdata and
112*4882a593Smuzhiyun  watchdog_get_drvdata routines.
113*4882a593Smuzhiyun* wd_data: a pointer to watchdog core internal data.
114*4882a593Smuzhiyun* status: this field contains a number of status bits that give extra
115*4882a593Smuzhiyun  information about the status of the device (Like: is the watchdog timer
116*4882a593Smuzhiyun  running/active, or is the nowayout bit set).
117*4882a593Smuzhiyun* deferred: entry in wtd_deferred_reg_list which is used to
118*4882a593Smuzhiyun  register early initialized watchdogs.
119*4882a593Smuzhiyun
120*4882a593SmuzhiyunThe list of watchdog operations is defined as::
121*4882a593Smuzhiyun
122*4882a593Smuzhiyun  struct watchdog_ops {
123*4882a593Smuzhiyun	struct module *owner;
124*4882a593Smuzhiyun	/* mandatory operations */
125*4882a593Smuzhiyun	int (*start)(struct watchdog_device *);
126*4882a593Smuzhiyun	/* optional operations */
127*4882a593Smuzhiyun	int (*stop)(struct watchdog_device *);
128*4882a593Smuzhiyun	int (*ping)(struct watchdog_device *);
129*4882a593Smuzhiyun	unsigned int (*status)(struct watchdog_device *);
130*4882a593Smuzhiyun	int (*set_timeout)(struct watchdog_device *, unsigned int);
131*4882a593Smuzhiyun	int (*set_pretimeout)(struct watchdog_device *, unsigned int);
132*4882a593Smuzhiyun	unsigned int (*get_timeleft)(struct watchdog_device *);
133*4882a593Smuzhiyun	int (*restart)(struct watchdog_device *);
134*4882a593Smuzhiyun	long (*ioctl)(struct watchdog_device *, unsigned int, unsigned long);
135*4882a593Smuzhiyun  };
136*4882a593Smuzhiyun
137*4882a593SmuzhiyunIt is important that you first define the module owner of the watchdog timer
138*4882a593Smuzhiyundriver's operations. This module owner will be used to lock the module when
139*4882a593Smuzhiyunthe watchdog is active. (This to avoid a system crash when you unload the
140*4882a593Smuzhiyunmodule and /dev/watchdog is still open).
141*4882a593Smuzhiyun
142*4882a593SmuzhiyunSome operations are mandatory and some are optional. The mandatory operations
143*4882a593Smuzhiyunare:
144*4882a593Smuzhiyun
145*4882a593Smuzhiyun* start: this is a pointer to the routine that starts the watchdog timer
146*4882a593Smuzhiyun  device.
147*4882a593Smuzhiyun  The routine needs a pointer to the watchdog timer device structure as a
148*4882a593Smuzhiyun  parameter. It returns zero on success or a negative errno code for failure.
149*4882a593Smuzhiyun
150*4882a593SmuzhiyunNot all watchdog timer hardware supports the same functionality. That's why
151*4882a593Smuzhiyunall other routines/operations are optional. They only need to be provided if
152*4882a593Smuzhiyunthey are supported. These optional routines/operations are:
153*4882a593Smuzhiyun
154*4882a593Smuzhiyun* stop: with this routine the watchdog timer device is being stopped.
155*4882a593Smuzhiyun
156*4882a593Smuzhiyun  The routine needs a pointer to the watchdog timer device structure as a
157*4882a593Smuzhiyun  parameter. It returns zero on success or a negative errno code for failure.
158*4882a593Smuzhiyun  Some watchdog timer hardware can only be started and not be stopped. A
159*4882a593Smuzhiyun  driver supporting such hardware does not have to implement the stop routine.
160*4882a593Smuzhiyun
161*4882a593Smuzhiyun  If a driver has no stop function, the watchdog core will set WDOG_HW_RUNNING
162*4882a593Smuzhiyun  and start calling the driver's keepalive pings function after the watchdog
163*4882a593Smuzhiyun  device is closed.
164*4882a593Smuzhiyun
165*4882a593Smuzhiyun  If a watchdog driver does not implement the stop function, it must set
166*4882a593Smuzhiyun  max_hw_heartbeat_ms.
167*4882a593Smuzhiyun* ping: this is the routine that sends a keepalive ping to the watchdog timer
168*4882a593Smuzhiyun  hardware.
169*4882a593Smuzhiyun
170*4882a593Smuzhiyun  The routine needs a pointer to the watchdog timer device structure as a
171*4882a593Smuzhiyun  parameter. It returns zero on success or a negative errno code for failure.
172*4882a593Smuzhiyun
173*4882a593Smuzhiyun  Most hardware that does not support this as a separate function uses the
174*4882a593Smuzhiyun  start function to restart the watchdog timer hardware. And that's also what
175*4882a593Smuzhiyun  the watchdog timer driver core does: to send a keepalive ping to the watchdog
176*4882a593Smuzhiyun  timer hardware it will either use the ping operation (when available) or the
177*4882a593Smuzhiyun  start operation (when the ping operation is not available).
178*4882a593Smuzhiyun
179*4882a593Smuzhiyun  (Note: the WDIOC_KEEPALIVE ioctl call will only be active when the
180*4882a593Smuzhiyun  WDIOF_KEEPALIVEPING bit has been set in the option field on the watchdog's
181*4882a593Smuzhiyun  info structure).
182*4882a593Smuzhiyun* status: this routine checks the status of the watchdog timer device. The
183*4882a593Smuzhiyun  status of the device is reported with watchdog WDIOF_* status flags/bits.
184*4882a593Smuzhiyun
185*4882a593Smuzhiyun  WDIOF_MAGICCLOSE and WDIOF_KEEPALIVEPING are reported by the watchdog core;
186*4882a593Smuzhiyun  it is not necessary to report those bits from the driver. Also, if no status
187*4882a593Smuzhiyun  function is provided by the driver, the watchdog core reports the status bits
188*4882a593Smuzhiyun  provided in the bootstatus variable of struct watchdog_device.
189*4882a593Smuzhiyun
190*4882a593Smuzhiyun* set_timeout: this routine checks and changes the timeout of the watchdog
191*4882a593Smuzhiyun  timer device. It returns 0 on success, -EINVAL for "parameter out of range"
192*4882a593Smuzhiyun  and -EIO for "could not write value to the watchdog". On success this
193*4882a593Smuzhiyun  routine should set the timeout value of the watchdog_device to the
194*4882a593Smuzhiyun  achieved timeout value (which may be different from the requested one
195*4882a593Smuzhiyun  because the watchdog does not necessarily have a 1 second resolution).
196*4882a593Smuzhiyun
197*4882a593Smuzhiyun  Drivers implementing max_hw_heartbeat_ms set the hardware watchdog heartbeat
198*4882a593Smuzhiyun  to the minimum of timeout and max_hw_heartbeat_ms. Those drivers set the
199*4882a593Smuzhiyun  timeout value of the watchdog_device either to the requested timeout value
200*4882a593Smuzhiyun  (if it is larger than max_hw_heartbeat_ms), or to the achieved timeout value.
201*4882a593Smuzhiyun  (Note: the WDIOF_SETTIMEOUT needs to be set in the options field of the
202*4882a593Smuzhiyun  watchdog's info structure).
203*4882a593Smuzhiyun
204*4882a593Smuzhiyun  If the watchdog driver does not have to perform any action but setting the
205*4882a593Smuzhiyun  watchdog_device.timeout, this callback can be omitted.
206*4882a593Smuzhiyun
207*4882a593Smuzhiyun  If set_timeout is not provided but, WDIOF_SETTIMEOUT is set, the watchdog
208*4882a593Smuzhiyun  infrastructure updates the timeout value of the watchdog_device internally
209*4882a593Smuzhiyun  to the requested value.
210*4882a593Smuzhiyun
211*4882a593Smuzhiyun  If the pretimeout feature is used (WDIOF_PRETIMEOUT), then set_timeout must
212*4882a593Smuzhiyun  also take care of checking if pretimeout is still valid and set up the timer
213*4882a593Smuzhiyun  accordingly. This can't be done in the core without races, so it is the
214*4882a593Smuzhiyun  duty of the driver.
215*4882a593Smuzhiyun* set_pretimeout: this routine checks and changes the pretimeout value of
216*4882a593Smuzhiyun  the watchdog. It is optional because not all watchdogs support pretimeout
217*4882a593Smuzhiyun  notification. The timeout value is not an absolute time, but the number of
218*4882a593Smuzhiyun  seconds before the actual timeout would happen. It returns 0 on success,
219*4882a593Smuzhiyun  -EINVAL for "parameter out of range" and -EIO for "could not write value to
220*4882a593Smuzhiyun  the watchdog". A value of 0 disables pretimeout notification.
221*4882a593Smuzhiyun
222*4882a593Smuzhiyun  (Note: the WDIOF_PRETIMEOUT needs to be set in the options field of the
223*4882a593Smuzhiyun  watchdog's info structure).
224*4882a593Smuzhiyun
225*4882a593Smuzhiyun  If the watchdog driver does not have to perform any action but setting the
226*4882a593Smuzhiyun  watchdog_device.pretimeout, this callback can be omitted. That means if
227*4882a593Smuzhiyun  set_pretimeout is not provided but WDIOF_PRETIMEOUT is set, the watchdog
228*4882a593Smuzhiyun  infrastructure updates the pretimeout value of the watchdog_device internally
229*4882a593Smuzhiyun  to the requested value.
230*4882a593Smuzhiyun
231*4882a593Smuzhiyun* get_timeleft: this routines returns the time that's left before a reset.
232*4882a593Smuzhiyun* restart: this routine restarts the machine. It returns 0 on success or a
233*4882a593Smuzhiyun  negative errno code for failure.
234*4882a593Smuzhiyun* ioctl: if this routine is present then it will be called first before we do
235*4882a593Smuzhiyun  our own internal ioctl call handling. This routine should return -ENOIOCTLCMD
236*4882a593Smuzhiyun  if a command is not supported. The parameters that are passed to the ioctl
237*4882a593Smuzhiyun  call are: watchdog_device, cmd and arg.
238*4882a593Smuzhiyun
239*4882a593SmuzhiyunThe status bits should (preferably) be set with the set_bit and clear_bit alike
240*4882a593Smuzhiyunbit-operations. The status bits that are defined are:
241*4882a593Smuzhiyun
242*4882a593Smuzhiyun* WDOG_ACTIVE: this status bit indicates whether or not a watchdog timer device
243*4882a593Smuzhiyun  is active or not from user perspective. User space is expected to send
244*4882a593Smuzhiyun  heartbeat requests to the driver while this flag is set.
245*4882a593Smuzhiyun* WDOG_NO_WAY_OUT: this bit stores the nowayout setting for the watchdog.
246*4882a593Smuzhiyun  If this bit is set then the watchdog timer will not be able to stop.
247*4882a593Smuzhiyun* WDOG_HW_RUNNING: Set by the watchdog driver if the hardware watchdog is
248*4882a593Smuzhiyun  running. The bit must be set if the watchdog timer hardware can not be
249*4882a593Smuzhiyun  stopped. The bit may also be set if the watchdog timer is running after
250*4882a593Smuzhiyun  booting, before the watchdog device is opened. If set, the watchdog
251*4882a593Smuzhiyun  infrastructure will send keepalives to the watchdog hardware while
252*4882a593Smuzhiyun  WDOG_ACTIVE is not set.
253*4882a593Smuzhiyun  Note: when you register the watchdog timer device with this bit set,
254*4882a593Smuzhiyun  then opening /dev/watchdog will skip the start operation but send a keepalive
255*4882a593Smuzhiyun  request instead.
256*4882a593Smuzhiyun
257*4882a593Smuzhiyun  To set the WDOG_NO_WAY_OUT status bit (before registering your watchdog
258*4882a593Smuzhiyun  timer device) you can either:
259*4882a593Smuzhiyun
260*4882a593Smuzhiyun  * set it statically in your watchdog_device struct with
261*4882a593Smuzhiyun
262*4882a593Smuzhiyun	.status = WATCHDOG_NOWAYOUT_INIT_STATUS,
263*4882a593Smuzhiyun
264*4882a593Smuzhiyun    (this will set the value the same as CONFIG_WATCHDOG_NOWAYOUT) or
265*4882a593Smuzhiyun  * use the following helper function::
266*4882a593Smuzhiyun
267*4882a593Smuzhiyun	static inline void watchdog_set_nowayout(struct watchdog_device *wdd,
268*4882a593Smuzhiyun						 int nowayout)
269*4882a593Smuzhiyun
270*4882a593SmuzhiyunNote:
271*4882a593Smuzhiyun   The WatchDog Timer Driver Core supports the magic close feature and
272*4882a593Smuzhiyun   the nowayout feature. To use the magic close feature you must set the
273*4882a593Smuzhiyun   WDIOF_MAGICCLOSE bit in the options field of the watchdog's info structure.
274*4882a593Smuzhiyun
275*4882a593SmuzhiyunThe nowayout feature will overrule the magic close feature.
276*4882a593Smuzhiyun
277*4882a593SmuzhiyunTo get or set driver specific data the following two helper functions should be
278*4882a593Smuzhiyunused::
279*4882a593Smuzhiyun
280*4882a593Smuzhiyun  static inline void watchdog_set_drvdata(struct watchdog_device *wdd,
281*4882a593Smuzhiyun					  void *data)
282*4882a593Smuzhiyun  static inline void *watchdog_get_drvdata(struct watchdog_device *wdd)
283*4882a593Smuzhiyun
284*4882a593SmuzhiyunThe watchdog_set_drvdata function allows you to add driver specific data. The
285*4882a593Smuzhiyunarguments of this function are the watchdog device where you want to add the
286*4882a593Smuzhiyundriver specific data to and a pointer to the data itself.
287*4882a593Smuzhiyun
288*4882a593SmuzhiyunThe watchdog_get_drvdata function allows you to retrieve driver specific data.
289*4882a593SmuzhiyunThe argument of this function is the watchdog device where you want to retrieve
290*4882a593Smuzhiyundata from. The function returns the pointer to the driver specific data.
291*4882a593Smuzhiyun
292*4882a593SmuzhiyunTo initialize the timeout field, the following function can be used::
293*4882a593Smuzhiyun
294*4882a593Smuzhiyun  extern int watchdog_init_timeout(struct watchdog_device *wdd,
295*4882a593Smuzhiyun                                   unsigned int timeout_parm,
296*4882a593Smuzhiyun                                   struct device *dev);
297*4882a593Smuzhiyun
298*4882a593SmuzhiyunThe watchdog_init_timeout function allows you to initialize the timeout field
299*4882a593Smuzhiyunusing the module timeout parameter or by retrieving the timeout-sec property from
300*4882a593Smuzhiyunthe device tree (if the module timeout parameter is invalid). Best practice is
301*4882a593Smuzhiyunto set the default timeout value as timeout value in the watchdog_device and
302*4882a593Smuzhiyunthen use this function to set the user "preferred" timeout value.
303*4882a593SmuzhiyunThis routine returns zero on success and a negative errno code for failure.
304*4882a593Smuzhiyun
305*4882a593SmuzhiyunTo disable the watchdog on reboot, the user must call the following helper::
306*4882a593Smuzhiyun
307*4882a593Smuzhiyun  static inline void watchdog_stop_on_reboot(struct watchdog_device *wdd);
308*4882a593Smuzhiyun
309*4882a593SmuzhiyunTo disable the watchdog when unregistering the watchdog, the user must call
310*4882a593Smuzhiyunthe following helper. Note that this will only stop the watchdog if the
311*4882a593Smuzhiyunnowayout flag is not set.
312*4882a593Smuzhiyun
313*4882a593Smuzhiyun::
314*4882a593Smuzhiyun
315*4882a593Smuzhiyun  static inline void watchdog_stop_on_unregister(struct watchdog_device *wdd);
316*4882a593Smuzhiyun
317*4882a593SmuzhiyunTo change the priority of the restart handler the following helper should be
318*4882a593Smuzhiyunused::
319*4882a593Smuzhiyun
320*4882a593Smuzhiyun  void watchdog_set_restart_priority(struct watchdog_device *wdd, int priority);
321*4882a593Smuzhiyun
322*4882a593SmuzhiyunUser should follow the following guidelines for setting the priority:
323*4882a593Smuzhiyun
324*4882a593Smuzhiyun* 0: should be called in last resort, has limited restart capabilities
325*4882a593Smuzhiyun* 128: default restart handler, use if no other handler is expected to be
326*4882a593Smuzhiyun  available, and/or if restart is sufficient to restart the entire system
327*4882a593Smuzhiyun* 255: highest priority, will preempt all other restart handlers
328*4882a593Smuzhiyun
329*4882a593SmuzhiyunTo raise a pretimeout notification, the following function should be used::
330*4882a593Smuzhiyun
331*4882a593Smuzhiyun  void watchdog_notify_pretimeout(struct watchdog_device *wdd)
332*4882a593Smuzhiyun
333*4882a593SmuzhiyunThe function can be called in the interrupt context. If watchdog pretimeout
334*4882a593Smuzhiyungovernor framework (kbuild CONFIG_WATCHDOG_PRETIMEOUT_GOV symbol) is enabled,
335*4882a593Smuzhiyunan action is taken by a preconfigured pretimeout governor preassigned to
336*4882a593Smuzhiyunthe watchdog device. If watchdog pretimeout governor framework is not
337*4882a593Smuzhiyunenabled, watchdog_notify_pretimeout() prints a notification message to
338*4882a593Smuzhiyunthe kernel log buffer.
339*4882a593Smuzhiyun
340*4882a593SmuzhiyunTo set the last known HW keepalive time for a watchdog, the following function
341*4882a593Smuzhiyunshould be used::
342*4882a593Smuzhiyun
343*4882a593Smuzhiyun  int watchdog_set_last_hw_keepalive(struct watchdog_device *wdd,
344*4882a593Smuzhiyun                                     unsigned int last_ping_ms)
345*4882a593Smuzhiyun
346*4882a593SmuzhiyunThis function must be called immediately after watchdog registration. It
347*4882a593Smuzhiyunsets the last known hardware heartbeat to have happened last_ping_ms before
348*4882a593Smuzhiyuncurrent time. Calling this is only needed if the watchdog is already running
349*4882a593Smuzhiyunwhen probe is called, and the watchdog can only be pinged after the
350*4882a593Smuzhiyunmin_hw_heartbeat_ms time has passed from the last ping.
351