Generic udelay() with watchdog support
[pandora-u-boot.git] / cpu / ixp / timer.c
index 920f34e..edf341f 100644 (file)
 #include <common.h>
 #include <asm/arch/ixp425.h>
 
-#ifndef CONFIG_USE_IRQ
+#ifdef CONFIG_TIMER_IRQ
+
+#define FREQ           66666666
+#define CLOCK_TICK_RATE        (((FREQ / CONFIG_SYS_HZ & ~IXP425_OST_RELOAD_MASK) + 1) * CONFIG_SYS_HZ)
+#define LATCH          ((CLOCK_TICK_RATE + CONFIG_SYS_HZ/2) / CONFIG_SYS_HZ)   /* For divider */
+
+/*
+ * When interrupts are enabled, use timer 2 for time/delay generation...
+ */
+
+static volatile ulong timestamp;
+
+static void timer_isr(void *data)
+{
+       unsigned int *pTime = (unsigned int *)data;
+
+       (*pTime)++;
+
+       /*
+        * Reset IRQ source
+        */
+       *IXP425_OSST = IXP425_OSST_TIMER_2_PEND;
+}
+
+ulong get_timer (ulong base)
+{
+       return timestamp - base;
+}
+
+void reset_timer (void)
+{
+       timestamp = 0;
+}
+
+int timer_init (void)
+{
+       /* install interrupt handler for timer */
+       irq_install_handler(IXP425_TIMER_2_IRQ, timer_isr, (void *)&timestamp);
+
+       /* setup the Timer counter value */
+       *IXP425_OSRT2 = (LATCH & ~IXP425_OST_RELOAD_MASK) | IXP425_OST_ENABLE;
+
+       /* enable timer irq */
+       *IXP425_ICMR = (1 << IXP425_TIMER_2_IRQ);
+
+       return 0;
+}
+#else
 ulong get_timer (ulong base)
 {
        return get_timer_masked () - base;
@@ -44,7 +91,7 @@ void ixp425_udelay(unsigned long usec)
         * This function has a max usec, but since it is called from udelay
         * we should not have to worry... be happy
         */
-       unsigned long usecs = CFG_HZ/1000000L & ~IXP425_OST_RELOAD_MASK;
+       unsigned long usecs = CONFIG_SYS_HZ/1000000L & ~IXP425_OST_RELOAD_MASK;
 
        *IXP425_OSST = IXP425_OSST_TIMER_1_PEND;
        usecs |= IXP425_OST_ONE_SHOT | IXP425_OST_ENABLE;
@@ -52,7 +99,7 @@ void ixp425_udelay(unsigned long usec)
        while (!(*IXP425_OSST & IXP425_OSST_TIMER_1_PEND));
 }
 
-void udelay (unsigned long usec)
+void __udelay (unsigned long usec)
 {
        while (usec--) ixp425_udelay(1);
 }
@@ -80,4 +127,9 @@ ulong get_timer_masked (void)
        }
        return (reload_constant - current);
 }
-#endif /* #ifndef CONFIG_USE_IRQ */
+
+int timer_init(void)
+{
+       return 0;
+}
+#endif