annotate tests/test-merge1 @ 1241:3b4f05ff3130

Add support for cloning with hardlinks on windows. In order to use hardlinks, the win32file module is needed, and this is present in ActivePython. If it isn't present, or hardlinks are not supported on the underlying filesystem, a regular copy is used. When using hardlinks the biggest benefit is probably the saving in space, but cloning can be much quicker. For example cloning the Xen tree (non trivial) without an update goes from about 95s to 15s. Unix-like platforms should be unaffected, although should be more tolerant on filesystems that don't support hard links. (tweaked by mpm to deal with new copyfiles function) --- hg.orig/mercurial/commands.py 2005-09-13 19:32:53.000000000 -0500 +++ hg/mercurial/commands.py 2005-09-14 12:11:34.000000000 -0500 @@ -620,10 +620,6 @@ def clone(ui, source, dest=None, **opts) if other.dev() != -1: abspath = os.path.abspath(source) - copyfile = (os.stat(dest).st_dev == other.dev() - and getattr(os, 'link', None) or shutil.copy2) - if copyfile is not shutil.copy2: - ui.note("cloning by hardlink\n") # we use a lock here because if we race with commit, we can # end up with extra data in the cloned revlogs that's not @@ -638,7 +634,7 @@ def clone(ui, source, dest=None, **opts) for f in files.split(): src = os.path.join(source, ".hg", f) dst = os.path.join(dest, ".hg", f) - util.copyfiles(src, dst, copyfile) + util.copyfiles(src, dst) repo = hg.repository(ui, dest) Index: hg/mercurial/util.py =================================================================== --- hg.orig/mercurial/util.py 2005-09-08 00:15:25.000000000 -0500 +++ hg/mercurial/util.py 2005-09-14 12:16:49.000000000 -0500 @@ -12,7 +12,7 @@ platform-specific details from the core. import os, errno from demandload import * -demandload(globals(), "re cStringIO") +demandload(globals(), "re cStringIO shutil") def binary(s): """return true if a string is binary data using diff's heuristic""" @@ -217,17 +217,28 @@ def rename(src, dst): os.unlink(dst) os.rename(src, dst) -def copyfiles(src, dst, copyfile): - """Copy a directory tree, files are copied using 'copyfile'.""" +def copyfiles(src, dst, hardlink=None): + """Copy a directory tree using hardlinks if possible""" + + if hardlink is None: + hardlink = (os.stat(src).st_dev == + os.stat(os.path.dirname(dst)).st_dev) if os.path.isdir(src): os.mkdir(dst) for name in os.listdir(src): srcname = os.path.join(src, name) dstname = os.path.join(dst, name) - copyfiles(srcname, dstname, copyfile) + copyfiles(srcname, dstname, hardlink) else: - copyfile(src, dst) + if hardlink: + try: + os_link(src, dst) + except: + hardlink = False + shutil.copy2(src, dst) + else: + shutil.copy2(src, dst) def opener(base): """ @@ -244,13 +255,13 @@ def opener(base): if mode[0] != "r": try: - s = os.stat(f) + nlink = nlinks(f) except OSError: d = os.path.dirname(f) if not os.path.isdir(d): os.makedirs(d) else: - if s.st_nlink > 1: + if nlink > 1: file(f + ".tmp", "wb").write(file(f, "rb").read()) rename(f+".tmp", f) @@ -266,10 +277,41 @@ def _makelock_file(info, pathname): def _readlock_file(pathname): return file(pathname).read() +def nlinks(pathname): + """Return number of hardlinks for the given file.""" + return os.stat(pathname).st_nlink + +if hasattr(os, 'link'): + os_link = os.link +else: + def os_link(src, dst): + raise OSError(0, "Hardlinks not supported") + # Platform specific variants if os.name == 'nt': nulldev = 'NUL:' + try: # ActivePython can create hard links using win32file module + import win32file + + def os_link(src, dst): # NB will only succeed on NTFS + win32file.CreateHardLink(dst, src) + + def nlinks(pathname): + """Return number of hardlinks for the given file.""" + try: + fh = win32file.CreateFile(pathname, + win32file.GENERIC_READ, win32file.FILE_SHARE_READ, + None, win32file.OPEN_EXISTING, 0, None) + res = win32file.GetFileInformationByHandle(fh) + fh.Close() + return res[7] + except: + return os.stat(pathname).st_nlink + + except ImportError: + pass + def is_exec(f, last): return last
author Stephen Darnell
date Wed, 14 Sep 2005 12:22:20 -0500
parents 67a28636ea64
children db10b7114de0
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
800
ec85f9e6f3b1 Don't use 'set -x', fix exports, sed and hexdump usage for Solaris.
Thomas Arendsen Hein <thomas@intevation.de>
parents: 749
diff changeset
1 #!/bin/sh
407
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
2
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
3 cat <<'EOF' > merge
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
4 #!/bin/sh
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
5 echo merging for `basename $1`
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
6 EOF
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
7 chmod +x merge
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
8
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
9 mkdir t
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
10 cd t
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
11 hg init
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
12 echo This is file a1 > a
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
13 hg add a
749
7e4843b7efd2 Update tests to use commit -m and default -u
mpm@selenic.com
parents: 430
diff changeset
14 hg commit -m "commit #0" -d "0 0"
407
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
15 echo This is file b1 > b
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
16 hg add b
749
7e4843b7efd2 Update tests to use commit -m and default -u
mpm@selenic.com
parents: 430
diff changeset
17 hg commit -m "commit #1" -d "0 0"
407
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
18
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
19 hg update 0
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
20 echo This is file c1 > c
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
21 hg add c
749
7e4843b7efd2 Update tests to use commit -m and default -u
mpm@selenic.com
parents: 430
diff changeset
22 hg commit -m "commit #2" -d "0 0"
407
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
23 echo This is file b1 > b
1236
67a28636ea64 Fix bug with co -C across branches, update tests
mpm@selenic.com
parents: 814
diff changeset
24 echo %% no merges expected
407
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
25 env HGMERGE=../merge hg update -m 1
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
26 cd ..; /bin/rm -rf t
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
27
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
28 mkdir t
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
29 cd t
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
30 hg init
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
31 echo This is file a1 > a
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
32 hg add a
749
7e4843b7efd2 Update tests to use commit -m and default -u
mpm@selenic.com
parents: 430
diff changeset
33 hg commit -m "commit #0" -d "0 0"
407
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
34 echo This is file b1 > b
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
35 hg add b
749
7e4843b7efd2 Update tests to use commit -m and default -u
mpm@selenic.com
parents: 430
diff changeset
36 hg commit -m "commit #1" -d "0 0"
407
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
37
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
38 hg update 0
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
39 echo This is file c1 > c
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
40 hg add c
749
7e4843b7efd2 Update tests to use commit -m and default -u
mpm@selenic.com
parents: 430
diff changeset
41 hg commit -m "commit #2" -d "0 0"
407
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
42 echo This is file b2 > b
1236
67a28636ea64 Fix bug with co -C across branches, update tests
mpm@selenic.com
parents: 814
diff changeset
43 echo %% merge of b expected
407
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
44 env HGMERGE=../merge hg update -m 1
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
45 cd ..; /bin/rm -rf t
1236
67a28636ea64 Fix bug with co -C across branches, update tests
mpm@selenic.com
parents: 814
diff changeset
46 echo %%
407
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
47
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
48 mkdir t
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
49 cd t
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
50 hg init
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
51 echo This is file a1 > a
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
52 hg add a
749
7e4843b7efd2 Update tests to use commit -m and default -u
mpm@selenic.com
parents: 430
diff changeset
53 hg commit -m "commit #0" -d "0 0"
407
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
54 echo This is file b1 > b
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
55 hg add b
749
7e4843b7efd2 Update tests to use commit -m and default -u
mpm@selenic.com
parents: 430
diff changeset
56 hg commit -m "commit #1" -d "0 0"
407
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
57 echo This is file b22 > b
749
7e4843b7efd2 Update tests to use commit -m and default -u
mpm@selenic.com
parents: 430
diff changeset
58 hg commit -m "commit #2" -d "0 0"
407
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
59 hg update 1
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
60 echo This is file c1 > c
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
61 hg add c
749
7e4843b7efd2 Update tests to use commit -m and default -u
mpm@selenic.com
parents: 430
diff changeset
62 hg commit -m "commit #3" -d "0 0"
1236
67a28636ea64 Fix bug with co -C across branches, update tests
mpm@selenic.com
parents: 814
diff changeset
63
67a28636ea64 Fix bug with co -C across branches, update tests
mpm@selenic.com
parents: 814
diff changeset
64 echo 'Contents of b should be "this is file b1"'
430
5b22029b5aa2 Fix up test-merge1
mpm@selenic.com
parents: 407
diff changeset
65 cat b
1236
67a28636ea64 Fix bug with co -C across branches, update tests
mpm@selenic.com
parents: 814
diff changeset
66
407
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
67 echo This is file b22 > b
1236
67a28636ea64 Fix bug with co -C across branches, update tests
mpm@selenic.com
parents: 814
diff changeset
68 echo %% merge expected!
407
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
69 env HGMERGE=../merge hg update -m 2
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
70 cd ..; /bin/rm -rf t
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
71
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
72 mkdir t
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
73 cd t
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
74 hg init
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
75 echo This is file a1 > a
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
76 hg add a
749
7e4843b7efd2 Update tests to use commit -m and default -u
mpm@selenic.com
parents: 430
diff changeset
77 hg commit -m "commit #0" -d "0 0"
407
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
78 echo This is file b1 > b
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
79 hg add b
749
7e4843b7efd2 Update tests to use commit -m and default -u
mpm@selenic.com
parents: 430
diff changeset
80 hg commit -m "commit #1" -d "0 0"
407
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
81 echo This is file b22 > b
749
7e4843b7efd2 Update tests to use commit -m and default -u
mpm@selenic.com
parents: 430
diff changeset
82 hg commit -m "commit #2" -d "0 0"
407
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
83 hg update 1
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
84 echo This is file c1 > c
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
85 hg add c
749
7e4843b7efd2 Update tests to use commit -m and default -u
mpm@selenic.com
parents: 430
diff changeset
86 hg commit -m "commit #3" -d "0 0"
407
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
87 echo This is file b33 > b
1236
67a28636ea64 Fix bug with co -C across branches, update tests
mpm@selenic.com
parents: 814
diff changeset
88 echo %% merge of b expected
407
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
89 env HGMERGE=../merge hg update -m 2
0e0d0670b2bc [PATCH] Merging identical changes from another branch
mpm@selenic.com
parents:
diff changeset
90 cd ..; /bin/rm -rf t