Files.walkFileTree() visits a file leading to a loop with LOOP_DETECT option enabled
Alan Bateman
Alan.Bateman at Sun.COM
Thu Aug 7 01:42:07 PDT 2008
Rajendra Gutupalli wrote:
> Hi Alan,
>
> I have a entry in directory structure that references ancestor of the
> directory (this is a loop according to spec) but still it is being
> visited by Files.walkFileTree().
> I created a directory structure as follows. /java/DirA/dirClink is a
> link file which points to /java/DirB/DirC and /java/DirB/DirC/dirBlink
> points to /java/DirB.
> Actually if there is link which points to ancestor that is not being
> visited by Files.walkFileTree(). Here is the scenario where it visits.
>
> Directory Structure:
> /java
> DirA
> dirClink -> /java/DirB/DirC
> DirB
> DirC
> dirBlink -> /java/DirB/ (This is the link which
> should not be visited at all)
>
> When I run code with all FileVisitOptions, I got the following print
>
> bash-3.00$ ./jdk1.7.0/bin/java TreeTest03 /java/DirA
> pre dir /java/DirA
> pre dir /java/DirA/dirClink
> pre dir /java/DirA/dirClink/dirBlink post dir
> /java/DirA/dirClink/dirBlink
> post dir /java/DirA/dirClink
> post dir /java/DirA
>
> So my query here is- Should pre and post VisitDirectory() be opened
> for the loop file /java/DirA/dirClink/dirBlink?
>
> >> when I run the code with /java/DirB input , then the pre and post
> VisitDirectory() methods will not be called for the loop file
> /java/DirB/dirBlink
>
> bash-3.00$ ./jdk1.7.0/bin/java TreeTest03 /java/DirB
> pre dir /java/DirB
> pre dir /java/DirB/DirC
> post dir /java/DirB/DirC
> post dir /java/DirB
The cycles in this directory structure do indeed highlight a problem.
The cycles are correctly detected but the "skipped" directories aren't
notified to the FileVisitor (this is a bug in the Files.walkFileTree's
spec). In a recursive copy for example, which follows sym links by
default, then the notification can be minimally used to report a warning
(like what "cp -r" would do for such cases). Here's what you should get
for this:
(pre) java
(pre) java/DirA
(pre) java/DirA/dirClink
(pre) java/DirA/dirClink/dirBlink
(skip) java/DirA/dirClink/dirBlink/DirC
(post) java/DirA/dirClink/dirBlink
(post) java/DirA/dirClink
(post) java/DirA
(pre) java/DirB
(pre) java/DirB/DirC
(skip) java/DirB/DirC/dirBlink
(post) java/DirB/DirC
(post) java/DirB
(post) java
The lines with "(skip)" are where a cycle is detected and aren't
(currently) notified to you.
-Alan.
More information about the nio-dev
mailing list