diff options
Diffstat (limited to 'user/bcachetest.c')
-rw-r--r-- | user/bcachetest.c | 189 |
1 files changed, 189 insertions, 0 deletions
diff --git a/user/bcachetest.c b/user/bcachetest.c new file mode 100644 index 0000000..5dc46ef --- /dev/null +++ b/user/bcachetest.c @@ -0,0 +1,189 @@ +#include "kernel/fcntl.h" +#include "kernel/param.h" +#include "kernel/types.h" +#include "kernel/stat.h" +#include "kernel/riscv.h" +#include "kernel/fs.h" +#include "user/user.h" + +void test0(); +void test1(); + +#define SZ 4096 +char buf[SZ]; + +int +main(int argc, char *argv[]) +{ + test0(); + test1(); + exit(0); +} + +void +createfile(char *file, int nblock) +{ + int fd; + char buf[BSIZE]; + int i; + + fd = open(file, O_CREATE | O_RDWR); + if(fd < 0){ + printf("createfile %s failed\n", file); + exit(-1); + } + for(i = 0; i < nblock; i++) { + if(write(fd, buf, sizeof(buf)) != sizeof(buf)) { + printf("write %s failed\n", file); + exit(-1); + } + } + close(fd); +} + +void +readfile(char *file, int nbytes, int inc) +{ + char buf[BSIZE]; + int fd; + int i; + + if(inc > BSIZE) { + printf("readfile: inc too large\n"); + exit(-1); + } + if ((fd = open(file, O_RDONLY)) < 0) { + printf("readfile open %s failed\n", file); + exit(-1); + } + for (i = 0; i < nbytes; i += inc) { + if(read(fd, buf, inc) != inc) { + printf("read %s failed for block %d (%d)\n", file, i, nbytes); + exit(-1); + } + } + close(fd); +} + +int ntas(int print) +{ + int n; + char *c; + + if (statistics(buf, SZ) <= 0) { + fprintf(2, "ntas: no stats\n"); + } + c = strchr(buf, '='); + n = atoi(c+2); + if(print) + printf("%s", buf); + return n; +} + +// Test reading small files concurrently +void +test0() +{ + char file[2]; + char dir[2]; + enum { N = 10, NCHILD = 3 }; + int m, n; + + dir[0] = '0'; + dir[1] = '\0'; + file[0] = 'F'; + file[1] = '\0'; + + printf("start test0\n"); + for(int i = 0; i < NCHILD; i++){ + dir[0] = '0' + i; + mkdir(dir); + if (chdir(dir) < 0) { + printf("chdir failed\n"); + exit(1); + } + unlink(file); + createfile(file, N); + if (chdir("..") < 0) { + printf("chdir failed\n"); + exit(1); + } + } + m = ntas(0); + for(int i = 0; i < NCHILD; i++){ + dir[0] = '0' + i; + int pid = fork(); + if(pid < 0){ + printf("fork failed"); + exit(-1); + } + if(pid == 0){ + if (chdir(dir) < 0) { + printf("chdir failed\n"); + exit(1); + } + + readfile(file, N*BSIZE, 1); + + exit(0); + } + } + + for(int i = 0; i < NCHILD; i++){ + wait(0); + } + printf("test0 results:\n"); + n = ntas(1); + if (n-m < 500) + printf("test0: OK\n"); + else + printf("test0: FAIL\n"); +} + +// Test bcache evictions by reading a large file concurrently +void test1() +{ + char file[3]; + enum { N = 200, BIG=100, NCHILD=2 }; + + printf("start test1\n"); + file[0] = 'B'; + file[2] = '\0'; + for(int i = 0; i < NCHILD; i++){ + file[1] = '0' + i; + unlink(file); + if (i == 0) { + createfile(file, BIG); + } else { + createfile(file, 1); + } + } + for(int i = 0; i < NCHILD; i++){ + file[1] = '0' + i; + int pid = fork(); + if(pid < 0){ + printf("fork failed"); + exit(-1); + } + if(pid == 0){ + if (i==0) { + for (i = 0; i < N; i++) { + readfile(file, BIG*BSIZE, BSIZE); + } + unlink(file); + exit(0); + } else { + for (i = 0; i < N*20; i++) { + readfile(file, 1, BSIZE); + } + unlink(file); + } + exit(0); + } + } + + for(int i = 0; i < NCHILD; i++){ + wait(0); + } + printf("test1 OK\n"); +} |