From bafa3d1142a79204c6d87517de002db6137d0ddf Mon Sep 17 00:00:00 2001 From: David du Colombier <0intro@gmail.com> Date: Tue, 21 Nov 2000 00:00:00 +0000 Subject: [PATCH] Plan 9 from Bell Labs 2000-11-21 --- bitsy/clock.c | 9 ++ bitsy/dat.h | 208 +++++++++++++++++++++++++++++++++++++---- bitsy/devpcmcia.c | 225 ++++++++++++++++++++++++++++----------------- bitsy/devuart.c | 8 ++ bitsy/devuda1341.c | 79 ++++++++-------- bitsy/fns.h | 2 +- bitsy/io.h | 217 +++++++++++-------------------------------- bitsy/main.c | 56 ++++------- bitsy/mem.h | 8 +- bitsy/mmu.c | 14 ++- bitsy/sa1110uart.c | 11 --- bitsy/trap.c | 7 +- ip/il.c | 2 +- 13 files changed, 485 insertions(+), 361 deletions(-) diff --git a/bitsy/clock.c b/bitsy/clock.c index df4f4dbaed525839f49e6936fe5e40cc29bb0520..de5006504084fb67d939d9a83513646cbbc5b308 100644 --- a/bitsy/clock.c +++ b/bitsy/clock.c @@ -24,6 +24,8 @@ static void clockintr(Ureg*, void*); void clockinit(void) { + ulong x; + /* map the clock registers */ timerregs = mapspecial(OSTIMERREGS, 32); @@ -32,6 +34,13 @@ clockinit(void) intrenable(IRQtimer0, clockintr, nil, "clock"); timerregs->oier = 1<<0; + /* figure out processor frequency */ + x = powerregs->ppcr & 0x1f; + conf.hz = ClockFreq*(x*4+16); + conf.mhz = (conf.hz+499999)/1000000; + + print("%lud MHZ WeakARM\n", conf.mhz); + /* post interrupt 1/HZ secs from now */ timerregs->osmr[0] = timerregs->oscr + ClockFreq/HZ; diff --git a/bitsy/dat.h b/bitsy/dat.h index 7b5e039cb5b283b304ad7193f8fe8c9b584a2b6c..c4bd21af5660063bcbb53bd8cfcd2298e8985f6d 100644 --- a/bitsy/dat.h +++ b/bitsy/dat.h @@ -1,19 +1,25 @@ -typedef struct Conf Conf; -typedef struct FPU FPU; -typedef struct FPenv FPenv; -typedef struct FPsave FPsave; -typedef struct Label Label; -typedef struct Lock Lock; -typedef struct MMU MMU; -typedef struct Mach Mach; -typedef struct Notsave Notsave; -typedef struct Page Page; -typedef struct PMMU PMMU; -typedef struct Proc Proc; -typedef struct Ureg Ureg; -typedef struct Vctl Vctl; -typedef struct PhysUart PhysUart; -typedef struct Uart Uart; +typedef struct Cisdat Cisdat; +typedef struct Conf Conf; +typedef struct Cycintr Cycintr; +typedef struct FPU FPU; +typedef struct FPenv FPenv; +typedef struct FPsave FPsave; +typedef struct Label Label; +typedef struct Lock Lock; +typedef struct MMU MMU; +typedef struct Mach Mach; +typedef struct Notsave Notsave; +typedef struct Page Page; +typedef struct PCMmap PCMmap; +typedef struct PCMslot PCMslot; +typedef struct PCMconftab PCMconftab; +typedef struct PhysUart PhysUart; +typedef struct PMMU PMMU; +typedef struct Proc Proc; +typedef struct Uart Uart; +typedef struct Ureg Ureg; +typedef struct Vctl Vctl; +typedef struct Uart Uart; /* * parameters for sysproc.c @@ -68,6 +74,8 @@ struct Conf int monitor; ulong ialloc; /* bytes available for interrupt time allocation */ ulong pipeqsize; /* size in bytes of pipe queues */ + ulong hz; /* processor cycle freq */ + ulong mhz; }; /* @@ -141,8 +149,6 @@ struct Mach int stack[1]; }; -typedef struct Cycintr Cycintr; - /* * fasttick timer interrupts */ @@ -179,3 +185,169 @@ enum { OneMeg= 1024*1024, }; + +/* + * routines to access UART hardware + */ +struct PhysUart +{ + void (*enable)(Uart*, int); + void (*disable)(Uart*); + void (*kick)(Uart*); + void (*intr)(Ureg*, void*); + void (*dobreak)(Uart*, int); + void (*baud)(Uart*, int); + void (*bits)(Uart*, int); + void (*stop)(Uart*, int); + void (*parity)(Uart*, int); + void (*modemctl)(Uart*, int); + void (*rts)(Uart*, int); + void (*dtr)(Uart*, int); + long (*status)(Uart*, void*, long, long); +}; + +enum { + Stagesize= 1024 +}; + +/* + * software UART + */ +struct Uart +{ + QLock; + int type; + int dev; + int opens; + void *regs; + PhysUart *phys; + + int enabled; + Uart *elist; /* next enabled interface */ + char name[NAMELEN]; + + uchar sticky[4]; /* sticky write register values */ + ulong freq; /* clock frequency */ + uchar mask; /* bits/char */ + int baud; /* baud rate */ + + int parity; /* parity errors */ + int frame; /* framing errors */ + int overrun; /* rcvr overruns */ + + /* buffers */ + int (*putc)(Queue*, int); + Queue *iq; + Queue *oq; + + uchar istage[Stagesize]; + uchar *iw; + uchar *ir; + uchar *ie; + + Lock tlock; /* transmit */ + uchar ostage[Stagesize]; + uchar *op; + uchar *oe; + + int modem; /* hardware flow control on */ + int xonoff; /* software flow control on */ + int blocked; + int cts, dsr, dcd, dcdts; /* keep track of modem status */ + int ctsbackoff; + int hup_dsr, hup_dcd; /* send hangup upstream? */ + int dohup; + + int kinuse; /* device in use by kernel */ + + Rendez r; +}; + +/* + * PCMCIA structures known by both port/cis.c and the pcmcia driver + */ + +/* + * Map between ISA memory space and PCMCIA card memory space. + */ +struct PCMmap { + ulong ca; /* card address */ + ulong cea; /* card end address */ + ulong isa; /* local virtual address */ + int len; /* length of the ISA area */ + int attr; /* attribute memory */ +}; + +/* + * a PCMCIA configuration entry + */ +struct PCMconftab +{ + int index; + ushort irqs; /* legal irqs */ + uchar irqtype; + uchar bit16; /* true for 16 bit access */ + struct { + ulong start; + ulong len; + } io[16]; + int nio; + uchar vpp1; + uchar vpp2; + uchar memwait; + ulong maxwait; + ulong readywait; + ulong otherwait; +}; + +/* + * For walking a PCMCIA card's information structure + */ +struct Cisdat +{ + uchar *cisbase; + int cispos; + int cisskip; + int cislen; +}; + +/* + * PCMCIA card slot + */ +struct PCMslot +{ + Ref; + + long memlen; /* memory length */ + uchar slotno; /* slot number */ + void *regs; /* i/o registers */ + void *mem; /* memory */ + void *attr; /* attribute memory */ + + /* status */ + uchar special; /* in use for a special device */ + uchar already; /* already inited */ + uchar occupied; + uchar battery; + uchar wrprot; + uchar powered; + uchar configed; + uchar enabled; + uchar busy; + + /* cis info */ + ulong msec; /* time of last slotinfo call */ + char verstr[512]; /* version string */ + uchar cpresent; /* config registers present */ + ulong caddr; /* relative address of config registers */ + int nctab; /* number of config table entries */ + PCMconftab ctab[8]; + PCMconftab *def; /* default conftab */ + + /* for walking through cis */ + Cisdat; + + /* maps are fixed */ + PCMmap memmap; + PCMmap attrmap; +}; diff --git a/bitsy/devpcmcia.c b/bitsy/devpcmcia.c index a6ad1c950fd1ebb1590dcf17ad98c9ca220f9e74..53a3aa39d824b0f7c067e2fecad19ca90fd821c4 100644 --- a/bitsy/devpcmcia.c +++ b/bitsy/devpcmcia.c @@ -27,6 +27,11 @@ enum #define TYPE(c) (c->qid.path&0xff) #define QID(s,t) (((s)<<8)|(t)) +static void increfp(PCMslot*); +static void decrefp(PCMslot*); +static void slotmap(int, ulong, ulong, ulong); +static void slottiming(int, int, int, int, int); + static int pcmgen(Chan *c, Dirtab *, int , int i, Dir *dp) { @@ -68,94 +73,19 @@ pcmgen(Chan *c, Dirtab *, int , int i, Dir *dp) return 1; } -static void -slotinfo(void) -{ - ulong x = gpioregs->level; - - if(x & GPIO_OPT_IND_i){ - /* no expansion pack */ - slot[0].occupied = 0; - slot[1].occupied = 0; - } else { - slot[0].occupied = (x & GPIO_CARD_IND0_i) == 0; - slot[1].occupied = (x & GPIO_CARD_IND1_i) == 0; - } -} - -static void -increfp(PCMslot *pp) -{ - if(incref(&pcmcia) == 1) - exppackpower(1); - lock(pp); - if(pp->ref++ == 0) - ; - unlock(pp); - slotinfo(); -} -static void -decrefp(PCMslot *pp) -{ - slotinfo(); - lock(pp); - if(pp->ref-- == 1) - ; - unlock(pp); - if(decref(&pcmcia) == 0) - exppackpower(0); -} - -/* - * get a map for pc card region, return corrected len - */ -PCMmap* -pcmmap(int slotno, ulong, int, int attr) -{ - if(slotno > nslot) - panic("pcmmap"); - if(attr) - return &slot[slotno].attrmap; - else - return &slot[slotno].memmap; -} -void -pcmunmap(int, PCMmap*) -{ -} - /* - * map in the space for the cards + * set up the cards, default timing is 300 ns */ static void pcmciareset(void) { - int j; - PCMslot *pp; + /* staticly map the whole area */ + slotmap(0, PHYSPCM0REGS, PYHSPCM0ATTR, PYHSPCM0MEM); + slotmap(1, PHYSPCM1REGS, PYHSPCM1ATTR, PYHSPCM1MEM); - for(j = 0; j < nslot; j++){ - pp = &slot[j]; - pp->slotno = j; - pp->memlen = 64*OneMeg; - pp->msec = ~0; - pp->verstr[0] = 0; - - pp->mem = mapmem(j == 0 ? PYHSPCM0MEM : PYHSPCM1MEM, 64*OneMeg); - pp->memmap.ca = 0; - pp->memmap.cea = 64*MB; - pp->memmap.isa = (ulong)pp->mem; - pp->memmap.len = 64*OneMeg; - pp->memmap.attr = 0; - - pp->attr = mapmem(j == 0 ? PYHSPCM0ATTR : PYHSPCM1ATTR, OneMeg); - pp->attrmap.ca = 0; - pp->attrmap.cea = 64*MB; - pp->attrmap.isa = (ulong)pp->attr; - pp->attrmap.len = OneMeg; - pp->attrmap.attr = 1; - - pp->regs = mapspecial(j == 0 ? PHYSPCM0REGS : PHYSPCM1REGS, 32*1024); - } + /* set timing to the default, 300 */ + slottiming(0, 300, 300, 300, 0); + slottiming(1, 300, 300, 300, 0); } static Chan* @@ -231,7 +161,7 @@ pcmread(void *a, long n, ulong off, uchar *start, ulong len) return 0; if(off + n > len) n = len - off; - memmoves(a, start+off, n); + memmoveb(a, start+off, n); return n; } @@ -353,3 +283,132 @@ Dev pcmciadevtab = { devremove, devwstat, }; + +/* see what's there */ +static void +slotinfo(void) +{ + ulong x = gpioregs->level; + + if(x & GPIO_OPT_IND_i){ + /* no expansion pack */ + slot[0].occupied = 0; + slot[1].occupied = 0; + } else { + slot[0].occupied = (x & GPIO_CARD_IND0_i) == 0; + slot[1].occupied = (x & GPIO_CARD_IND1_i) == 0; + } +} + +/* use reference card to turn cards on and off */ +static void +increfp(PCMslot *pp) +{ + if(incref(&pcmcia) == 1){ + egpiobits(EGPIO_exp_nvram_power|EGPIO_exp_full_power, 1); + egpiobits(EGPIO_pcmcia_reset, 0); + delay(100); /* time to power up */ + } + + incref(pp); + + slotinfo(); +} + +static void +decrefp(PCMslot *pp) +{ + slotinfo(); + decref(pp); + if(decref(&pcmcia) == 0) + egpiobits(EGPIO_exp_nvram_power|EGPIO_exp_full_power, 0); +} + +/* + * the regions are staticly mapped + */ +static void +slotmap(int slotno, ulong regs, ulong attr, ulong mem) +{ + PCMslot *pp; + + pp = &slot[slotno]; + pp->slotno = slotno; + pp->memlen = 64*OneMeg; + pp->msec = ~0; + pp->verstr[0] = 0; + + pp->mem = mapmem(mem, 64*OneMeg, 0); + pp->memmap.ca = 0; + pp->memmap.cea = 64*MB; + pp->memmap.isa = (ulong)pp->mem; + pp->memmap.len = 64*OneMeg; + pp->memmap.attr = 0; + + pp->attr = mapmem(attr, OneMeg, 0); + pp->attrmap.ca = 0; + pp->attrmap.cea = MB; + pp->attrmap.isa = (ulong)pp->attr; + pp->attrmap.len = OneMeg; + pp->attrmap.attr = 1; + + pp->regs = mapspecial(regs, 32*1024); +} +PCMmap* +pcmmap(int slotno, ulong, int, int attr) +{ + if(slotno > nslot) + panic("pcmmap"); + if(attr) + return &slot[slotno].attrmap; + else + return &slot[slotno].memmap; +} +void +pcmunmap(int, PCMmap*) +{ +} + +/* + * setup card timings + * times are in ns + * count = ceiling[access-time/(2*3*T)] - 1, where T is a processor cycle + * + */ +static int +ns2count(int ns) +{ + ulong y; + + /* get 100 times cycle time */ + y = 100000000/(conf.hz/1000); + + /* get 10 times ns/(cycle*6) */ + y = (1000*ns)/(6*y); + + /* round up */ + y += 9; + y /= 10; + + /* subtract 1 */ + return y-1; +} +static void +slottiming(int slotno, int tio, int tattr, int tmem, int fast) +{ + ulong x; + + x = 0; + if(fast) + x |= 1<mecr & 0xffff0000; + } else { + x <<= 16; + x |= memconfregs->mecr & 0xffff; + } + memconfregs->mecr = x; +} diff --git a/bitsy/devuart.c b/bitsy/devuart.c index 39eefe7662d269b656622c185430db709eab956b..9a65fc470f779dd8775d1ffeb5e13b49fc33ac78 100644 --- a/bitsy/devuart.c +++ b/bitsy/devuart.c @@ -8,6 +8,14 @@ #include "../port/netif.h" +enum +{ + Nuart = 4, + + /* soft flow control chars */ + CTLS= 023, + CTLQ= 021, +}; static Uart* uart[Nuart]; static int nuart; diff --git a/bitsy/devuda1341.c b/bitsy/devuda1341.c index 1d8c6216c46337d2a26abe6b9068b3ec7f6d841e..c4222333c5848b2ee6b58e70f69b1c2775f3659d 100644 --- a/bitsy/devuda1341.c +++ b/bitsy/devuda1341.c @@ -19,7 +19,7 @@ #include "io.h" #include "sa1110dma.h" -static int debug = 0; +static int debug = 2; /* * GPIO based L3 bus support. @@ -417,7 +417,7 @@ audioqnotempty(void *x) { IOstate *s = x; - return dmaidle(s->dma) || s->emptying != s->next; + return dmaidle(s->dma) || s->emptying != s->current; } static int @@ -428,10 +428,17 @@ audioqnotfull(void *x) return dmaidle(s->dma) || s->filling != s->current; } +SSPregs *sspregs; +MCPregs *mcpregs; + static void audioinit(void) { - /* do nothing */ + /* Turn MCP operations off */ + mcpregs = mapspecial(MCPREGS, 0x34); + mcpregs->status &= ~(1<<16); + + sspregs = mapspecial(SSPREGS, 32); } uchar status0 = 0x22; @@ -464,8 +471,6 @@ enable(void) /* Enable the audio power */ audiopower(1); - amplifierpower(1); - audiomute(0); /* external clock configured for 44100 samples/sec */ gpioregs->set = GPIO_CLK_SET0_o; @@ -577,6 +582,8 @@ mxvolume(void) { static void outenable(void) { /* turn on DAC, set output gain switch */ + amplifierpower(1); + audiomute(0); status1 |= 0x41; L3_write(UDA1341_L3Addr | UDA1341_STATUS, (uchar*)&status1, 1); /* set volume */ @@ -591,6 +598,8 @@ outenable(void) { static void outdisable(void) { /* turn off DAC, clear output gain switch */ + audiomute(1); + amplifierpower(0); status1 &= ~0x41; L3_write(UDA1341_L3Addr | UDA1341_STATUS, (uchar*)&status1, 1); if (debug) { @@ -683,22 +692,15 @@ static void audiointr(void *x, ulong ndma) { IOstate *s = x; - if (s == &audio.o) { - /* Only interrupt routine touches s->current */ - if (debug > 1) iprint("#A: audio interrupt @%p\n", s->current); - s->current++; - if (s->current == &s->buf[Nbuf]) - s->current = &s->buf[0]; - if (ndma > 0) + if (debug > 1) iprint("#A: audio interrupt @%p\n", s->current); + /* Only interrupt routine touches s->current */ + s->current++; + if (s->current == &s->buf[Nbuf]) + s->current = &s->buf[0]; + if (ndma > 0) { + if (s == &audio.o) sendaudio(s); - } else if (s == &audio.i) { - /* Only interrupt routine touches s->current */ - if (debug > 1) iprint("#A: audio interrupt @%p\n", s->current); - s->current->nbytes = Bufsize; - s->current++; - if (s->current == &s->buf[Nbuf]) - s->current = &s->buf[0]; - if (ndma > 0) + else if (s == &audio.i) recvaudio(s); } wakeup(&s->vous); @@ -723,9 +725,10 @@ audiostat(Chan *c, char *db) } static Chan* -audioopen(Chan *c, int omode) +audioopen(Chan *c, int mode) { IOstate *s; + int omode = mode; switch(c->qid.path & ~CHDIR) { default: @@ -741,8 +744,7 @@ audioopen(Chan *c, int omode) case Qaudio: omode = (omode & 0x7) + 1; -// if (omode & ~(Aread | Awrite)) - if (omode & ~(Awrite)) + if (omode & ~(Aread | Awrite)) error(Ebadarg); qlock(&audio); if(audio.amode & omode){ @@ -754,20 +756,17 @@ audioopen(Chan *c, int omode) if (omode & Aread) { inenable(); s = &audio.i; - /* read */ audio.amode |= Aread; - if(audio.i.bufinit == 0) + if(s->bufinit == 0) bufinit(s); setempty(s); + s->emptying = &s->buf[Nbuf-1]; s->chan = c; s->dma = dmaalloc(0, 0, 4, 2, SSPRecvDMA, Port4SSP, audiointr, (void*)s); } - if (omode & 0x2) { + if (omode & Awrite) { outenable(); s = &audio.o; - /* write */ -// amplifierpower(1); -// audiomute(0); audio.amode |= Awrite; if(s->bufinit == 0) bufinit(s); @@ -781,8 +780,8 @@ audioopen(Chan *c, int omode) if (debug) print("#A: open done\n"); break; } - c = devopen(c, omode, audiodir, nelem(audiodir), devgen); - c->mode = openmode(omode); + c = devopen(c, mode, audiodir, nelem(audiodir), devgen); + c->mode = openmode(mode); c->flag |= COPEN; c->offset = 0; @@ -892,15 +891,22 @@ audioread(Chan *c, void *v, long n, vlong off) if (debug > 1) print("#A: read %ld\n", n); if((audio.amode & Aread) == 0) error(Emode); - s = &audio.o; + s = &audio.i; qlock(s); if(waserror()){ qunlock(s); nexterror(); } while(n > 0) { + if(s->emptying->nbytes == 0) { + if (debug > 1) print("#A: emptied @%p\n", s->emptying); + recvaudio(s); + s->emptying++; + if (s->emptying == &s->buf[Nbuf]) + s->emptying = s->buf; + } /* wait if dma in progress */ - while (!dmaidle(s->dma) && s->emptying == s->next) { + while (!dmaidle(s->dma) && s->emptying == s->current) { if (debug > 1) print("#A: sleep\n"); sleep(&s->vous, audioqnotempty, s); } @@ -913,13 +919,6 @@ audioread(Chan *c, void *v, long n, vlong off) s->emptying->nbytes -= m; n -= m; p += m; - if(s->emptying->nbytes == 0) { - if (debug > 1) print("#A: emptied @%p\n", s->emptying); - s->emptying++; - if (s->emptying == &s->buf[Nbuf]) - s->emptying = s->buf; - recvaudio(s); - } } poperror(); qunlock(s); diff --git a/bitsy/fns.h b/bitsy/fns.h index f5760898a47bfa548c07b1755d3aae1b1f788adb..513e4a6750ee2b42fa0cbad0e61983b6aea39504 100644 --- a/bitsy/fns.h +++ b/bitsy/fns.h @@ -33,7 +33,7 @@ void intrenable(int, void (*)(Ureg*, void*), void*, char*); int iprint(char*, ...); void irpower(int); void lcdpower(int); -void* mapmem(ulong, int); +void* mapmem(ulong, int, int); void mappedIvecEnable(void); void mappedIvecDisable(void); void* mapspecial(ulong, int); diff --git a/bitsy/io.h b/bitsy/io.h index 326be19af229d33f0a5b52af626b1c42462e0343..e1015c8c02c680b907d2eae0f48cbd7c14fab5fd 100644 --- a/bitsy/io.h +++ b/bitsy/io.h @@ -1,8 +1,12 @@ /* * Definitions for IO devices. Used only in C. */ -typedef struct Uartregs Uartregs; -Uartregs *uart3regs; + +enum +{ + /* hardware counter frequency */ + ClockFreq= 3686400, +}; /* * IRQ's defined by SA1100 @@ -105,89 +109,17 @@ enum GPIO_32_768kHz_o= 1<<27, /* 32.768 kHz clock (O, RTC) */ }; -enum -{ - /* hardware counter frequency */ - ClockFreq= 3686400, - Stagesize= 1024, - Nuart = 4, - - /* soft flow control chars */ - CTLS= 023, - CTLQ= 021, -}; - -typedef struct PhysUart PhysUart; -typedef struct Uart Uart; - -/* link twixt hardware and software */ -struct PhysUart -{ - void (*enable)(Uart*, int); - void (*disable)(Uart*); - void (*kick)(Uart*); - void (*intr)(Ureg*, void*); - void (*dobreak)(Uart*, int); - void (*baud)(Uart*, int); - void (*bits)(Uart*, int); - void (*stop)(Uart*, int); - void (*parity)(Uart*, int); - void (*modemctl)(Uart*, int); - void (*rts)(Uart*, int); - void (*dtr)(Uart*, int); - long (*status)(Uart*, void*, long, long); -}; - -/* software representation */ -struct Uart +/* hardware registers */ +typedef struct Uartregs Uartregs; +struct Uartregs { - QLock; - int type; - int dev; - int opens; - void *regs; - PhysUart *phys; - - int enabled; - Uart *elist; /* next enabled interface */ - char name[NAMELEN]; - - uchar sticky[4]; /* sticky write register values */ - ulong freq; /* clock frequency */ - uchar mask; /* bits/char */ - int baud; /* baud rate */ - - int parity; /* parity errors */ - int frame; /* framing errors */ - int overrun; /* rcvr overruns */ - - /* buffers */ - int (*putc)(Queue*, int); - Queue *iq; - Queue *oq; - - uchar istage[Stagesize]; - uchar *iw; - uchar *ir; - uchar *ie; - - Lock tlock; /* transmit */ - uchar ostage[Stagesize]; - uchar *op; - uchar *oe; - - int modem; /* hardware flow control on */ - int xonoff; /* software flow control on */ - int blocked; - int cts, dsr, dcd, dcdts; /* keep track of modem status */ - int ctsbackoff; - int hup_dsr, hup_dcd; /* send hangup upstream? */ - int dohup; - - int kinuse; /* device in use by kernel */ - - Rendez r; + ulong ctl[4]; + ulong dummya; + ulong data; + ulong dummyb; + ulong status[2]; }; +Uartregs *uart3regs; /* general purpose I/O lines control registers */ typedef struct GPIOregs GPIOregs; @@ -266,90 +198,53 @@ struct MCPregs { extern MCPregs *mcpregs; /* - * PCMCIA support code. - */ - -typedef struct PCMmap PCMmap; -typedef struct PCMslot PCMslot; -typedef struct PCMconftab PCMconftab; -typedef struct Cisdat Cisdat; - -/* - * Map between ISA memory space and PCMCIA card memory space. + * memory configuration */ -struct PCMmap { - ulong ca; /* card address */ - ulong cea; /* card end address */ - ulong isa; /* local virtual address */ - int len; /* length of the ISA area */ - int attr; /* attribute memory */ -}; - -/* configuration table entry */ -struct PCMconftab +enum { - int index; - ushort irqs; /* legal irqs */ - uchar irqtype; - uchar bit16; /* true for 16 bit access */ - struct { - ulong start; - ulong len; - } io[16]; - int nio; - uchar vpp1; - uchar vpp2; - uchar memwait; - ulong maxwait; - ulong readywait; - ulong otherwait; + /* bit shifts for pcmcia access time counters */ + MECR_io0= 0, + MECR_attr0= 5, + MECR_mem0= 10, + MECR_fast0= 11, + MECR_io1= MECR_io0+16, + MECR_attr1= MECR_attr0+16, + MECR_mem1= MECR_mem0+16, + MECR_fast1= MECR_fast0+16, }; -/* cis memory walking */ -struct Cisdat +typedef struct MemConfRegs MemConfRegs; +struct MemConfRegs { - uchar *cisbase; - int cispos; - int cisskip; - int cislen; + ulong mdcnfg; /* dram */ + ulong mdcas00; /* dram banks 0/1 */ + ulong mdcas01; + ulong mdcas02; + ulong msc0; /* static */ + ulong msc1; + ulong mecr; /* pcmcia */ + ulong mdrefr; /* dram refresh */ + ulong mdcas20; /* dram banks 2/3 */ + ulong mdcas21; + ulong mdcas22; + ulong msc2; /* static */ + ulong smcnfg; /* SMROM config */ }; +extern MemConfRegs *memconfregs; -/* a card slot */ -struct PCMslot +/* + * power management + */ +typedef struct PowerRegs PowerRegs; +struct PowerRegs { - Lock; - int ref; - - long memlen; /* memory length */ - uchar slotno; /* slot number */ - void *regs; /* i/o registers */ - void *mem; /* memory */ - void *attr; /* attribute memory */ - - /* status */ - uchar special; /* in use for a special device */ - uchar already; /* already inited */ - uchar occupied; - uchar battery; - uchar wrprot; - uchar powered; - uchar configed; - uchar enabled; - uchar busy; - - /* cis info */ - ulong msec; /* time of last slotinfo call */ - char verstr[512]; /* version string */ - uchar cpresent; /* config registers present */ - ulong caddr; /* relative address of config registers */ - int nctab; /* number of config table entries */ - PCMconftab ctab[8]; - PCMconftab *def; /* default conftab */ - - /* for walking through cis */ - Cisdat; - - /* maps are fixed */ - PCMmap memmap; - PCMmap attrmap; + ulong pmcr; + ulong pssr; + ulong pspr; + ulong pwer; + ulong pcfr; + ulong ppcr; + ulong pgsr; + ulong posr; }; +extern PowerRegs *powerregs; diff --git a/bitsy/main.c b/bitsy/main.c index 52682c032b96aac1d555615bdceb889dc2c41a67..9e75a49f5f12d13a2684c9c029638b826197bc94 100644 --- a/bitsy/main.c +++ b/bitsy/main.c @@ -13,11 +13,6 @@ Proc *up; Conf conf; int noprint; -static void gpioinit(void); -static void ppcinit(void); -static void sspinit(void); -static void mcpinit(void); - void main(void) { @@ -38,10 +33,7 @@ main(void) confinit(); xinit(); mmuinit(); - gpioinit(); - ppcinit(); - mcpinit(); - sspinit(); + machinit(); trapinit(); sa1100_uartsetup(1); rs232power(1); @@ -361,10 +353,17 @@ confinit(void) GPIOregs *gpioregs; ulong *egpioreg = (ulong*)EGPIOREGS; +PPCregs *ppcregs; +MemConfRegs *memconfregs; +PowerRegs *powerregs; -static void -gpioinit(void) +/* + * configure the machine + */ +void +machinit(void) { + /* set direction of SA1110 io pins and select alternate functions for some */ gpioregs = mapspecial(GPIOREGS, 32); gpioregs->direction = GPIO_LDD8_o|GPIO_LDD9_o|GPIO_LDD10_o|GPIO_LDD11_o @@ -379,32 +378,23 @@ gpioinit(void) |GPIO_LDD12_o|GPIO_LDD13_o|GPIO_LDD14_o|GPIO_LDD15_o |GPIO_SSP_CLK_i; + /* map in special H3650 io pins */ egpioreg = mapspecial(EGPIOREGS, 4); -} - -PPCregs *ppcregs; -static void -ppcinit(void) { + /* map in peripheral pin controller (ssp will need it) */ ppcregs = mapspecial(PPCREGS, 32); -} -MCPregs *mcpregs; + /* SA1110 power management */ + powerregs = mapspecial(POWERREGS, 32); -static void -mcpinit(void) { - mcpregs = mapspecial(MCPREGS, 0x34); - mcpregs->status &= ~(1<<16); - /* Turn MCP operations off */ + /* memory configuraton */ + memconfregs = mapspecial(MEMCONFREGS, 32); } -SSPregs *sspregs; - -static void -sspinit(void) { - sspregs = mapspecial(SSPREGS, 32); -} +/* + * manage egpio bits + */ static ulong egpiosticky; void @@ -458,11 +448,3 @@ flashprogpower(int on) { egpiobits(EGPIO_prog_flash, on); } - -void -exppackpower(int on) -{ - egpiobits(EGPIO_exp_full_power|EGPIO_exp_nvram_power, on); - if(on) - delay(100); -} diff --git a/bitsy/mem.h b/bitsy/mem.h index 385df721bdaf694d05ed9bb113372c6a2ee9f580..f3bd62df684a3e0dfe5ca1041050fdd605cd5664 100644 --- a/bitsy/mem.h +++ b/bitsy/mem.h @@ -94,7 +94,6 @@ /* * peripheral control module physical addresses */ -#define LCDREGS 0xB0100000 /* display */ #define USBREGS 0x80000000 /* serial port 0 - USB */ #define UART1REGS 0x80010000 /* serial port 1 - UART */ #define GPCLKREGS 0x80020060 /* serial port 1 - general purpose clock */ @@ -103,10 +102,13 @@ #define UART3REGS 0x80050000 /* serial port 3 - RS232 UART */ #define MCPREGS 0x80060000 /* serial port 4 - multimedia comm port */ #define SSPREGS 0x80070060 /* serial port 4 - synchronous serial port */ -#define PPCREGS 0x90060000 /* peripheral pin controller */ +#define OSTIMERREGS 0x90000000 /* operating system timer registers */ +#define POWERREGS 0x90020000 /* power management */ #define GPIOREGS 0x90040000 /* 28 general purpose IO pins */ #define INTRREGS 0x90050000 /* interrupt registers */ -#define OSTIMERREGS 0x90000000 /* operating system timer registers */ +#define PPCREGS 0x90060000 /* peripheral pin controller */ +#define MEMCONFREGS 0xA0000000 /* memory configuration */ +#define LCDREGS 0xB0100000 /* display */ /* * PCMCIA addresses diff --git a/bitsy/mmu.c b/bitsy/mmu.c index 2abcc34f7e3bc7fb47a381cc318e9a5874a10c69..2399b81ddc194f81df415bf30744b0e7a398118a 100644 --- a/bitsy/mmu.c +++ b/bitsy/mmu.c @@ -211,10 +211,18 @@ mapspecial(ulong pa, int len) /* map add on memory */ void* -mapmem(ulong pa, int len) +mapmem(ulong pa, int len, int cached) { - return _map(pa, len, EMEMZERO, EMEMTOP, L1KernelRW|L1Cached|L1Buffered, - L2KernelRW|L2Cached|L2Buffered); + ulong l1, l2; + + if(cached){ + l1 = L1KernelRW|L1Cached|L1Buffered; + l2 = L2KernelRW|L2Cached|L2Buffered; + } else { + l1 = L1KernelRW; + l2 = L2KernelRW; + } + return _map(pa, len, EMEMZERO, EMEMTOP, l1, l2); } /* map a virtual address to a physical one */ diff --git a/bitsy/sa1110uart.c b/bitsy/sa1110uart.c index e491a1f0f58d658be47a93246a97330e3b8a698f..0c2e285df6cb2b0d73f2ef295e2565007280b9bd 100644 --- a/bitsy/sa1110uart.c +++ b/bitsy/sa1110uart.c @@ -10,17 +10,6 @@ /* this isn't strictly a sa1100 driver. The rts/cts stuff is h3650 specific */ -/* hardware registers */ -typedef struct Uartregs Uartregs; -struct Uartregs -{ - ulong ctl[4]; - ulong dummya; - ulong data; - ulong dummyb; - ulong status[2]; -}; - enum { /* ctl[0] bits */ diff --git a/bitsy/trap.c b/bitsy/trap.c index b8408a953d0c6da272830ca7da5f036e8dff320a..17581135e87fc13ee9f13e5959272cccc0a20148 100644 --- a/bitsy/trap.c +++ b/bitsy/trap.c @@ -179,7 +179,7 @@ trap(Ureg *ureg) int found; Vctl *v; int user, x, rv; - ulong va; + ulong va, fsr; char buf[ERRLEN]; user = (ureg->psr & PsrMask) == PsrMusr; @@ -217,7 +217,8 @@ trap(Ureg *ureg) case PsrMabt+1: /* data fault */ va = getfar(); inst = *(ulong*)(ureg->pc); - switch(getfsr() & 0xf){ + fsr = getfsr() & 0xf; + switch(fsr){ case 0x0: panic("vector exception at %lux\n", ureg->pc); break; @@ -239,7 +240,7 @@ trap(Ureg *ureg) case 0xa: case 0xc: case 0xe: - panic("external abort at %lux\n", ureg->pc); + panic("external abort 0x%ux pc 0x%lux addr 0x%lux\n", fsr, ureg->pc, va); break; case 0x5: case 0x7: diff --git a/ip/il.c b/ip/il.c index e76545426a71e83b153b2548a5f6951dac391df4..facf2425cf2b057fa9f7656a24dc9c66977e4be4 100644 --- a/ip/il.c +++ b/ip/il.c @@ -58,7 +58,7 @@ enum AckDelay = 2*Iltickms, /* max time twixt message rcvd & ack sent */ MaxTimeout = 30*Seconds, /* max time between rexmit */ QueryTime = 10*Seconds, /* time between subsequent queries */ - DeathTime = 5*QueryTime, + DeathTime = 30*QueryTime, MaxRexmit = 16, /* max retransmissions before hangup */ Defaultwin = 20,