user: simplify login when running with --disable_clonew_newuser by using prctl(PR_SET...
authorRobert Swiecki <robert@swiecki.net>
Sun, 1 Oct 2017 14:11:46 +0000 (16:11 +0200)
committerRobert Swiecki <robert@swiecki.net>
Sun, 1 Oct 2017 14:11:46 +0000 (16:11 +0200)
contain.c
user.c

index a511cfbdb41ebd9a6c1661b8a319b6a9044bf6f4..7b152ad35ffdeafb723c9df4dcc5a4bfe4626e2f 100644 (file)
--- a/contain.c
+++ b/contain.c
@@ -90,29 +90,6 @@ static bool containDropPrivs(struct nsjconf_t *nsjconf)
                }
        }
 
-       if (nsjconf->clone_newuser == false) {
-               LOG_D("setresgid(%d, %d, %d)", TAILQ_FIRST(&nsjconf->gids)->inside_id,
-                     TAILQ_FIRST(&nsjconf->gids)->inside_id,
-                     TAILQ_FIRST(&nsjconf->gids)->inside_id);
-               if (syscall(__NR_setresgid, TAILQ_FIRST(&nsjconf->gids)->inside_id,
-                           TAILQ_FIRST(&nsjconf->gids)->inside_id,
-                           TAILQ_FIRST(&nsjconf->gids)->inside_id)
-                   == -1) {
-                       PLOG_E("setresgid(%u)", TAILQ_FIRST(&nsjconf->gids)->inside_id);
-                       return false;
-               }
-               LOG_D("setresuid(%d, %d, %d)", TAILQ_FIRST(&nsjconf->uids)->inside_id,
-                     TAILQ_FIRST(&nsjconf->uids)->inside_id,
-                     TAILQ_FIRST(&nsjconf->uids)->inside_id);
-               if (syscall(__NR_setresuid, TAILQ_FIRST(&nsjconf->uids)->inside_id,
-                           TAILQ_FIRST(&nsjconf->uids)->inside_id,
-                           TAILQ_FIRST(&nsjconf->uids)->inside_id)
-                   == -1) {
-                       PLOG_E("setresuid(%u)", TAILQ_FIRST(&nsjconf->uids)->inside_id);
-                       return false;
-               }
-       }
-
        if (capsInitNs(nsjconf) == false) {
                return false;
        }
diff --git a/user.c b/user.c
index 067372d19cea738d345444beb108bb9b0bc922b0..e8f7016f2fd20ea45f4263d588971e65dd824cb6 100644 (file)
--- a/user.c
+++ b/user.c
 #include <errno.h>
 #include <fcntl.h>
 #include <grp.h>
+#include <linux/securebits.h>
 #include <pwd.h>
 #include <stdbool.h>
 #include <stddef.h>
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
+#include <sys/prctl.h>
 #include <sys/syscall.h>
 #include <sys/types.h>
 #include <unistd.h>
@@ -264,13 +266,11 @@ bool userInitNsFromChild(struct nsjconf_t * nsjconf)
                PLOG_D("setgroups(NULL) failed");
        }
 
-       /*
-        * If we don't use CLONE_NEWUSER, then presumably this binary has been run with euid==0, in
-        * which case we need to avoid calling setuid/setgid, in order to avoid loosing capabilities
-        * which will be needed for uname/mount/etc.-like syscalls
-        */
-       if (nsjconf->clone_newuser == false) {
-               return true;
+       /* Make sure all capabilities are retained after the subsequent setuid/setgid */
+       if (prctl(PR_SET_SECUREBITS, SECBIT_KEEP_CAPS | SECBIT_NO_SETUID_FIXUP, 0UL, 0UL, 0UL) ==
+           -1) {
+               PLOG_W("prctl(PR_SET_KEEPCAPS, 1UL)");
+               return false;
        }
 
        LOG_D("setresgid(%d, %d, %d)", TAILQ_FIRST(&nsjconf->gids)->inside_id,