[PATCH 8 of 9 stable] largefiles: simplify cachelfiles - don't spend a lot of time checking hashes

Mads Kiilerich mads at kiilerich.com
Mon Feb 25 20:41:28 CST 2013

# HG changeset patch
# User Mads Kiilerich <madski at unity3d.com>
# Date 1361846443 -3600
# Branch stable
# Node ID fba3b0f812f9f5db45e03b2bdce12ec7d9b71c79
# Parent  51dfa49cb71bb83e7520003a0c7c6fefccc36519
largefiles: simplify cachelfiles - don't spend a lot of time checking hashes

cachelfiles jumped through loops to handle merges and modified files ... but it
did apparently no longer have a valid reason to do so. It should just always
make sure that the largefiles referenced from the standins are present - no
matter which actual largefile is stored in the working directory. If there is
no standin then there is nothing to fetch.

The old code usually verified the hash of all largefiles every time this
function was invoked - for examply by 'update'.

This change makes a trivial noop update 5-10 seconds faster on our repo (with
the other 50% spent doing another unnecessary hashing of all largefiles).

diff --git a/hgext/largefiles/lfcommands.py b/hgext/largefiles/lfcommands.py
--- a/hgext/largefiles/lfcommands.py
+++ b/hgext/largefiles/lfcommands.py
@@ -8,7 +8,7 @@
 '''High-level command function for lfconvert, plus the cmdtable.'''
-import os
+import os, errno
 import shutil
 from mercurial import util, match as match_, hg, node, context, error, \
@@ -403,22 +403,13 @@
     toget = []
     for lfile in lfiles:
-        # If we are mid-merge, then we have to trust the standin that is in the
-        # working copy to have the correct hashvalue.  This is because the
-        # original hg.merge() already updated the standin as part of the normal
-        # merge process -- we just have to update the largefile to match.
-        if (getattr(repo, "_ismerging", False) and
-             os.path.exists(repo.wjoin(lfutil.standin(lfile)))):
-            expectedhash = lfutil.readstandin(repo, lfile)
-        else:
+        try:
             expectedhash = repo[node][lfutil.standin(lfile)].data().strip()
-        # if it exists and its hash matches, it might have been locally
-        # modified before updating and the user chose 'local'.  in this case,
-        # it will not be in any store, so don't look for it.
-        if ((not os.path.exists(repo.wjoin(lfile)) or
-             expectedhash != lfutil.hashfile(repo.wjoin(lfile))) and
-            not lfutil.findfile(repo, expectedhash)):
+        except IOError, err:
+            if err.errno == errno.ENOENT:
+                continue # node must be None and standin wasn't found in wctx
+            raise
+        if not lfutil.findfile(repo, expectedhash):
             toget.append((lfile, expectedhash))
     if toget:
diff --git a/hgext/largefiles/overrides.py b/hgext/largefiles/overrides.py
--- a/hgext/largefiles/overrides.py
+++ b/hgext/largefiles/overrides.py
@@ -684,15 +684,8 @@
     return result
 def hgmerge(orig, repo, node, force=None, remind=True):
-    # Mark the repo as being in the middle of a merge, so that
-    # updatelfiles() will know that it needs to trust the standins in
-    # the working copy, not in the standins in the current node
-    repo._ismerging = True
-    try:
-        result = orig(repo, node, force, remind)
-        lfcommands.updatelfiles(repo.ui, repo)
-    finally:
-        repo._ismerging = False
+    result = orig(repo, node, force, remind)
+    lfcommands.updatelfiles(repo.ui, repo)
     return result
 # When we rebase a repository with remotely changed largefiles, we need to

More information about the Mercurial-devel mailing list