[PATCH 36] LEON3: GPTIMER timer watchdog driver

Joel Sherrill joel.sherrill at OARcorp.com
Wed Apr 18 16:35:36 UTC 2012


On 04/18/2012 10:53 AM, Joel Sherrill wrote:
>
> + Looks like tabs on indentation in the new C file
>
> + 2011 date
>
> + You are proposing new bsp_watchdog methods. I am
> not opposed to them but they shouldn't go in your bsp.h.
> It would be better to add this as a possible API for all BSPs.
> This would have to be reconciled with the following existing
> code in the tree:
>
> ./cpukit/libcsupport/include/rtems/watchdogdrv.h
> ./c/src/lib/libcpu/powerpc/mpc55xx/include/watchdog.h
> ./c/src/lib/libbsp/powerpc/mpc55xxevb/startup/start-watchdog.c
>
> And I did some work on a prototype which never got the
> attention it deserved. Chris and I discussed this as a libchip
> framework where you could have multiple reset watchdogs
> for different pieces of hardware.
>
> I prototyped a simple one based upon a test fixture reset
> driver and a some code for the Intel ich4 chipset watchdog.
> Longer term, we envisioned a library of watchdog management
> code which helped the application. Say reset from timer or
> a special task.
http://www.rtems.org/ftp/pub/rtems/people/joel/watchdog/
> I would like to take this as an opportunity to discuss this
> all again and get on the right path long term. Your
> "bsp_watchdog_xxx" could be the names for the
> main board reset and the framework could be
> layered on top of it.
>
> You seem to be the lucky guy who asks the questions which
> need to be answered. :)
>
> On 04/18/2012 10:19 AM, Daniel Hellstrom wrote:
>> Last timer instance of GPTIMER is sometimes a watchdog timer that
>> can reset the system on timer underflow.
>>
>> Signed-off-by: Daniel Hellstrom<daniel at gaisler.com>
>> ---
>>    c/src/lib/libbsp/sparc/leon3/Makefile.am      |    1 +
>>    c/src/lib/libbsp/sparc/leon3/include/bsp.h    |   25 +++++++
>>    c/src/lib/libbsp/sparc/leon3/timer/watchdog.c |   89 +++++++++++++++++++++++++
>>    3 files changed, 115 insertions(+), 0 deletions(-)
>>    create mode 100644 c/src/lib/libbsp/sparc/leon3/timer/watchdog.c
>>
>> diff --git a/c/src/lib/libbsp/sparc/leon3/Makefile.am b/c/src/lib/libbsp/sparc/leon3/Makefile.am
>> index cc25993..9b8af4b 100644
>> --- a/c/src/lib/libbsp/sparc/leon3/Makefile.am
>> +++ b/c/src/lib/libbsp/sparc/leon3/Makefile.am
>> @@ -115,6 +115,7 @@ libbsp_a_SOURCES += ../../sparc/shared/i2c/i2cmst.c
>>
>>    # timer
>>    libbsp_a_SOURCES += timer/timer.c
>> +libbsp_a_SOURCES += timer/watchdog.c
>>
>>    if HAS_SMP
>>    libbsp_a_SOURCES += smp/getcpuid.c
>> diff --git a/c/src/lib/libbsp/sparc/leon3/include/bsp.h b/c/src/lib/libbsp/sparc/leon3/include/bsp.h
>> index d883064..32407dd 100644
>> --- a/c/src/lib/libbsp/sparc/leon3/include/bsp.h
>> +++ b/c/src/lib/libbsp/sparc/leon3/include/bsp.h
>> @@ -192,6 +192,31 @@ extern void BSP_shared_interrupt_unmask(int irq);
>>     */
>>    extern void BSP_shared_interrupt_mask(int irq);
>>
>> +/* Initialize BSP watchdog routines. Returns number of watchdog timers found.
>> + * Currently only one is supported.
>> + */
>> +extern int bsp_watchdog_init(void);
>> +
>> +/* Reload watchdog (last timer on the first GPTIMER core), all systems does not
>> + * feature a watchdog, it is expected that if this function is called the
>> + * user knows that there is a watchdog available.
>> + *
>> + * The prescaler is normally set to number of MHz of system, this is to
>> + * make the system clock tick be stable.
>> + *
>> + * Arguments
>> + *  watchdog       - Always 0 for now
>> + *  reload_value   - Number of timer clocks (after prescaler) to count before
>> + *                   watchdog is woken.
>> + */
>> +extern void bsp_watchdog_reload(int watchdog, unsigned int reload_value);
>> +
>> +/* Stop watchdog timer */
>> +extern void bsp_watchdog_stop(int watchdog);
>> +
>> +/* Use watchdog0 timer to reset the system */
>> +extern void bsp_watchdog_system_reset(void);
>> +
>>    #ifdef __cplusplus
>>    }
>>    #endif
>> diff --git a/c/src/lib/libbsp/sparc/leon3/timer/watchdog.c b/c/src/lib/libbsp/sparc/leon3/timer/watchdog.c
>> new file mode 100644
>> index 0000000..d3a9c15
>> --- /dev/null
>> +++ b/c/src/lib/libbsp/sparc/leon3/timer/watchdog.c
>> @@ -0,0 +1,89 @@
>> +/*  GPTIMER Watchdog timer routines. On some systems the first GPTIMER
>> + *  core's last Timer instance underflow signal is connected to system
>> + *  reset.
>> + *
>> + *  COPYRIGHT (c) 2011
>> + *  Aeroflex Gaisler
>> + *
>> + *  The license and distribution terms for this file may be
>> + *  found in the file LICENSE in this distribution or at
>> + *  http://www.rtems.com/license/LICENSE.
>> + */
>> +
>> +#include<bsp.h>
>> +#include<grlib.h>
>> +
>> +extern volatile struct gptimer_regs *LEON3_Timer_Regs;
>> +
>> +struct gptimer_watchdog_priv {
>> +	struct gptimer_regs *regs;
>> +	struct gptimer_timer_regs *timer;
>> +	int timerno;
>> +};
>> +
>> +struct gptimer_watchdog_priv bsp_watchdogs[1];
>> +int bsp_watchdog_count = 0;
>> +
>> +int bsp_watchdog_init(void)
>> +{
>> +	int timercnt;
>> +
>> +	if (!LEON3_Timer_Regs)
>> +		return 0;
>> +
>> +	/* Get Watchdogs in system, this is implemented for one GPTIMER core
>> +	 * only.
>> +	 *
>> +	 * First watchdog is a special case, we can get the first timer core by
>> +	 * looking at LEON3_Timer_Regs, the watchdog within a timer core is
>> +	 * always the last timer. Unfortunately we can not know it the watchdog
>> +	 * functionality is available or not, we assume that it is if we
>> +	 * reached this function.
>> +	 */
>> +	bsp_watchdogs[0].regs = (struct gptimer_regs *)LEON3_Timer_Regs;
>> +
>> +	/* Find Timer that has watchdog functionality */
>> +	timercnt = bsp_watchdogs[0].regs->cfg&   0x7;
>> +	if (timercnt<   2) /* First timer system clock timer */
>> +		return 0;
>> +
>> +	bsp_watchdogs[0].timerno = timercnt - 1;
>> +	bsp_watchdogs[0].timer =&bsp_watchdogs[0].regs->timer[bsp_watchdogs[0].timerno];
>> +
>> +	bsp_watchdog_count = 1;
>> +	return bsp_watchdog_count;
>> +}
>> +
>> +void bsp_watchdog_reload(int watchdog, unsigned int reload_value)
>> +{
>> +	if (bsp_watchdog_count == 0)
>> +		bsp_watchdog_init();
>> +
>> +	if (bsp_watchdog_count<= watchdog)
>> +		return;
>> +
>> +	/* Kick watchdog, and clear interrupt pending bit */
>> +	bsp_watchdogs[watchdog].timer->reload = reload_value;
>> +	bsp_watchdogs[watchdog].timer->ctrl =
>> +		(LEON3_GPTIMER_LD | LEON3_GPTIMER_EN) |
>> +		(bsp_watchdogs[watchdog].timer->ctrl&   ~(1<<4));
>> +}
>> +
>> +void bsp_watchdog_stop(int watchdog)
>> +{
>> +	if (bsp_watchdog_count == 0)
>> +		bsp_watchdog_init();
>> +
>> +	if (bsp_watchdog_count<= watchdog)
>> +		return;
>> +
>> +	/* Stop watchdog timer */
>> +	bsp_watchdogs[watchdog].timer->ctrl = 0;
>> +}
>> +
>> +/* Use watchdog timer to reset system */
>> +void bsp_watchdog_system_reset(void)
>> +{
>> +	sparc_disable_interrupts();
>> +	bsp_watchdog_reload(0, 1);
>> +}
>


-- 
Joel Sherrill, Ph.D.             Director of Research&   Development
joel.sherrill at OARcorp.com        On-Line Applications Research
Ask me about RTEMS: a free RTOS  Huntsville AL 35805
     Support Available             (256) 722-9985


-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.rtems.org/pipermail/devel/attachments/20120418/fa68e8cc/attachment.html>


More information about the devel mailing list