summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--sys/src/cmd/9660srv/9660srv.c8
-rw-r--r--sys/src/cmd/9660srv/dat.h1
-rw-r--r--sys/src/cmd/9660srv/fns.h2
-rw-r--r--sys/src/cmd/9660srv/iobuf.c20
4 files changed, 21 insertions, 10 deletions
diff --git a/sys/src/cmd/9660srv/9660srv.c b/sys/src/cmd/9660srv/9660srv.c
index 37dbd444b..8fe773d1b 100644
--- a/sys/src/cmd/9660srv/9660srv.c
+++ b/sys/src/cmd/9660srv/9660srv.c
@@ -69,7 +69,7 @@ iattach(Xfile *root)
dp = nil;
haveplan9 = 0;
for(i=VOLDESC;i<VOLDESC+100; i++){ /* +100 for sanity */
- p = getbuf(cd->d, i);
+ p = getbuf(cd->d, i, 1);
v = (Voldesc*)(p->iobuf);
if(memcmp(v->byte, "\01CD001\01", 7) == 0){ /* iso */
if(dirp)
@@ -372,7 +372,7 @@ iread(Xfile *f, char *buf, vlong offset, long count)
while(count > 0){
if(n > count)
n = count;
- p = getbuf(f->xf->d, addr);
+ p = getbuf(f->xf->d, addr, 0);
memmove(&buf[rcnt], &p->iobuf[o], n);
putbuf(p);
count -= n;
@@ -499,7 +499,7 @@ getdrec(Xfile *f, void *buf)
ip->offset += Sectorsize-boff;
continue;
}
- p = getbuf(f->xf->d, addr/Sectorsize);
+ p = getbuf(f->xf->d, addr/Sectorsize, 1);
len = p->iobuf[boff];
if(len >= 34)
break;
@@ -754,7 +754,7 @@ getcontin(Xdata *dev, uchar *p, uchar **s)
off = l32(p+12);
len = l32(p+20);
chat("getcontin %d...", bn);
- b = getbuf(dev, bn);
+ b = getbuf(dev, bn, 1);
if(b == 0){
*s = 0;
return 0;
diff --git a/sys/src/cmd/9660srv/dat.h b/sys/src/cmd/9660srv/dat.h
index bee14db61..3949251a1 100644
--- a/sys/src/cmd/9660srv/dat.h
+++ b/sys/src/cmd/9660srv/dat.h
@@ -31,6 +31,7 @@ struct Ioclust
int nbuf;
Iobuf* buf;
uchar* iobuf;
+ ulong tag; /* cache tag for eviction: 0 = data, 1 = metadata */
};
struct Xdata
diff --git a/sys/src/cmd/9660srv/fns.h b/sys/src/cmd/9660srv/fns.h
index 1bae3b507..2862d5a63 100644
--- a/sys/src/cmd/9660srv/fns.h
+++ b/sys/src/cmd/9660srv/fns.h
@@ -1,7 +1,7 @@
void chat(char*, ...);
void* ealloc(long);
void error(char*);
-Iobuf* getbuf(Xdata*, ulong);
+Iobuf* getbuf(Xdata*, ulong, ulong);
Xdata* getxdata(char*);
void iobuf_init(void);
void nexterror(void);
diff --git a/sys/src/cmd/9660srv/iobuf.c b/sys/src/cmd/9660srv/iobuf.c
index 6bba533e8..a617483e6 100644
--- a/sys/src/cmd/9660srv/iobuf.c
+++ b/sys/src/cmd/9660srv/iobuf.c
@@ -31,7 +31,7 @@ int nclust = NCLUST;
static Ioclust* iohead;
static Ioclust* iotail;
-static Ioclust* getclust(Xdata*, long);
+static Ioclust* getclust(Xdata*, long, ulong);
static void putclust(Ioclust*);
static void xread(Ioclust*);
@@ -53,6 +53,16 @@ iobuf_init(void)
for(i=0; i<nclust; i++){
c = (Ioclust*)mem;
mem += sizeof(Ioclust);
+
+ /*
+ * on a iso filesystem, data is usually layed out sequentially
+ * but directory information is at the end of the disk. to avoid
+ * evicting directory information when reading large sequential
+ * files, we keep them tagged in the cache. for now, we use
+ * an 8th of the clusters for meta data.
+ */
+ c->tag = i <= (nclust/8);
+
c->addr = -1;
c->prev = iotail;
if(iotail)
@@ -87,13 +97,13 @@ purgebuf(Xdata *dev)
}
static Ioclust*
-getclust(Xdata *dev, long addr)
+getclust(Xdata *dev, long addr, ulong tag)
{
Ioclust *c, *f;
f = nil;
for(c=iohead; c; c=c->next){
- if(!c->busy)
+ if(!c->busy && c->tag == tag)
f = c;
if(c->addr == addr && c->dev == dev){
c->busy++;
@@ -141,13 +151,13 @@ putclust(Ioclust *c)
}
Iobuf*
-getbuf(Xdata *dev, ulong addr)
+getbuf(Xdata *dev, ulong addr, ulong tag)
{
int off;
Ioclust *c;
off = addr%BUFPERCLUST;
- c = getclust(dev, addr - off);
+ c = getclust(dev, addr - off, tag);
if(c->nbuf < off){
c->busy--;
error("I/O read error");