ref: 11f9df0ac2980f77023e3a59e581faccf83d69ba
parent: d5122d1bcd61d4112f14dbbf3180e732f196ad63
author: Ori Bernstein <ori@eigenstate.org>
date: Sat May 27 21:20:32 EDT 2023
freplay: fix file sizing, add read-only mode
--- a/test/freplay.c
+++ b/test/freplay.c
@@ -4,13 +4,16 @@
#include <thread.h>
#include <9p.h>
+File* ctlfile;
+File* datfile;
char* mountpt = "/n/replay";
char* logfile;
char* replayfile;
char* membuf;
vlong membufsz;
-vlong replaycount = -1;
-int logfd;
+vlong replaycount = -1;
+int logfd = -1;
+vlong nwrites;
void
log1(int fd, void *buf, vlong off, vlong sz)
@@ -52,25 +55,48 @@
void
fsread(Req *r)
{
- readbuf(r, membuf, membufsz);
- respond(r, nil);
+ char buf[128];
+
+ if(r->fid->file == datfile){
+ readbuf(r, membuf, membufsz);
+ respond(r, nil);
+ }else if(r->fid->file == ctlfile){
+ snprint(buf, sizeof(buf), "writes %lld\n", nwrites);
+ readstr(r, buf);
+ respond(r, nil);
+ }else
+ abort();
}
void
fswrite(Req *r)
{
- if(r->ifcall.offset + r->ifcall.count >= membufsz)
- respond(r, "operation exceeds file size");
- log1(logfd, r->ifcall.data, r->ifcall.offset, r->ifcall.count);
- memcpy(membuf + r->ifcall.offset, r->ifcall.data, r->ifcall.count);
- r->ofcall.count = r->ifcall.count;
- respond(r, nil);
+ if(r->fid->file == datfile){
+ if(logfile == nil)
+ respond(r, "read-only replay file: no log defined");
+ if(r->ifcall.offset + r->ifcall.count >= membufsz)
+ respond(r, "operation exceeds file size");
+ log1(logfd, r->ifcall.data, r->ifcall.offset, r->ifcall.count);
+ memcpy(membuf + r->ifcall.offset, r->ifcall.data, r->ifcall.count);
+ r->ofcall.count = r->ifcall.count;
+ respond(r, nil);
+ nwrites++;
+ }else if(r->fid->file == ctlfile){
+ if(strncmp(r->ifcall.data, "exit", 4) == 0){
+ print("exiting...\n");
+ r->ofcall.count = r->ifcall.count;
+ respond(r, nil);
+ exits(nil);
+ }
+ respond(r, "unknown ctl message");
+ }else
+ abort();
}
void
usage(void)
{
- fprint(2, "usage: %s -l log [-r replay] [-c count] file\n", argv0);
+ fprint(2, "usage: %s [-l log] [-r replay] [-c count] file\n", argv0);
exits("usage");
}
@@ -84,7 +110,6 @@
int fd, replayfd;
vlong n, off;
char *uid;
- File *f;
Dir *d;
int i;
@@ -98,6 +123,8 @@
case 'r':
replayfile = EARGF(usage());
break;
+ case 'W':
+
case 'c':
replaycount = atoi(EARGF(usage()));
break;
@@ -108,7 +135,7 @@
usage();
}ARGEND;
- if(argc != 1 || logfile == nil)
+ if(argc != 1)
usage();
if((fd = open(argv[0], OREAD)) == -1)
@@ -115,10 +142,11 @@
sysfatal("open %s: %r", argv[0]);
if((d = dirfstat(fd)) == nil)
sysfatal("failed to stat file: %r");
- if((membuf = mallocz(d->length, 1)) == nil)
+ if((membuf = sbrk(d->length)) == nil)
sysfatal("failed to allocate buffer: %r");
+ memset(membuf, 0, d->length);
for(off = 0; off < d->length; off += n)
- if((n = read(fd, membuf+off, d->length - off)) <= 0)
+ if((n = read(fd, membuf+off, 8192)) <= 0)
sysfatal("read %s: short read", argv[0]);
membufsz = d->length;
free(d);
@@ -128,15 +156,19 @@
for(i = 0; i < replaycount || replaycount == -1; i++)
if(replay1(replayfd) == 0)
break;
+ print("replayed %d ops\n", i);
close(replayfd);
}
- if((logfd = create(logfile, OWRITE, 0666)) == -1)
- sysfatal("failed to open log file: %r");
+ if(logfile != nil){
+ if((logfd = create(logfile, OWRITE, 0666)) == -1)
+ sysfatal("failed to open log file: %r");
+ }
uid = getuser();
fs.tree = alloctree(uid, uid, DMDIR|0555, nil);
- f = createfile(fs.tree->root, "data", uid, 0666, nil);
- f->length = membufsz;
+ ctlfile = createfile(fs.tree->root, "ctl", uid, 0666, nil);
+ datfile = createfile(fs.tree->root, "data", uid, 0666, nil);
+ datfile->length = membufsz;
postmountsrv(&fs, nil, mountpt, 0);
exits(nil);
}