silly cache hack, also fix vtfilewritebefore not to be so aggressive.
diff --git a/src/libventi/cache.c b/src/libventi/cache.c
index fb0be90..394641d 100644
--- a/src/libventi/cache.c
+++ b/src/libventi/cache.c
@@ -39,6 +39,7 @@
 	int		nblock;
 	uchar	*mem;	/* memory for all blocks and data */
 	int		mode;
+	int		(*write)(VtConn*, uchar[VtScoreSize], uint, uchar*, int);
 };
 
 static void cachecheck(VtCache*);
@@ -56,13 +57,13 @@
 	c->z = z;
 	c->blocksize = (blocksize + 127) & ~127;
 	c->nblock = nblock;
-
 	c->nhash = nblock;
 	c->hash = vtmallocz(nblock*sizeof(VtBlock*));
 	c->heap = vtmallocz(nblock*sizeof(VtBlock*));
 	c->block = vtmallocz(nblock*sizeof(VtBlock));
 	c->mem = vtmallocz(nblock*c->blocksize);
 	c->mode = mode;
+	c->write = vtwrite;
 
 	p = c->mem;
 	for(i=0; i<nblock; i++){
@@ -79,6 +80,19 @@
 	return c;
 }
 
+/*
+ * BUG This is here so that vbackup can override it and do some
+ * pipelining of writes.  Arguably vtwrite or vtwritepacket or the
+ * cache itself should be providing this functionality.
+ */
+void
+vtcachesetwrite(VtCache *c, int (*write)(VtConn*, uchar[VtScoreSize], uint, uchar*, int))
+{
+	if(write == nil)
+		write = vtwrite;
+	c->write = write;
+}
+
 void
 vtcachefree(VtCache *c)
 {
@@ -405,6 +419,8 @@
 
 	n = vtread(c->z, score, type, b->data, c->blocksize);
 	if(n < 0){
+		werrstr("vtread %V: %r", score);
+abort();
 		b->iostate = BioVentiError;
 		vtblockput(b);
 		return nil;
@@ -494,7 +510,7 @@
 
 	c = b->c;
 	n = vtzerotruncate(b->type, b->data, c->blocksize);
-	if(vtwrite(c->z, score, b->type, b->data, n) < 0)
+	if(c->write(c->z, score, b->type, b->data, n) < 0)
 		return -1;
 
 	memmove(b->score, score, VtScoreSize);
diff --git a/src/libventi/file.c b/src/libventi/file.c
index dac53a5..b2f5b15 100644
--- a/src/libventi/file.c
+++ b/src/libventi/file.c
@@ -1222,10 +1222,13 @@
 			 * if the rest of the block is already flushed,
 			 * we can flush the whole block.
 			 */
-			ok = 1;
-			for(; j<ppb; j++)
-				if(vtglobaltolocal(b->data+j*VtScoreSize) != NilBlock)
-					ok = 0;
+			ok = 0;
+			if(index[i] != index1[i]){
+				ok = 1;
+				for(; j<ppb; j++)
+					if(vtglobaltolocal(b->data+j*VtScoreSize) != NilBlock)
+						ok = 0;
+			}
 		}
 		if(ok){
 			if(i == depth)