summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorFrancisco Redondo Marchena <francisco.marchena@codethink.co.uk>2014-09-15 11:59:07 +0100
committerFrancisco Redondo Marchena <francisco.marchena@codethink.co.uk>2014-09-15 11:59:07 +0100
commita32de7934cce79dda2b8dc20be1c5ec94109869e (patch)
tree86de277c25b161122fc44816e35022c6cd532714
parent368ac1d818b1f06b433a4367e76c366b410468cc (diff)
parentcfbb7cd7b06a953944a16966291190b90f07cdb5 (diff)
downloadmorph-a32de7934cce79dda2b8dc20be1c5ec94109869e.tar.gz
Merge branch 'baserock/franred/bugfix/python-tarfile-chown'
Reviewed by: Richard Maw <richard.maw@codethink.co.uk> Sam Thursfield <sam.thursfield@codethink.co.uk> Merged by: Francisco Redondo Marchena <francisco.marchena@codethink.co.uk>
-rw-r--r--morphlib/bins.py47
1 files changed, 38 insertions, 9 deletions
diff --git a/morphlib/bins.py b/morphlib/bins.py
index 23e3b812..560e68bb 100644
--- a/morphlib/bins.py
+++ b/morphlib/bins.py
@@ -24,6 +24,7 @@ Binaries are chunks, strata, and system images.
import cliapp
import logging
import os
+import sys
import re
import errno
import stat
@@ -35,20 +36,48 @@ import morphlib
from morphlib.extractedtarball import ExtractedTarball
from morphlib.mountableimage import MountableImage
-
# Work around http://bugs.python.org/issue16477
-def safe_makefile(self, tarinfo, targetpath):
- '''Create a file, closing correctly in case of exception'''
+if sys.version_info < (2, 7, 4): # pragma: no cover
+ def safe_makefile(self, tarinfo, targetpath):
+ '''Create a file, closing correctly in case of exception'''
- source = self.extractfile(tarinfo)
+ source = self.extractfile(tarinfo)
+ try:
+ with open(targetpath, "wb") as target:
+ shutil.copyfileobj(source, target)
+ finally:
+ source.close()
+ tarfile.TarFile.makefile = safe_makefile
+
+# Work around http://bugs.python.org/issue12841
+if sys.version_info < (2, 7, 3): # pragma: no cover
try:
- with open(targetpath, "wb") as target:
- shutil.copyfileobj(source, target)
- finally:
- source.close()
+ import grp, pwd
+ except ImportError:
+ grp = pwd = None
-tarfile.TarFile.makefile = safe_makefile
+ def fixed_chown(self, tarinfo, targetpath):
+ '''Set owner of targetpath according to tarinfo.'''
+ if pwd and hasattr(os, "geteuid") and os.geteuid() == 0:
+ # We have to be root to do so.
+ try:
+ g = grp.getgrnam(tarinfo.gname)[2]
+ except KeyError:
+ g = tarinfo.gid
+ try:
+ u = pwd.getpwnam(tarinfo.uname)[2]
+ except KeyError:
+ u = tarinfo.uid
+ try:
+ if tarinfo.issym() and hasattr(os, "lchown"):
+ os.lchown(targetpath, u, g)
+ else:
+ if sys.platform != "os2emx":
+ os.chown(targetpath, u, g)
+ except EnvironmentError, e:
+ raise ExtractError("could not change owner")
+ tarfile.TarFile.chown = fixed_chown
def create_chunk(rootdir, f, include, dump_memory_profile=None):
'''Create a chunk from the contents of a directory.