mercurial/commands.py
changeset 1799 b942f5cfd326
parent 1782 b9671b41e360
child 1800 414e81ae971f
equal deleted inserted replaced
1798:d610fe0e6893 1799:b942f5cfd326
    80     possible display
    80     possible display
    81 
    81 
    82     "iter", rev, None: in-order traversal of the revs earlier iterated
    82     "iter", rev, None: in-order traversal of the revs earlier iterated
    83     over with "add" - use to display data'''
    83     over with "add" - use to display data'''
    84 
    84 
       
    85     def increasing_windows(start, end, windowsize=8, sizelimit=512):
       
    86         if start < end:
       
    87             while start < end:
       
    88                 yield start, min(windowsize, end-start)
       
    89                 start += windowsize
       
    90                 if windowsize < sizelimit:
       
    91                     windowsize *= 2
       
    92         else:
       
    93             while start > end:
       
    94                 yield start, min(windowsize, start-end-1)
       
    95                 start -= windowsize
       
    96                 if windowsize < sizelimit:
       
    97                     windowsize *= 2
       
    98 
       
    99 
    85     files, matchfn, anypats = matchpats(repo, pats, opts)
   100     files, matchfn, anypats = matchpats(repo, pats, opts)
    86 
   101 
    87     if repo.changelog.count() == 0:
   102     if repo.changelog.count() == 0:
    88         return [], False, matchfn
   103         return [], False, matchfn
    89 
   104 
    90     revs = map(int, revrange(ui, repo, opts['rev'] or ['tip:0']))
   105     revs = map(int, revrange(ui, repo, opts['rev'] or ['tip:0']))
    91     wanted = {}
   106     wanted = {}
    92     slowpath = anypats
   107     slowpath = anypats
    93     window = 300
       
    94     fncache = {}
   108     fncache = {}
    95 
   109 
    96     chcache = {}
   110     chcache = {}
    97     def getchange(rev):
   111     def getchange(rev):
    98         ch = chcache.get(rev)
   112         ch = chcache.get(rev)
   104         # No files, no patterns.  Display all revs.
   118         # No files, no patterns.  Display all revs.
   105         wanted = dict(zip(revs, revs))
   119         wanted = dict(zip(revs, revs))
   106     if not slowpath:
   120     if not slowpath:
   107         # Only files, no patterns.  Check the history of each file.
   121         # Only files, no patterns.  Check the history of each file.
   108         def filerevgen(filelog):
   122         def filerevgen(filelog):
   109             for i in xrange(filelog.count() - 1, -1, -window):
   123             for i, window in increasing_windows(filelog.count()-1, -1):
   110                 revs = []
   124                 revs = []
   111                 for j in xrange(max(0, i - window), i + 1):
   125                 for j in xrange(max(0, i - window), i + 1):
   112                     revs.append(filelog.linkrev(filelog.node(j)))
   126                     revs.append(filelog.linkrev(filelog.node(j)))
   113                 revs.reverse()
   127                 revs.reverse()
   114                 for rev in revs:
   128                 for rev in revs:
   130                     fncache[rev].append(file_)
   144                     fncache[rev].append(file_)
   131                     wanted[rev] = 1
   145                     wanted[rev] = 1
   132     if slowpath:
   146     if slowpath:
   133         # The slow path checks files modified in every changeset.
   147         # The slow path checks files modified in every changeset.
   134         def changerevgen():
   148         def changerevgen():
   135             for i in xrange(repo.changelog.count() - 1, -1, -window):
   149             for i, window in increasing_windows(repo.changelog.count()-1, -1):
   136                 for j in xrange(max(0, i - window), i + 1):
   150                 for j in xrange(max(0, i - window), i + 1):
   137                     yield j, getchange(j)[3]
   151                     yield j, getchange(j)[3]
   138 
   152 
   139         for rev, changefiles in changerevgen():
   153         for rev, changefiles in changerevgen():
   140             matches = filter(matchfn, changefiles)
   154             matches = filter(matchfn, changefiles)
   141             if matches:
   155             if matches:
   142                 fncache[rev] = matches
   156                 fncache[rev] = matches
   143                 wanted[rev] = 1
   157                 wanted[rev] = 1
   144 
   158 
   145     def iterate():
   159     def iterate():
   146         for i in xrange(0, len(revs), window):
   160         for i, window in increasing_windows(0, len(revs)):
   147             yield 'window', revs[0] < revs[-1], revs[-1]
   161             yield 'window', revs[0] < revs[-1], revs[-1]
   148             nrevs = [rev for rev in revs[i:min(i+window, len(revs))]
   162             nrevs = [rev for rev in revs[i:min(i+window, len(revs))]
   149                      if rev in wanted]
   163                      if rev in wanted]
   150             srevs = list(nrevs)
   164             srevs = list(nrevs)
   151             srevs.sort()
   165             srevs.sort()