summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSam Thursfield <sam.thursfield@codethink.co.uk>2015-06-01 11:46:11 +0000
committerSam Thursfield <sam.thursfield@codethink.co.uk>2015-06-01 13:31:57 +0000
commit4210307bf8776953d9a1d54e2f5ebd4de2c78737 (patch)
tree72301aa0bc613611f7cbcac4610ad14c6efff6ab
parentef24fd8a8f87720f8ef400d904cbb4417acc585b (diff)
downloadsandboxlib-4210307bf8776953d9a1d54e2f5ebd4de2c78737.tar.gz
Fix creating missing mountpoints in linux-user-chroot backend, update docs
Creating missing mountpoints is done later now, so that there's less chance of them being created if bad sandbox configuration was passed. The previous code didn't seem work correctly, probably because of Python os.path.join() having the annoying behaviour of deleting all previous path components if it finds one with a preceeding '/'.
-rw-r--r--sandboxlib/__init__.py8
-rw-r--r--sandboxlib/linux_user_chroot.py20
2 files changed, 21 insertions, 7 deletions
diff --git a/sandboxlib/__init__.py b/sandboxlib/__init__.py
index b4199f1..946ba52 100644
--- a/sandboxlib/__init__.py
+++ b/sandboxlib/__init__.py
@@ -96,8 +96,12 @@ def run_sandbox(command, cwd=None, env=None,
- mounts: configures mount sharing. Defaults to 'undefined', where no
no attempt is made to isolate mounts. Backends may support
'isolated' as well.
- - extra_mounts: a list of locations to mount inside 'rootfs_path', with
- type and options specified in a backend-specific way.
+ - extra_mounts: a list of locations to mount inside 'rootfs_path',
+ specified as a list of tuples of (source_path, target_path, type,
+ options). The 'type' and 'options' should match what would be
+ specified in /etc/fstab, but a backends may support only a limited
+ subset of values. The 'target_path' is relative to filesystem_root
+ and will be created before mounting if it doesn't exist.
- network: configures network sharing. Defaults to 'undefined', where
no attempt is made to either prevent or provide networking
inside the sandbox. Backends may support 'isolated' and/or other
diff --git a/sandboxlib/linux_user_chroot.py b/sandboxlib/linux_user_chroot.py
index cca734f..c397d8f 100644
--- a/sandboxlib/linux_user_chroot.py
+++ b/sandboxlib/linux_user_chroot.py
@@ -65,8 +65,6 @@ def process_mount_config(root, mounts, extra_mounts):
"'linux-user-chroot' backend. Supported values: %s" \
% (mounts, ', '.join(supported_values))
- extra_mounts = sandboxlib.validate_extra_mounts(extra_mounts)
-
# Use 'unshare' to create a new mount namespace.
#
# In order to mount the things specified in 'extra_mounts' inside the
@@ -117,9 +115,6 @@ def process_mount_config(root, mounts, extra_mounts):
''')
for source, mount_point, mount_type, mount_options in extra_mounts:
- path = os.path.join(root, mount_point)
- if not os.path.exists(path):
- os.makedirs(path)
mount_script_args.extend((mount_point, mount_type, source,
mount_options))
mount_script_args.append('--')
@@ -259,6 +254,17 @@ def process_writable_paths(fs_root, writable_paths):
return extra_linux_user_chroot_args
+def create_mount_points_if_missing(filesystem_root, mount_info_list):
+ for source, mount_point, mount_type, mount_options in mount_info_list:
+ # Strip the preceeding '/' from mount_point, because it'll break
+ # os.path.join().
+ mount_point_no_slash = os.path.relpath(mount_point, start='/')
+
+ path = os.path.join(filesystem_root, mount_point_no_slash)
+ if not os.path.exists(path):
+ os.makedirs(path)
+
+
def run_sandbox(command, cwd=None, env=None,
filesystem_root='/', filesystem_writable_paths='all',
mounts='undefined', extra_mounts=None,
@@ -269,6 +275,8 @@ def run_sandbox(command, cwd=None, env=None,
linux_user_chroot_command = ['linux-user-chroot']
+ extra_mounts = sandboxlib.validate_extra_mounts(extra_mounts)
+
unshare_command = process_mount_config(
root=filesystem_root, mounts=mounts, extra_mounts=extra_mounts or [])
@@ -282,6 +290,8 @@ def run_sandbox(command, cwd=None, env=None,
linux_user_chroot_command.append(filesystem_root)
+ create_mount_points_if_missing(filesystem_root, extra_mounts)
+
argv = (unshare_command + linux_user_chroot_command + command)
exit, out, err = sandboxlib._run_command(argv, stdout, stderr, env=env)
return exit, out, err