summaryrefslogtreecommitdiffstats
path: root/meta/lib
diff options
context:
space:
mode:
authorRichard Purdie <richard.purdie@linuxfoundation.org>2011-02-09 13:01:23 +0000
committerRichard Purdie <rpurdie@linux.intel.com>2011-02-09 22:46:30 +0000
commit58ae42cbc386a8cd59f12527d3e47bea82d9b36f (patch)
tree7df0d8bf79ebe53ab7a8bce8a0596272d9264f41 /meta/lib
parentbb3db5106d4722ac177fcd5b2ae3d4e45d12be47 (diff)
downloadpoky-58ae42cbc386a8cd59f12527d3e47bea82d9b36f.tar.gz
lib.oe.path: Update copytree function to call shell commands since its twice as fast
As an added bonus, hardlinks between files in the tree will be preserved too. Signed-off-by: Richard Purdie <richard.purdie@linuxfoundation.org>
Diffstat (limited to 'meta/lib')
-rw-r--r--meta/lib/oe/path.py44
1 files changed, 12 insertions, 32 deletions
diff --git a/meta/lib/oe/path.py b/meta/lib/oe/path.py
index f42faeab26..da7811fac4 100644
--- a/meta/lib/oe/path.py
+++ b/meta/lib/oe/path.py
@@ -46,43 +46,23 @@ def format_display(path, metadata):
46 return rel 46 return rel
47 47
48 48
49class Error(EnvironmentError): 49class CopyFailed(Exception):
50 pass 50 pass
51 51
52# Based on shutil.copytree but with features removed and
53# No fatal error is dst already exists
54# Handle symlinks that already exist
55def copytree(src, dst): 52def copytree(src, dst):
56 names = os.listdir(src) 53 # We could use something like shutil.copytree here but it turns out to
54 # to be slow. It takes twice as long copying to an empty directory.
55 # If dst already has contents performance can be 15 time slower
56 # This way we also preserve hardlinks between files in the tree.
57 57
58 bb.mkdirhier(dst) 58 import subprocess
59 59
60 errors = [] 60 bb.mkdirhier(dst)
61 for name in names: 61 cmd = 'tar -cf - -C %s -ps . | tar -xf - -C %s' % (src, dst)
62 srcname = os.path.join(src, name) 62 ret = subprocess.call(cmd, shell=True)
63 dstname = os.path.join(dst, name) 63 if ret != 0:
64 try: 64 raise CopyFailed("Command %s failed with return value %s" % (cmd, ret))
65 if os.path.islink(srcname): 65 return
66 linkto = os.readlink(srcname)
67 if os.path.lexists(dstname):
68 os.unlink(dstname)
69 os.symlink(linkto, dstname)
70 elif os.path.isdir(srcname):
71 copytree(srcname, dstname)
72 else:
73 bb.utils.copyfile(srcname, dstname)
74 except (IOError, os.error), why:
75 errors.append((srcname, dstname, str(why)))
76 # catch the Error from the recursive copytree so that we can
77 # continue with other files
78 except Error, err:
79 errors.extend(err.args[0])
80 try:
81 shutil.copystat(src, dst)
82 except OSError, why:
83 errors.extend((src, dst, str(why)))
84 if errors:
85 raise Error, errors
86 66
87def remove(path): 67def remove(path):
88 """Equivalent to rm -f or rm -rf""" 68 """Equivalent to rm -f or rm -rf"""