ref: 4a29d3fe0aada31421c2c48f167049ab373a96bf
parent: 6b3bff3c893fa5ffab171cf8010a23512926e196
author: Ori Bernstein <ori@eigenstate.org>
date: Tue Jan 11 01:08:39 EST 2022
fs: fix truncation.
--- a/blk.c
+++ b/blk.c
@@ -151,6 +151,7 @@
return -1;
r->off = off;
r->len = len;
+ assert(avllookup(t, r, 0) == nil);
avlinsert(t, r);
Again:
@@ -231,6 +232,7 @@
Blk *pb, *lb;
vlong o;
char *p;
+ int r;
assert(off % Blksz == 0);
assert(op == LogAlloc || op == LogFree || op == LogDead);
@@ -245,21 +247,24 @@
return -1;
if((lb = initblk(o, Tlog)) == nil)
return -1;
+ cacheblk(lb);
lb->logsz = Loghdsz;
p = lb->data + lb->logsz;
PBIT64(p, (uvlong)LogEnd);
finalize(lb);
if(syncblk(lb) == -1){
- free(lb);
+ putblk(lb);
return -1;
}
-
ol->tail = lb;
+
if(pb != nil){
p = pb->data + pb->logsz;
PBIT64(p + 0, lb->bp.addr|LogChain);
finalize(pb);
- if(syncblk(pb) == -1)
+ r = syncblk(pb);
+ putblk(pb);
+ if(r == -1)
return -1;
}
}
@@ -711,6 +716,7 @@
if((b = lookupblk(bp)) == nil){
if((b = mallocz(sizeof(Blk), 1)) == nil)
return nil;
+ setmalloctag(b, getcallerpc(&bp));
/*
* If the block is cached,
* then the cache holds a ref
@@ -835,7 +841,8 @@
if((b = readblk(bp.addr, flg)) == nil){
qunlock(&fs->blklk);
return nil;
- }
+ }else
+ setmalloctag(b, getcallerpc(&bp));
h = blkhash(b);
if((flg&GBnochk) == 0 && h != bp.hash){
fprint(2, "corrupt block %B: %llx != %llx\n", bp, blkhash(b), bp.hash);
--- a/fs.c
+++ b/fs.c
@@ -1069,6 +1069,10 @@
rerror(m, Enomem);
putfid(f);
return;
+ }else{
+ wlock(de);
+ de->length = 0;
+ wunlock(de);
}
lock(f);
@@ -1182,14 +1186,15 @@
void
fsopen(Fmsg *m)
{
- char *e, buf[Kvmax];
+ char *p, *e, buf[Kvmax];
+ int mbits;
Fcall r;
Xdir d;
Fid *f;
Kvp kv;
- int mb;
+ Msg mb;
- mb = mode2bits(m->mode);
+ mbits = mode2bits(m->mode);
if((f = getfid(m->fid)) == nil){
rerror(m, Efid);
return;
@@ -1204,7 +1209,7 @@
putfid(f);
return;
}
- if(fsaccess(f->mnt, d.mode, d.uid, d.gid, mb) == -1){
+ if(fsaccess(f->mnt, d.mode, d.uid, d.gid, mbits) == -1){
rerror(m, Eperm);
putfid(f);
return;
@@ -1224,16 +1229,33 @@
return;
}
f->mode = mode2bits(m->mode);
-// if((f->mode & DMEXEC)){
+// if(!fs->rdonly && (m->mode == OEXEC)){
// lock(&fs->root.lk);
// f->root = fs->root;
// refblk(fs->root.bp);
// unlock(&fs->root.lk);
// }
- if(f->mode & OTRUNC){
+ if(m->mode & OTRUNC){
wlock(f->dent);
- clearb(f, 0, f->dent->length);
+ f->dent->muid = f->mnt->uid;
+ f->dent->qid.vers++;
f->dent->length = 0;
+
+ mb.op = Owstat;
+ p = buf;
+ p[0] = Owsize|Owmuid; p += 1;
+ PBIT64(p, 0); p += 8;
+ PBIT32(p, f->mnt->uid); p += 4;
+ mb.k = f->dent->k;
+ mb.nk = f->dent->nk;
+ mb.v = buf;
+ mb.nv = p - buf;
+ clearb(f, 0, f->dent->length);
+ if((e = btupsert(f->mnt->root, &mb, 1)) != nil){
+ wunlock(f->dent);
+ rerror(m, e);
+ return;
+ }
wunlock(f->dent);
}
unlock(f);
@@ -1251,6 +1273,8 @@
s = f->scan;
if(s != nil && s->offset != 0 && s->offset != m->offset)
return Edscan;
+ if((r->data = malloc(m->count)) == nil)
+ return Enomem;
if(s == nil || m->offset == 0){
if((s = mallocz(sizeof(Scan), 1)) == nil)
return Enomem;
@@ -1258,7 +1282,6 @@
pfx[0] = Kent;
PBIT64(pfx+1, f->qpath);
if((e = btscan(f->mnt->root, s, pfx, sizeof(pfx))) != nil){
- free(r->data);
btdone(s);
return e;
}
@@ -1305,8 +1328,6 @@
char *p;
Dent *e;
- r->type = Rread;
- r->count = 0;
e = f->dent;
rlock(e);
if(m->offset > e->length){
@@ -1313,10 +1334,6 @@
runlock(e);
return nil;
}
- if((r->data = malloc(m->count)) == nil){
- runlock(e);
- return Enomem;
- }
p = r->data;
c = m->count;
o = m->offset;
@@ -1362,12 +1379,10 @@
e = fsreaddir(m, f, &r);
else
e = fsreadfile(m, f, &r);
- if(e != nil){
+ if(e != nil)
rerror(m, e);
- putfid(f);
- return;
- }
- respond(m, &r);
+ else
+ respond(m, &r);
free(r.data);
putfid(f);
}
@@ -1484,7 +1499,6 @@
case Tversion: fsversion(m, &msgmax); break;
case Tauth: fsauth(m); break;
case Tclunk: fsclunk(m); break;
- case Topen: fsopen(m); break;
case Tattach: fsattach(m, msgmax); break;
/* mutators */
@@ -1498,6 +1512,16 @@
case Twalk: chsend(fs->rdchan, m); break;
case Tread: chsend(fs->rdchan, m); break;
case Tstat: chsend(fs->rdchan, m); break;
+
+ /* both */
+ case Topen:
+ if(m->mode & OTRUNC)
+ chsend(fs->wrchan, m);
+ else
+
+ chsend(fs->rdchan, m);
+ break;
+
default:
fprint(2, "unknown message %F\n", &m->Fcall);
snprint(err, sizeof(err), "unknown message: %F", &m->Fcall);
@@ -1536,6 +1560,7 @@
case Twrite: fswrite(m); break;
case Twstat: fswstat(m); break;
case Tremove: fsremove(m); break;
+ case Topen: fsopen(m); break;
}
break;
case AOsync:
@@ -1570,6 +1595,7 @@
case Twalk: fswalk(m); break;
case Tread: fsread(m); break;
case Tstat: fsstat(m); break;
+ case Topen: fsopen(m); break;
}
quiesce(wid);
}
--- a/load.c
+++ b/load.c
@@ -90,10 +90,11 @@
}
fprint(2, "load: %8s\n", p);
fprint(2, "\tsnaptree:\t%B\n", fs->snap.bp);
- fprint(2, "\tarenas:\t%d\n", fs->narena);
+ fprint(2, "\tnarenas:\t%d\n", fs->narena);
fprint(2, "\tarenasz:\t%lld\n", fs->arenasz);
fprint(2, "\tnextqid:\t%lld\n", fs->nextqid);
fprint(2, "\tnextgen:\t%lld\n", fs->nextgen);
+ fprint(2, "\tcachesz:\t%lld MiB\n", fs->cmax*Blksz/MiB);
if((fs->arenas = calloc(fs->narena, sizeof(Arena))) == nil)
sysfatal("malloc: %r");
for(i = 0; i < fs->narena; i++)