changeset 18017:74912fe3d718

dirstate: move file type filtering to its source This prepares us to move to a much faster statfiles implementation on Unix.
author Bryan O'Sullivan <bryano@fb.com>
date Fri, 30 Nov 2012 15:55:07 -0800
parents a39fe76c4c65
children 0fed3fe45ea7
files mercurial/dirstate.py mercurial/posix.py mercurial/windows.py
diffstat 3 files changed, 16 insertions(+), 7 deletions(-) [+]
line wrap: on
line diff
--- a/mercurial/dirstate.py	Mon Oct 08 19:34:04 2012 +0200
+++ b/mercurial/dirstate.py	Fri Nov 30 15:55:07 2012 -0800
@@ -697,9 +697,6 @@
         if not skipstep3 and not exact:
             visit = sorted([f for f in dmap if f not in results and matchfn(f)])
             for nf, st in zip(visit, util.statfiles([join(i) for i in visit])):
-                if (not st is None and
-                    getkind(st.st_mode) not in (regkind, lnkkind)):
-                    st = None
                 results[nf] = st
         for s in subrepos:
             del results[s]
--- a/mercurial/posix.py	Mon Oct 08 19:34:04 2012 +0200
+++ b/mercurial/posix.py	Fri Nov 30 15:55:07 2012 -0800
@@ -352,12 +352,18 @@
 def setsignalhandler():
     pass
 
+_wantedkinds = set([stat.S_IFREG, stat.S_IFLNK])
+
 def statfiles(files):
-    'Stat each file in files and yield stat or None if file does not exist.'
+    '''Stat each file in files. Yield each stat, or None if a file does not
+    exist or has a type we don't care about.'''
     lstat = os.lstat
+    getkind = stat.S_IFMT
     for nf in files:
         try:
             st = lstat(nf)
+            if getkind(st.st_mode) not in _wantedkinds:
+                st = None
         except OSError, err:
             if err.errno not in (errno.ENOENT, errno.ENOTDIR):
                 raise
--- a/mercurial/windows.py	Mon Oct 08 19:34:04 2012 +0200
+++ b/mercurial/windows.py	Fri Nov 30 15:55:07 2012 -0800
@@ -7,7 +7,7 @@
 
 from i18n import _
 import osutil, encoding
-import errno, msvcrt, os, re, sys, _winreg
+import errno, msvcrt, os, re, stat, sys, _winreg
 
 import win32
 executablepath = win32.executablepath
@@ -213,10 +213,15 @@
             return executable
     return findexisting(os.path.expanduser(os.path.expandvars(command)))
 
+_wantedkinds = set([stat.S_IFREG, stat.S_IFLNK])
+
 def statfiles(files):
-    '''Stat each file in files and yield stat or None if file does not exist.
+    '''Stat each file in files. Yield each stat, or None if a file
+    does not exist or has a type we don't care about.
+
     Cluster and cache stat per directory to minimize number of OS stat calls.'''
     dircache = {} # dirname -> filename -> status | None if file does not exist
+    getkind = stat.S_IFMT
     for nf in files:
         nf  = normcase(nf)
         dir, base = os.path.split(nf)
@@ -226,7 +231,8 @@
         if cache is None:
             try:
                 dmap = dict([(normcase(n), s)
-                    for n, k, s in osutil.listdir(dir, True)])
+                             for n, k, s in osutil.listdir(dir, True)
+                             if getkind(s) in _wantedkinds])
             except OSError, err:
                 # handle directory not found in Python version prior to 2.5
                 # Python <= 2.4 returns native Windows code 3 in errno