diff options
Diffstat (limited to 'lib')
-rw-r--r-- | lib/spack/spack/binary_distribution.py | 54 | ||||
-rw-r--r-- | lib/spack/spack/cmd/clean.py | 6 |
2 files changed, 25 insertions, 35 deletions
diff --git a/lib/spack/spack/binary_distribution.py b/lib/spack/spack/binary_distribution.py index c976dc80fb..165ba219b3 100644 --- a/lib/spack/spack/binary_distribution.py +++ b/lib/spack/spack/binary_distribution.py @@ -4,11 +4,9 @@ # SPDX-License-Identifier: (Apache-2.0 OR MIT) import codecs -import glob import hashlib import json import os -import re import shutil import sys import tarfile @@ -1428,42 +1426,30 @@ def extract_tarball(spec, filename, allow_root=False, unsigned=False, buildinfo = spec_dict.get('buildinfo', {}) old_relative_prefix = buildinfo.get('relative_prefix', new_relative_prefix) rel = buildinfo.get('relative_rpaths') - # if the original relative prefix and new relative prefix differ the - # directory layout has changed and the buildcache cannot be installed - # if it was created with relative rpaths info = 'old relative prefix %s\nnew relative prefix %s\nrelative rpaths %s' tty.debug(info % (old_relative_prefix, new_relative_prefix, rel)) -# if (old_relative_prefix != new_relative_prefix and (rel)): -# shutil.rmtree(tmpdir) -# msg = "Package tarball was created from an install " -# msg += "prefix with a different directory layout. " -# msg += "It cannot be relocated because it " -# msg += "uses relative rpaths." -# raise NewLayoutException(msg) - - # extract the tarball in a temp directory - with closing(tarfile.open(tarfile_path, 'r')) as tar: - tar.extractall(path=tmpdir) - # get the parent directory of the file .spack/binary_distribution - # this should the directory unpacked from the tarball whose - # name is unknown because the prefix naming is unknown - bindist_file = glob.glob('%s/*/.spack/binary_distribution' % tmpdir)[0] - workdir = re.sub('/.spack/binary_distribution$', '', bindist_file) - tty.debug('workdir %s' % workdir) - # install_tree copies hardlinks - # create a temporary tarfile from prefix and exract it to workdir - # tarfile preserves hardlinks - temp_tarfile_name = tarball_name(spec, '.tar') - temp_tarfile_path = os.path.join(tmpdir, temp_tarfile_name) - with closing(tarfile.open(temp_tarfile_path, 'w')) as tar: - tar.add(name='%s' % workdir, - arcname='.') - with closing(tarfile.open(temp_tarfile_path, 'r')) as tar: - tar.extractall(spec.prefix) - os.remove(temp_tarfile_path) - # cleanup + # Extract the tarball into the store root, presumably on the same filesystem. + # The directory created is the base directory name of the old prefix. + # Moving the old prefix name to the new prefix location should preserve + # hard links and symbolic links. + extract_tmp = os.path.join(spack.store.layout.root, '.tmp') + mkdirp(extract_tmp) + extracted_dir = os.path.join(extract_tmp, + old_relative_prefix.split(os.path.sep)[-1]) + + with closing(tarfile.open(tarfile_path, 'r')) as tar: + try: + tar.extractall(path=extract_tmp) + except Exception as e: + shutil.rmtree(extracted_dir) + raise e + try: + shutil.move(extracted_dir, spec.prefix) + except Exception as e: + shutil.rmtree(extracted_dir) + raise e os.remove(tarfile_path) os.remove(specfile_path) diff --git a/lib/spack/spack/cmd/clean.py b/lib/spack/spack/cmd/clean.py index c4012f5032..de4abd2fc2 100644 --- a/lib/spack/spack/cmd/clean.py +++ b/lib/spack/spack/cmd/clean.py @@ -76,7 +76,11 @@ def clean(parser, args): if args.stage: tty.msg('Removing all temporary build stages') spack.stage.purge() - + # Temp directory where buildcaches are extracted + extract_tmp = os.path.join(spack.store.layout.root, '.tmp') + if os.path.exists(extract_tmp): + tty.debug('Removing {0}'.format(extract_tmp)) + shutil.rmtree(extract_tmp) if args.downloads: tty.msg('Removing cached downloads') spack.caches.fetch_cache.destroy() |