summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTavian Barnes <tavianator@tavianator.com>2024-05-27 13:39:42 -0400
committerTavian Barnes <tavianator@tavianator.com>2024-05-27 14:04:39 -0400
commit470589cbd9ca3e73d8c01ac3a96cbc065179dcc5 (patch)
tree71a86e212ce58e3dc9fb5e6c1f25d895ec488983
parentf095481862ccd175d297da67d0e313d135bd75c3 (diff)
downloadbfs-470589cbd9ca3e73d8c01ac3a96cbc065179dcc5.tar.xz
bfstd: Treat ELOOP like ENOENT
GNU findutils just made the same change, so looping symlinks will be considered broken rather than a hard error. Link: https://savannah.gnu.org/bugs/?51926
-rw-r--r--src/bfstd.c2
-rw-r--r--src/printf.c2
-rw-r--r--tests/bfs/xtype_depth.sh9
-rw-r--r--tests/gnu/L_loops_continue.out1
-rw-r--r--tests/gnu/ignore_readdir_race_loop.out12
-rw-r--r--tests/gnu/ignore_readdir_race_loop.sh2
6 files changed, 25 insertions, 3 deletions
diff --git a/src/bfstd.c b/src/bfstd.c
index 44eda7c..1c5e289 100644
--- a/src/bfstd.c
+++ b/src/bfstd.c
@@ -44,7 +44,7 @@ bool error_is_like(int error, int category) {
switch (category) {
case ENOENT:
- return error == ENOTDIR;
+ return error == ENOTDIR || error == ELOOP;
case ENOSYS:
// https://github.com/opencontainers/runc/issues/2151
diff --git a/src/printf.c b/src/printf.c
index be09ebd..f514361 100644
--- a/src/printf.c
+++ b/src/printf.c
@@ -544,7 +544,7 @@ static int bfs_printf_Y(CFILE *cfile, const struct bfs_fmt *fmt, const struct BF
int error = 0;
if (type == BFS_ERROR) {
- if (errno_is_like(ELOOP)) {
+ if (errno == ELOOP) {
str = "L";
} else if (errno_is_like(ENOENT)) {
str = "N";
diff --git a/tests/bfs/xtype_depth.sh b/tests/bfs/xtype_depth.sh
index 02c8173..93c4fb7 100644
--- a/tests/bfs/xtype_depth.sh
+++ b/tests/bfs/xtype_depth.sh
@@ -1,2 +1,9 @@
+cd "$TEST"
+"$XTOUCH" -p foo/bar
+ln -s foo/bar baz
+
+chmod a-rx foo
+defer chmod +rx foo
+
# Make sure -xtype is considered side-effecting for facts_when_impure
-! invoke_bfs loops -xtype l -depth 100
+! invoke_bfs . -xtype l -depth 100
diff --git a/tests/gnu/L_loops_continue.out b/tests/gnu/L_loops_continue.out
index a514555..faf33d3 100644
--- a/tests/gnu/L_loops_continue.out
+++ b/tests/gnu/L_loops_continue.out
@@ -4,6 +4,7 @@ loops/deeply
loops/deeply/nested
loops/deeply/nested/dir
loops/file
+loops/loop
loops/notdir
loops/skip
loops/skip/dir
diff --git a/tests/gnu/ignore_readdir_race_loop.out b/tests/gnu/ignore_readdir_race_loop.out
new file mode 100644
index 0000000..faf33d3
--- /dev/null
+++ b/tests/gnu/ignore_readdir_race_loop.out
@@ -0,0 +1,12 @@
+loops
+loops/broken
+loops/deeply
+loops/deeply/nested
+loops/deeply/nested/dir
+loops/file
+loops/loop
+loops/notdir
+loops/skip
+loops/skip/dir
+loops/skip/loop
+loops/symlink
diff --git a/tests/gnu/ignore_readdir_race_loop.sh b/tests/gnu/ignore_readdir_race_loop.sh
new file mode 100644
index 0000000..3329169
--- /dev/null
+++ b/tests/gnu/ignore_readdir_race_loop.sh
@@ -0,0 +1,2 @@
+# Make sure -ignore_readdir_race doesn't suppress ELOOP from an actual filesystem loop
+! bfs_diff -L loops -ignore_readdir_race