strlcpy(to, merge_file, *len_ptr + 1);
merge_file = to;
}
- if (!sanitize_path(fn, merge_file, r, dirbuf_depth, NULL)) {
+ if (!sanitize_path(fn, merge_file, r, dirbuf_depth)) {
rprintf(FERROR, "merge-file name overflows: %s\n",
merge_file);
return NULL;
clean_fname(thisname, 0);
if (sanitize_paths)
- sanitize_path(thisname, thisname, "", 0, NULL);
+ sanitize_path(thisname, thisname, "", 0);
if ((basename = strrchr(thisname, '/')) != NULL) {
int len = basename++ - thisname;
} else
read_sbuf(f, bp, linkname_len - 1);
if (sanitize_paths)
- sanitize_path(bp, bp, "", lastdir_depth, NULL);
+ sanitize_path(bp, bp, "", lastdir_depth);
}
#endif
}
clean_fname(thisname, 0);
if (sanitize_paths)
- sanitize_path(thisname, thisname, "", 0, NULL);
+ sanitize_path(thisname, thisname, "", 0);
if (stp && S_ISDIR(stp->st_mode)) {
st = *stp; /* Needed for "symlink/." with --relative. */
if (use_ff_fd) {
if (read_line(filesfrom_fd, fbuf, sizeof fbuf, rl_flags) == 0)
break;
- sanitize_path(fbuf, fbuf, "", 0, NULL);
+ sanitize_path(fbuf, fbuf, "", 0);
} else {
if (argc-- == 0)
break;
strlcpy(fbuf, *argv++, MAXPATHLEN);
if (sanitize_paths)
- sanitize_path(fbuf, fbuf, "", 0, NULL);
+ sanitize_path(fbuf, fbuf, "", 0);
}
len = strlen(fbuf);
if (sanitize_paths) {
char **dir;
for (dir = basis_dir; *dir; dir++) {
- *dir = sanitize_path(NULL, *dir, NULL, curr_dir_depth, NULL);
+ *dir = sanitize_path(NULL, *dir, NULL, curr_dir_depth);
}
if (partial_dir) {
- partial_dir = sanitize_path(NULL, partial_dir, NULL, curr_dir_depth, NULL);
+ partial_dir = sanitize_path(NULL, partial_dir, NULL, curr_dir_depth);
}
}
fix_basis_dirs();
case OPT_INCLUDE_FROM:
arg = poptGetOptArg(pc);
if (sanitize_paths)
- arg = sanitize_path(NULL, arg, NULL, 0, NULL);
+ arg = sanitize_path(NULL, arg, NULL, 0);
if (server_filter_list.head) {
int rej;
char *cp = strdup(arg);
if (sanitize_paths) {
int i;
for (i = argc; i-- > 0; )
- argv[i] = sanitize_path(NULL, argv[i], "", 0, NULL);
+ argv[i] = sanitize_path(NULL, argv[i], "", 0);
if (tmpdir)
- tmpdir = sanitize_path(NULL, tmpdir, NULL, 0, NULL);
+ tmpdir = sanitize_path(NULL, tmpdir, NULL, 0);
if (backup_dir)
- backup_dir = sanitize_path(NULL, backup_dir, NULL, 0, NULL);
+ backup_dir = sanitize_path(NULL, backup_dir, NULL, 0);
}
if (server_filter_list.head && !am_sender) {
struct filter_list_struct *elp = &server_filter_list;
}
} else {
if (sanitize_paths)
- files_from = sanitize_path(NULL, files_from, NULL, 0, NULL);
+ files_from = sanitize_path(NULL, files_from, NULL, 0);
if (server_filter_list.head) {
if (!*files_from)
goto options_rejected;
s = ".";
if (sanitize_paths)
- s = sanitize_path(NULL, s, "", 0, NULL);
+ s = sanitize_path(NULL, s, "", 0);
else
s = strdup(s);
if (!s)
* Specify NULL to get the default of "module_dir".
*
* The depth var is a count of how many '..'s to allow at the start of the
- * path. If symlink is set, combine its value with the "p" value to get
- * the target path, and **return NULL if any '..'s try to escape**.
+ * path.
*
* We also clean the path in a manner similar to clean_fname() but with a
* few differences:
* ALWAYS collapses ".." elements (except for those at the start of the
* string up to "depth" deep). If the resulting name would be empty,
* change it into a ".". */
-char *sanitize_path(char *dest, const char *p, const char *rootdir, int depth,
- const char *symlink)
+char *sanitize_path(char *dest, const char *p, const char *rootdir, int depth)
{
- char *start, *sanp, *save_dest = dest;
+ char *start, *sanp;
int rlen = 0, leave_one_dotdir = relative_paths;
- if (symlink && *symlink == '/') {
- p = symlink;
- symlink = "";
- }
-
if (dest != p) {
int plen = strlen(p);
if (*p == '/') {
}
start = sanp = dest + rlen;
- while (1) {
- if (*p == '\0') {
- if (!symlink || !*symlink)
- break;
- while (sanp != start && sanp[-1] != '/') {
- /* strip last element */
- sanp--;
- }
- /* Append a relative symlink */
- p = symlink;
- symlink = "";
- }
+ while (*p) {
/* discard leading or extra slashes */
if (*p == '/') {
p++;
if (*p == '.' && p[1] == '.' && (p[2] == '/' || p[2] == '\0')) {
/* ".." component followed by slash or end */
if (depth <= 0 || sanp != start) {
- if (symlink && sanp == start) {
- if (!save_dest)
- free(dest);
- return NULL;
- }
p += 2;
if (sanp != start) {
/* back up sanp one level */