M carrera/dat.h => carrera/dat.h +1 -0
@@ 102,6 102,7 @@ struct Mach
int tlbpurge; /* MUST BE SIXTH */
/* the following is safe to move */
+ ulong otlbfault; /* tlbfault at last sched */
ulong ticks; /* of the clock since boot time */
Label sched; /* scheduler wakeup */
Lock alarmlock; /* access to alarm list */
M pc/dat.h => pc/dat.h +1 -0
@@ 125,6 125,7 @@ struct Mach
void *alarm; /* alarms bound to this clock */
int tlbfault;
+ int otlbfault;
int tlbpurge;
int pfault;
int cs;
M port/devmouse.c => port/devmouse.c +2 -4
@@ 516,7 516,7 @@ mousetrack(int b, int dx, int dy)
* shift & right button is the same as middle button (for 2 button mice)
*/
int
-m3mouseputc(IOQ *q, int c)
+m3mouseputc(int c)
{
static uchar msg[3];
static int nb;
@@ 525,7 525,6 @@ m3mouseputc(IOQ *q, int c)
short x;
int dx, dy, newbuttons;
- USED(q);
/*
* check bit 6 for consistency
*/
@@ 557,14 556,13 @@ m3mouseputc(IOQ *q, int c)
* shift & right button is the same as middle button (for 2 button mice)
*/
int
-mouseputc(IOQ *q, int c)
+mouseputc(int c)
{
static short msg[5];
static int nb;
static uchar b[] = {0, 4, 2, 6, 1, 5, 3, 7, 0, 2, 2, 6, 1, 5, 3, 7};
int dx, dy, newbuttons;
- USED(q);
if((c&0xF0) == 0x80)
nb=0;
msg[nb] = c;
M port/devproc.c => port/devproc.c +50 -1
@@ 23,6 23,7 @@ enum
Qregs,
Qsegment,
Qstatus,
+ Qcounters,
Qtext,
Qwait,
};
@@ 30,6 31,7 @@ enum
#define STATSIZE (2*NAMELEN+12+7*12)
Dirtab procdir[] =
{
+ "counters", {Qcounters}, 0, 0444,
"ctl", {Qctl}, 0, 0000,
"fpregs", {Qfpregs}, sizeof(FPsave), 0000,
"kregs", {Qkregs}, sizeof(Ureg), 0000,
@@ 71,6 73,7 @@ Chan* proctext(Chan*, Proc*);
Segment* txt2data(Proc*, Segment*);
int procstopped(void*);
void mntscan(Mntwalk*);
+ulong readcounters(Proc*, ulong, void*, int);
int
procgen(Chan *c, Dirtab *tab, int ntab, int s, Dir *dp)
@@ 118,6 121,11 @@ procgen(Chan *c, Dirtab *tab, int ntab, int s, Dir *dp)
void
procinit(void)
{
+ /* standard counters - this ordering is important */
+ proccounter("sched");
+ proccounter("fault");
+ proccounter("tlbmiss");
+
if(conf.nproc >= (1<<(16-QSHIFT))-1)
print("warning: too many procs for devproc\n");
}
@@ 188,6 196,7 @@ procopen(Chan *c, int omode)
error(Eperm);
break;
+ case Qcounters:
case Qctl:
case Qnote:
case Qnoteid:
@@ 340,7 349,6 @@ procread(Chan *c, void *va, long n, ulong offset)
return n;
case Qproc:
-
return readnum(offset, va, n, (ulong)p, NUMSIZE);
case Qregs:
@@ 366,6 374,9 @@ procread(Chan *c, void *va, long n, ulong offset)
memmove(a, rptr+offset, n);
return n;
+ case Qcounters:
+ return readcounters(p, offset, va, n);
+
case Qstatus:
if(offset >= STATSIZE)
return 0;
@@ 847,3 858,41 @@ data2txt(Segment *s)
return ps;
}
+
+static char *counter[Pcounter];
+int ncounter;
+
+int
+proccounter(char *name)
+{
+ if(ncounter >= Pcounter)
+ panic("too many process counters");
+ counter[ncounter] = name;
+ return ncounter++;
+}
+
+ulong
+readcounters(Proc *p, ulong offset, void *va, int n)
+{
+ char *bp;
+ int i, j, m;
+ extern char *sysctab[];
+
+ bp = smalloc((NSYSCALL+ncounter)*(NAMELEN+8));
+ m = 0;
+ for(i = 0; i < Pcounter; i++)
+ if(counter[i])
+ m += sprint(bp+m, "%s\t%8d\n", counter[i], p->counter[i]);
+ j = 0;
+ for(i = 0; i < NSYSCALL; i++)
+ j += p->syscall[i];
+ m += sprint(bp+m, "syscall\t%8d\n", j);
+ for(i = 0; i < NSYSCALL; i++)
+ if(p->syscall[i])
+ m += sprint(bp+m, "%s\t%8d\n", sysctab[i], p->syscall[i]);
+ n = readstr(offset, va, n, bp);
+ free(bp);
+ memset(p->counter, 0, sizeof(p->counter));
+ memset(p->syscall, 0, sizeof(p->syscall));
+ return n;
+}
M port/fault.c => port/fault.c +1 -0
@@ 18,6 18,7 @@ fault(ulong addr, int read)
spllo();
m->pfault++;
+ up->counter[FAULTCNTR]++;
for(;;) {
s = seg(up, addr, 1);
if(s == 0) {
M port/portdat.h => port/portdat.h +10 -1
@@ 8,7 8,6 @@ typedef struct Egrp Egrp;
typedef struct Evalue Evalue;
typedef struct Fgrp Fgrp;
typedef struct Image Image;
-typedef struct IOQ IOQ;
typedef struct List List;
typedef struct Mntcache Mntcache;
typedef struct Mount Mount;
@@ 470,6 469,12 @@ enum
NERR = 15,
NNOTE = 5,
+
+ NSYSCALL = 37, /* MUST be equal to the real thing!!!! */
+ Pcounter = 6, /* per process counters */
+ CSCNTR = 0, /* sched counter */
+ FAULTCNTR = 1, /* fault counter */
+ TLBCNTR = 2, /* utlbmiss */
};
struct Proc
@@ 552,6 557,10 @@ struct Proc
void *dbgreg; /* User registers for devproc */
Notsave;
+ /* statistics */
+ ulong counter[Pcounter]; /* specialized per process counters */
+ ulong syscall[NSYSCALL];
+
/*
* machine specific MMU
*/
M port/portfns.h => port/portfns.h +1 -0
@@ 157,6 157,7 @@ int postnote(Proc*, int, char*, int);
int pprint(char*, ...);
void printinit(void);
ulong procalarm(ulong);
+int proccounter(char *name);
void procctl(Proc*);
void procdump(void);
void procinit0(void);
M port/proc.c => port/proc.c +5 -0
@@ 87,6 87,9 @@ sched(void)
if(up) {
splhi();
m->cs++;
+ up->counter[CSCNTR]++;
+up->counter[TLBCNTR] += m->tlbfault - m->otlbfault;
+m->otlbfault = m->tlbfault;
procsave(up);
if(setlabel(&up->sched)) {
procrestore(up);
@@ 229,6 232,8 @@ newproc(void)
panic("pidalloc");
if(p->kstack == 0)
p->kstack = smalloc(KSTACK);
+ memset(p->counter, 0, sizeof(p->counter));
+ memset(p->syscall, 0, sizeof(p->syscall));
return p;
}
D port/queue.c => port/queue.c +0 -118
@@ 1,118 0,0 @@
-#include "u.h"
-#include "../port/lib.h"
-#include "mem.h"
-#include "dat.h"
-#include "fns.h"
-#include "io.h"
-
-void
-initq(IOQ *q)
-{
- lock(q);
- unlock(q);
- q->in = q->out = q->buf;
- q->puts = puts;
- q->putc = putc;
- q->gets = gets;
- q->getc = getc;
-}
-
-int
-putc(IOQ *q, int c)
-{
- uchar *nextin;
- if(q->in >= &q->buf[sizeof(q->buf)-1])
- nextin = q->buf;
- else
- nextin = q->in+1;
- if(nextin == q->out)
- return -1;
- *q->in = c;
- q->in = nextin;
- return 0;
-}
-
-int
-getc(IOQ *q)
-{
- int c;
-
- if(q->in == q->out)
- return -1;
- c = *q->out;
- if(q->out == q->buf+sizeof(q->buf)-1)
- q->out = q->buf;
- else
- q->out++;
- return c;
-}
-
-void
-puts(IOQ *q, void *buf, int n)
-{
- int m; uchar *nextin;
- uchar *s = buf;
-
- while(n){
- m = q->out - q->in - 1;
- if(m < 0)
- m = &q->buf[NQ] - q->in;
- if(m == 0)
- break;
- if(m > n)
- m = n;
- memmove(q->in, s, m);
- n -= m;
- s += m;
- nextin = q->in + m;
- if(nextin >= &q->buf[NQ])
- q->in = q->buf;
- else
- q->in = nextin;
- }
-}
-
-int
-gets(IOQ *q, void *buf, int n)
-{
- int m, k = 0; uchar *nextout;
- uchar *s = buf;
-
- while(n){
- m = q->in - q->out;
- if(m < 0)
- m = &q->buf[NQ] - q->out;
- if(m == 0)
- return k;
- if(m > n)
- m = n;
- if(buf)
- memmove(s, q->out, m);
- s += m;
- k += m;
- n -= m;
- nextout = q->out + m;
- if(nextout >= &q->buf[NQ])
- q->out = q->buf;
- else
- q->out = nextout;
- }
- return k;
-}
-
-int
-cangetc(void *arg)
-{
- IOQ *q = (IOQ *)arg;
- int n = q->in - q->out;
- if (n < 0)
- n += sizeof(q->buf);
- return n;
-}
-
-int
-canputc(void *arg)
-{
- IOQ *q = (IOQ *)arg;
- return sizeof(q->buf)-cangetc(q)-1;
-}
M port/systab.h => port/systab.h +6 -0
@@ 40,6 40,8 @@ Syscall syssegflush;
Syscall sysrendezvous;
Syscall sysunmount;
Syscall syswait;
+Syscall ;
+Syscall /* make sure port/portdat.h has nsyscall defined correctly!!! */;
Syscall sysdeath;
Syscall *systab[]={
@@ 80,6 82,8 @@ Syscall *systab[]={
[RENDEZVOUS] sysrendezvous,
[UNMOUNT] sysunmount,
[WAIT] syswait,
+
+/* make sure port/portdat.h has NSYSCALL defined correctly!!! */
};
char *sysctab[]={
@@ 120,4 124,6 @@ char *sysctab[]={
[RENDEZVOUS] "Rendez",
[UNMOUNT] "Unmount",
[WAIT] "Wait",
+
+/* make sure port/portdat.h has NSYSCALL defined correctly!!! */
};
M power/dat.h => power/dat.h +1 -0
@@ 130,6 130,7 @@ struct Mach
int load;
int intr;
int ledval; /* value last written to LED */
+ int otlbfault;
int stack[1];
};
M power/main.c => power/main.c +0 -8
@@ 727,11 727,3 @@ buzz(int f, int d)
USED(f);
USED(d);
}
-
-int
-mouseputc(IOQ *q, int c)
-{
- USED(q);
- USED(c);
- return 0;
-}
M power/trap.c => power/trap.c +1 -0
@@ 518,6 518,7 @@ syscall(Ureg *aur)
postnote(up, 1, "sys: bad sys call", NDebug);
error(Ebadarg);
}
+ up->syscall[up->scallnr]++;
if(sp & (BY2WD-1)){
pprint("odd sp in sys call pc %lux sp %lux\n", ur->pc, ur->sp);