From b58ff8f523fa9cf69f66c5476c4ac87ae8f20a43 Mon Sep 17 00:00:00 2001 From: David du Colombier <0intro@gmail.com> Date: Sat, 10 Dec 1994 00:00:00 +0000 Subject: [PATCH] Plan 9 from Bell Labs 1994-12-10 --- pc/devastar.c | 3 ++ pc/devi82365.c | 4 ++- pc/ether8003.c | 3 ++ pc/fns.h | 3 +- pc/main.c | 37 +++++++++++++++++++- pc/mmu.c | 95 ++++++++++++++++++++++++++++++++++++++++---------- 6 files changed, 123 insertions(+), 22 deletions(-) diff --git a/pc/devastar.c b/pc/devastar.c index 5121f26c902f23359e65fa3234ccd32c1f9c2d2c..7300d43988bef9d9ec7af0e5557e3a2b1538e848 100644 --- a/pc/devastar.c +++ b/pc/devastar.c @@ -417,6 +417,9 @@ astarreset(void) a->irq = 15; a->id = i; + if(isaget(a->mem, Pagesize, 0) == 0) + panic("astarreset: %lux", a->mem); + if(astarsetup(a) < 0){ xfree(a); astar[nastar] = 0; diff --git a/pc/devi82365.c b/pc/devi82365.c index 5d26d29d4c07b3d261e2fa516b65def495dcb244..c0ee2d4062bc349871a16f025d855191569acf1e 100644 --- a/pc/devi82365.c +++ b/pc/devi82365.c @@ -316,7 +316,9 @@ getmap(Slot *pp, ulong offset, int attr) /* grab ISA address space for memory maps */ for(i = 0; i < Nmap; i++) - pp->mmap[i].isa = isamem(Mchunk); + pp->mmap[i].isa = getisa(0, Mchunk, BY2PG); + if(pp->mmap[i].isa == 0) + panic("getmap"); } /* look for a map that starts in the right place */ diff --git a/pc/ether8003.c b/pc/ether8003.c index a8c85a0aadf82e483cb00c6e658dc206ca3286fe..b2c4d2c503a89bcdae5be47ed05f74dd28cdc5cb 100644 --- a/pc/ether8003.c +++ b/pc/ether8003.c @@ -190,6 +190,9 @@ reset(Ether *ether) } dp8390setea(ether); + if(getisa(ether->mem, ether->size, 0) == 0) + panic("ether8003: %lux reused", ether->mem); + return 0; } diff --git a/pc/fns.h b/pc/fns.h index f9dc1e3c3b7f898712e30b450a6303445c322750..32aaa0784c976360dd722b2ecb9214b1718fc54f 100644 --- a/pc/fns.h +++ b/pc/fns.h @@ -42,7 +42,8 @@ ulong inl(int); void insl(int, void*, int); int iprint(char*, ...); int isaconfig(char*, int, ISAConf*); -ulong isamem(int); +ulong getisa(ulong, int, int); +void putisa(ulong, int); void kbdinit(void); long* mapaddr(ulong); void mathinit(void); diff --git a/pc/main.c b/pc/main.c index 7500b40ffdc146bdb8c18abd98a212faefd632a9..bc88dbee58f90a5322cdb4cde8b5507134ff984e 100644 --- a/pc/main.c +++ b/pc/main.c @@ -313,11 +313,37 @@ memclrtest(int meg, int len, long seed) for(n = 0; n < BY2PG/BY2WD; n++) if(lp[n] != ~(seed + (n^((BY2PG/BY2WD)-1)))) return -1; - memset(lp, '!', BY2PG); +/* memset(lp, '!', BY2PG);/**/ } return 0; } +/* + * look for unused address space in 0xC8000 to 1 meg + */ +void +romscan(void) +{ + uchar *p; + + p = (uchar*)(KZERO+0xC8000); + while(p < (uchar*)(KZERO+0xE0000)){ + p[0] = 0x55; + p[1] = 0xAA; + p[2] = 4; + if(p[0] != 0x55 || p[1] != 0xAA){ + putisa(PADDR(p), 2048); + p += 2048; + continue; + } + p += p[2]*512; + } + + p = (uchar*)(KZERO+0xE0000); + if(p[0] != 0x55 || p[1] != 0xAA) + putisa(PADDR(p), 64*1024); +} + void confinit(void) { @@ -360,6 +386,7 @@ confinit(void) nconf++; } + /* * size memory above 1 meg. Kernel sits at 1 meg. We * only recognize MB size chunks. @@ -437,6 +464,14 @@ confinit(void) break; } + /* + * add address space holes holes under 16 meg to available + * isa space. + */ + romscan(); + if(conf.topofmem < 16*MB) + putisa(conf.topofmem, 16*MB - conf.topofmem); + conf.npage = conf.npage0 + conf.npage1; conf.ldepth = 0; if(pcnt < 10) diff --git a/pc/mmu.c b/pc/mmu.c index d8aa14c8c25db164856b5f1876a3258243ee5086..80be42025d5469900dddb73be7609e2d2c1ce49e 100644 --- a/pc/mmu.c +++ b/pc/mmu.c @@ -88,12 +88,15 @@ static ulong *kpt; /* 2nd level page tables for kernel mem */ #define MAXUMEG 64 /* maximum memory per user process in megabytes */ #define ONEMEG (1024*1024) +enum { + Nisa= 256, +}; struct { Lock; - ulong addr; /* next available address for isa bus memory */ - ulong end; /* one past available isa bus memory */ -} isamemalloc; + ulong s[Nisa]; + ulong e[Nisa]; +} isaalloc; /* * Change current page table and the stack to use for exceptions @@ -149,10 +152,8 @@ mmuinit(void) ktoppg.va = (ulong)top; ktoppg.pa = ktoppg.va & ~KZERO; - /* map all memory to KZERO (add some address space for ISA memory) */ - isamemalloc.addr = 0xd8000; - isamemalloc.end = 0xe0000; - npage = 64*MB/BY2PG; + /* map all memory to KZERO */ + npage = 128*MB/BY2PG; nbytes = PGROUND(npage*BY2WD); /* words of page map */ nkpt = nbytes/BY2PG; /* pages of page map */ kpt = xspanalloc(nbytes, BY2PG, 0); @@ -335,24 +336,80 @@ putmmu(ulong va, ulong pa, Page *pg) splx(s); } +/* + * make isa address space available + */ +void +putisa(ulong addr, int len) +{ + ulong e; + int i, hole; + + addr &= ~KZERO; + + e = addr + len; + lock(&isaalloc); + hole = -1; + for(i = 0; i < Nisa; i++){ + if(isaalloc.s[i] == e){ + isaalloc.s[i] = addr; + break; + } + if(isaalloc.e[i] == addr){ + isaalloc.e[i] = e; + break; + } + if(isaalloc.s[i] == 0) + hole = i; + } + if(i >= Nisa && hole >= 0){ + isaalloc.s[hole] = addr; + isaalloc.e[hole] = e; + } + unlock(&isaalloc); +} + /* * allocate some address space (already mapped into the kernel) * for ISA bus memory. */ ulong -isamem(int len) +getisa(ulong addr, int len, int align) { - ulong a, x; - - lock(&isamemalloc); - len = PGROUND(len); - x = isamemalloc.addr + len; - if(x > isamemalloc.end) - panic("isamem"); - a = isamemalloc.addr; - isamemalloc.addr = x; - unlock(&isamemalloc); - return a; + int i; + ulong os, s, e; + + lock(&isaalloc); + os = s = e = 0; + for(i = 0; i < Nisa; i++){ + s = os = isaalloc.s[i]; + if(s == 0) + continue; + e = isaalloc.e[i]; + if(addr && addr >= s && addr < isaalloc.e[i]) + break; + if(align > 0) + s = ((s + align - 1)/align)*align; + if(e - s >= len) + break; + } + if(i >= Nisa){ + unlock(&isaalloc); + return 0; + } + + /* remove */ + isaalloc.s[i] = 0; + unlock(&isaalloc); + + /* give back edges */ + if(s != os) + putisa(os, s - os); + os = s + len; + if(os != e) + putisa(os, e - os); + + return KZERO|s; } /*