summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authortmm <tmm@FreeBSD.org>2003-05-29 17:49:21 +0000
committertmm <tmm@FreeBSD.org>2003-05-29 17:49:21 +0000
commite330758d56bad341f3b6004687dae494c845e9f0 (patch)
treecfaf16cfa37c0aa9dd63a002ddd5c024618102eb
parentcccb8a341841afbb6950f77adfed8b5bf81138ae (diff)
downloadFreeBSD-src-e330758d56bad341f3b6004687dae494c845e9f0.zip
FreeBSD-src-e330758d56bad341f3b6004687dae494c845e9f0.tar.gz
Completely disable interrupts (not just raise %pil) when calculating the
value to be written into tick_compare in tick_hardclock(). While we were taking care that the value to be written was at least TICK_GRACE ticks in the future, a vector interrupt could happen between calculating the value and writing it. If it took longer than TICK_GRACE to complete (which is doubtful for a single device-triggered vector interrupt, but quite likely for some IPIs), the value written would be in the past and tick interrupts (which drive hardclock and statclock) would stop until %tick wraps around, which takes a long time. Also, increase TICK_GRACE from 1000 to 10000 for good measure. Reported by: kris Reviewed by: jake Approved by: re (scottl)
-rw-r--r--sys/sparc64/sparc64/tick.c9
1 files changed, 5 insertions, 4 deletions
diff --git a/sys/sparc64/sparc64/tick.c b/sys/sparc64/sparc64/tick.c
index 46c3b59..6189653 100644
--- a/sys/sparc64/sparc64/tick.c
+++ b/sys/sparc64/sparc64/tick.c
@@ -53,7 +53,7 @@
int tick_missed; /* statistics */
-#define TICK_GRACE 1000
+#define TICK_GRACE 10000
void
cpu_initclocks(void)
@@ -80,6 +80,7 @@ tick_hardclock(struct clockframe *cf)
{
int missed;
u_long next;
+ register_t i;
tick_process(cf);
/*
@@ -91,14 +92,14 @@ tick_hardclock(struct clockframe *cf)
*/
missed = 0;
next = rd(asr23) + tick_increment;
- critical_enter();
+ i = intr_disable();
while (next < rd(tick) + TICK_GRACE) {
next += tick_increment;
missed++;
}
- atomic_add_int(&tick_missed, missed);
wr(asr23, next, 0);
- critical_exit();
+ intr_restore(i);
+ atomic_add_int(&tick_missed, missed);
for (; missed > 0; missed--)
tick_process(cf);
}
OpenPOWER on IntegriCloud