ref: 77d59f66059e6632fa5dec987b05fa52315325d1
parent: 421f12180aa74b9628ba189b7bef9bdb24319935
author: Ori Bernstein <ori@eigenstate.org>
date: Sat Apr 8 20:45:49 EDT 2023
ream: add support for growing file systems
--- a/fns.h
+++ b/fns.h
@@ -67,6 +67,7 @@
void closesnap(Tree*);
uvlong siphash(void*, usize);
void reamfs(char*);
+void growfs(char*);
int loadarena(Arena*, Fshdr *fi, vlong);
void loadfs(char*);
void sync(void);
--- a/main.c
+++ b/main.c
@@ -9,6 +9,7 @@
Gefs *fs;
int ream;
+int grow;
int debug;
int stdio;
int noauth;
@@ -144,6 +145,9 @@
case 'r':
ream = 1;
break;
+ case 'g':
+ grow = 1;
+ break;
case 'm':
cachesz = strtoll(EARGF(usage()), nil, 0)*MiB;
break;
@@ -204,6 +208,10 @@
nproc = 8;
if(ream){
reamfs(dev);
+ exits(nil);
+ }
+ if(grow){
+ growfs(dev);
exits(nil);
}
--- a/ream.c
+++ b/ream.c
@@ -148,7 +148,7 @@
sysfatal("ream: %r");
sz = d->length;
free(d);
- if(sz < 64*MiB)
+ if(sz < 512*MiB)
sysfatal("ream: disk too small");
if((mnt = mallocz(sizeof(Mount), 1)) == nil)
sysfatal("ream: alloc mount: %r");
@@ -165,8 +165,6 @@
asz = sz/fs->narena;
asz = asz - (asz % Blksz) - Blksz;
- if(asz < 128*MiB)
- sysfatal("disk too small");
fs->arenasz = asz;
off = 0;
for(i = 0; i < fs->narena; i++){
@@ -222,4 +220,59 @@
sysfatal("sync arena: %r");
}
free(mnt);
+}
+
+void
+growfs(char *dev)
+{
+ vlong sz, off;
+ int i, narena;
+ Arena *a;
+ Fshdr fi;
+ Dir *d;
+
+ if((fs->fd = open(dev, ORDWR)) == -1)
+ sysfatal("open %s: %r", dev);
+ if((d = dirfstat(fs->fd)) == nil)
+ sysfatal("ream: %r");
+ sz = d->length;
+ free(d);
+
+ if((fs->arenas = calloc(1, sizeof(Arena))) == nil)
+ sysfatal("malloc: %r");
+ fs->narena = 1;
+ for(i = 0; i < fs->narena; i++){
+ Arena *a;
+ a = &fs->arenas[i];
+ if((loadarena(a, &fi, i*fs->arenasz)) == -1)
+ sysfatal("growfs: %r");
+ if(fs->narena == 1){
+ fs->Fshdr = fi;
+ if((fs->arenas = realloc(fs->arenas, fs->narena*sizeof(Arena))) == nil)
+ sysfatal("malloc: %r");
+ }
+ }
+ narena = sz/fs->arenasz;
+ off = fs->arenasz * fs->narena;
+ if(narena <= fs->narena)
+ sysfatal("disk too small for more arenas");
+ if((fs->arenas = realloc(fs->arenas, narena*sizeof(Arena))) == nil)
+ sysfatal("malloc: %r");
+ for(i = fs->narena; i < narena; i++){
+ a = &fs->arenas[i];
+ print("\tadding %d: %lld blocks at %llx\n", i, fs->arenasz/Blksz, off);
+ initarena(&fs->arenas[i], fs, off, fs->arenasz);
+ if((loadarena(a, &fi, i*fs->arenasz)) == -1)
+ sysfatal("growfs: %r");
+ off += fs->arenasz;
+ }
+
+ fs->narena = narena;
+ for(i = 0; i < narena; i++){
+ a = &fs->arenas[i];
+ packarena(a->b->data, Blksz, a, fs);
+ finalize(a->b);
+ if(syncblk(a->b) == -1)
+ sysfatal("sync arena: %r");
+ }
}