plugin: Fix uid and gid maps

When minijail is given a uid/gid map but is not given a uid/gid to
change to, it will default to setting the uid/gid inside the new user
namespace to root.  This works fine if crosvm is launched as root but
fails miserably otherwise since we only map the current euid/egid into
the user namespace (and so 0 is not a valid uid/gid).

We would normally want to fix this by having minijail change its uid/gid
to the current euid/egid.  However, because of the way minijail is set
up it only attempts to enter a new net namespace after exec-ing the
program to be jailed.  Entering a new net namespace requires
CAP_SYS_ADMIN in the current namespace and this capability gets dropped
the moment we switch to a non-root user.

So to deal with this we map root inside the namespace to the crosvm user
outside the namespace.  This allows us to enter a new net namespace and
we already tell minijail to drop all caps so the plugin will not have
any caps when it actually runs.

BUG=b:80150167
TEST=run plugin_adder

Change-Id: I10c9e6bef859fd787dd6e17d5cf2ff3e552501fb
Signed-off-by: Chirantan Ekbote <chirantan@chromium.org>
Reviewed-on: https://chromium-review.googlesource.com/1341103
Commit-Ready: ChromeOS CL Exonerator Bot <chromiumos-cl-exonerator@appspot.gserviceaccount.com>
Reviewed-by: Dylan Reid <dgreid@chromium.org>
This commit is contained in:
Chirantan Ekbote 2018-11-16 11:40:44 -08:00 committed by chrome-bot
parent 1502a11ed0
commit 7a97366e96

View file

@ -222,9 +222,9 @@ fn create_plugin_jail(root: &Path, seccomp_policy: &Path) -> Result<Minijail> {
let mut j = Minijail::new().map_err(Error::CreateJail)?;
j.namespace_pids();
j.namespace_user();
j.uidmap(&format!("{0} {0} 1", geteuid()))
j.uidmap(&format!("0 {0} 1", geteuid()))
.map_err(Error::SetUidMap)?;
j.gidmap(&format!("{0} {0} 1", getegid()))
j.gidmap(&format!("0 {0} 1", getegid()))
.map_err(Error::SetGidMap)?;
j.namespace_user_disable_setgroups();
// Don't need any capabilities.