diff options
Diffstat (limited to 'os/fads')
| -rw-r--r-- | os/fads/NOTICE | 4 | ||||
| -rw-r--r-- | os/fads/archfads.c | 619 | ||||
| -rw-r--r-- | os/fads/archfads.h | 33 | ||||
| -rw-r--r-- | os/fads/dat.h | 162 | ||||
| -rw-r--r-- | os/fads/fads | 121 | ||||
| -rw-r--r-- | os/fads/fns.h | 117 | ||||
| -rw-r--r-- | os/fads/io.h | 1 | ||||
| -rw-r--r-- | os/fads/main.c | 392 | ||||
| -rw-r--r-- | os/fads/mem.h | 157 | ||||
| -rw-r--r-- | os/fads/mkfile | 107 | ||||
| -rw-r--r-- | os/fads/mmu.c | 20 | ||||
| -rw-r--r-- | os/fads/tlb.s | 23 |
12 files changed, 1756 insertions, 0 deletions
diff --git a/os/fads/NOTICE b/os/fads/NOTICE new file mode 100644 index 00000000..95589fda --- /dev/null +++ b/os/fads/NOTICE @@ -0,0 +1,4 @@ +Inferno® Copyright © 1996-1999 Lucent Technologies Inc. All rights reserved. +PowerPC support Copyright © 1995-1997 C H Forsyth (forsyth@terzarima.net). All rights reserved. +MPC8xx Inferno PowerPC port Copyright © 1998-2003 Vita Nuova Holdings Limited. All rights reserved. +FADS Inferno PowerPC port Copyright © 1998-2003 Vita Nuova Holdings Limited. All rights reserved. diff --git a/os/fads/archfads.c b/os/fads/archfads.c new file mode 100644 index 00000000..4ceb02a1 --- /dev/null +++ b/os/fads/archfads.c @@ -0,0 +1,619 @@ +#include "u.h" +#include "../port/lib.h" +#include "mem.h" +#include "dat.h" +#include "fns.h" +#include "io.h" + +#include "../port/netif.h" +#include "../mpc/etherif.h" +#include "../port/flashif.h" + +#include <draw.h> +#include <memdraw.h> +#include <cursor.h> +#include "screen.h" + +#include "archfads.h" + +/* + * board-specific support for the 8xxFADS (including 860/21 development system) + */ + +enum { + /* CS assignment on FADS boards */ + BOOTCS = 0, + BCSRCS = 1, + DRAM1 = 2, + DRAM2 = 3, + SDRAM = 4, + + /* sccr */ + RTSEL = IBIT(8), /* =0, select main oscillator (OSCM); =1, select external crystal (EXTCLK) */ + RTDIV = IBIT(7), /* =0, divide by 4; =1, divide by 512 */ + CRQEN = IBIT(9), /* =1, switch to high frequency when CPM active */ + PRQEN = IBIT(10), /* =1, switch to high frequency when interrupt pending */ + + /* plprcr */ + CSRC = IBIT(21), /* =0, clock is DFNH; =1, clock is DFNL */ +}; + +/* + * called early in main.c, after machinit: + * using board and architecture specific registers, initialise + * 8xx registers that need it and complete initialisation of the Mach structure. + */ +void +archinit(void) +{ + IMM *io; + int mf; + + m->bcsr = KADDR(PHYSBCSR); + m->bcsr[1] |= DisableRS232a | DisableIR | DisableEther | DisablePCMCIA | DisableRS232b; + m->bcsr[1] &= ~(DisableDRAM|DisableFlash); + m->bcsr[1] &= ~EnableSDRAM; + m->bcsr[4] &= ~EnableVideoClock; + m->bcsr[4] |= DisableVideoLamp; + io = m->iomem; /* run by reset code: no need to lock */ + if(1 || (io->sccr & RTDIV) != 0){ + /* oscillator frequency can't be determined independently: check a switch */ + if((m->bcsr[2]>>19)&(1<<2)) + m->clockgen = 5*MHz; + else + m->clockgen = 4*MHz; + } else + m->clockgen = 32768; + m->oscclk = m->clockgen/MHz; /* TO DO: 32k clock */ + io->plprcrk = KEEP_ALIVE_KEY; + io->plprcr &= ~CSRC; /* general system clock is DFNH */ + mf = (io->plprcr >> 20)+1; /* use timing set by bootstrap */ + io->plprcrk = ~KEEP_ALIVE_KEY; + io->sccrk = KEEP_ALIVE_KEY; + io->sccr |= CRQEN | PRQEN; + io->sccr |= RTSEL; /* select EXTCLK */ + io->sccrk = ~KEEP_ALIVE_KEY; + m->cpuhz = m->clockgen*mf; + m->speed = m->cpuhz/MHz; +} + +static ulong +banksize(int x, ulong *pa) +{ + IMM *io; + + io = m->iomem; + if((io->memc[x].base & 1) == 0) + return 0; /* bank not valid */ + *pa = io->memc[x].base & ~0x7FFF; + return -(io->memc[x].option&~0x7FFF); +} + +/* + * initialise the kernel's memory configuration: + * there are two banks (base0, npage0) and (base1, npage1). + * initialise any other values in conf that are board-specific. + */ +void +archconfinit(void) +{ + ulong nbytes, pa, ktop; + + conf.nscc = 2; + conf.nocts2 = 1; /* not connected on the FADS board */ + + conf.npage0 = 0; + if((m->bcsr[1] & DisableDRAM) == 0){ + nbytes = banksize(DRAM1, &pa); + if(nbytes){ + conf.npage0 = nbytes/BY2PG; + conf.base0 = pa; + } + } + + conf.npage1 = 0; + if(m->bcsr[1] & EnableSDRAM){ + nbytes = banksize(SDRAM, &pa); + if(nbytes){ + conf.npage1 = nbytes/BY2PG; + conf.base1 = pa; + } + } + + /* the following assumes the kernel text and/or data is in bank 0 */ + ktop = PGROUND((ulong)end); + ktop = PADDR(ktop) - conf.base0; + conf.npage0 -= ktop/BY2PG; + conf.base0 += ktop; +} + +static void +archidprint(void) +{ + int f, i; + ulong v; + + /* 8xx and FADS specific */ + print("IMMR: "); + v = getimmr() & 0xFFFF; + switch(v>>8){ + case 0x00: print("MPC860/821"); break; + case 0x20: print("MPC823"); break; + case 0x21: print("MPC823A"); break; + default: print("Type #%lux", v>>8); break; + } + print(", mask #%lux\n", v&0xFF); + v = m->bcsr[3]>>16; + print("MPC8xxFADS rev %lud, DB: ", ((v>>4)&8)|((v>>1)&4)|(v&3)); + f = (v>>8)&0x3F; + switch(f){ + default: print("ID#%x", f); break; + case 0x00: print("MPC860/821"); break; + case 0x01: print("MPC813"); break; + case 0x02: print("MPC821"); break; + case 0x03: print("MPC823"); break; + case 0x20: print("MPC801"); break; + case 0x21: print("MPC850"); break; + case 0x22: print("MPC860"); break; + case 0x23: print("MPC860SAR"); break; + case 0x24: print("MPC860T"); break; + } + print("ADS, rev #%lux\n", (m->bcsr[2]>>16)&7); + for(i=0; i<=4; i++) + print("BCSR%d: %8.8lux\n", i, m->bcsr[i]); + v = m->bcsr[2]; + f = (v>>28)&0xF; + switch(f){ + default: print("Unknown"); break; + case 4: print("SM732A2000/SM73228 - 8M SIMM"); break; + case 5: print("SM732A1000A/SM73218 - 4M SIMM"); break; + case 6: print("MCM29080 - 8M SIMM"); break; + case 7: print("MCM29040 - 4M SIMM"); break; + case 8: print("MCM29020 - 2M SIMM"); break; + } + switch((m->bcsr[3]>>20)&7){ + default: i = 0; break; + case 1: i = 150; break; + case 2: i = 120; break; + case 3: i = 90; break; + } + print(" flash, %dns\n", i); + f = (v>>23)&0xF; + switch(f&3){ + case 0: i = 4; break; + case 1: i = 32; break; + case 2: i = 16; break; + case 3: i = 8; break; + } + print("%dM SIMM, ", i); + switch(f>>2){ + default: i = 0; break; + case 2: i = 70; break; + case 3: i = 60; break; + } + print("%dns\n", i); + print("options: #%lux\n", (m->bcsr[2]>>19)&0xF); + print("plprcr=%8.8lux sccr=%8.8lux\n", m->iomem->plprcr, m->iomem->sccr); +} + +void +cpuidprint(void) +{ + print("PVR: "); + switch(m->cputype){ + case 0x01: print("MPC601"); break; + case 0x03: print("MPC603"); break; + case 0x04: print("MPC604"); break; + case 0x06: print("MPC603e"); break; + case 0x07: print("MPC603e-v7"); break; + case 0x50: print("MPC8xx"); break; + default: print("PowerPC version #%x", m->cputype); break; + } + print(", revision #%lux\n", getpvr()&0xffff); + archidprint(); + print("%lud MHz system\n", m->cpuhz/MHz); + print("\n"); +} + +/* + * provide value for #r/switch (devrtc.c) + */ +int +archoptionsw(void) +{ + return (m->bcsr[2]>>19)&0xF; /* value of switch DS1 */ +} + +/* + * invoked by clock.c:/^clockintr + */ +static void +twinkle(void) +{ + if(m->ticks%MS2TK(1000) == 0) + m->bcsr[4] ^= DisableLamp; +} + +void (*archclocktick)(void) = twinkle; + +/* + * invoked by ../port/taslock.c:/^ilock: + * reset watchdog timer here, if there is one and it is enabled + * (qboot currently disables it on the FADS board) + */ +void +clockcheck(void) +{ +} + +/* + * for devflash.c:/^flashreset + * retrieve flash type, virtual base and length and return 0; + * return -1 on error (no flash) + */ +int +archflashreset(int bank, Flash *f) +{ + char *t; + int mbyte; + + if(bank != 0) + return -1; + switch((m->bcsr[2]>>28)&0xF){ + default: return -1; /* unknown or not there */ + case 4: mbyte=8; t = "SM732x8"; break; + case 5: mbyte=4; t = "SM732x8"; break; + case 6: mbyte=8; t = "AMD29F0x0"; break; + case 7: mbyte=4; t = "AMD29F0x0"; break; + case 8: mbyte=2; t = "AMD29F0x0"; break; + } + f->type = t; + f->addr = KADDR(PHYSFLASH); + f->size = mbyte*1024*1024; + f->width = 4; + f->interleave = 3; + return 0; +} + +void +archflashwp(Flash*, int) +{ +} + +int +archether(int ctlrno, Ether *ether) +{ + if(isaconfig("ether", ctlrno, ether) == 0) + return -1; + return 1; +} + +/* + * enable the clocks for the given SCC ether and reveal them to the caller. + * do anything else required to prepare the transceiver (eg, set full-duplex, reset loopback). + */ +int +archetherenable(int cpmid, int *rcs, int *tcs, int mbps, int fullduplex) +{ + IMM *io; + + USED(mbps, fullduplex); /* TO DO */ + switch(cpmid){ + default: + /* no other SCCs are wired on the FADS board */ + return -1; + + case CPscc2: /* assume 8xxFADS board with 823DABS */ + io = ioplock(); + m->bcsr[1] |= DisableIR|DisableRS232b; + m->bcsr[1] &= ~DisableEther; + io->papar |= SIBIT(6)|SIBIT(5); /* enable CLK2 and CLK3 */ + io->padir &= ~(SIBIT(6)|SIBIT(5)); + /* ETHLOOP etc reset in BCSR elsewhere */ + iopunlock(); + *rcs = CLK2; + *tcs = CLK3; + break; + + case CPscc1: /* assume 860/21 development board */ + io = ioplock(); + m->bcsr[1] |= DisableIR|DisableRS232b; /* TO DO: might not be shared with RS232b */ + m->bcsr[1] &= ~DisableEther; + io->papar |= SIBIT(6)|SIBIT(7); /* enable CLK2 and CLK1 */ + io->padir &= ~(SIBIT(6)|SIBIT(7)); + + /* settings peculiar to 860/821 development board */ + io->pcpar &= ~(SIBIT(4)|SIBIT(5)|SIBIT(6)); /* ETHLOOP, TPFULDL~, TPSQEL~ */ + io->pcdir |= SIBIT(4)|SIBIT(5)|SIBIT(6); + io->pcdat &= ~SIBIT(4); + io->pcdat |= SIBIT(5)|SIBIT(6); + iopunlock(); + *rcs = CLK2; + *tcs = CLK1; + break; + } + return 0; +} + +/* + * do anything extra required to enable the UART on the given CPM port + */ +void +archenableuart(int id, int irda) +{ + switch(id){ + case CPsmc1: + m->bcsr[1] &= ~DisableRS232a; + break; + case CPscc2: + m->bcsr[1] |= DisableEther|DisableIR|DisableRS232b; + if(irda) + m->bcsr[1] &= ~DisableIR; + else + m->bcsr[1] &= ~DisableRS232b; + break; + default: + /* nothing special */ + break; + } +} + +/* + * do anything extra required to disable the UART on the given CPM port + */ +void +archdisableuart(int id) +{ + switch(id){ + case CPsmc1: + m->bcsr[1] |= DisableRS232a; + break; + case CPscc2: + m->bcsr[1] |= DisableIR|DisableRS232b; + break; + default: + /* nothing special */ + break; + } +} + +/* + * enable the external USB transceiver + * speed is 12MHz if highspeed is non-zero; 1.5MHz if zero + * master is non-zero if the node is acting as USB Host and should provide power + */ +void +archenableusb(int highspeed, int master) +{ + if(highspeed) + m->bcsr[4] |= USBFullSpeed; + else + m->bcsr[4] &= ~USBFullSpeed; + if(master) + m->bcsr[4] &= ~DisableUSBVcc; + else + m->bcsr[4] |= DisableUSBVcc; + eieio(); + m->bcsr[4] &= ~DisableUSB; +} + +/* + * shut down the USB transceiver + */ +void +archdisableusb(void) +{ + m->bcsr[4] |= DisableUSBVcc | DisableUSB; +} + +/* + * set the external infrared transceiver to the given speed + */ +void +archsetirxcvr(int highspeed) +{ + if(!highspeed){ + /* force low edge after enable to put TFDS6000 xcvr in low-speed mode (see 4.9.2.1 in FADS manual) */ + m->bcsr[1] |= DisableIR; + microdelay(2); + } + m->bcsr[1] &= ~DisableIR; +} + +/* + * force hardware reset/reboot + */ +void +archreboot(void) +{ + IMM *io; + + io = m->iomem; + io->plprcrk = KEEP_ALIVE_KEY; + io->plprcr |= 1<<7; /* checkstop reset enable */ + io->plprcrk = ~KEEP_ALIVE_KEY; + m->iomem->padat &= ~SIBIT(4); /* drop backlight */ + eieio(); + io->sdcr = 1; + eieio(); + io->lccr = 0; + eieio(); + firmware(0); +} + +/* + * board-specific PCMCIA support: assumes slot B on 82xFADS + */ + +int +pcmslotavail(int slotno) +{ + return slotno == 1; +} + +void +pcmenable(void) +{ + ioplock(); + m->bcsr[1] = (m->bcsr[1] | PCCVPPHiZ) & ~PCCVPP5V; + m->bcsr[1] |= PCCVCC0V; + m->bcsr[1] &= ~DisablePCMCIA; + m->bcsr[1] &= ~PCCVCC5V; /* apply Vcc */ + iopunlock(); +} + +int +pcmpowered(int) +{ + ulong r; + + r = ~m->bcsr[1]&PCCVCCMask; /* active low */ + if(r == PCCVCC5V) + return 5; + if(r == PCCVCC3V) + return 3; + return 0; +} + +void +pcmsetvcc(int, int v) +{ + if(v == 5) + v = PCCVCC5V; + else if(v == 3) + v = PCCVCC3V; + else + v = 0; + ioplock(); + m->bcsr[1] = (m->bcsr[1] | PCCVCCMask) & ~v; /* active low */ + iopunlock(); +} + +void +pcmsetvpp(int, int v) +{ + if(v == 5) + v = PCCVPP5V; + else if(v == 12) + v = PCCVPP12V; + else if(v == 0) + v = PCCVPP0V; + else + v = 0; /* Hi-Z */ + ioplock(); + m->bcsr[1] = (m->bcsr[1] | PCCVPPHiZ) & ~v; /* active low */ + iopunlock(); +} + +void +pcmpower(int slotno, int on) +{ + if(!on){ + pcmsetvcc(slotno, 0); /* turn off card power */ + pcmsetvpp(slotno, -1); /* turn off programming voltage (Hi-Z) */ + }else + pcmsetvcc(slotno, 5); +} + +/* + * enable/disable the LCD panel's backlight via + * York touch panel interface (does no harm without it) + */ +void +archbacklight(int on) +{ + IMM *io; + + delay(2); + io = ioplock(); + io->papar &= ~SIBIT(4); + io->padir |= SIBIT(4); + if(on) + io->padat |= SIBIT(4); + else + io->padat &= ~SIBIT(4); + iopunlock(); +} + +/* + * set parameters to describe the screen + */ +int +archlcdmode(Mode *m) +{ + m->x = 640; + m->y = 480; + m->d = 3; + m->lcd.freq = 25000000; + m->lcd.ac = 0; + m->lcd.vpw = 2; + m->lcd.wbf = 34; + m->lcd.wbl = 106; + m->lcd.flags = IsColour | IsTFT | OELow | HsyncLow | VsyncLow; + m->lcd.notpdpar = SIBIT(6); + return 0; +} + +/* + * reset 823 video port for devvid.c + */ +void +archresetvideo(void) +{ + ioplock(); + m->bcsr[4] &= ~DisableVideoLamp; + m->bcsr[4] |= EnableVideoPort; + eieio(); + m->bcsr[4] &= ~EnableVideoPort; /* falling edge to reset */ + iopunlock(); + delay(6); + ioplock(); + m->bcsr[4] |= EnableVideoPort; + iopunlock(); + delay(6); +} + +/* + * enable 823 video port and clock + */ +void +archenablevideo(void) +{ + ioplock(); + m->bcsr[4] |= EnableVideoClock|EnableVideoPort; /* enable AFTER pdpar/pddir to avoid damage */ + iopunlock(); +} + +/* + * disable 823 video port and clock + */ +void +archdisablevideo(void) +{ + ioplock(); + m->bcsr[4] &= ~(EnableVideoClock|EnableVideoPort); + m->bcsr[4] |= DisableVideoLamp; + iopunlock(); +} + +/* + * allocate a frame buffer for the video, aligned on 16 byte boundary + */ +uchar* +archvideobuffer(long nbytes) +{ + /* we shall use the on-board SDRAM if the kernel hasn't grabbed it */ + if((m->bcsr[1] & EnableSDRAM) == 0){ + m->bcsr[1] |= EnableSDRAM; + return KADDR(PHYSSDRAM); + } + return xspanalloc(nbytes, 16, 0); +} + +/* + * there isn't a hardware keyboard port + */ +void +archkbdinit(void) +{ +} diff --git a/os/fads/archfads.h b/os/fads/archfads.h new file mode 100644 index 00000000..a35230f9 --- /dev/null +++ b/os/fads/archfads.h @@ -0,0 +1,33 @@ + +enum { + /* BCSR1 bits */ + DisableFlash= IBIT(0), + DisableDRAM= IBIT(1), + DisableEther= IBIT(2), + DisableIR= IBIT(3), + DisableRS232a= IBIT(7), + DisablePCMCIA= IBIT(8), + PCCVCCMask= IBIT(9)|IBIT(15), + PCCVPPMask= IBIT(10)|IBIT(11), + DisableRS232b= IBIT(13), + EnableSDRAM= IBIT(14), + + PCCVCC0V= IBIT(15)|IBIT(9), + PCCVCC5V= IBIT(9), /* active low */ + PCCVCC3V= IBIT(15), /* active low */ + PCCVPP0V= IBIT(10)|IBIT(11), /* active low */ + PCCVPP5V= IBIT(10), /* active low */ + PCCVPP12V= IBIT(11), /* active low */ + PCCVPPHiZ= IBIT(10)|IBIT(11), + + /* BCSR4 bits */ + DisableTPDuplex= IBIT(1), + DisableLamp= IBIT(3), + DisableUSB= IBIT(4), + USBFullSpeed= IBIT(5), + DisableUSBVcc= IBIT(6), + DisableVideoLamp= IBIT(8), + EnableVideoClock= IBIT(9), + EnableVideoPort= IBIT(10), + DisableModem= IBIT(11), +}; diff --git a/os/fads/dat.h b/os/fads/dat.h new file mode 100644 index 00000000..19d7c560 --- /dev/null +++ b/os/fads/dat.h @@ -0,0 +1,162 @@ +typedef struct Conf Conf; +typedef struct FPU FPU; +typedef struct FPenv FPenv; +typedef struct IMM IMM; +typedef struct Irqctl Irqctl; +typedef struct ISAConf ISAConf; +typedef struct Label Label; +typedef struct Lock Lock; +typedef struct Mach Mach; +typedef struct Map Map; +typedef struct Power Power; +typedef struct RMap RMap; +typedef struct Ureg Ureg; + +typedef ulong Instr; + +#define MACHP(n) (n==0? &mach0 : *(Mach**)0) + +struct Lock +{ + ulong key; + ulong pc; + ulong sr; + int pri; +}; + +struct Label +{ + ulong sp; + ulong pc; +}; + +/* + * Proc.fpstate + */ +enum +{ + FPINIT, + FPACTIVE, + FPINACTIVE, +}; + +/* + * This structure must agree with FPsave and FPrestore asm routines + */ +struct FPenv +{ + union { + double fpscrd; + struct { + ulong pad; + ulong fpscr; + }; + }; + int fpistate; /* emulated fp */ + ulong emreg[32][3]; /* emulated fp */ +}; +/* + * This structure must agree with fpsave and fprestore asm routines + */ +struct FPU +{ + double fpreg[32]; + FPenv env; +}; + +struct Conf +{ + ulong nmach; /* processors */ + ulong nproc; /* processes */ + ulong npage0; /* total physical pages of memory */ + ulong npage1; /* total physical pages of memory */ + ulong npage; /* total physical pages of memory */ + ulong base0; /* base of bank 0 */ + ulong base1; /* base of bank 1 */ + ulong ialloc; /* max interrupt time allocation in bytes */ + + int nscc; /* number of SCCs implemented */ + ulong smcuarts; /* bits for SMCs to define as eiaN */ + ulong sccuarts; /* bits for SCCs to define as eiaN */ + int nocts2; /* CTS2 and CD2 aren't connected */ + uchar* nvrambase; /* virtual address of nvram */ + ulong nvramsize; /* size in bytes */ +}; + +#include "../port/portdat.h" + +/* + * machine dependent definitions not used by ../port/dat.h + */ + +struct Mach +{ + /* OFFSETS OF THE FOLLOWING KNOWN BY l.s */ + int machno; /* physical id of processor (unused) */ + ulong splpc; /* pc of last caller to splhi (unused) */ + int mmask; /* 1<<m->machno (unused) */ + + /* ordering from here on irrelevant */ + ulong ticks; /* of the clock since boot time */ + Proc *proc; /* current process on this processor */ + Label sched; /* scheduler wakeup */ + Lock alarmlock; /* access to alarm list */ + void *alarm; /* alarms bound to this clock */ + int nrdy; + int speed; /* general system clock in MHz */ + long oscclk; /* oscillator frequency (MHz) */ + long cpuhz; /* general system clock (cycles) */ + long clockgen; /* clock generator frequency (cycles) */ + int cputype; + ulong delayloop; + ulong* bcsr; + IMM* iomem; /* MPC8xx internal i/o control memory */ + + /* MUST BE LAST */ + int stack[1]; +}; +extern Mach mach0; + + +/* + * a parsed .ini line + */ +#define NISAOPT 8 + +struct ISAConf { + char* type; + ulong port; + ulong irq; + ulong mem; + int dma; + ulong size; + ulong freq; + uchar bus; + + int nopt; + char* opt[NISAOPT]; +}; + +struct Map { + int size; + ulong addr; +}; + +struct RMap { + char* name; + Map* map; + Map* mapend; + + Lock; +}; + +struct Power { + Dev* dev; + int (*powerdown)(Power*); + int (*powerup)(Power*); + int state; + void* arg; +}; + +extern register Mach *m; +extern register Proc *up; diff --git a/os/fads/fads b/os/fads/fads new file mode 100644 index 00000000..1f1a2959 --- /dev/null +++ b/os/fads/fads @@ -0,0 +1,121 @@ +# fads board with remote file system on ether or ppp +dev + root + cons archfads screen + env + mnt + pipe + prog + rtc + srv + dup + ssl + cap + + draw + pointer + + ip bootp ip ipv6 ipaux iproute arp netlog ptclbsum iprouter plan9 nullmedium pktmedium + ether netif netaux + uart + flash +# usb + touch spi +# pcmcia cis +# ata inb + + ftl +# kfs chk kcon console dat dentry fcall fs fswren iobuf kfs sub uid +# kprof + +# vid i2c + i2c i2c + +ip + il + tcp + udp + ipifc + icmp + icmp6 + ipmux + +lib + interp + tk + draw + memlayer + memdraw + keyring + sec + mp + math + kern + +link + etherscc + ethermedium + flashamd29f0x0 +# pppmedium ppp compress + +mod + sys + draw + tk + math + keyring + +port + alarm + alloc + allocb + chan + dev + dial + dis + discall + exception + exportfs + inferno + latin1 + nocache + nodynld + parse + pgrp + print + proc + qio + qlock + random + sysfile + taslock + xalloc + +code + int cflag = 0; + int consoleprint = 1; + int panicreset = 0; + int kernel_pool_pcnt = 10; + int main_pool_pcnt = 40; + int heap_pool_pcnt = 20; + int image_pool_pcnt = 40; + +init + mpcinit + +root + /chan + /dev + /dis + /env + /fd / + /n + /net + /nvfs / + /prog + /icons + /osinit.dis + /dis/lib/auth.dis + /dis/lib/ssl.dis + /n/local / + /nvfs/default /usr/inferno/keyring/default diff --git a/os/fads/fns.h b/os/fads/fns.h new file mode 100644 index 00000000..c4892a82 --- /dev/null +++ b/os/fads/fns.h @@ -0,0 +1,117 @@ +#include "../port/portfns.h" + +void addpower(Power*); +void archbacklight(int); +void archconfinit(void); +void archdisableuart(int); +void archdisableusb(void); +void archdisablevideo(void); +void archenableuart(int, int); +void archenableusb(int, int); +void archenablevideo(void); +void archkbdinit(void); +void archresetvideo(void); +int archetherenable(int, int*, int*, int, int); +void archinit(void); +int archoptionsw(void); +void archreboot(void); +void archsetirxcvr(int); +uchar* archvideobuffer(long); +ulong baudgen(int, int); +int brgalloc(void); +void brgfree(int); +int cistrcmp(char*, char*); +int cistrncmp(char*, char*, int); +void clockcheck(void); +void clockinit(void); +void clockintr(Ureg*); +void clrfptrap(void); +#define coherence() /* nothing needed for uniprocessor */ +void cpminit(void); +void cpuidprint(void); +void dcflush(void*, ulong); +void dcinval(void*, ulong); +void delay(int); +void dtlbmiss(void); +void dumplongs(char*, ulong*, int); +void dumpregs(Ureg*); +void eieio(void); +void faultpower(Ureg*); +void firmware(int); +void fpinit(void); +int fpipower(Ureg*); +void fpoff(void); +void fprestore(FPU*); +void fpsave(FPU*); +ulong fpstatus(void); +char* getconf(char*); +ulong getdar(void); +ulong getdec(void); +ulong getdepn(void); +ulong getdsisr(void); +ulong getimmr(void); +ulong getmsr(void); +ulong getpvr(void); +ulong gettbl(void); +ulong gettbu(void); +void gotopc(ulong); +void icflush(void*, ulong); +void idle(void); +#define idlehands() /* nothing to do in the runproc */ +void intr(Ureg*); +void intrenable(int, void (*)(Ureg*, void*), void*, int, char*); +void intrdisable(int, void (*)(Ureg*, void*), void*, int, char*); +int intrstats(char*, int); +void intrvec(void); +int isaconfig(char*, int, ISAConf*); +int isvalid_va(void*); +void itlbmiss(void); +void kbdinit(void); +void kbdreset(void); +void lcdpanel(int); +void links(void); +void mapfree(RMap*, ulong, int); +void mapinit(RMap*, Map*, int); +void mathinit(void); +void mmuinit(void); +ulong* mmuwalk(ulong*, ulong, int); +void pcmenable(void); +void pcmintrenable(int, void (*)(Ureg*, void*), void*); +int pcmpin(int slot, int type); +void pcmpower(int, int); +int pcmpowered(int); +void pcmsetvcc(int, int); +void pcmsetvpp(int, int); +int pcmslotsavail(int); +void procsave(Proc*); +void procsetup(Proc*); +void putdec(ulong); +void putmsr(ulong); +void puttwb(ulong); +ulong rmapalloc(RMap*, ulong, int, int); +void screeninit(void); +int screenprint(char*, ...); /* debugging */ +void screenputs(char*, int); +int segflush(void*, ulong); +void setpanic(void); +long spioutin(void*, long, void*); +void spireset(void); +ulong _tas(ulong*); +void trapinit(void); +void trapvec(void); +void uartinstall(void); +void uartspecial(int, int, Queue**, Queue**, int (*)(Queue*, int)); +void uartwait(void); /* debugging */ +void videoreset(void); +void videotest(void); +void wbflush(void); + +#define waserror() (up->nerrlab++, setlabel(&up->errlab[up->nerrlab-1])) +ulong getcallerpc(void*); + +#define KADDR(a) ((void*)((ulong)(a)|KZERO)) +#define PADDR(a) ((((ulong)(a)&KSEGM)!=KSEG0)?(ulong)(a):((ulong)(a)&~KZERO)) + +/* IBM bit field order */ +#define IBIT(b) ((ulong)1<<(31-(b))) +#define SIBIT(n) ((ushort)1<<(15-(n))) diff --git a/os/fads/io.h b/os/fads/io.h new file mode 100644 index 00000000..30312c68 --- /dev/null +++ b/os/fads/io.h @@ -0,0 +1 @@ +#include "../mpc/800io.h" diff --git a/os/fads/main.c b/os/fads/main.c new file mode 100644 index 00000000..93ba7f95 --- /dev/null +++ b/os/fads/main.c @@ -0,0 +1,392 @@ +#include "u.h" +#include "../port/lib.h" +#include "mem.h" +#include "dat.h" +#include "fns.h" +#include "io.h" +#include "ureg.h" +#include "version.h" + +/* where b.com or qboot leaves configuration info */ +#define BOOTARGS ((char*)CONFADDR) +#define BOOTARGSLEN 1024 +#define MAXCONF 32 + +extern ulong kerndate; +extern int cflag; +int remotedebug; + +extern int main_pool_pcnt; +extern int heap_pool_pcnt; +extern int image_pool_pcnt; + +char bootargs[BOOTARGSLEN+1]; +char bootdisk[KNAMELEN]; +char *confname[MAXCONF]; +char *confval[MAXCONF]; +int nconf; + +extern void addconf(char *, char *); + +/* + * arguments passed to initcode and /boot + */ +char argbuf[128]; + +static void +options(void) +{ + long i, n; + char *cp, *line[MAXCONF], *p, *q; + + /* + * parse configuration args from bootstrap + */ + memmove(bootargs, BOOTARGS, BOOTARGSLEN); /* where b.com leaves its config */ + cp = bootargs; + cp[BOOTARGSLEN-1] = 0; + + /* + * Strip out '\r', change '\t' -> ' '. + */ + p = cp; + for(q = cp; *q; q++){ + if(*q == '\r') + continue; + if(*q == '\t') + *q = ' '; + *p++ = *q; + } + *p = 0; + + n = getfields(cp, line, MAXCONF, 1, "\n"); + for(i = 0; i < n; i++){ + if(*line[i] == '#') + continue; + cp = strchr(line[i], '='); + if(cp == 0) + continue; + *cp++ = 0; + confname[nconf] = line[i]; + confval[nconf] = cp; + nconf++; + } +} + +void +doc(char *m) +{ + USED(m); + print("%s...\n", m); uartwait(); +} + +static void +poolsizeinit(void) +{ + ulong nb; + + nb = conf.npage*BY2PG; + poolsize(mainmem, (nb*main_pool_pcnt)/100, 0); + poolsize(heapmem, (nb*heap_pool_pcnt)/100, 0); + poolsize(imagmem, (nb*image_pool_pcnt)/100, 1); +} + +static void +serialconsole(void) +{ + char *p; + int port, baud; + + p = getconf("console"); + if(p == nil) + p = "0"; + if(p != nil && !remotedebug){ + port = strtol(p, nil, 0); + baud = 9600; + p = getconf("baud"); + if(p != nil){ + baud = strtol(p, nil, 0); + if(baud < 9600) + baud = 9600; + } + uartspecial(port, baud, &kbdq, &printq, kbdcr2nl); + } +} + +void +main(void) +{ + machinit(); + options(); + archinit(); + quotefmtinstall(); + confinit(); + cpminit(); + xinit(); + poolsizeinit(); + trapinit(); + mmuinit(); + printinit(); + uartinstall(); + serialconsole(); + doc("screeninit"); + screeninit(); + doc("kbdinit"); + kbdinit(); + doc("clockinit"); + clockinit(); + doc("procinit"); + procinit(); + cpuidprint(); + doc("links"); + links(); + doc("chandevreset"); + chandevreset(); + + eve = strdup("inferno"); + + print("\nInferno %s\n", VERSION); + print("Vita Nuova\n"); + print("conf %s (%lud) jit %d\n\n",conffile, kerndate, cflag); + + doc("userinit"); + userinit(); + doc("schedinit"); + schedinit(); +} + +void +machinit(void) +{ + int n; + + n = m->machno; + memset(m, 0, sizeof(Mach)); + m->machno = n; + m->mmask = 1<<m->machno; + m->iomem = KADDR(getimmr() & ~0xFFFF); + m->cputype = getpvr()>>16; + m->delayloop = 20000; /* initial estimate only; set by clockinit */ + m->speed = 50; /* initial estimate only; set by archinit */ +} + +void +init0(void) +{ + Osenv *o; + int i; + char buf[2*KNAMELEN]; + + up->nerrlab = 0; + + spllo(); + + if(waserror()) + panic("init0"); + /* + * These are o.k. because rootinit is null. + * Then early kproc's will have a root and dot. + */ + o = up->env; + o->pgrp->slash = namec("#/", Atodir, 0, 0); + cnameclose(o->pgrp->slash->name); + o->pgrp->slash->name = newcname("/"); + o->pgrp->dot = cclone(o->pgrp->slash); + + chandevinit(); + + if(!waserror()){ + ksetenv("cputype", "power", 0); + snprint(buf, sizeof(buf), "power %s", conffile); + ksetenv("terminal", buf, 0); + poperror(); + } + for(i = 0; i < nconf; i++) + if(confname[i][0] != '*'){ + if(!waserror()){ + ksetenv(confname[i], confval[i], 0); + poperror(); + } + } + + poperror(); + disinit("/osinit.dis"); +} + +void +userinit(void) +{ + Proc *p; + Osenv *o; + + p = newproc(); + o = p->env; + + o->fgrp = newfgrp(nil); + + o->pgrp = newpgrp(); + o->egrp = newegrp(); + kstrdup(&o->user, eve); + + strcpy(p->text, "interp"); + + /* + * Kernel Stack + */ + p->sched.pc = (ulong)init0; + p->sched.sp = (ulong)p->kstack+KSTACK; + + ready(p); +} + +Conf conf; + +void +addconf(char *name, char *val) +{ + if(nconf >= MAXCONF) + return; + confname[nconf] = name; + confval[nconf] = val; + nconf++; +} + +char* +getconf(char *name) +{ + int i; + + for(i = 0; i < nconf; i++) + if(cistrcmp(confname[i], name) == 0) + return confval[i]; + return 0; +} + +void +confinit(void) +{ + char *p; + int pcnt; + + if(p = getconf("*kernelpercent")) + pcnt = 100 - strtol(p, 0, 0); + else + pcnt = 0; + + conf.nscc = 4; + conf.smcuarts = 1<<0; /* SMC1 (usual console) */ + conf.sccuarts = 1<<1; /* SCC2 available by default */ + + archconfinit(); + + conf.npage = conf.npage0 + conf.npage1; + if(pcnt < 10) + pcnt = 70; + conf.ialloc = (((conf.npage*(100-pcnt))/100)/2)*BY2PG; + + conf.nproc = 100 + ((conf.npage*BY2PG)/MB)*5; + conf.nmach = MAXMACH; +} + +void +exit(int ispanic) +{ + up = 0; + spllo(); + print("cpu %d exiting\n", m->machno); + + /* Shutdown running devices */ + chandevshutdown(); + + delay(1000); + splhi(); + if(ispanic) + for(;;); + archreboot(); +} + +void +reboot(void) +{ + exit(0); +} + +void +halt(void) +{ + print("cpu halted\n"); + microdelay(1000); + for(;;) + ; +} + +int +isaconfig(char *class, int ctlrno, ISAConf *isa) +{ + char cc[KNAMELEN], *p; + int i; + + snprint(cc, sizeof cc, "%s%d", class, ctlrno); + p = getconf(cc); + if(p == nil) + return 0; + + isa->nopt = tokenize(p, isa->opt, NISAOPT); + for(i = 0; i < isa->nopt; i++){ + p = isa->opt[i]; + if(cistrncmp(p, "type=", 5) == 0) + isa->type = p + 5; + else if(cistrncmp(p, "port=", 5) == 0) + isa->port = strtoul(p+5, &p, 0); + else if(cistrncmp(p, "irq=", 4) == 0) + isa->irq = strtoul(p+4, &p, 0); + else if(cistrncmp(p, "mem=", 4) == 0) + isa->mem = strtoul(p+4, &p, 0); + else if(cistrncmp(p, "size=", 5) == 0) + isa->size = strtoul(p+5, &p, 0); + else if(cistrncmp(p, "freq=", 5) == 0) + isa->freq = strtoul(p+5, &p, 0); + else if(cistrncmp(p, "dma=", 4) == 0) + isa->dma = strtoul(p+4, &p, 0); + } + return 1; +} + +/* + * Save the mach dependent part of the process state. + */ +void +procsave(Proc*) +{ +} + +void +uartputs(char *s, int n) +{ +// screenputs(buf, n); + putstrn(s, n); + uartwait(); +} + +/* stubs */ +void +setfsr(ulong) +{ +} + +ulong +getfsr() +{ + return 0; +} + +void +setfcr(ulong) +{ +} + +ulong +getfcr() +{ + return 0; +} diff --git a/os/fads/mem.h b/os/fads/mem.h new file mode 100644 index 00000000..02cf8f43 --- /dev/null +++ b/os/fads/mem.h @@ -0,0 +1,157 @@ +/* + * Memory and machine-specific definitions. Used in C and assembler. + */ + +/* + * Sizes + */ + +#define BI2BY 8 /* bits per byte */ +#define BI2WD 32 /* bits per word */ +#define BY2WD 4 /* bytes per word */ +#define BY2V 8 /* bytes per double word */ +#define BY2PG 4096 /* bytes per page */ +#define WD2PG (BY2PG/BY2WD) /* words per page */ +#define PGSHIFT 12 /* log(BY2PG) */ +#define ROUND(s, sz) (((s)+(sz-1))&~(sz-1)) +#define PGROUND(s) ROUND(s, BY2PG) +#define CACHELINELOG 4 +#define CACHELINESZ (1<<CACHELINELOG) + +#define MAXMACH 1 /* max # cpus system can run */ +#define MACHSIZE BY2PG + +/* + * Time + */ +#define HZ 100 /* clock frequency */ +#define MS2HZ (1000/HZ) /* millisec per clock tick */ +#define TK2SEC(t) ((t)/HZ) /* ticks to seconds */ +#define MS2TK(t) ((t)/MS2HZ) /* milliseconds to ticks */ +#define MHz 1000000 + +/* + * MSR bits + */ + +#define POW 0x40000 /* enable power mgmt */ +#define TGPR 0x20000 /* GPR0-3 remapped; 603/603e specific */ +#define ILE 0x10000 /* interrupts little endian */ +#define EE 0x08000 /* enable external/decrementer interrupts */ +#define PR 0x04000 /* =1, user mode */ +#define FPE 0x02000 /* enable floating point */ +#define ME 0x01000 /* enable machine check exceptions */ +#define FE0 0x00800 +#define SE 0x00400 /* single-step trace */ +#define BE 0x00200 /* branch trace */ +#define FE1 0x00100 +#define MSR_IP 0x00040 /* =0, vector to nnnnn; =1, vector to FFFnnnnn */ +#define IR 0x00020 /* enable instruction address translation */ +#define DR 0x00010 /* enable data address translation */ +#define RI 0x00002 /* exception is recoverable */ +#define LE 0x00001 /* little endian mode */ + +#define KMSR (ME|FE0|FE1|FPE) +#define UMSR (KMSR|PR|EE|IR|DR) + +/* + * Magic registers + */ + +#define MACH 30 /* R30 is m-> */ +#define USER 29 /* R29 is up-> */ +#define IOMEMR 28 /* R28 will be iomem-> */ + +/* + * Fundamental addresses + */ + +#define UREGSIZE ((8+32)*4) + +/* + * MMU + */ + +/* L1 table entry and Mx_TWC flags */ +#define PTEVALID (1<<0) +#define PTEWT (1<<1) /* write through */ +#define PTE4K (0<<2) +#define PTE512K (1<<2) +#define PTE8MB (3<<2) +#define PTEG (1<<4) /* guarded */ + +/* L2 table entry and Mx_RPN flags (also PTEVALID) */ +#define PTECI (1<<1) /* cache inhibit */ +#define PTESH (1<<2) /* page is shared; ASID ignored */ +#define PTELPS (1<<3) /* large page size */ +#define PTEWRITE 0x9F0 + +/* TLB and MxEPN flag */ +#define TLBVALID (1<<9) + +/* + * Address spaces + */ + +#define KUSEG 0x00000000 +#define KSEG0 0x20000000 +#define KSEGM 0xE0000000 /* mask to check which seg */ + +#define KZERO KSEG0 /* base of kernel address space */ +#define KTZERO (KZERO+0x3000) /* first address in kernel text */ +#define KSTACK 8192 /* Size of kernel stack */ + +#define CONFADDR (KZERO|0x200000) /* where qboot leaves configuration info */ + +/* + * Exception codes (trap vectors) + */ +#define CRESET 0x01 +#define CMCHECK 0x02 +#define CDSI 0x03 +#define CISI 0x04 +#define CEI 0x05 +#define CALIGN 0x06 +#define CPROG 0x07 +#define CFPU 0x08 +#define CDEC 0x09 +#define CSYSCALL 0x0C +#define CTRACE 0x0D +#define CFPA 0x0E +/* rest are power-implementation dependent (8xx) */ +#define CEMU 0x10 +#define CIMISS 0x11 +#define CDMISS 0x12 +#define CITLBE 0x13 +#define CDTLBE 0x14 +#define CDBREAK 0x1C +#define CIBREAK 0x1D +#define CPBREAK 0x1E +#define CDPORT 0x1F + +/* + * MPC8xx physical addresses + */ + +/* those encouraged by mpc8bug */ +#define PHYSDRAM 0x00000000 +#define PHYSBCSR 0x02100000 +#define PHYSIMM 0x02200000 +#define PHYSFLASH 0x02800000 + +/* remaining ones are our choice */ +#define PHYSSDRAM 0x03000000 +#define PHYSPCMCIA 0x04000000 +#define PCMCIALEN (8*MB) /* chosen to allow mapping by single TLB entry */ +#define ISAIO (KZERO|PHYSPCMCIA) /* for inb.s */ + +/* + * MPC8xx dual-ported CPM memory physical addresses + */ +#define PHYSDPRAM (PHYSIMM+0x2000) +#define DPLEN1 0x200 +#define DPLEN2 0x400 +#define DPLEN3 0x800 +#define DPBASE (PHYSDPRAM+DPLEN1) + +#define KEEP_ALIVE_KEY 0x55ccaa33 /* clock and rtc register key */ diff --git a/os/fads/mkfile b/os/fads/mkfile new file mode 100644 index 00000000..afc241a1 --- /dev/null +++ b/os/fads/mkfile @@ -0,0 +1,107 @@ +SYSTARG=Inferno +OBJTYPE=power +<../../mkconfig + +#Configurable parameters + +CONF=fads #default configuration +CONFLIST=fads fadskfs fads2 +CLEANCONFLIST=paq +KZERO=0x20003020 + +SYSTARG=$OSTARG +OBJTYPE=power +INSTALLDIR=$ROOT/Inferno/$OBJTYPE/bin #path of directory where kernel is installed +#INSTALLDIR=/$OBJTYPE + +#end configurable parameters + +<$ROOT/mkfiles/mkfile-$SYSTARG-$OBJTYPE #set vars based on target system + +<| $SHELLNAME ../port/mkdevlist $CONF #sets $IP, $DEVS, $ETHERS, $VGAS, $PORT, $MISC, $LIBS, $OTHERS + +OBJ=\ + l.$O\ + tlb.$O\ + nofp.$O\ + clock.$O\ + cpm.$O\ + faultpower.$O\ + fpi.$O\ + fpimem.$O\ + fpipower.$O\ + kbd.$O\ + main.$O\ + mmu.$O\ + rmap.$O\ + trap.$O\ + $CONF.root.$O\ + $IP\ + $DEVS\ + $ETHERS\ + $LINKS\ + $VGAS\ + $PORT\ + $MISC\ + $OTHERS\ + +LIBNAMES=${LIBS:%=lib%.a} + +HFILES=\ + mem.h\ + dat.h\ + fns.h\ + io.h\ + ../mpc/800io.h\ + ../mpc/screen.h\ + +CFLAGS=-wFV -I. -I../mpc -I../port -I$ROOT/Inferno/$OBJTYPE/include -I$ROOT/include -I$ROOT/libinterp +KERNDATE=`{$NDATE} + +#default:V: i$CONF.sq +default:V: i$CONF + +i$CONF: $OBJ $CONF.c $CONF.root.h $LIBNAMES + $CC $CFLAGS '-DKERNDATE='$KERNDATE $CONF.c + $LD -o $target -T$KZERO -l $OBJ $CONF.$O $LIBFILES + $KSIZE $target + +i$CONF.sq: i$CONF + sqz -w i$CONF >$target + +install:V: i$CONF # i$CONF.sq + cp i$CONF $INSTALLDIR/i$CONF + #cp i$CONF.sq $INSTALLDIR/i$CONF.sq + +uninstall:V: + rm -f $ROOT/$OBJDIR/bin/i$CONF + rm -f $ROOT/$OBJDIR/bin/i$CONF.sq + +<../port/portmkfile + +../init/$INIT.dis: ../init/$INIT.b + cd ../init; mk $INIT.dis + +%.$O: ../mpc/%.c + $CC $CFLAGS -I. -I../mpc ../mpc/$stem.c + +%.$O: ../mpc/%.s + $AS -I. -I../mpc ../mpc/$stem.s + +clock.$O: $ROOT/Inferno/$OBJTYPE/include/ureg.h +devether.$O: $ROOT/Inferno/$OBJTYPE/include/ureg.h +faultpower.$O: $ROOT/Inferno/$OBJTYPE/include/ureg.h +main.$O: $ROOT/Inferno/$OBJTYPE/include/ureg.h +trap.$O: $ROOT/Inferno/$OBJTYPE/include/ureg.h +screen.h:NV: ../mpc/screen.h + +devether.$O $ETHERS: ../mpc/etherif.h ../port/netif.h + +#$VGAS: screen.h vga.h +$IP devip.$O: ../ip/ip.h + +devboot.$O: devboot.c + $CC $CFLAGS devboot.c + +devuart.$O: ../mpc/devuart.c + $CC $CFLAGS ../mpc/devuart.c diff --git a/os/fads/mmu.c b/os/fads/mmu.c new file mode 100644 index 00000000..c9cd758b --- /dev/null +++ b/os/fads/mmu.c @@ -0,0 +1,20 @@ +#include "u.h" +#include "../port/lib.h" +#include "mem.h" +#include "dat.h" +#include "fns.h" + +void +mmuinit(void) +{ + /* the l.s initial TLB settings do all that's required */ +} + +int +segflush(void *a, ulong n) +{ + /* flush dcache then invalidate icache */ + dcflush(a, n); + icflush(a, n); + return 0; +} diff --git a/os/fads/tlb.s b/os/fads/tlb.s new file mode 100644 index 00000000..68ebf4e7 --- /dev/null +++ b/os/fads/tlb.s @@ -0,0 +1,23 @@ +#include "mem.h" + +#define MB (1024*1024) + +/* + * TLB prototype entries, loaded once-for-all at startup, + * remaining unchanged thereafter. + * Limit the table to at most 8 entries to ensure + * it works on the 823 (other 8xx processors allow up to 32 TLB entries). + */ +#define TLBE(epn,rpn,twc) WORD $(epn); WORD $(twc); WORD $(rpn) + +TEXT tlbtab(SB), $-4 + + /* epn, rpn, twc */ + TLBE(KZERO|PHYSDRAM|TLBVALID, PHYSDRAM|PTEWRITE|PTELPS|PTESH|PTEVALID, PTE8MB|/*PTEWT|*/PTEVALID) /* DRAM, 8M */ + TLBE(KZERO|PHYSBCSR|TLBVALID, PHYSBCSR|PTEWRITE|PTESH|PTECI|PTEVALID, PTE4K|PTEWT|PTEVALID) /* Board CSR, 4K */ + TLBE(KZERO|PHYSIMM|TLBVALID, PHYSIMM|PTEWRITE|PTELPS|PTESH|PTECI|PTEVALID, PTE4K|PTEWT|PTEVALID) /* IMMR, 16K */ + TLBE(KZERO|PHYSFLASH|TLBVALID, PHYSFLASH|PTEWRITE|PTELPS|PTESH|PTECI|PTEVALID, PTE8MB|PTEWT|PTEVALID) /* Flash, 8M */ + TLBE(KZERO|PHYSSDRAM|TLBVALID, PHYSSDRAM|PTEWRITE|PTELPS|PTESH|PTEVALID, PTE8MB|/*PTEWT|*/PTEVALID) /* SDRAM, 8M */ + TLBE(KZERO|PHYSPCMCIA|TLBVALID, PHYSPCMCIA|PTEWRITE|PTELPS|PTESH|PTECI|PTEVALID, PTE8MB|PTEWT|PTEG|PTEVALID) /* PCMCIA, 8M */ +TEXT tlbtabe(SB), $-4 + RETURN |
