From e385f541859982337f60cadcaaadc96301b26dcb Mon Sep 17 00:00:00 2001 From: Harshavardhana Date: Mon, 4 Mar 2024 15:58:35 -0800 Subject: [PATCH] fix: nLink is unreliable on all filesystems (#19187) ext4, xfs support this behavior however btrfs, nfs may not support it properly. in-case when we see Nlink < 2 then we know that we need to fallback on readdir() fixes a regression from #19100 fixes #19181 --- cmd/is-dir-empty_linux.go | 18 ++++++++++++++++-- 1 file changed, 16 insertions(+), 2 deletions(-) diff --git a/cmd/is-dir-empty_linux.go b/cmd/is-dir-empty_linux.go index f7ad4f74f..c205955f8 100644 --- a/cmd/is-dir-empty_linux.go +++ b/cmd/is-dir-empty_linux.go @@ -20,7 +20,9 @@ package cmd -import "syscall" +import ( + "syscall" +) // Returns true if no error and there is no object or prefix inside this directory func isDirEmpty(dirname string) bool { @@ -28,5 +30,17 @@ func isDirEmpty(dirname string) bool { if err := syscall.Stat(dirname, &stat); err != nil { return false } - return stat.Mode&syscall.S_IFMT == syscall.S_IFDIR && stat.Nlink < 3 + if stat.Mode&syscall.S_IFMT == syscall.S_IFDIR && stat.Nlink == 2 { + return true + } + // On filesystems such as btrfs, nfs this is not true, so fallback + // to performing readdir() instead. + if stat.Mode&syscall.S_IFMT == syscall.S_IFDIR && stat.Nlink < 2 { + entries, err := readDirN(dirname, 1) + if err != nil { + return false + } + return len(entries) == 0 + } + return false }