Permalink
Browse files

Add support for classic confinement

This patch adds support for classic confinement in snap-confine.  The
main idea is that whenever --classic command line option is given the
mount namespace is not unshared. The application executes in the same
mount namespace as all classic applications would. While not strictly
related to the mount namespace, the devices cgroup is not used and PATH
is not reset.

On the snapd side the application will receive different apparmor and
seccomp profiles. The apprmor profile is wide open and the seccomp
profile uses the special "@unrestricted" command to essentially switch
apparmor off entirely.

NOTE: Using classic confinement is incompatible with nvidia driver
sharing as we cannot bind mount anything into /var/lib/snapd/lib/gl but
at the same time the application can just look at /usr/lib/nvidia for
that.

Signed-off-by: Zygmunt Krynicki <zygmunt.krynicki@canonical.com>
  • Loading branch information...
1 parent 889c8f4 commit 43f5041deb8ed061f8a38f4342a5c3065b8ec3cf @zyga zyga committed Dec 2, 2016
Showing with 29 additions and 26 deletions.
  1. +29 −26 src/snap-confine.c
View
@@ -82,33 +82,36 @@ int main(int argc, char **argv)
#endif // ifdef HAVE_SECCOMP
if (geteuid() == 0) {
- const char *group_name = getenv("SNAP_NAME");
- if (group_name == NULL) {
- die("SNAP_NAME is not set");
+ if (sc_args_is_classic_confinement(args) == false) {
@jdstrand

jdstrand Dec 2, 2016

Contributor

LGTM but please add a code comment. Ie:

/* 'classic confinement' is designed to run without the sandbox inside
 * the shared namespace. Specifically:
 * - snap-confine skips using the snap-specific mount namespace
 * - snap-confine skips using device cgroups
 * - snapd sets up a lenient AppArmor profile for snap-confine to use
 * - snapd sets up a lenient seccomp profile for snap-confine to use
 */

Feel free to wordsmith that as desired. This should also be documented in README.md.

+ const char *group_name = getenv("SNAP_NAME");
+ if (group_name == NULL) {
+ die("SNAP_NAME is not set");
+ }
+ sc_initialize_ns_groups();
+ struct sc_ns_group *group = NULL;
+ group = sc_open_ns_group(group_name, 0);
+ sc_lock_ns_mutex(group);
+ sc_create_or_join_ns_group(group, &apparmor);
+ if (sc_should_populate_ns_group(group)) {
+ sc_populate_mount_ns(security_tag);
+ sc_preserve_populated_ns_group(group);
+ }
+ sc_unlock_ns_mutex(group);
+ sc_close_ns_group(group);
+ // Reset path as we cannot rely on the path from the host OS to
+ // make sense. The classic distribution may use any PATH that makes
+ // sense but we cannot assume it makes sense for the core snap
+ // layout. Note that the /usr/local directories are explicitly
+ // left out as they are not part of the core snap.
+ debug
+ ("resetting PATH to values in sync with core snap");
+ setenv("PATH",
+ "/usr/sbin:/usr/bin:/sbin:/bin:/usr/games", 1);
+ struct snappy_udev udev_s;
+ if (snappy_udev_init(security_tag, &udev_s) == 0)
+ setup_devices_cgroup(security_tag, &udev_s);
+ snappy_udev_cleanup(&udev_s);
}
- sc_initialize_ns_groups();
- struct sc_ns_group *group = NULL;
- group = sc_open_ns_group(group_name, 0);
- sc_lock_ns_mutex(group);
- sc_create_or_join_ns_group(group, &apparmor);
- if (sc_should_populate_ns_group(group)) {
- sc_populate_mount_ns(security_tag);
- sc_preserve_populated_ns_group(group);
- }
- sc_unlock_ns_mutex(group);
- sc_close_ns_group(group);
- // Reset path as we cannot rely on the path from the host OS to
- // make sense. The classic distribution may use any PATH that makes
- // sense but we cannot assume it makes sense for the core snap
- // layout. Note that the /usr/local directories are explicitly
- // left out as they are not part of the core snap.
- debug("resetting PATH to values in sync with core snap");
- setenv("PATH", "/usr/sbin:/usr/bin:/sbin:/bin:/usr/games", 1);
- struct snappy_udev udev_s;
- if (snappy_udev_init(security_tag, &udev_s) == 0)
- setup_devices_cgroup(security_tag, &udev_s);
- snappy_udev_cleanup(&udev_s);
-
// The rest does not so temporarily drop privs back to calling
// user (we'll permanently drop after loading seccomp)
if (setegid(real_gid) != 0)

0 comments on commit 43f5041

Please sign in to comment.