M pc/apic.c => pc/apic.c +15 -14
@@ 88,6 88,7 @@ enum { /* LapicTDCR */
};
static ulong* lapicbase;
+static int clkin;
static int
lapicr(int r)
@@ 104,7 105,7 @@ lapicw(int r, int data)
}
void
-lapiconline(int clkin)
+lapiconline(void)
{
/*
* Reload the timer to de-synchronise the processors,
@@ 118,7 119,7 @@ lapiconline(int clkin)
lapicw(LapicTPR, 0);
}
-static int
+static void
lapictimerinit(void)
{
ulong lo, v;
@@ 128,21 129,23 @@ lapictimerinit(void)
lapicw(LapicTDCR, LapicX1);
lapicw(LapicTIMER, ApicIMASK|LapicCLKIN|LapicONESHOT|VectorTIMER);
- lapicw(LapicTICR, v);
- wrmsr(0x10, 0);
+ if(clkin == 0){
+ lapicw(LapicTICR, v);
+ wrmsr(0x10, 0);
- do{
- rdmsr(0x10, &tsc);
- lo = (ulong)tsc;
- }while(lo < v);
+ do{
+ rdmsr(0x10, &tsc);
+ lo = (ulong)tsc;
+ }while(lo < v);
- return ((v-lapicr(LapicTCCR)+500)/1000)*1000*1000;
+ clkin = ((v-lapicr(LapicTCCR)+500)/1000)*1000*1000;
+ }
}
-int
+void
lapicinit(Apic* apic)
{
- ulong clkin, r, lvt;
+ ulong r, lvt;
if(lapicbase == 0)
lapicbase = apic->addr;
@@ 153,7 156,7 @@ lapicinit(Apic* apic)
lapicw(LapicTPR, 0xFF);
lapicw(LapicSVR, LapicENABLE|VectorSPURIOUS);
- clkin = lapictimerinit();
+ lapictimerinit();
/*
* Some Pentium revisions have a bug whereby spurious
@@ 200,8 203,6 @@ lapicinit(Apic* apic)
* interrupts.
lapicw(LapicTPR, 0);
*/
-
- return clkin;
}
void
M pc/archgeneric.c => pc/archgeneric.c +1 -0
@@ 210,6 210,7 @@ static uvlong fasthz;
void
cycletimerinit(void)
{
+ wrmsr(0x10, 0);
fasthz = 1000000LL*m->cpumhz;
}
M pc/dat.h => pc/dat.h +2 -0
@@ 187,6 187,8 @@ struct Mach
vlong mtrrfix[11];
vlong mtrrvar[32]; /* 256 max. */
+ vlong clockstart; /* starting value for cycle clock */
+
int stack[1];
};
M pc/mp.c => pc/mp.c +9 -7
@@ 354,9 354,11 @@ checkmtrr(void)
static void
squidboy(Apic* apic)
{
- int clkin;
-
// iprint("Hello Squidboy\n");
+
+ /* synchronize cycle clocks */
+ wrmsr(0x10, m->clockstart);
+
machinit();
mmuinit();
@@ 374,8 376,8 @@ squidboy(Apic* apic)
while(MACHP(0)->ticks == 0)
;
- clkin = lapicinit(apic);
- lapiconline(clkin);
+ lapicinit(apic);
+ lapiconline();
lock(&active);
active.machs |= 1<<m->machno;
@@ 441,6 443,7 @@ mpstartap(Apic* apic)
*p = i>>8;
nvramwrite(0x0F, 0x0A);
+ rdmsr(0x10, &mach->clockstart);
lapicstartap(apic, PADDR(APBOOTSTRAP));
for(i = 0; i < 100000; i++){
lock(&mprdthilock);
@@ 460,7 463,6 @@ mpinit(void)
PCMP *pcmp;
uchar *e, *p;
Apic *apic, *bpapic;
- int clkin;
i8259init();
@@ 529,7 531,7 @@ mpinit(void)
if(bpapic == 0)
return;
- clkin = lapicinit(bpapic);
+ lapicinit(bpapic);
lock(&mprdthilock);
mprdthi |= (1<<bpapic->apicno)<<24;
unlock(&mprdthilock);
@@ 542,7 544,7 @@ mpinit(void)
intrenable(VectorTIMER, clockintr, 0, BUSUNKNOWN);
intrenable(VectorERROR, lapicerror, 0, BUSUNKNOWN);
intrenable(VectorSPURIOUS, lapicspurious, 0, BUSUNKNOWN);
- lapiconline(clkin);
+ lapiconline();
checkmtrr();
M pc/mp.h => pc/mp.h +2 -2
@@ 210,8 210,8 @@ enum {
extern void ioapicrdtr(Apic*, int, int*, int*);
extern void ioapicrdtw(Apic*, int, int, int);
extern void ioapicinit(Apic*, int);
-extern void lapiconline(int);
-extern int lapicinit(Apic*);
+extern void lapiconline(void);
+extern void lapicinit(Apic*);
extern void lapicstartap(Apic*, int);
extern void lapicerror(Ureg*, void*);
extern void lapicspurious(Ureg*, void*);