bitkeeper revision 1.137 (3e745d6egPhbuKyLs12XPZOtKEunKA)

schedule.c, ac_timer.c, time.c, apic.c:
  Some timer fixes.
This commit is contained in:
kaf24@scramble.cl.cam.ac.uk committed 2003-03-16 11:18:06 +00:00
1 parent 93615cf273
commit 3350e93244
4 files changed
+51 -46

No files matched your search

+26 -23
View File
@@ -19,15 +19,15 @@
*/
/*
* Local APIC handling, local APIC timers
* Local APIC handling, local APIC timers
*
* (c) 1999, 2000 Ingo Molnar <mingo@redhat.com>
* (c) 1999, 2000 Ingo Molnar <mingo@redhat.com>
*
* Fixes
* Maciej W. Rozycki : Bits for genuine 82489DX APICs;
* thanks to Eric Gilmore
* and Rolf G. Tews
* for testing these extensively.
* Fixes
* Maciej W. Rozycki : Bits for genuine 82489DX APICs;
* thanks to Eric Gilmore
* and Rolf G. Tews
* for testing these extensively.
*/
@@ -329,13 +329,13 @@ void __init setup_local_APIC (void)
value = APIC_DM_NMI;
else
value = APIC_DM_NMI | APIC_LVT_MASKED;
if (!APIC_INTEGRATED(ver)) /* 82489DX */
if (!APIC_INTEGRATED(ver)) /* 82489DX */
value |= APIC_LVT_LEVEL_TRIGGER;
apic_write_around(APIC_LVT1, value);
if (APIC_INTEGRATED(ver)) { /* !82489DX */
if (APIC_INTEGRATED(ver)) { /* !82489DX */
maxlvt = get_maxlvt();
if (maxlvt > 3) /* Due to the Pentium erratum 3AP. */
if (maxlvt > 3) /* Due to the Pentium erratum 3AP. */
apic_write(APIC_ESR, 0);
value = apic_read(APIC_ESR);
printk("ESR value before enabling vector: %08lx\n", value);
@@ -653,25 +653,28 @@ void __init setup_APIC_clocks (void)
*/
int reprogram_ac_timer(s_time_t timeout)
{
int cpu = smp_processor_id();
s_time_t now;
s_time_t expire;
u64 apic_tmict;
int cpu = smp_processor_id();
s_time_t now;
s_time_t expire;
u64 apic_tmict;
if (timeout == 0) {
/* XXX RN: not sure if this disables it or cause interruptto
* go off imediately */
apic_tmict = 0;
/*
* We use this value because we don't trust zero (we think it may just
* cause an immediate interrupt). At least this is guaranteed to hold it
* off for ages (esp. since the clock ticks on bus clock, not cpu clock!).
*/
if (timeout == 0) {
apic_tmict = 0xffffffff;
goto reprogram;
}
now = NOW();
expire = timeout - now; /* value from now */
expire = timeout - now; /* value from now */
if (expire <= 0) {
printk("APICT[%02d] Timeout in the past 0x%08X%08X > 0x%08X%08X\n",
cpu, (u32)(now>>32), (u32)now, (u32)(timeout>>32),(u32)timeout);
return 0; /* timeout value in the past */
return 0; /* timeout value in the past */
}
/* conversion to bus units */
@@ -687,7 +690,7 @@ int reprogram_ac_timer(s_time_t timeout)
}
reprogram:
/* programm timer */
/* Program the timer. */
apic_write(APIC_TMICT, (unsigned long)apic_tmict);
TRC(printk("APICT[%02d] reprog(): expire=%lld %u\n",
@@ -755,9 +758,9 @@ void smp_apic_timer_interrupt(struct pt_regs * regs)
*/
ack_APIC_irq();
/* call the local handler */
/* call the local handler */
irq_enter(cpu, 0);
perfc_incrc(apic_timer);
perfc_incrc(apic_timer);
smp_local_timer_interrupt(regs);
irq_exit(cpu, 0);
+13 -12
View File
@@ -240,15 +240,12 @@ static u32 st_scale_i;
u32 stime_pcc; /* cycle counter value at last timer irq */
s_time_t stime_now; /* time in ns at last timer IRQ */
s_time_t get_s_time(void)
static inline s_time_t __get_s_time(void)
{
unsigned long flags;
u32 delta_tsc, low, pcc;
u64 delta;
s_time_t now;
spin_lock_irqsave(&stime_lock, flags);
pcc = stime_pcc;
now = stime_now;
@@ -259,9 +256,17 @@ s_time_t get_s_time(void)
delta >>= 32;
delta += ((u64)delta_tsc * st_scale_i);
spin_unlock_irqrestore(&stime_lock, flags);
return now + delta;
}
return now + delta;
s_time_t get_s_time(void)
{
s_time_t now;
unsigned long flags;
spin_lock_irqsave(&stime_lock, flags);
now = __get_s_time();
spin_unlock_irqrestore(&stime_lock, flags);
return now;
}
@@ -326,17 +331,13 @@ static struct ac_timer update_timer;
static void update_time(unsigned long foo)
{
unsigned long flags;
u32 new_pcc;
s_time_t new_st;
unsigned long usec;
new_st = NOW();
rdtscl(new_pcc);
/* Update system time. */
spin_lock_irqsave(&stime_lock, flags);
stime_now = new_st;
stime_pcc=new_pcc;
stime_now = new_st = __get_s_time();
rdtscl(stime_pcc);
/* Don't reeenable IRQs until we release wctime_lock. */
spin_unlock(&stime_lock);
+8 -8
View File
@@ -82,7 +82,9 @@ int add_ac_timer(struct ac_timer *timer)
(u32)(timer->expires>>32), (u32)timer->expires));
return 1;
}
spin_lock_irqsave(&ac_timers[cpu].lock, flags);
/*
* Add timer to the list. If it gets added to the front we have to
* reprogramm the timer
@@ -154,8 +156,12 @@ int rem_ac_timer(struct ac_timer *timer)
/* just removed the head */
if (list_empty(&ac_timers[cpu].timers)) {
reprogram_ac_timer((s_time_t) 0);
} else {
timer = list_entry(ac_timers[cpu].timers.next,
struct ac_timer, timer_list);
if ( timer->expires > (NOW() + TIMER_SLOP) )
reprogram_ac_timer(timer->expires);
}
/* XXX should actaully reprogramm APIC to new head */
}
} else
res = -1;
@@ -201,13 +207,7 @@ void do_ac_timer(void)
/* Sanity: is the timer list empty? */
if ( list_empty(&ac_timers[cpu].timers) ) {
/*
* XXX RN: This shouldn't happen, but does! Two possibilities:
* - Race condition between removing and reseting APIC
* - setting an APIC timeout value of 0 causes an immediate
* timer interrupt to fire.
* None of these should be critical!
*/
/* This does sometimes happen: race condition in resetting timeout? */
spin_unlock_irqrestore(&ac_timers[cpu].lock, flags);
return;
}
+4 -3
View File
@@ -368,9 +368,9 @@ asmlinkage void schedule(void)
sched_done:
ASSERT(r_time != 0);
ASSERT(r_time > ctx_allow);
ASSERT(r_time >= ctx_allow);
#if 0
#ifndef NDEBUG
if ( (r_time==0) || (r_time < ctx_allow)) {
printk("[%02d]: %lx\n", this_cpu, r_time);
dump_rqueue(&schedule_data[this_cpu].runqueue, "foo");
@@ -389,7 +389,8 @@ asmlinkage void schedule(void)
timer_redo:
schedule_data[this_cpu].s_timer.expires = now + r_time;
if (add_ac_timer(&schedule_data[this_cpu].s_timer) == 1) {
printk("SCHED[%02d]: Shit this shouldn't happen\n", this_cpu);
printk("SCHED[%02d]: Shit this shouldn't happen %08x\n",
this_cpu, r_time);
now = NOW();
goto timer_redo;
}
Reference in new issue
Block a user
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.