Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/sys/arch/sparc64 use system tick timer instead of %tick on U...
details: https://anonhg.NetBSD.org/src/rev/7d40ec171f80
branches: trunk
changeset: 782585:7d40ec171f80
user: macallan <macallan%NetBSD.org@localhost>
date: Thu Nov 08 00:34:37 2012 +0000
description:
use system tick timer instead of %tick on UltraSPARC-III-ish CPUs
review & fixes by Takeshi Nakayama
diffstat:
sys/arch/sparc64/include/cpu.h | 11 +++-
sys/arch/sparc64/include/ctlreg.h | 5 +-
sys/arch/sparc64/include/psl.h | 3 +-
sys/arch/sparc64/sparc64/clock.c | 96 ++++++++++++++++++++++++++++++++++----
sys/arch/sparc64/sparc64/cpu.c | 27 ++++++++--
sys/arch/sparc64/sparc64/locore.s | 82 +++++++++++++++++++++++++++++++-
6 files changed, 199 insertions(+), 25 deletions(-)
diffs (truncated from 449 to 300 lines):
diff -r 18964251c403 -r 7d40ec171f80 sys/arch/sparc64/include/cpu.h
--- a/sys/arch/sparc64/include/cpu.h Wed Nov 07 17:14:02 2012 +0000
+++ b/sys/arch/sparc64/include/cpu.h Thu Nov 08 00:34:37 2012 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: cpu.h,v 1.98 2011/07/30 19:29:12 martin Exp $ */
+/* $NetBSD: cpu.h,v 1.99 2012/11/08 00:34:37 macallan Exp $ */
/*
* Copyright (c) 1992, 1993
@@ -128,7 +128,8 @@
/* %tick and cpu frequency information */
u_long ci_tick_increment;
- uint64_t ci_cpu_clockrate[2];
+ uint64_t ci_cpu_clockrate[2]; /* %tick */
+ uint64_t ci_system_clockrate[2]; /* %stick */
/* Interrupts */
struct intrhand *ci_intrpending[16];
@@ -351,10 +352,12 @@
/* clock.c */
struct timeval;
int tickintr(void *); /* level 10/14 (tick) interrupt code */
+int stickintr(void *); /* system tick interrupt code */
int clockintr(void *); /* level 10 (clock) interrupt code */
int statintr(void *); /* level 14 (statclock) interrupt code */
int schedintr(void *); /* level 10 (schedclock) interrupt code */
void tickintr_establish(int, int (*)(void *));
+void stickintr_establish(int, int (*)(void *));
/* locore.s */
struct fpstate64;
void savefpstate(struct fpstate64 *);
@@ -372,6 +375,10 @@
void switchtoctx_us(int);
void switchtoctx_usiii(int);
void next_tick(long);
+void next_stick(long);
+void setstick(long);
+long getstick(void);
+
/* trap.c */
void cpu_vmspace_exec(struct lwp *, vaddr_t, vaddr_t);
int rwindow_save(struct lwp *);
diff -r 18964251c403 -r 7d40ec171f80 sys/arch/sparc64/include/ctlreg.h
--- a/sys/arch/sparc64/include/ctlreg.h Wed Nov 07 17:14:02 2012 +0000
+++ b/sys/arch/sparc64/include/ctlreg.h Thu Nov 08 00:34:37 2012 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: ctlreg.h,v 1.56 2011/10/08 08:49:07 nakayama Exp $ */
+/* $NetBSD: ctlreg.h,v 1.57 2012/11/08 00:34:37 macallan Exp $ */
/*
* Copyright (c) 1996-2002 Eduardo Horvath
@@ -415,6 +415,8 @@
#define CLEAR_SOFTINT %asr21 /* Clears these bits */
#define SOFTINT %asr22 /* Reads the register */
#define TICK_CMPR %asr23
+#define STICK %asr24
+#define STICK_CMPR %asr25
#define TICK_INT 0x01 /* level-14 clock tick */
#define SOFTINT1 (0x1<<1)
@@ -432,6 +434,7 @@
#define SOFTINT13 (0x1<<13)
#define SOFTINT14 (0x1<<14)
#define SOFTINT15 (0x1<<15)
+#define STICK_INTR (0x1<<16) /* system tick */
/* Interrupt Dispatch -- usually reserved for cross-calls */
#define ASR_IDSR 0x48 /* Interrupt dispatch status reg */
diff -r 18964251c403 -r 7d40ec171f80 sys/arch/sparc64/include/psl.h
--- a/sys/arch/sparc64/include/psl.h Wed Nov 07 17:14:02 2012 +0000
+++ b/sys/arch/sparc64/include/psl.h Thu Nov 08 00:34:37 2012 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: psl.h,v 1.49 2011/07/12 07:51:34 mrg Exp $ */
+/* $NetBSD: psl.h,v 1.50 2012/11/08 00:34:37 macallan Exp $ */
/*
* Copyright (c) 1992, 1993
@@ -330,6 +330,7 @@
#define GETVER_CPU_IMPL() ((getver() & VER_IMPL) >> VER_IMPL_SHIFT)
#define GETVER_CPU_MANUF() ((getver() & VER_MANUF) >> VER_MANUF_SHIFT)
#define CPU_IS_SPITFIRE() (GETVER_CPU_IMPL() == IMPL_SPITFIRE)
+#define CPU_IS_HUMMINGBIRD() (GETVER_CPU_IMPL() == IMPL_HUMMINGBIRD)
#define CPU_IS_USIIIi() ((GETVER_CPU_IMPL() == IMPL_JALAPENO) || \
(GETVER_CPU_IMPL() == IMPL_SERRANO))
#define CPU_IS_USIII_UP() (GETVER_CPU_IMPL() >= IMPL_CHEETAH)
diff -r 18964251c403 -r 7d40ec171f80 sys/arch/sparc64/sparc64/clock.c
--- a/sys/arch/sparc64/sparc64/clock.c Wed Nov 07 17:14:02 2012 +0000
+++ b/sys/arch/sparc64/sparc64/clock.c Thu Nov 08 00:34:37 2012 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: clock.c,v 1.106 2011/09/04 12:17:46 nakayama Exp $ */
+/* $NetBSD: clock.c,v 1.107 2012/11/08 00:34:38 macallan Exp $ */
/*
* Copyright (c) 1992, 1993
@@ -55,7 +55,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: clock.c,v 1.106 2011/09/04 12:17:46 nakayama Exp $");
+__KERNEL_RCSID(0, "$NetBSD: clock.c,v 1.107 2012/11/08 00:34:38 macallan Exp $");
#include "opt_multiprocessor.h"
@@ -99,6 +99,7 @@
* counter-timer timer#0 timer#1 %tick
* counter-timer + SMP timer#0/%tick - timer#1 or %tick
* no counter-timer %tick - %tick
+ * US-IIIi %stick - %stick
*/
/*
@@ -137,6 +138,7 @@
int timerblurb = 10; /* Guess a value; used before clock is attached */
static u_int tick_get_timecount(struct timecounter *);
+static u_int stick_get_timecount(struct timecounter *);
/*
* define timecounter "tick-counter"
@@ -153,6 +155,17 @@
NULL /* next timecounter */
};
+static struct timecounter stick_timecounter = {
+ stick_get_timecount, /* get_timecount */
+ 0, /* no poll_pps */
+ ~0u, /* counter_mask */
+ 0, /* frequency - set at initialisation */
+ "stick-counter", /* name */
+ 100, /* quality */
+ 0, /* private reference - UNUSED */
+ NULL /* next timecounter */
+};
+
/*
* tick_get_timecount provide current tick counter value
*/
@@ -162,6 +175,12 @@
return cpu_counter();
}
+static u_int
+stick_get_timecount(struct timecounter *tc)
+{
+ return getstick();
+}
+
#ifdef MULTIPROCESSOR
static u_int counter_get_timecount(struct timecounter *);
@@ -329,6 +348,27 @@
intr_restore(s);
}
+void
+stickintr_establish(int pil, int (*fun)(void *))
+{
+ int s;
+ struct intrhand *ih;
+ struct cpu_info *ci = curcpu();
+
+ ih = sparc_softintr_establish(pil, fun, NULL);
+ ih->ih_number = 1;
+ if (CPU_IS_PRIMARY(ci))
+ intr_establish(pil, true, ih);
+ ci->ci_tick_ih = ih;
+
+ /* set the next interrupt time */
+ ci->ci_tick_increment = ci->ci_system_clockrate[0] / hz;
+
+ s = intr_disable();
+ next_stick(ci->ci_tick_increment);
+ intr_restore(s);
+}
+
/*
* Set up the real-time and statistics clocks. Leave stathz 0 only if
* no alternative timer is available.
@@ -338,6 +378,7 @@
void
cpu_initclocks(void)
{
+ struct cpu_info *ci = curcpu();
#ifndef MULTIPROCESSOR
int statint, minint;
#endif
@@ -361,17 +402,24 @@
}
/* Make sure we have a sane cpu_clockrate -- we'll need it */
- if (!curcpu()->ci_cpu_clockrate[0]) {
+ if (!ci->ci_cpu_clockrate[0]) {
/* Default to 200MHz clock XXXXX */
- curcpu()->ci_cpu_clockrate[0] = 200000000;
- curcpu()->ci_cpu_clockrate[1] = 200000000 / 1000000;
+ ci->ci_cpu_clockrate[0] = 200000000;
+ ci->ci_cpu_clockrate[1] = 200000000 / 1000000;
}
/* Initialize the %tick register */
settick(0);
- tick_timecounter.tc_frequency = curcpu()->ci_cpu_clockrate[0];
- tc_init(&tick_timecounter);
+ if (ci->ci_system_clockrate[0] == 0) {
+ tick_timecounter.tc_frequency = ci->ci_cpu_clockrate[0];
+ tc_init(&tick_timecounter);
+ } else {
+ setstick(0);
+ stick_timecounter.tc_frequency =
+ ci->ci_system_clockrate[0];
+ tc_init(&stick_timecounter);
+ }
/*
* Now handle machines w/o counter-timers.
@@ -379,13 +427,21 @@
if (!timerreg_4u.t_timer || !timerreg_4u.t_clrintr) {
- aprint_normal("No counter-timer -- using %%tick at %luMHz as "
- "system clock.\n",
- (unsigned long)curcpu()->ci_cpu_clockrate[1]);
+ if (ci->ci_system_clockrate[0] == 0) {
+ aprint_normal("No counter-timer -- using %%tick "
+ "at %luMHz as system clock.\n",
+ (unsigned long)ci->ci_cpu_clockrate[1]);
- /* We don't have a counter-timer -- use %tick */
- tickintr_establish(PIL_CLOCK, tickintr);
+ /* We don't have a counter-timer -- use %tick */
+ tickintr_establish(PIL_CLOCK, tickintr);
+ } else {
+ aprint_normal("No counter-timer -- using %%stick "
+ "at %luMHz as system clock.\n",
+ (unsigned long)ci->ci_system_clockrate[1]);
+ /* We don't have a counter-timer -- use %stick */
+ stickintr_establish(PIL_CLOCK, stickintr);
+ }
/* We only have one timer so we have no statclock */
stathz = 0;
@@ -525,6 +581,22 @@
return (1);
}
+int
+stickintr(void *cap)
+{
+ int s;
+
+ hardclock((struct clockframe *)cap);
+
+ s = intr_disable();
+ /* Reset the interrupt */
+ next_stick(curcpu()->ci_tick_increment);
+ intr_restore(s);
+ curcpu()->ci_tick_evcnt.ev_count++;
+
+ return (1);
+}
+
#ifndef MULTIPROCESSOR
/*
* Level 14 (stat clock) interrupt handler.
diff -r 18964251c403 -r 7d40ec171f80 sys/arch/sparc64/sparc64/cpu.c
--- a/sys/arch/sparc64/sparc64/cpu.c Wed Nov 07 17:14:02 2012 +0000
+++ b/sys/arch/sparc64/sparc64/cpu.c Thu Nov 08 00:34:37 2012 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: cpu.c,v 1.102 2012/10/27 17:18:12 chs Exp $ */
+/* $NetBSD: cpu.c,v 1.103 2012/11/08 00:34:38 macallan Exp $ */
/*
* Copyright (c) 1996
@@ -52,7 +52,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: cpu.c,v 1.102 2012/10/27 17:18:12 chs Exp $");
+__KERNEL_RCSID(0, "$NetBSD: cpu.c,v 1.103 2012/11/08 00:34:38 macallan Exp $");
#include "opt_multiprocessor.h"
@@ -242,7 +242,7 @@
cpu_attach(device_t parent, device_t dev, void *aux)
{
int node;
- long clk;
+ long clk, sclk = 0;
struct mainbus_attach_args *ma = aux;
struct cpu_info *ci;
const char *sep;
@@ -299,12 +299,23 @@
ci->ci_cpu_clockrate[1] = clk / 1000000;
}
+ if (!CPU_IS_HUMMINGBIRD()) {
+ sclk = prom_getpropint(findroot(), "stick-frequency", 0);
Home |
Main Index |
Thread Index |
Old Index