commit - 067d852abe242ee1d267bcc0d652cd6bb31b7e17
commit + 6fc7da3c529ca7c610e8172f5b02980c75597dd5
blob - 9fea5bcfd60f67c6f39e2d0e1285f3ce8063da86
blob + af5bb78841d15ad49b3c6eba0ad8957a0afa85fd
--- include/venti.h
+++ include/venti.h
int vtversion(VtConn *z);
void vtdebug(VtConn *z, char*, ...);
void vthangup(VtConn *z);
+int vtgoodbye(VtConn *z);
+
/* #pragma varargck argpos vtdebug 2 */
/* server */
u32int used;
u32int used2;
u32int addr;
+ uintptr pc;
};
u32int vtglobaltolocal(uchar[VtScoreSize]);
blob - 91fa221d399afd070b6e4499f1c27b769a32552a
blob + d9fcd404536555254d9767db92e46e50f96cdf64
--- src/cmd/vbackup/queue.c
+++ src/cmd/vbackup/queue.c
rwakeup(&q->r);
qunlock(&q->lk);
}
+
+void
+qfree(Queue *q)
+{
+ vtfree(q);
+}
blob - 6b2317c3b878ac3542a9e44f7a5279e81fb5d925
blob + 00320069d7da279d27d6645edbb5685369f165c7
--- src/cmd/vbackup/queue.h
+++ src/cmd/vbackup/queue.h
void qclose(Queue*);
Block *qread(Queue*, u32int*);
void qwrite(Queue*, Block*, u32int);
+void qfree(Queue*);
blob - 9e4c3b00d3ccc00d285a70bcfbdd917ee0e4f2a9
blob + 4c9fd386ecb492356c940041d9d44cace843b4d0
--- src/cmd/vbackup/vbackup.c
+++ src/cmd/vbackup/vbackup.c
* wait for processes to finish
*/
wlock(&endlk);
+
+ qfree(qcmp);
+ qfree(qventi);
if(statustime)
print("# %T procs exited: %d blocks changed, %d read, %d written, %d skipped, %d copied\n",
sysfatal("vtfileflush: %r");
if(vtfilegetentry(vfile, &e) < 0)
sysfatal("vtfilegetentry: %r");
+ vtfileunlock(vfile);
+ vtfileclose(vfile);
b = vtcacheallocblock(c, VtDirType);
if(b == nil)
sysfatal("vtsync: %r");
if(statustime)
print("# %T synced\n");
+
+ fsysclose(fsys);
+ diskclose(disk);
+ vtcachefree(zcache);
+ vtgoodbye(z);
+ // Leak here, because I can't seem to make
+ // the vtrecvproc exit.
+ // vtfreeconn(z);
+ free(tmpnam);
+ z = nil;
+ zcache = nil;
+ fsys = nil;
+ disk = nil;
threadexitsall(nil);
}
}
if(vtwritepacket(z, wr.score, wr.type, wr.p) < 0)
sysfatal("vtwritepacket: %r");
+ packetfree(wr.p);
}
}
vtcachesetwrite(zcache, nil);
for(i=0; i<nwritethread; i++)
send(writechan, nil);
+ chanfree(writechan);
if(statustime)
print("# %T venti proc exiting - nsend %d nrecv %d\n", nsend, nrecv);
runlock(&endlk);
if(threadspawnl(fd, "sh", "sh", "-c", cmd, nil) < 0)
sysfatal("exec mount|awk (to find mtpt of %s): %r", dev);
/* threadspawnl closed p[1] */
+ free(cmd);
n = readn(p[0], buf, sizeof buf-1);
close(p[0]);
if(n <= 0)
blob - f1af6f1b66e2422b4757778f96769424eff50e41
blob + 7b06fa4f3e0235809ca35e3c2012d54bd9364d02
--- src/libdiskfs/cache.c
+++ src/libdiskfs/cache.c
/*
* Disk cache. Caches by offset, so higher levels have
* to deal with alignment issues (if we get asked for the
- * blocks at offsets 0 and 1, we'll do two reads.
+ * blocks at offsets 0 and 1, we'll do two reads).
*/
typedef struct DiskCache DiskCache;
blob - 7864c7193c7fee4dc83506381ac31be041bfae6d
blob + 9607cfbebb91c1a8f782a264f2d0b7b7d6d6601b
--- src/libdiskfs/ffs.c
+++ src/libdiskfs/ffs.c
fsys->_readfile = ffsreadfile;
fsys->_readlink = ffsreadlink;
fsys->_readdir = ffsreaddir;
+ fsys->_close = ffsclose;
fsys->fileblock = ffsxfileblock;
if(ffssync(fsys) < 0)
blob - 24cb8c2f3e77b5b27a7e193a6d2854740343ca2a
blob + 809e340fa51b3b33777bc898a80aabeba2609467
--- src/libventi/cache.c
+++ src/libventi/cache.c
for(i = 0; i < c->nblock; i++){
b = &c->block[i];
if(b->ref){
-if(1)fprint(2, "a=%ud %V ref=%d\n", b->addr, b->score, b->ref);
+if(1)fprint(2, "a=%ud %V ref=%d pc=%#lux\n", b->addr, b->score, b->ref, (ulong)b->pc);
refed++;
}
}
qlock(&b->lk);
b->nlock = 1;
+ b->pc = getcallerpc(&c);
return b;
}
qlock(&b->lk);
b->nlock = 1;
-
+ b->pc = getcallerpc(&b);
return b;
}
if(addr != NilBlock){
if(vttracelevel)
fprint(2, "vtcacheglobal %V %d => local\n", score, type);
- return vtcachelocal(c, addr, type);
+ b = vtcachelocal(c, addr, type);
+ if(b)
+ b->pc = getcallerpc(&c);
+ return b;
}
h = (u32int)(score[0]|(score[1]<<8)|(score[2]<<16)|(score[3]<<24)) % c->nhash;
}
if(vttracelevel)
fprint(2, "vtcacheglobal %V %d => found in cache; returning\n", score, type);
+ b->pc = getcallerpc(&c);
return b;
}
b->nlock = 1;
if(vttracelevel)
fprint(2, "vtcacheglobal %V %d => loaded into cache; returning\n", score, type);
+ b->pc = getcallerpc(&b);
return b;
}
}
memmove(bb->data, b->data, b->c->blocksize);
vtblockput(b);
+ bb->pc = getcallerpc(&b);
return bb;
}
blob - 3396386086e6f05b1ac1370eee4f7fc7a8da72e1
blob + 40ee85175cb73d830cf53e64e0bdd4dba448ac19
--- src/libventi/client.c
+++ src/libventi/client.c
return 0;
}
+int
+vtgoodbye(VtConn *z)
+{
+ VtFcall tx, rx;
+
+ tx.msgtype = VtTgoodbye;
+ vtfcallrpc(z, &tx, &rx); /* always fails: no VtRgoodbye */
+ return 0;
+}
blob - 990e7db2f54f749dd7338a51a61689e901eccbc6
blob + 5b6d5436c41f99f1f681dd1701fccc2ea9303ea6
--- src/libventi/conn.c
+++ src/libventi/conn.c
{
vthangup(z);
qlock(&z->lk);
- for(;;){
+ /*
+ * Wait for send and recv procs to notice
+ * the hangup and clear out the queues.
+ */
+ while(z->readq || z->writeq){
if(z->readq)
_vtqhangup(z->readq);
- else if(z->writeq)
+ if(z->writeq)
_vtqhangup(z->writeq);
- else
- break;
rsleep(&z->rpcfork);
}
packetfree(z->part);
+ vtfree(z->version);
+ vtfree(z->sid);
vtfree(z);
}
blob - 9f721b426367cb35acb5ccd703361c9dbfd1a338
blob + 65ee2d17837cdc74600d8027e7b02c200a1d616a
--- src/libventi/fcall.c
+++ src/libventi/fcall.c
Err:
werrstr("bad packet");
+ vtfcallclear(f);
return -1;
}
blob - 174561eccf6d482fc89eb8b815ace8a01dad1f7b
blob + 6604ef67ea103226e2d245d0b036b8e882a5302f
--- src/libventi/file.c
+++ src/libventi/file.c
i = mkindices(&e, bn, index);
if(i < 0)
- return nil;
+ goto Err;
if(i > DEPTH(e.type)){
if(mode == VtOREAD){
werrstr("bad address 0x%lux", (ulong)bn);
vtblockput(b);
b = bb;
}
+ b->pc = getcallerpc(&r);
return b;
Err:
vtblockput(b);
b = vtcacheglobal(r->c, r->score, VtDirType);
if(b == nil)
return nil;
+ b->pc = getcallerpc(&r);
return b;
}
assert(r->parent != nil);
*/
assert(r->b == nil);
r->b = b;
+ b->pc = getcallerpc(&r);
return 0;
}
*/
r->b = b;
rr->b = bb;
+ b->pc = getcallerpc(&r);
+ bb->pc = getcallerpc(&r);
return 0;
}
blob - 5a992e731f010a4bb3763d8f38f93080fb9da642
blob + 230758649c2d3a91d902cc1fa203e868aaaa0248
--- src/libventi/hangup.c
+++ src/libventi/hangup.c
#include <u.h>
+#include <sys/socket.h>
#include <libc.h>
#include <venti.h>
#include "queue.h"
{
qlock(&z->lk);
z->state = VtStateClosed;
+ /* try to make the read in vtsendproc fail */
+ shutdown(SHUT_WR, z->infd);
+ shutdown(SHUT_WR, z->outfd);
if(z->infd >= 0)
close(z->infd);
if(z->outfd >= 0 && z->outfd != z->infd)
_vtqhangup(z->readq);
qunlock(&z->lk);
}
+
blob - aa5b2a0ec2f06d057cc624bbbc3a72f02ff9e881
blob + 9947939937c1ee2d5e6959f4a808aec4867f1173
--- src/libventi/packet.c
+++ src/libventi/packet.c
}
}
}
-
static Frag *
fragalloc(Packet *p, int n, int pos, Frag *next)
blob - 6e9bfa8dc8cc0ff7b0dfdf6995194e5faf56944e
blob + 3a1f6ea56d71bacf8dd503fe2ad6de5ebcb29972
--- src/libventi/queue.c
+++ src/libventi/queue.c
return q;
}
+void
+_vtqfree(Queue *q)
+{
+ Qel *e;
+
+ /* Leaks the pointers e->p! */
+ while(q->head){
+ e = q->head;
+ q->head = e->next;
+ free(e);
+ }
+ free(q);
+}
+
int
_vtqsend(Queue *q, void *p)
{
blob - 99e087635ec59e2feea2b714190df8bbbc879f4c
blob + 2807783bddf7184c2426e36418c8f4156cf2bd2b
--- src/libventi/queue.h
+++ src/libventi/queue.h
void *_vtqrecv(Queue*);
void _vtqhangup(Queue*);
void *_vtnbqrecv(Queue*);
+void _vtqfree(Queue*);
blob - faf806293e1c1d21639f9c24f4b0cfc9a767d64c
blob + 5a820a995cd9dfed9fb0614ac8ce1925dfb90c5e
--- src/libventi/rpc.c
+++ src/libventi/rpc.c
if(top == buf){
werrstr("first two bytes must be in same packet fragment");
packetfree(p);
+ vtfree(r);
return nil;
}
top[1] = tag;
qunlock(&z->lk);
- if(vtsend(z, p) < 0)
+ if(vtsend(z, p) < 0){
+ vtfree(r);
return nil;
+ }
qlock(&z->lk);
/* wait for the muxer to give us our packet */
if((p = vtrecv(z)) == nil){
werrstr("unexpected eof on venti connection");
z->muxer = 0;
+ vtfree(r);
return nil;
}
qlock(&z->lk);
blob - 1d8477d5624b2c521ff3d432b091916fd284c493
blob + 7ada51af76155c6e1b84cf213292b75bd83e4ccc
--- src/libventi/send.c
+++ src/libventi/send.c
_vtqhangup(q);
while((p = _vtnbqrecv(q)) != nil)
packetfree(p);
- vtfree(q);
+ _vtqfree(q);
z->readq = nil;
rwakeup(&z->rpcfork);
qunlock(&z->lk);
_vtqhangup(q);
while((p = _vtnbqrecv(q)) != nil)
packetfree(p);
- vtfree(q);
+ _vtqfree(q);
z->writeq = nil;
rwakeup(&z->rpcfork);
qunlock(&z->lk);