aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorElliott Hughes <enh@google.com>2019-08-06 13:21:21 -0700
committerRob Landley <rob@landley.net>2019-08-09 20:35:09 -0500
commit99cfd03d8576de6ac760269f66eb37e3c732243f (patch)
tree57baaa5f094bed7fb644dc7a33a15ffdf96aacb3
parent5fbdad94ac145c59308200d689eea40e79a7ec5e (diff)
downloadtoybox-99cfd03d8576de6ac760269f66eb37e3c732243f.tar.gz
find: fix dangling symlink behavior.
ENOENT is ignored, but other errors are reported.
-rw-r--r--lib/dirtree.c2
-rwxr-xr-xtests/find.test4
-rw-r--r--toys/posix/find.c6
3 files changed, 9 insertions, 3 deletions
diff --git a/lib/dirtree.c b/lib/dirtree.c
index c5cf654a..e44df66c 100644
--- a/lib/dirtree.c
+++ b/lib/dirtree.c
@@ -36,7 +36,7 @@ struct dirtree *dirtree_add_node(struct dirtree *parent, char *name, int flags)
int fd = parent ? parent->dirfd : AT_FDCWD;
if (fstatat(fd, name, &st,AT_SYMLINK_NOFOLLOW*!(flags&DIRTREE_SYMFOLLOW))) {
- if (flags&DIRTREE_STATLESS) statless++;
+ if ((flags&DIRTREE_STATLESS) && errno == ENOENT) statless++;
else goto error;
}
if (S_ISLNK(st.st_mode)) {
diff --git a/tests/find.test b/tests/find.test
index ab84fb07..cbca8e76 100755
--- a/tests/find.test
+++ b/tests/find.test
@@ -104,6 +104,10 @@ testing "-printf" "find dir -name file -printf '%f %p %P %s'" \
"file dir/file file 0" "" ""
testing "-printf .N" "find dir -name file -printf %.2f" "fi" "" ""
+ln -s does-not-exist dir/dangler
+ln -s looper dir/looper
+testing "-L dangling link" "LANG=C find -L dir -name file 2>&1 | sed s/\'//g" \
+ "dir/file\nfind: dir/looper: Too many levels of symbolic links\n" "" ""
testing "-false" "find dir -false" "" "" ""
testing "-true" "find dir/file -true" "dir/file\n" "" ""
diff --git a/toys/posix/find.c b/toys/posix/find.c
index 5fc9b0ce..782cc3bc 100644
--- a/toys/posix/find.c
+++ b/toys/posix/find.c
@@ -211,7 +211,8 @@ static int do_find(struct dirtree *new)
struct double_list *argdata = TT.argdata;
char *s, **ss;
- recurse = DIRTREE_COMEAGAIN|(DIRTREE_SYMFOLLOW*!!(toys.optflags&FLAG_L));
+ recurse = DIRTREE_STATLESS|DIRTREE_COMEAGAIN|
+ (DIRTREE_SYMFOLLOW*!!(toys.optflags&FLAG_L));
// skip . and .. below topdir, handle -xdev and -depth
if (new) {
@@ -669,7 +670,8 @@ void find_main(void)
// Loop through paths
for (i = 0; i < len; i++)
- dirtree_flagread(ss[i], DIRTREE_SYMFOLLOW*!!(toys.optflags&(FLAG_H|FLAG_L)),
+ dirtree_flagread(ss[i],
+ DIRTREE_STATLESS|(DIRTREE_SYMFOLLOW*!!(toys.optflags&(FLAG_H|FLAG_L))),
do_find);
execdir(0, 1);