From f05569f01b5dbfe49c7006ccd017091f023eddc3 Mon Sep 17 00:00:00 2001 From: David du Colombier <0intro@gmail.com> Date: Sat, 10 Aug 1991 00:00:00 +0000 Subject: [PATCH] Plan 9 from Bell Labs 1991-08-10 --- pc/devfloppy.c | 6 ++-- pc/devhard.c | 13 +++----- pc/devuart.c | 87 +++++++++++++++++++++++++++----------------------- pc/io.h | 4 +-- pc/main.c | 1 + pc/trap.c | 3 -- port/portdat.h | 4 +++ port/proc.c | 7 +++- port/queue.c | 86 ++++++++++++++++++++++++++++--------------------- 9 files changed, 117 insertions(+), 94 deletions(-) diff --git a/pc/devfloppy.c b/pc/devfloppy.c index 87b8ecec0e1161c7a512ca7668fc5abdc9376671..aace35e043443eb7293aa03d767c04ff355fb4c4 100644 --- a/pc/devfloppy.c +++ b/pc/devfloppy.c @@ -180,6 +180,7 @@ floppyreset(void) { Drive *dp; Type *t; + int n; /* * init dependent parameters @@ -211,8 +212,9 @@ floppyreset(void) */ for(dp = floppy.d; dp < &floppy.d[conf.nfloppy]; dp++){ do { - dp->ccache = ialloc(dp->t->cap, 1); - } while(k64(dp->ccache) != k64(dp->ccache+dp->t->cap)); + n = 512 * 18 * 2; /* MF2HD cylinder size */ + dp->ccache = ialloc(n, 1); + } while(k64(dp->ccache) != k64(dp->ccache+n)); dp->ccyl = -1; } setvec(Floppyvec, floppyintr); diff --git a/pc/devhard.c b/pc/devhard.c index 9b4437239384bb2f623851dd8cf7f6c818e7b980..7fa303ff41fd7a447ba1f74bf2cb38eb826629c6 100644 --- a/pc/devhard.c +++ b/pc/devhard.c @@ -13,7 +13,7 @@ typedef struct Controller Controller; enum { /* ports */ - Pbase= 0x10, + Pbase= 0x1F0, Pdata= Pbase+0, /* data port (16 bits) */ Perror= Pbase+1, /* error port */ Pcount= Pbase+2, /* sector count port */ @@ -164,9 +164,11 @@ hardattach(char *spec) dp->bytes = 512; dp->cap = dp->bytes * dp->cyl * dp->heads * dp->sectors; dp->online = 1; + poperror(); } } - return devattach('f', spec); + qunlock(&hard); + return devattach('h', spec); } Chan* @@ -301,17 +303,11 @@ interrupted(void *a) static long hardident(Drive *dp) { -print("identify hard drive\n"); hard.intr = 0; outb(Pdh, dp->dev<<4); outb(Pcmd, Cident); -print("waiting for hard drive interupt\n"); sleep(&hard.r, interrupted, 0); -print("getting hard drive ident\n"); inss(Pdata, &hard.id, 512/2); -print(" magic %lux lcyls %d rcyl %d lheads %d b2t %d b2s %d ls2t %d\n", - hard.id.magic, hard.id.lcyls, hard.id.rcyl, hard.id.lheads, - hard.id.b2t, hard.id.b2s, hard.id.ls2t); } static long @@ -374,7 +370,6 @@ hardintr(Ureg *ur) if(hard.status & Sbusy) panic("disk busy"); hard.intr = 1; -print("hardintr\n"); wakeup(&hard.r); } diff --git a/pc/devuart.c b/pc/devuart.c index b33a9b5ad5ae6162622886db63e46ce115b4ac62..0d31c6fcfea7d103c7e68fd4bf2ec6cb471df21e 100644 --- a/pc/devuart.c +++ b/pc/devuart.c @@ -32,7 +32,7 @@ enum Dtr= (1<<0), /* data terminal ready */ Rts= (1<<1), /* request to send */ Ri= (1<<2), /* ring */ - Dcd= (1<<3), /* carrier */ + Inton= (1<<3), /* turn on interrupts */ Loop= (1<<4), /* loop bask */ Lstat= 5, /* line status */ Inready=(1<<0), /* receive buffer full */ @@ -164,10 +164,13 @@ uartsetup(void) * set rate to 9600 baud. * 8 bits/character. * 1 stop bit. + * interrupts enabled. */ uartsetbaud(up, 9600); up->sticky[Format] = Bits8; uartwrreg(up, Format, 0); + up->sticky[Mctl] |= Inton; + uartwrreg(up, Mctl, 0x0); } } @@ -209,48 +212,58 @@ uartintr(Uart *up) IOQ *cq; int s, l; - l = uartrdreg(up, Lstat); - s = uartrdreg(up, Istat); - - cq = up->iq; - while(l & Inready){ - ch = uartrdreg(up, Data) & 0xff; - if(cq->putc) - (*cq->putc)(cq, ch); - else { - putc(cq, ch); - if(up->delim[ch/8] & (1<<(ch&7)) ) + for(;;){ + s = uartrdreg(up, Istat); + switch(s){ + case 6: /* receiver line status */ + l = uartrdreg(up, Lstat); + break; + + case 4: /* received data available */ + cq = up->iq; + ch = uartrdreg(up, Data) & 0xff; + if(cq->putc) + (*cq->putc)(cq, ch); + else { + putc(cq, ch); + if(up->delim[ch/8] & (1<<(ch&7)) ) + wakeup(&cq->r); + } + break; + + case 2: /* transmitter empty */ + cq = up->oq; + lock(cq); + ch = getc(cq); + if(ch < 0){ + up->printing = 0; wakeup(&cq->r); + }else + outb(up->port + Data, ch); + unlock(cq); + break; + + case 0: /* modem status */ + l = uartrdreg(up, Mstat); + break; + + default: + if(s&1) + return; + print("weird modem interrupt\n"); + break; } - l = uartrdreg(up, Lstat); - } - - /* - * send next output character - */ - if(up->printing && (l&Outready)){ - cq = up->oq; - lock(cq); - ch = getc(cq); - if(ch < 0){ - up->printing = 0; - wakeup(&cq->r); - }else - outb(up->port + Data, ch); - unlock(cq); } } void uartintr0(Ureg *ur) { - if(uart[0].enabled) - uartintr(&uart[0]); + uartintr(&uart[0]); } void uartintr1(Ureg *ur) { - if(uart[1].enabled) - uartintr(&uart[1]); + uartintr(&uart[1]); } /* @@ -271,8 +284,8 @@ uartenable(Uart *up) /* * speed up the clock to poll the uart - */ fclockinit(); + */ /* * set up i/o routines @@ -285,21 +298,18 @@ uartenable(Uart *up) up->iq->ptr = up; } up->enabled = 1; - up->sticky[Iena] = 0xf; /* * turn on interrupts */ + up->sticky[Iena] = 0x7; uartwrreg(up, Iena, 0); - uartwrreg(up, Tctl, 0x0); /* * turn on DTR and RTS */ uartdtr(up, 1); uartrts(up, 1); - -print("uart enabled: Iena=%lux\n", uartrdreg(up, Iena)); } /* @@ -393,9 +403,6 @@ uartstopen(Queue *q, Stream *s) Uart *up; char name[NAMELEN]; -print("uartstopen: q=0x%ux, inuse=%d, type=%d, dev=%d, id=%d\n", - q, s->inuse, s->type, s->dev, s->id); - up = &uart[s->id]; up->iq->putc = 0; uartenable(up); diff --git a/pc/io.h b/pc/io.h index 0a213a62d01902ec96910f0a4d1a60102cf2948d..b3467bcfce4fcc8f5f1594da5a49bffb97542938 100644 --- a/pc/io.h +++ b/pc/io.h @@ -7,8 +7,8 @@ enum Int0vec= 16, /* first 8259 */ Clockvec= Int0vec+0, /* clock interrupts */ Kbdvec= Int0vec+1, /* keyboard interrupts */ - Uart0vec= Int0vec+3, /* serial line */ - Uart1vec= Int0vec+4, /* modem line */ + Uart0vec= Int0vec+4, /* serial line */ + Uart1vec= Int0vec+3, /* modem line */ Floppyvec= Int0vec+6, /* floppy interrupts */ Int1vec= Int0vec+8, /* second 8259 */ Mousevec= Int1vec+4, /* mouse interrupt */ diff --git a/pc/main.c b/pc/main.c index 6eb0b24661d96f2073f0484baa95d7857d105cb0..24410fda4d9a800355fa3eeb660138f63367ddf1 100644 --- a/pc/main.c +++ b/pc/main.c @@ -374,6 +374,7 @@ pmuwrbit(int index, int bit, int pos) return -1; } unlock(&pmulock); + return 0; } /* diff --git a/pc/trap.c b/pc/trap.c index 15d6411942fd397d428b7fdf5073fb270d882014..c8893d99c30812211c2b163806bad78a371348ea 100644 --- a/pc/trap.c +++ b/pc/trap.c @@ -178,9 +178,6 @@ trap(Ureg *ur) return; } - if(v==19 || v==20) - print("trap = %d\n", v); - /* * tell the 8259 that we're done with the * highest level interrupt (interrupts are still diff --git a/port/portdat.h b/port/portdat.h index 792d7a9a36bace60a774c1d217fd43be1804514c..9bf067d4354f763224294a8b0e1a571e425a02e1 100644 --- a/port/portdat.h +++ b/port/portdat.h @@ -220,6 +220,10 @@ struct IOQ void (*puts)(IOQ*, void*, int); /* output */ int (*putc)(IOQ*, int); /* input */ }; + union{ + int (*gets)(IOQ*, void*, int); /* input */ + int (*getc)(IOQ*); /* output */ + }; void *ptr; }; struct KIOQ diff --git a/port/proc.c b/port/proc.c index e105975f23eb877d718360cf10a8351a607875a3..d38a687c2cedbf36d5638ddab2be712a567b6ba7 100644 --- a/port/proc.c +++ b/port/proc.c @@ -401,8 +401,11 @@ postnote(Proc *p, int dolock, char *n, int flag) if(dolock) lock(&p->debug); - if(p->upage == 0) + if(p->upage == 0){ + if(dolock) + unlock(&p->debug); errors("noted process disappeared"); + } if(u == 0 || p != u->p){ k = kmap(p->upage); @@ -416,6 +419,8 @@ postnote(Proc *p, int dolock, char *n, int flag) else if(up->nnote == NNOTE-1){ if(up != u) kunmap(k); + if(dolock) + unlock(&p->debug); return 0; } p->notepending = 1; diff --git a/port/queue.c b/port/queue.c index 6c7c15b22154fd6345fe3441c2101f54c5dd76c0..a5fab13e3071bb4d67b4762a237c30caf8e85af0 100644 --- a/port/queue.c +++ b/port/queue.c @@ -13,21 +13,22 @@ initq(IOQ *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 *next; - - if(q->in == &q->buf[NQ-1]) - next = q->buf; + uchar *nextin; + if(q->in >= &q->buf[sizeof(q->buf)-1]) + nextin = q->buf; else - next = q->in+1; - if(next == q->out) + nextin = q->in+1; + if(nextin == q->out) return -1; *q->in = c; - q->in = next; + q->in = nextin; return 0; } @@ -39,7 +40,7 @@ getc(IOQ *q) if(q->in == q->out) return -1; c = *q->out; - if(q->out == &q->buf[NQ-1]) + if(q->out == q->buf+sizeof(q->buf)-1) q->out = q->buf; else q->out++; @@ -49,44 +50,61 @@ getc(IOQ *q) void puts(IOQ *q, void *buf, int n) { - uchar *next; - uchar *p = buf; + int m; uchar *nextin; + uchar *s = buf; - for(; n; n--){ - if(q->in == &q->buf[NQ-1]) - next = q->buf; - else - next = q->in + 1; - if(next == q->out) + while(n){ + m = q->out - q->in - 1; + if(m < 0) + m = &q->buf[NQ] - q->in; + if(m == 0) break; - *q->in = *p++; - q->in = next; + 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) { - uchar *p = buf; + int m, k = 0; uchar *nextout; + uchar *s = buf; - for(; n && q->out != q->in; n--){ - *p++ = *q->out; - if(q->out == &q->buf[NQ-1]) + 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++; + q->out = nextout; } - return p - (uchar*)buf; + return k; } int cangetc(void *arg) { - IOQ *q; - int n; - - q = (IOQ *)arg; - n = q->in - q->out; + IOQ *q = (IOQ *)arg; + int n = q->in - q->out; if (n < 0) n += sizeof(q->buf); return n; @@ -95,12 +113,6 @@ cangetc(void *arg) int canputc(void *arg) { - IOQ *q; - int n; - - q = (IOQ *)arg; - n = q->out - q->in - 1; - if (n < 0) - n += sizeof(q->buf); - return n; + IOQ *q = (IOQ *)arg; + return sizeof(q->buf)-cangetc(q)-1; }