Expand ~ and ~user in config file

Fixes #243
This commit is contained in:
Yorhel 2024-11-15 15:17:21 +01:00
parent 73ef3294e8
commit 93edebc81c
3 changed files with 53 additions and 7 deletions

View file

@ -191,7 +191,7 @@ static char *argparser_arg(struct argparser *p) {
#define OPT(_s) (strcmp(argparser_state.last, (_s)) == 0) #define OPT(_s) (strcmp(argparser_state.last, (_s)) == 0)
#define ARG (argparser_arg(&argparser_state)) #define ARG (argparser_arg(&argparser_state))
static int arg_option(void) { static int arg_option(int infile) {
char *arg, *tmp; char *arg, *tmp;
if(OPT("-q") || OPT("--slow-ui-updates")) update_delay = 2000; if(OPT("-q") || OPT("--slow-ui-updates")) update_delay = 2000;
else if(OPT("--fast-ui-updates")) update_delay = 100; else if(OPT("--fast-ui-updates")) update_delay = 100;
@ -253,10 +253,14 @@ static int arg_option(void) {
else if(OPT("--no-si")) si = 0; else if(OPT("--no-si")) si = 0;
else if(OPT("-L") || OPT("--follow-symlinks")) follow_symlinks = 1; else if(OPT("-L") || OPT("--follow-symlinks")) follow_symlinks = 1;
else if(OPT("--no-follow-symlinks")) follow_symlinks = 0; else if(OPT("--no-follow-symlinks")) follow_symlinks = 0;
else if(OPT("--exclude")) exclude_add(ARG); else if(OPT("--exclude")) {
else if(OPT("-X") || OPT("--exclude-from")) { arg = infile ? expanduser(ARG) : ARG;
arg = ARG; exclude_add(arg);
if(infile) free(arg);
} else if(OPT("-X") || OPT("--exclude-from")) {
arg = infile ? expanduser(ARG) : ARG;
if(exclude_addfile(arg)) die("Can't open %s: %s\n", arg, strerror(errno)); if(exclude_addfile(arg)) die("Can't open %s: %s\n", arg, strerror(errno));
if(infile) free(arg);
} else if(OPT("--exclude-caches")) cachedir_tags = 1; } else if(OPT("--exclude-caches")) cachedir_tags = 1;
else if(OPT("--include-caches")) cachedir_tags = 0; else if(OPT("--include-caches")) cachedir_tags = 0;
else if(OPT("--exclude-kernfs")) exclude_kernfs = 1; else if(OPT("--exclude-kernfs")) exclude_kernfs = 1;
@ -347,7 +351,7 @@ static void config_read(const char *fn) {
argparser_state.argc = argslen; argparser_state.argc = argslen;
while((r = argparser_next(&argparser_state)) > 0) while((r = argparser_next(&argparser_state)) > 0)
if(r == 2 || !arg_option()) if(r == 2 || !arg_option(1))
die("Unknown option in config file '%s': %s.\nRun with --ignore-config to skip reading config files.\n", fn, argparser_state.last); die("Unknown option in config file '%s': %s.\nRun with --ignore-config to skip reading config files.\n", fn, argparser_state.last);
for(argsi=args; argsi && *argsi; argsi++) free(*argsi); for(argsi=args; argsi && *argsi; argsi++) free(*argsi);
@ -394,7 +398,7 @@ static void argv_parse(int argc, char **argv) {
else if(OPT("-o")) export = ARG; else if(OPT("-o")) export = ARG;
else if(OPT("-f")) import = ARG; else if(OPT("-f")) import = ARG;
else if(OPT("--ignore-config")) {} else if(OPT("--ignore-config")) {}
else if(!arg_option()) die("Unknown option '%s'.\n", argparser_state.last); else if(!arg_option(0)) die("Unknown option '%s'.\n", argparser_state.last);
} }
#if !(HAVE_LINUX_MAGIC_H && HAVE_SYS_STATFS_H && HAVE_STATFS) #if !(HAVE_LINUX_MAGIC_H && HAVE_SYS_STATFS_H && HAVE_STATFS)

View file

@ -30,6 +30,8 @@
#include <ncurses.h> #include <ncurses.h>
#include <stdarg.h> #include <stdarg.h>
#include <unistd.h> #include <unistd.h>
#include <pwd.h>
#ifdef HAVE_LOCALE_H #ifdef HAVE_LOCALE_H
#include <locale.h> #include <locale.h>
#endif #endif
@ -441,7 +443,7 @@ void addparentstats(struct dir *d, int64_t size, int64_t asize, uint64_t mtime,
char buf[128];\ char buf[128];\
while((ptr = f) == NULL) {\ while((ptr = f) == NULL) {\
close_nc();\ close_nc();\
write(2, oom_msg, sizeof(oom_msg));\ write(2, oom_msg, sizeof(oom_msg)-1);\
read(0, buf, sizeof(buf));\ read(0, buf, sizeof(buf));\
}\ }\
return ptr; return ptr;
@ -455,3 +457,41 @@ char *xstrdup(const char *str) {
strcpy(r, str); strcpy(r, str);
return r; return r;
} }
/* Expands '~' and '~user' */
char *expanduser(const char *path) {
size_t len, size;
struct passwd *pwd;
char *home = NULL, *tmp;
if(path[0] != '~') return xstrdup(path);
len = strcspn(path+1, "/");
if(len == 0) {
home = getenv("HOME");
if(!home) {
pwd = getpwuid(getuid());
if(pwd) home = pwd->pw_dir;
}
} else {
tmp = xmalloc(len+1);
memcpy(tmp, path+1, len);
tmp[len] = 0;
pwd = getpwnam(tmp);
free(tmp);
if(pwd) home = pwd->pw_dir;
}
if(!home) return xstrdup(path);
size = strlen(home);
while(size > 0 && home[size-1] == '/') size--;
home[size] = 0;
if(size == 0 && path[len+1] == 0) return xstrdup("/");
size += strlen(path) - len;
tmp = xmalloc(size);
snprintf(tmp, size, "%s%s", home, path+1+len);
return tmp;
}

View file

@ -190,5 +190,7 @@ void *xrealloc(void *, size_t);
char *xstrdup(const char *); char *xstrdup(const char *);
char *expanduser(const char *);
#endif #endif