From 09af33ec1a4cb29602272277887862d95e66bd59 Mon Sep 17 00:00:00 2001 From: "Bryn M. Reeves" Date: Mon, 30 Jun 2014 18:26:08 +0100 Subject: [PATCH] [plugintools] preserve permissions on all path components When a path is added to the archive via addCopySpec() we copy the content itself with shutil.copy2() which propagates permissions from the source to the destination. This ignores any directory components in the path leading up to the item to be copied. For e.g.: self.addCopySpec("/foo/bar/baz/qux") Will collect the file 'qux' and preserve its permissions vai a shutil.copy2() call but '/foo/bar/baz' will be created via an os.makedirs() call (receiving whatever permissions the current umask allows). Fix this by replacing the call to os.makedirs() with a call to Plugin.__copydirs() which will walk the path from root down to the final containing directory calling makedirs() and copystat() as appropriate to copy permissions for the entire path. --- sos/plugintools.py | 15 ++++++++++++++- 1 file changed, 14 insertions(+), 1 deletion(-) diff --git a/sos/plugintools.py b/sos/plugintools.py index 1034ac3..6b02fa5 100644 --- a/sos/plugintools.py +++ b/sos/plugintools.py @@ -274,6 +274,19 @@ class PluginBase: return abspath + # Permission-copying version of makedirs(). For each component in a path + # ensure that the corresponding directory in dstroot exists and copy the + # permissions over from the host file system. + def __copydirs(self, src_dir, dst_root): + pathcomps = src_dir.split(os.path.sep) + path = "" + for comp in pathcomps: + path = os.path.join(path, comp) + dst_path = os.path.join(dst_root, path) + if not os.path.exists(dst_path): + os.makedirs(dst_path) + shutil.copystat(os.path.join('/', path), dst_path) + def __copyFile(self, src): """ call cp to copy a file, collect return status and output. Returns the destination file name. @@ -284,7 +297,7 @@ class PluginBase: if not os.path.exists(new_fname): if not os.path.isdir(new_dir): - os.makedirs(new_dir) + self.__copydirs(os.path.dirname(src), self.cInfo['dstroot']) if os.path.islink(src): linkto = os.readlink(src) -- 1.9.3