## diffname alphapc/clock.c 1999/0415 ## diff -e /dev/null /n/emeliedump/1999/0415/sys/src/brazil/alphapc/clock.c 0a #include "u.h" #include "../port/lib.h" #include "mem.h" #include "dat.h" #include "fns.h" #include "io.h" #include "ureg.h" void (*kproftimer)(ulong); typedef struct Clock0link Clock0link; typedef struct Clock0link { void (*clock)(void); Clock0link* link; } Clock0link; static Clock0link *clock0link; static Lock clock0lock; void addclock0link(void (*clock)(void)) { Clock0link *lp; if((lp = malloc(sizeof(Clock0link))) == 0){ print("addclock0link: too many links\n"); return; } ilock(&clock0lock); lp->clock = clock; lp->link = clock0link; clock0link = lp; iunlock(&clock0lock); } /* * delay for l milliseconds more or less. delayloop is set by * clockinit() to match the actual CPU speed. */ void delay(int l) { ulong i, j; j = m->delayloop; while(l-- > 0) for(i=0; i < j; i++) ; } void microdelay(int l) { ulong i, j; // j = m->delayloop/1000; j = 10000; while(l-- > 0) for(i=0; i < j; i++) ; } void clockinit(void) { m->delayloop = 250*1000; /* BUG */ #ifdef NOTYET long x; m->delayloop = m->speed*100; do { x = rdcount(); delay(10); x = rdcount() - x; } while(x < 0); /* * fix count */ m->delayloop = (m->delayloop*m->speed*1000*10)/x; if(m->delayloop == 0) m->delayloop = 1; /* wrcompare(rdcount()+(m->speed*1000000)/HZ); */ #endif } void clock(Ureg *ur) { Clock0link *lp; static int count; /* HZ == 100, timer == 1024Hz. error < 1ms */ count += 100; if (count < 1024) return; count -= 1024; m->ticks++; if(m->proc) m->proc->pc = ur->pc; accounttime(); if(kproftimer != nil) kproftimer(ur->pc); if((active.machs&(1<machno)) == 0) return; if(active.exiting && (active.machs & (1<machno))) { print("someone's exiting\n"); exit(0); } checkalarms(); if(m->machno == 0){ lock(&clock0lock); for(lp = clock0link; lp; lp = lp->link) lp->clock(); unlock(&clock0lock); } if(up == 0 || up->state != Running) return; if(anyready()) sched(); /* user profiling clock */ if(ur->status & UMODE) { (*(ulong*)(USTKTOP-BY2WD)) += TK2MS(1); segclock(ur->pc); } } vlong fastticks(uvlong *hz) { if (hz) *hz = 100; return m->ticks; } . ## diffname alphapc/clock.c 1999/0429 ## diff -e /n/emeliedump/1999/0415/sys/src/brazil/alphapc/clock.c /n/emeliedump/1999/0429/sys/src/brazil/alphapc/clock.c 138,145d 79,87c void /*milli*/delay(int ms) { microdelay(ms*1000); . 72,77c eot = cycletimer() + (m->cpuhz/1000000)*us; while(cycletimer() < eot) ; } . 68,70c uvlong eot; . 66c microdelay(int us) . 58,62c x = splhi(); ticks = cycletimer(); splx(x); if(hz) *hz = m->cpuhz; return (vlong)ticks; . 56c uvlong ticks; int x; . 53,54c vlong fastticks(uvlong* hz) . 47,50c uvlong cycletimer(void) { ulong pcc; pcc = rpcc(nil) & 0xFFFFFFFF; if(m->cpuhz == 0){ /* * pcclast is needed to detect wraparound of * the cycle timer which is only 32-bits. * m->cpuhz is set from the info passed from * the firmware. * This could be in clockinit if can * guarantee no wraparound between then and now. * * All the clock stuff needs work. */ m->cpuhz = hwrpb->cfreq; m->pcclast = pcc; } if(pcc < m->pcclast) m->fastclock += 0x100000000LL; m->fastclock += pcc; m->pcclast = pcc; return MACHP(0)->fastclock; . 45c } . 43c clockinit(void) . 37,41d 6a #include "axp.h" . ## diffname alphapc/clock.c 1999/0430 ## diff -e /n/emeliedump/1999/0429/sys/src/brazil/alphapc/clock.c /n/emeliedump/1999/0430/sys/src/brazil/alphapc/clock.c 108a cycletimer(); . 66a m->fastclock += delta; . 63,65c delta = pcc - m->pcclast; if(delta < 0) delta += 0x100000000LL; . 46a vlong delta; . ## diffname alphapc/clock.c 1999/0501 ## diff -e /n/emeliedump/1999/0430/sys/src/brazil/alphapc/clock.c /n/emeliedump/1999/0501/sys/src/brazil/alphapc/clock.c 94,95c eot = fastticks(nil) + (m->cpuhz/1000000)*us; while(fastticks(nil) < eot) . ## diffname alphapc/clock.c 2001/0727 ## diff -e /n/emeliedump/1999/0501/sys/src/brazil/alphapc/clock.c /n/emeliedump/2001/0727/sys/src/9/alphapc/clock.c 118,153c portclock(ureg); . 111a . 108d 106c clock(Ureg *ureg) . 102c microdelay(millisecs*1000); . 100c delay(int millisecs) . 23,38d 11,21d 8d ## diffname alphapc/clock.c 2001/1023 ## diff -e /n/emeliedump/2001/0727/sys/src/9/alphapc/clock.c /n/emeliedump/2001/1023/sys/src/9/alphapc/clock.c 91a ulong TK2MS(ulong ticks) { uvlong t, hz; t = ticks; hz = HZ; t *= 1000L; t = t/hz; ticks = t; return ticks; } . ## diffname alphapc/clock.c 2002/0410 ## diff -e /n/emeliedump/2001/1023/sys/src/9/alphapc/clock.c /n/emeliedump/2002/0410/sys/src/9/alphapc/clock.c 90c timerintr(ureg, 0); . 61a timerset(uvlong) { } void . 58c return ticks; . 45c uvlong . ## diffname alphapc/clock.c 2002/0710 ## diff -e /n/emeliedump/2002/0410/sys/src/9/alphapc/clock.c /n/emeliedump/2002/0710/sys/src/9/alphapc/clock.c 97,109d ## diffname alphapc/clock.c 2002/0822 ## diff -e /n/emeliedump/2002/0710/sys/src/9/alphapc/clock.c /n/emeliedump/2002/0822/sys/src/9/alphapc/clock.c 60a /* * performance measurement ticks. must be low overhead. * doesn't have to count over a second. */ ulong perfticks(void) { return rpcc(nil); } .