[perl #33892] Add Interix support
[p5sagit/p5-mst-13.2.git] / lib / File / Find.pm
index f9fb16b..f2cecc1 100644 (file)
@@ -3,7 +3,7 @@ use 5.006;
 use strict;
 use warnings;
 use warnings::register;
-our $VERSION = '1.06';
+our $VERSION = '1.09';
 require Exporter;
 require Cwd;
 
@@ -44,21 +44,23 @@ but have subtle differences.
   find(\&wanted,  @directories);
   find(\%options, @directories);
 
-C<find()> does a breadth-first search over the given C<@directories> in the
-order they are given.  In essence, it works from the top down.
-
-For each file or directory found, the C<&wanted> subroutine is called,
-with the return code ignored.  (See below for details on how to use
-the C<&wanted> function).  Additionally, for each directory found,
-it will go into that directory and continue the search.
+C<find()> does a depth-first search over the given C<@directories> in
+the order they are given.  For each file or directory found, it calls
+the C<&wanted> subroutine.  (See below for details on how to use the
+C<&wanted> function).  Additionally, for each directory found, it will
+C<chdir()> into that directory and continue the search, invoking the
+C<&wanted> function on each file or subdirectory in the directory.
 
 =item B<finddepth>
 
   finddepth(\&wanted,  @directories);
   finddepth(\%options, @directories);
 
-C<finddepth()> works just like C<find()> except it does a depth-first search.
-It works from the bottom of the directory tree up.
+C<finddepth()> works just like C<find()> except that is invokes the
+C<&wanted> function for a directory I<after> invoking it for the
+directory's contents.  It does a postorder traversal instead of a
+preorder traversal, working from the bottom of the directory tree up
+where C<find()> works from the top of the tree down.
 
 =back
 
@@ -124,7 +126,8 @@ C<wanted()> function is called. This enables fast file checks involving S< _>.
 =item *
 
 There is a variable C<$File::Find::fullname> which holds the absolute
-pathname of the file with all symbolic links resolved
+pathname of the file with all symbolic links resolved.  If the link is
+a dangling symbolic link, then fullname will be set to C<undef>.
 
 =back
 
@@ -388,6 +391,12 @@ volume actually maintains its own "Desktop Folder" directory.
 
 =back
 
+=head1 BUGS AND CAVEATS
+
+Despite the name of the C<finddepth()> function, both C<find()> and
+C<finddepth()> perform a depth-first search of the directory
+hierarchy.
+
 =head1 HISTORY
 
 File::Find used to produce incorrect results if called recursively.
@@ -583,7 +592,8 @@ sub _find_opt {
     local ($wanted_callback, $avoid_nlink, $bydepth, $no_chdir, $follow,
        $follow_skip, $full_check, $untaint, $untaint_skip, $untaint_pat,
        $pre_process, $post_process, $dangling_symlinks);
-    local($dir, $name, $fullname, $prune, $_);
+    local($dir, $name, $fullname, $prune);
+    local *_ = \my $a;
 
     my $cwd            = $wanted->{bydepth} ? Cwd::fastcwd() : Cwd::getcwd();
     my $cwd_untainted  = $cwd;
@@ -1092,7 +1102,21 @@ sub _find_dir_symlnk($$$) {
            $new_loc = Follow_SymLink($loc_pref.$FN);
 
            # ignore if invalid symlink
-           next unless defined $new_loc;
+            unless (defined $new_loc) {
+               if ($dangling_symlinks) {
+                   if (ref $dangling_symlinks eq 'CODE') {
+                       $dangling_symlinks->($FN, $dir_pref);
+                   } else {
+                       warnings::warnif "$dir_pref$FN is a dangling symbolic link\n";
+                   }
+               }
+
+               $fullname = undef;
+               $name = $dir_pref . $FN;
+               $_ = ($no_chdir ? $name : $FN);
+               { $wanted_callback->() };
+               next;
+           }
 
            if (-d _) {
                push @Stack,[$new_loc,$updir_loc,$dir_name,$FN,1];
@@ -1212,7 +1236,7 @@ $File::Find::current_dir = File::Spec->curdir || '.';
 
 $File::Find::dont_use_nlink = 1
     if $^O eq 'os2' || $^O eq 'dos' || $^O eq 'amigaos' || $^O eq 'MSWin32' ||
-       $^O eq 'cygwin' || $^O eq 'epoc' || $^O eq 'qnx' ||
+       $^O eq 'interix' || $^O eq 'cygwin' || $^O eq 'epoc' || $^O eq 'qnx' ||
           $^O eq 'nto';
 
 # Set dont_use_nlink in your hint file if your system's stat doesn't