From 943382559f0389fdd1ba3e57c0477d04f0b4e344 Mon Sep 17 00:00:00 2001 From: NeilBrown Date: Sun, 13 Mar 2011 14:39:07 +1100 Subject: [PATCH] Add 'reset' and 'newfs' commands. Also fix 'runfile' so it sees EOF, and add 'verbose' state. Signed-off-by: NeilBrown --- tools/Makefile | 2 +- tools/lafs.c | 98 ++++++++++++++++++++++++++++++++++++++++++++++++-- 2 files changed, 96 insertions(+), 4 deletions(-) diff --git a/tools/Makefile b/tools/Makefile index 592289a..98ebab9 100644 --- a/tools/Makefile +++ b/tools/Makefile @@ -24,7 +24,7 @@ CPPFLAGS = -I../include CFLAGS = -Wall -Werror -g LDFLAGS = -L../lib -LDLIBS = -llafs -ltalloc -lreadline +LDLIBS = -llafs -ltalloc -lreadline -luuid all : mkfs.lafs lafs diff --git a/tools/lafs.c b/tools/lafs.c index 5ffad7e..97c3848 100644 --- a/tools/lafs.c +++ b/tools/lafs.c @@ -40,6 +40,7 @@ #include #include #include +#include /* This is the global state which is passed around among * the various commands. @@ -47,6 +48,7 @@ struct state { struct lafs *lafs; int done; + int verbose; }; /* Every command can have arguments, both positional and @@ -202,6 +204,19 @@ static char *take_word(char **line) return NULL; } +static int get_int(char *str, int *result) +{ + long int num; + char *ep; + + num = strtol(str, &ep, 10); + if (*str && !*ep) { + *result = num; + return 0; + } + return -1; +} + /* Return an array of void* corresponding to the entries in * 'args'. If an arg is present, the array entry is not NULL. * For flags, the array entry will be the full flag. @@ -353,6 +368,7 @@ static void interact(void) { struct state st = {0}; st.lafs = lafs_alloc(); + st.verbose = 1; rl_attempted_completion_function = complete_in_context; rl_basic_word_break_characters = " \t\n="; rl_completer_quote_characters = "\"'"; @@ -382,14 +398,18 @@ static void runfile(FILE *f) { struct state st = {0}; st.lafs = lafs_alloc(); + st.verbose = 0; while (!st.done) { char *line = NULL; - size_t len, size; + ssize_t len; + size_t size; len = getline(&line, &size, f); - if (execute_line(&st, line) < 0) + if (len <= 0) + st.done = 1; + else if (execute_line(&st, line) < 0) st.done = 1; free(line); @@ -681,6 +701,33 @@ static void c_help(struct state *st, void **args) } } +/****** RESET ******/ +static char help_reset[] = "Forget all fs information, and prepare to start afresh"; +static struct args args_reset[] = { + { "-force", flag, -1, {NULL}, "Reset even if there are unflushed changes"}, + TERMINAL_ARG +}; +static void c_reset(struct state *st, void **args) +{ + + if (st->lafs->blocksize == 0) { + printf("reset: Filesystem state is already clear\n"); + return; + } + + if (args[1] == NULL && + !list_empty(&st->lafs->wc[0].blocks)) { + printf("reset: filesystem has unflushed changes. Consider using\n" + " \"flush\" command of \"--force\" argument\n"); + return; + } + talloc_free(st->lafs); + st->lafs = lafs_alloc(); + if (st->verbose) + printf("Filesystem state has been reset\n"); +} + + /****** NEWFS ******/ static char help_newfs[] = "Create a new LaFS filesystem, which can then be stored on one or more devices."; static char *block_sizes[] = { "512", "1024", "2048", "4096", NULL }; @@ -696,7 +743,51 @@ static struct args args_newfs[] = { }; static void c_newfs(struct state *st, void **args) { - /* FIXME */ + int blockbytes = 1024; + int state_size = 0; + char *err = NULL; + char uuidstr[37]; + uuid_t uu; + if (st->lafs->blocksize) { + printf("newfs: Filesytem already has state - consider using \"reset\"\n"); + return; + } + + if (args[1]) + /* As this is a 'choice' it must be a valid number. */ + get_int(args[1], &blockbytes); + + if (args[3]) { + /* state-size was given */ + if (get_int(args[3], &state_size) < 0) + err = "state-size must be a number"; + else if (state_size <= 0 || state_size % 1024) + err = "state-size must be a positive multiple of 1024"; + if (err) { + printf("newfs: %s: %s\n", err, (char*)args[3]); + return; + } + } + if (args[4]) { + /* uuid was given */ + if (uuid_parse((char*)args[4], uu) < 0) { + printf("newfs: UUID in wrong format: %s\n", (char*)args[4]); + return; + } + } + lafs_new(st->lafs, blockbytes); + if (state_size) + st->lafs->statesize = state_size; + if (args[4]) + memcpy(st->lafs->uuid, uu, 16); + + if (st->verbose) { + uuid_unparse(st->lafs->uuid, uuidstr); + printf("Filesystem has been initilised: block size %d, " + "state size %d\n UUID=%s\n", + st->lafs->blocksize, st->lafs->statesize, + uuidstr); + } return; } @@ -728,6 +819,7 @@ static struct cmd lafs_cmds[] = { CMD(help), CMD(newfs), CMD(quit), + CMD(reset), CMD(store), { NULL, NULL, NULL, NULL} }; -- 2.39.5