Skip to content

patches/0004: resolve NTFS symlink at readdir root before walkFileTree - #11

Merged
Ilia (k15tfu) merged 1 commit into
masterfrom
fix-readdir-symlink-on-windows
May 2, 2026
Merged

Ilia (k15tfu) merged 1 commit into
masterfrom
fix-readdir-symlink-on-windows

Conversation

@mfilippov

Copy link
Copy Markdown
Collaborator

Files.walkFileTree(NOFOLLOW) treats an NTFS symbolic link to a directory as a file: it calls visitFile on the link instead of preVisitDirectory, so the children of the link target are never enumerated. The patched WindowsFileSystem#readdir then returns a single Dirent for the link itself, and any glob() over a package whose subdirectories are NTFS symlinks (e.g. external/llvm++llvm_source+libcxx{,abi}, where src/, include/, etc. are symlinks into llvm-raw) silently matches nothing and trips --incompatible_disallow_empty_glob.

Resolve the link with toRealPath() when called with NOFOLLOW. Junctions report isDirectory()==true under NOFOLLOW and are unaffected; the extra Files.isSymbolicLink() check is one GetFileAttributes call per readdir.

@mfilippov
Mikhail Filippov (mfilippov) force-pushed the fix-readdir-symlink-on-windows branch from 27489ad to a4b5162 Compare May 1, 2026 17:58
Files.walkFileTree(NOFOLLOW) treats an NTFS symbolic link to a directory
as a file: it calls visitFile on the link instead of preVisitDirectory,
so the children of the link target are never enumerated. The patched
WindowsFileSystem#readdir then returns a single Dirent for the link
itself, and any glob() over a package whose subdirectories are NTFS
symlinks (e.g. external/llvm++llvm_source+libcxx{,abi}, where src/,
include/, etc. are symlinks into llvm-raw) silently matches nothing
and trips --incompatible_disallow_empty_glob.

Resolve the link with toRealPath() unconditionally: readdir's contract
follows symlinks when resolving the directory itself regardless of
followSymlinks (which only governs entry types). Junctions are not
recognized as symlinks here and report isDirectory()==true natively,
so they're unaffected; the extra Files.isSymbolicLink() check is one
GetFileAttributes call per readdir.
@k15tfu
Ilia (k15tfu) force-pushed the fix-readdir-symlink-on-windows branch from a4b5162 to 47ee50f Compare May 2, 2026 10:45
@k15tfu
Ilia (k15tfu) merged commit af1df2f into master May 2, 2026
13 of 14 checks passed
@k15tfu
Ilia (k15tfu) deleted the fix-readdir-symlink-on-windows branch May 2, 2026 10:47
+ }
+
+ @Override
+ public FileVisitResult preVisitDirectory(Path dir, BasicFileAttributes attrs) {

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

from https://docs.oracle.com/javase/8/docs/api/java/nio/file/Files.html:

The visitFile method is invoked for all files, including directories, encountered at maxDepth, unless the basic file attributes cannot be read, in which case the visitFileFailed method is invoked.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants