Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/sys/arch/hpcmips Implement TX3912/22 clock/timer module.



details:   https://anonhg.NetBSD.org/src/rev/e1492314caf5
branches:  trunk
changeset: 479824:e1492314caf5
user:      uch <uch%NetBSD.org@localhost>
date:      Wed Dec 22 15:35:33 1999 +0000

description:
Implement TX3912/22 clock/timer module.

diffstat:

 sys/arch/hpcmips/hpcmips/clock.c   |    9 +-
 sys/arch/hpcmips/tx/tx39.c         |   22 ++-
 sys/arch/hpcmips/tx/tx39clock.c    |  249 ++++++++++++++++++++++++++++--------
 sys/arch/hpcmips/tx/tx39icu.c      |   12 +-
 sys/arch/hpcmips/tx/tx39timerreg.h |   32 +++-
 sys/arch/hpcmips/tx/tx39var.h      |   14 +-
 6 files changed, 255 insertions(+), 83 deletions(-)

diffs (truncated from 627 to 300 lines):

diff -r 60fc37d77930 -r e1492314caf5 sys/arch/hpcmips/hpcmips/clock.c
--- a/sys/arch/hpcmips/hpcmips/clock.c  Wed Dec 22 14:55:49 1999 +0000
+++ b/sys/arch/hpcmips/hpcmips/clock.c  Wed Dec 22 15:35:33 1999 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: clock.c,v 1.4 1999/12/08 15:57:12 uch Exp $ */
+/* $NetBSD: clock.c,v 1.5 1999/12/22 15:35:33 uch Exp $ */
 
 /*
  * Copyright (c) 1988 University of Utah.
@@ -41,10 +41,11 @@
  *
  *     @(#)clock.c     8.1 (Berkeley) 6/10/93
  */
+#include "opt_tx39xx.h"
 
 #include <sys/cdefs.h>                 /* RCS ID & Copyright macro defns */
 
-__KERNEL_RCSID(0, "$NetBSD: clock.c,v 1.4 1999/12/08 15:57:12 uch Exp $");
+__KERNEL_RCSID(0, "$NetBSD: clock.c,v 1.5 1999/12/22 15:35:33 uch Exp $");
 
 #include <sys/param.h>
 #include <sys/kernel.h>
@@ -127,7 +128,7 @@
 {
        if (clockfns == NULL)
                panic("cpu_initclocks: no clock attached");
-
+#ifndef TX39XX /* TX3912/22 periodic timer is not 256Hz */
        hz = CLOCK_RATE;        /* 256 Hz clock */
        tick = 1000000 / hz;    /* number of microseconds between interrupts */
        tickfix = 1000000 - (hz * tick);
@@ -138,7 +139,7 @@
                tickfix >>= (ftp - 1);
                tickfixinterval = hz >> (ftp - 1);
         }
-
+#endif /* !TX39XX */
 #ifdef alpha
        /*
         * Establish the clock interrupt; it's a special case.
diff -r 60fc37d77930 -r e1492314caf5 sys/arch/hpcmips/tx/tx39.c
--- a/sys/arch/hpcmips/tx/tx39.c        Wed Dec 22 14:55:49 1999 +0000
+++ b/sys/arch/hpcmips/tx/tx39.c        Wed Dec 22 15:35:33 1999 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: tx39.c,v 1.7 1999/12/12 18:40:33 uch Exp $ */
+/*     $NetBSD: tx39.c,v 1.8 1999/12/22 15:35:35 uch Exp $ */
 
 /*
  * Copyright (c) 1999, by UCHIYAMA Yasushi
@@ -84,6 +84,7 @@
 void   tx_init __P((void));
 int    tx39icu_intr __P((u_int32_t, u_int32_t, u_int32_t, u_int32_t));
 int    tx39_find_dram __P((u_int32_t, u_int32_t));
+void   tx39clock_cpuspeed __P((int*, int*));
 
 /* TX39-specific initialization vector */
 void   tx_os_init __P((void));
@@ -101,6 +102,7 @@
 {
        tx_chipset_tag_t tc;
        int model, rev;
+       int cpuclock;
        
        tc = tx_conf_get_tag();
        /*
@@ -123,14 +125,18 @@
                        cpu_id.cpu.cp_majrev, cpu_id.cpu.cp_minrev);
                break;
        case TMPR3912:
-               sprintf(cpu_model, "TOSHIBA TMPR3912");
-               cpuspeed = 50; /* XXX Should calibrate XXX */
+               tx39clock_cpuspeed(&cpuclock, &cpuspeed);
+
+               sprintf(cpu_model, "TOSHIBA TMPR3912 %d.%02d MHz",
+                       cpuclock / 1000000, (cpuclock % 1000000) / 10000);
                break;
        case TMPR3922:
+               tx39clock_cpuspeed(&cpuclock, &cpuspeed);
                rev = tx_conf_read(tc, TX3922_REVISION_REG);
-               sprintf(cpu_model, "TOSHIBA TMPR3922 rev. %x.%x",
-                       (rev >> 4) & 0xf, rev & 0xf);
-               cpuspeed = 100; /* XXX Should calibrate XXX */
+
+               sprintf(cpu_model, "TOSHIBA TMPR3922 rev. %x.%x "
+                       "%d.%02d MHz", (rev >> 4) & 0xf, rev & 0xf, 
+                       cpuclock / 1000000, (cpuclock % 1000000) / 10000);
                break;
        }
 }
@@ -343,7 +349,7 @@
        tx_chipset_tag_t t;
        int reg;
 {
-       return *((txreg_t*)(TX39_SYSADDR_CONFIG_REG_KSEG1 + reg));
+       return *((volatile txreg_t*)(TX39_SYSADDR_CONFIG_REG_KSEG1 + reg));
 }
 
 void
@@ -352,7 +358,7 @@
        int reg;
        txreg_t val;
 {
-       *((txreg_t*)(TX39_SYSADDR_CONFIG_REG_KSEG1 + reg)) = val;
+       *((volatile txreg_t*)(TX39_SYSADDR_CONFIG_REG_KSEG1 + reg)) = val;
 }
 #endif /* TX39_PREFER_FUNCTION */
 
diff -r 60fc37d77930 -r e1492314caf5 sys/arch/hpcmips/tx/tx39clock.c
--- a/sys/arch/hpcmips/tx/tx39clock.c   Wed Dec 22 14:55:49 1999 +0000
+++ b/sys/arch/hpcmips/tx/tx39clock.c   Wed Dec 22 15:35:33 1999 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: tx39clock.c,v 1.2 1999/12/07 17:08:10 uch Exp $ */
+/*     $NetBSD: tx39clock.c,v 1.3 1999/12/22 15:35:35 uch Exp $ */
 
 /*
  * Copyright (c) 1999, by UCHIYAMA Yasushi
@@ -28,40 +28,63 @@
 #include "opt_tx39_debug.h"
 
 #include <sys/param.h>
+#include <sys/kernel.h>
 #include <sys/systm.h>
 #include <sys/device.h>
 
+#include <dev/clock_subr.h>
+
 #include <machine/bus.h>
 #include <machine/clock_machdep.h>
 #include <machine/cpu.h>
 
 #include <hpcmips/tx/tx39var.h>
-#include <hpcmips/tx/tx39icureg.h> /* XXX */
+#include <hpcmips/tx/tx39icureg.h>
 #include <hpcmips/tx/tx39clockreg.h>
 #include <hpcmips/tx/tx39timerreg.h>
+
 #include <dev/dec/clockvar.h>
 
+#ifdef TX39CLKDEBUG
+#define        DPRINTF(arg) printf arg
+#else
+#define        DPRINTF(arg)
+#endif
+
 #define ISSETPRINT(r, m) __is_set_print(r, TX39_CLOCK_EN##m##CLK, #m)
 
-void   clock_init __P((struct device*));
-void   clock_get __P((struct device*, time_t, struct clocktime*));
-void   clock_set __P((struct device*, struct clocktime*));
+void   tx39clock_init __P((struct device*));
+void   tx39clock_get __P((struct device*, time_t, struct clocktime*));
+void   tx39clock_set __P((struct device*, struct clocktime*));
+
+const struct clockfns tx39clockfns = {
+       tx39clock_init, tx39clock_get, tx39clock_set,
+};
 
-static const struct clockfns clockfns = {
-       clock_init, clock_get, clock_set,
+struct txtime {
+       u_int32_t t_hi;
+       u_int32_t t_lo;
+};
+
+struct tx39clock_softc {
+       struct  device sc_dev;
+       tx_chipset_tag_t sc_tc;
+
+       int sc_enabled;
+       int sc_year;
+       struct clocktime sc_epoch;
 };
 
 int    tx39clock_match __P((struct device*, struct cfdata*, void*));
 void   tx39clock_attach __P((struct device*, struct device*, void*));
 void   tx39clock_dump __P((tx_chipset_tag_t));
 
-void   tx39timer_freeze __P((tx_chipset_tag_t));
-void   tx39timer_rtcreset __P((tx_chipset_tag_t));
+void   tx39clock_cpuspeed __P((int*, int*));
 
-struct tx39clock_softc {
-       struct  device sc_dev;
-       tx_chipset_tag_t sc_tc;
-};
+void   __tx39timer_rtcfreeze __P((tx_chipset_tag_t));
+void   __tx39timer_rtcreset __P((tx_chipset_tag_t));
+__inline void  __tx39timer_rtcget __P((struct txtime*));
+__inline time_t        __tx39timer_rtc2sec __P((struct txtime*));
 
 struct cfattach tx39clock_ca = {
        sizeof(struct tx39clock_softc), tx39clock_match, tx39clock_attach
@@ -89,112 +112,225 @@
 
        tc = sc->sc_tc = ta->ta_tc;
 
-       /* 
-        *      Enable periodic timer 
-        *       but interrupt don't arise yet. see clock_init().
-        */
+       /* Reset timer module */
+       tx_conf_write(tc, TX39_TIMERCONTROL_REG, 0);
+
+       /* Enable periodic timer */
        reg = tx_conf_read(tc, TX39_TIMERCONTROL_REG);
        reg |= TX39_TIMERCONTROL_ENPERTIMER;
        tx_conf_write(tc, TX39_TIMERCONTROL_REG, reg);
-       
-       /* Set counter */
-#if 0
-       {
-               int cnt = 0xffff; /* XXX the most slower. */
-               reg = tx_conf_read(tc, TX39_TIMERPERIODIC_REG);
-               reg = TX39_TIMERPERIODIC_PERVAL_SET(reg, cnt);
-               tx_conf_write(tc, TX39_TIMERPERIODIC_REG, reg);
-       }
-#endif
-       clockattach(self, &clockfns);   
+
+       sc->sc_enabled = 0;
+       /* 
+        * RTC and ALARM 
+        *    RTCINT    ... INTR5 bit 31  (roll over)
+        *    ALARMINT  ... INTR5 bit 30
+        *    PERINT    ... INTR5 bit 29
+        */
+
+       clockattach(self, &tx39clockfns);       
 
 #ifdef TX39CLKDEBUG
        tx39clock_dump(tc);
 #endif /* TX39CLKDEBUG */
 }
 
-/* 
- * RTC and ALARM 
- *    RTCINT    ... INTR5 bit 31  (roll over)
- *    ALARMINT  ... INTR5 bit 30
- *    PERINT    ... INTR5 bit 29
+/*
+ * cpuclock ... CPU clock (Hz)
+ * cpuspeed ... instructions-per-microsecond
  */
 void
-tx39timer_freeze(tc)
+tx39clock_cpuspeed(cpuclock, cpuspeed)
+       int *cpuclock;
+       int *cpuspeed;
+{
+       struct txtime t0, t1;
+       int elapsed;
+       
+       __tx39timer_rtcget(&t0);
+       __asm __volatile("
+               .set    noreorder;
+               li      $8, 10000000;
+       1:      nop;
+               nop;
+               nop;
+               nop;
+               nop;
+               nop;
+               nop;
+               add     $8, $8, -1;
+               bnez    $8, 1b;
+               nop;
+               .set    reorder;
+       ");
+       __tx39timer_rtcget(&t1);
+
+       elapsed = t1.t_lo - t0.t_lo;
+
+       *cpuclock = (100000000 / elapsed) * TX39_RTCLOCK;
+       *cpuspeed = *cpuclock / 1000000;
+
+}
+
+void
+__tx39timer_rtcfreeze(tc)
        tx_chipset_tag_t tc;
 {
        txreg_t reg;    
 
        reg = tx_conf_read(tc, TX39_TIMERCONTROL_REG);
+
        /* Freeze RTC */
        reg |= TX39_TIMERCONTROL_FREEZEPRE; /* Upper 8bit */
        reg |= TX39_TIMERCONTROL_FREEZERTC; /* Lower 32bit */
+
        /* Freeze periodic timer */
        reg |= TX39_TIMERCONTROL_FREEZETIMER;
        reg &= ~TX39_TIMERCONTROL_ENPERTIMER;
        tx_conf_write(tc, TX39_TIMERCONTROL_REG, reg);
 }
 
+__inline time_t
+__tx39timer_rtc2sec(t)
+       struct txtime *t;
+{
+       /* This rely on RTC is 32.768kHz */



Home | Main Index | Thread Index | Old Index