summaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
authorGreg Becker <becker33@llnl.gov>2019-05-10 16:38:13 +0900
committerTodd Gamblin <tgamblin@llnl.gov>2019-05-10 00:38:13 -0700
commitf67a59fabc1b2e3c4f5613a7bf10c619ca59095e (patch)
tree0d2692f99cb3826ce755143d90f9e03ec62f2764 /lib
parentc752af098d6f70005b5bf178bb49d5cb1f709f85 (diff)
downloadspack-f67a59fabc1b2e3c4f5613a7bf10c619ca59095e.tar.gz
spack-f67a59fabc1b2e3c4f5613a7bf10c619ca59095e.tar.bz2
spack-f67a59fabc1b2e3c4f5613a7bf10c619ca59095e.tar.xz
spack-f67a59fabc1b2e3c4f5613a7bf10c619ca59095e.zip
permissions: preserve suid and sgid bits (#10727)
* Don't overwrite suid/sgid bits when setting permissions * add tests for permission setting
Diffstat (limited to 'lib')
-rw-r--r--lib/spack/spack/hooks/permissions_setters.py11
-rw-r--r--lib/spack/spack/test/permissions.py35
2 files changed, 46 insertions, 0 deletions
diff --git a/lib/spack/spack/hooks/permissions_setters.py b/lib/spack/spack/hooks/permissions_setters.py
index 631118ffac..9ada697ad8 100644
--- a/lib/spack/spack/hooks/permissions_setters.py
+++ b/lib/spack/spack/hooks/permissions_setters.py
@@ -4,11 +4,13 @@
# SPDX-License-Identifier: (Apache-2.0 OR MIT)
import os
+import stat
from llnl.util.filesystem import chmod_x, chgrp
from spack.package_prefs import get_package_permissions, get_package_group
from spack.package_prefs import get_package_dir_permissions
+from spack.error import SpackError
def forall_files(path, fn, args, dir_args=None):
@@ -31,6 +33,11 @@ def forall_files(path, fn, args, dir_args=None):
def chmod_real_entries(path, perms):
# Don't follow links so we don't change things outside the prefix
if not os.path.islink(path):
+ mode = os.stat(path).st_mode
+ perms |= mode & (stat.S_ISUID | stat.S_ISGID | stat.S_ISVTX)
+ if perms & stat.S_ISUID and perms & stat.S_IWGRP:
+ raise InvalidPermissionsError(
+ 'Attempting to set suid with world writable')
chmod_x(path, perms)
@@ -44,3 +51,7 @@ def post_install(spec):
if group:
forall_files(spec.prefix, chgrp, [group])
+
+
+class InvalidPermissionsError(SpackError):
+ """Error class for invalid permission setters"""
diff --git a/lib/spack/spack/test/permissions.py b/lib/spack/spack/test/permissions.py
new file mode 100644
index 0000000000..223b3e8319
--- /dev/null
+++ b/lib/spack/spack/test/permissions.py
@@ -0,0 +1,35 @@
+# Copyright 2013-2019 Lawrence Livermore National Security, LLC and other
+# Spack Project Developers. See the top-level COPYRIGHT file for details.
+#
+# SPDX-License-Identifier: (Apache-2.0 OR MIT)
+
+import os
+import pytest
+import stat
+
+from spack.hooks.permissions_setters import (
+ chmod_real_entries, InvalidPermissionsError
+)
+import llnl.util.filesystem as fs
+
+
+def test_chmod_real_entries_ignores_suid_sgid(tmpdir):
+ path = str(tmpdir.join('file').ensure())
+ mode = stat.S_ISUID | stat.S_ISGID | stat.S_ISVTX
+ os.chmod(path, mode)
+ mode = os.stat(path).st_mode # adds a high bit we aren't concerned with
+
+ perms = stat.S_IRWXU
+ chmod_real_entries(path, perms)
+
+ assert os.stat(path).st_mode == mode | perms & ~stat.S_IXUSR
+
+
+def test_chmod_rejects_group_writable_suid(tmpdir):
+ path = str(tmpdir.join('file').ensure())
+ mode = stat.S_ISUID | stat.S_ISGID | stat.S_ISVTX
+ fs.chmod_x(path, mode)
+
+ perms = stat.S_IRWXU | stat.S_IRWXG | stat.S_IRWXO
+ with pytest.raises(InvalidPermissionsError):
+ chmod_real_entries(path, perms)