diff --git a/sys/src/9/bitsy/mmu.c b/sys/src/9/bitsy/mmu.c index 9d420fd06..ca7df136a 100644 --- a/sys/src/9/bitsy/mmu.c +++ b/sys/src/9/bitsy/mmu.c @@ -379,9 +379,9 @@ putmmu(uintptr va, uintptr pa, Page *pg) if(l2pg != nil){ up->mmufree = l2pg->next; } else { - l2pg = auxpage(); - if(l2pg == nil) - pexit("out of memory", 1); + splx(s); + l2pg = newpage(0, 0, 0); + splhi(); } l2pg->va = VA(kmap(l2pg)); up->l1page[va>>20] = l2pg; diff --git a/sys/src/9/port/cache.c b/sys/src/9/port/cache.c index a64088abf..a03945b4a 100644 --- a/sys/src/9/port/cache.c +++ b/sys/src/9/port/cache.c @@ -205,6 +205,11 @@ ccache(Chan *c) return nil; } +enum { + VABITS = 8*sizeof(uintptr) - 2*PGSHIFT, + VAMASK = (((uintptr)1 << VABITS)-1) << PGSHIFT, +}; + static Page* cpage(Mntcache *m, ulong pn, ulong *po, ulong *pe) { @@ -219,12 +224,19 @@ cpage(Mntcache *m, ulong pn, ulong *po, ulong *pe) m->bitmap[pn/MAPBITS] &= ~b; return nil; } - /* see cachedata() below */ - *po = (ulong)p->va & (BY2PG-1); - *pe = (ulong)p->va >> PGSHIFT; + *po = p->va & (BY2PG-1); + *pe = 1 + (p->va >> (PGSHIFT+VABITS)); + assert(*po < *pe); return p; } +static void +cpageset(Page *p, ulong po, ulong pe) +{ + assert(po < pe); + p->va = po | (p->va & VAMASK) | ((uintptr)pe - 1) << (PGSHIFT+VABITS); +} + int cread(Chan *c, uchar *buf, int len, vlong off) { @@ -253,7 +265,7 @@ cread(Chan *c, uchar *buf, int len, vlong off) p = cpage(m, pn, &po, &pe); if(p == nil) break; - if(po >= pe || offset < po || offset >= pe){ + if(offset < po || offset >= pe){ putpage(p); break; } @@ -326,8 +338,8 @@ cachedata(Mntcache *m, uchar *buf, int len, vlong off) l = len; p = cpage(m, pn, &po, &pe); if(p != nil){ - if(po >= pe || offset > pe || (offset+l) < po){ - /* cached range empty or not extendable, set new cached range */ + if(offset > pe || (offset+l) < po){ + /* cached range not extendable, set new cached range */ po = offset; pe = offset+l; } else { @@ -338,13 +350,12 @@ cachedata(Mntcache *m, uchar *buf, int len, vlong off) pe = offset+l; } } else { - p = auxpage(); - if(p == nil){ + if(needpages(nil) || waserror()){ invalidate(m, offset + pn*BY2PG, len); break; } - - p->va = 0; + p = newpage(0, nil, pn*BY2PG); + poperror(); p->daddr = cacheaddr(m, pn); cachedel(&fscache, p->daddr); cachepage(p, &fscache); @@ -353,6 +364,7 @@ cachedata(Mntcache *m, uchar *buf, int len, vlong off) po = offset; pe = offset+l; } + cpageset(p, po, pe); k = kmap(p); if(waserror()) { @@ -365,9 +377,6 @@ cachedata(Mntcache *m, uchar *buf, int len, vlong off) memmove((uchar*)VA(k) + offset, buf, l); poperror(); kunmap(k); - - /* update cached range */ - p->va = po | (pe << PGSHIFT); putpage(p); offset = 0; diff --git a/sys/src/9/port/page.c b/sys/src/9/port/page.c index 4945b3436..da5f41aec 100644 --- a/sys/src/9/port/page.c +++ b/sys/src/9/port/page.c @@ -234,26 +234,6 @@ putpage(Page *p) freepages(p, p, 1); } -Page* -auxpage(void) -{ - Page *p; - - lock(&palloc); - p = palloc.head; - if(p == nil || palloc.freecount < swapalloc.highwater) { - unlock(&palloc); - return nil; - } - palloc.head = p->next; - p->next = nil; - palloc.freecount--; - unlock(&palloc); - p->ref = 1; - - return p; -} - void copypage(Page *f, Page *t) { diff --git a/sys/src/9/port/portfns.h b/sys/src/9/port/portfns.h index a93ddd2ab..8b1675816 100644 --- a/sys/src/9/port/portfns.h +++ b/sys/src/9/port/portfns.h @@ -10,7 +10,6 @@ Block* allocb(int); int anyhigher(void); int anyready(void); Image* attachimage(int, Chan*, uintptr, ulong); -Page* auxpage(void); Block* bl2mem(uchar*, Block*, int); int blocklen(Block*); void bootlinks(void); @@ -185,6 +184,7 @@ void mul64fract(uvlong*, uvlong, uvlong); void muxclose(Mnt*); Chan* namec(char*, int, int, ulong); void nameerror(char*, char*); +int needpages(void*); Chan* newchan(void); int newfd(Chan*); Mhead* newmhead(Chan*);