Merge pull request #1598 from N-R-K/tilde_handling

More correct tilde handling
This commit is contained in:
Arun 2023-03-10 18:15:16 +05:30 committed by GitHub
commit 03ae86cca4
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
1 changed files with 27 additions and 20 deletions

View File

@ -1127,6 +1127,16 @@ static inline bool getutil(char *util)
return spawn("which", util, NULL, NULL, F_NORMAL | F_NOTRACE) == 0; return spawn("which", util, NULL, NULL, F_NORMAL | F_NOTRACE) == 0;
} }
static inline bool tilde_is_home(const char *s)
{
return s[0] == '~' && (s[1] == '\0' || s[1] == '/');
}
static inline bool tilde_is_home_strict(const char *s)
{
return s[0] == '~' && s[1] == '/';
}
/* /*
* Updates out with "dir/name or "/name" * Updates out with "dir/name or "/name"
* Returns the number of bytes copied including the terminating NULL byte * Returns the number of bytes copied including the terminating NULL byte
@ -1137,16 +1147,9 @@ static size_t mkpath(const char *dir, const char *name, char *out)
{ {
size_t len = 0; size_t len = 0;
if (name[0] == '~') { //NOLINT /* same rational for being strict as abspath() */
if (tilde_is_home_strict(name)) { //NOLINT
len = xstrsncpy(out, home, PATH_MAX); len = xstrsncpy(out, home, PATH_MAX);
if (!name[1])
return len;
if (name[1] != '/') {
out[0] = '\0';
return 0;
}
--len; --len;
++name; ++name;
} else if (name[0] != '/') { // NOLINT } else if (name[0] != '/') { // NOLINT
@ -1213,11 +1216,12 @@ static char *abspath(const char *filepath, char *cwd, char *buf)
if (!path) if (!path)
return NULL; return NULL;
if (path[0] == '~') { /* when dealing with tilde, we need to be strict.
* otherwise a file named "~" can end up expanding to
* $HOME and causing disaster */
if (tilde_is_home_strict(path)) {
cwd = home; cwd = home;
++path; path += 2; /* advance 2 bytes past the "~/" */
if (*path == '/')
++path;
} else if ((path[0] != '/') && !cwd) { } else if ((path[0] != '/') && !cwd) {
cwd = getcwd(NULL, 0); cwd = getcwd(NULL, 0);
if (!cwd) if (!cwd)
@ -1331,15 +1335,17 @@ static void xterm_cfg(char *path)
} }
#endif #endif
static void convert_tilde(const char *path, char *buf) static bool convert_tilde(const char *path, char *buf)
{ {
if (path[0] == '~') { if (tilde_is_home(path)) {
ssize_t len = xstrlen(home); ssize_t len = xstrlen(home);
ssize_t loclen = xstrlen(path); ssize_t loclen = xstrlen(path);
xstrsncpy(buf, home, len + 1); xstrsncpy(buf, home, len + 1);
xstrsncpy(buf + len, path + 1, loclen); xstrsncpy(buf + len, path + 1, loclen);
return true;
} }
return false;
} }
static int create_tmp_file(void) static int create_tmp_file(void)
@ -2763,13 +2769,14 @@ static void archive_selection(const char *cmd, const char *archive)
static void write_lastdir(const char *curpath, const char *outfile) static void write_lastdir(const char *curpath, const char *outfile)
{ {
bool tilde = false;
if (!outfile) if (!outfile)
xstrsncpy(cfgpath + xstrlen(cfgpath), "/.lastd", 8); xstrsncpy(cfgpath + xstrlen(cfgpath), "/.lastd", 8);
else else
convert_tilde(outfile, g_buf); tilde = convert_tilde(outfile, g_buf);
int fd = open(outfile int fd = open(outfile
? (outfile[0] == '~' ? g_buf : outfile) ? (tilde ? g_buf : outfile)
: cfgpath, O_CREAT | O_WRONLY | O_TRUNC, S_IWUSR | S_IRUSR); : cfgpath, O_CREAT | O_WRONLY | O_TRUNC, S_IWUSR | S_IRUSR);
if (fd != -1) { if (fd != -1) {
@ -3837,8 +3844,8 @@ static char *get_kv_val(kv *kvarr, char *buf, int key, uchar_t max, uchar_t id)
return pluginstr + kvarr[r].off; return pluginstr + kvarr[r].off;
val = bmstr + kvarr[r].off; val = bmstr + kvarr[r].off;
convert_tilde(val, g_buf); bool tilde = convert_tilde(val, g_buf);
return abspath(((val[0] == '~') ? g_buf : val), NULL, buf); return abspath((tilde ? g_buf : val), NULL, buf);
} }
} }
@ -8297,7 +8304,7 @@ static bool setup_config(void)
/* Set up configuration file paths */ /* Set up configuration file paths */
if (xdgcfg && xdgcfg[0]) { if (xdgcfg && xdgcfg[0]) {
DPRINTF_S(xdgcfg); DPRINTF_S(xdgcfg);
if (xdgcfg[0] == '~') { if (tilde_is_home(xdgcfg)) {
r = xstrsncpy(g_buf, home, PATH_MAX); r = xstrsncpy(g_buf, home, PATH_MAX);
xstrsncpy(g_buf + r - 1, xdgcfg + 1, PATH_MAX); xstrsncpy(g_buf + r - 1, xdgcfg + 1, PATH_MAX);
xdgcfg = g_buf; xdgcfg = g_buf;