fix memory usage of revlog caches by limiting cache size [issue1639]
authorMatt Mackall <mpm@selenic.com>
Thu, 09 Jul 2009 17:10:07 -0500
changeset 9097 431462bd8478
parent 9096 47bc92755b95
child 9098 5e4654f5522d
fix memory usage of revlog caches by limiting cache size [issue1639]
mercurial/commands.py
mercurial/context.py
mercurial/copies.py
mercurial/util.py
--- a/mercurial/commands.py	Thu Jul 09 11:59:12 2009 +0200
+++ b/mercurial/commands.py	Thu Jul 09 17:10:07 2009 -0500
@@ -1206,18 +1206,7 @@
     if opts.get('print0'):
         sep = eol = '\0'
 
-    fcache = {}
-    forder = []
-    def getfile(fn):
-        if fn not in fcache:
-            if len(fcache) > 20:
-                del fcache[forder.pop(0)]
-            fcache[fn] = repo.file(fn)
-        else:
-            forder.remove(fn)
-
-        forder.append(fn)
-        return fcache[fn]
+    getfile = util.lrucachefunc(repo.file)
 
     def matchlines(body):
         begin = 0
--- a/mercurial/context.py	Thu Jul 09 11:59:12 2009 +0200
+++ b/mercurial/context.py	Thu Jul 09 17:10:07 2009 -0500
@@ -379,11 +379,11 @@
                 child[0][b1:b2] = parent[0][a1:a2]
             return child
 
-        getlog = util.cachefunc(lambda x: self._repo.file(x))
+        getlog = util.lrucachefunc(lambda x: self._repo.file(x))
         def getctx(path, fileid):
             log = path == self._path and self._filelog or getlog(path)
             return filectx(self._repo, path, fileid=fileid, filelog=log)
-        getctx = util.cachefunc(getctx)
+        getctx = util.lrucachefunc(getctx)
 
         def parents(f):
             # we want to reuse filectx objects as much as possible
--- a/mercurial/copies.py	Thu Jul 09 11:59:12 2009 +0200
+++ b/mercurial/copies.py	Thu Jul 09 17:10:07 2009 -0500
@@ -120,8 +120,8 @@
                 return c1.filectx(f)
             return c2.filectx(f)
         return repo.filectx(f, fileid=n)
-    ctx = util.cachefunc(makectx)
 
+    ctx = util.lrucachefunc(makectx)
     copy = {}
     fullcopy = {}
     diverge = {}
--- a/mercurial/util.py	Thu Jul 09 11:59:12 2009 +0200
+++ b/mercurial/util.py	Thu Jul 09 17:10:07 2009 -0500
@@ -115,6 +115,33 @@
 
     return f
 
+def lrucachefunc(func):
+    '''cache most recent results of function calls'''
+    cache = {}
+    order = []
+    if func.func_code.co_argcount == 1:
+        def f(arg):
+            if arg not in cache:
+                if len(cache) > 20:
+                    del cache[order.pop(0)]
+                cache[arg] = func(arg)
+            else:
+                order.remove(arg)
+            order.append(arg)
+            return cache[arg]
+    else:
+        def f(*args):
+            if args not in cache:
+                if len(cache) > 20:
+                    del cache[order.pop(0)]
+                cache[args] = func(*args)
+            else:
+                order.remove(args)
+            order.append(args)
+            return cache[args]
+
+    return f
+
 class propertycache(object):
     def __init__(self, func):
         self.func = func