]> git.ipfire.org Git - thirdparty/util-linux.git/commitdiff
nsenter: add -Z to set selinux context
authorKarel Zak <kzak@redhat.com>
Fri, 20 Mar 2015 14:26:58 +0000 (15:26 +0100)
committerKarel Zak <kzak@redhat.com>
Fri, 20 Mar 2015 14:39:38 +0000 (15:39 +0100)
The new context is copied from --target <PID>. This solution allows to
keep SELinux happy when you enter container by nsenter(1).

Addresses: https://bugzilla.redhat.com/show_bug.cgi?id=1116100
Signed-off-by: Karel Zak <kzak@redhat.com>
sys-utils/Makemodule.am
sys-utils/nsenter.1
sys-utils/nsenter.c

index c1d587af1f01a62a5ceddd200e795c7ce2840d56..d538cdad716b7dca750c9166cd46ea2d7b6d368f 100644 (file)
@@ -358,7 +358,7 @@ if BUILD_NSENTER
 usrbin_exec_PROGRAMS += nsenter
 dist_man_MANS += sys-utils/nsenter.1
 nsenter_SOURCES = sys-utils/nsenter.c
-nsenter_LDADD = $(LDADD) libcommon.la
+nsenter_LDADD = $(LDADD) libcommon.la $(SELINUX_LIBS)
 
 if HAVE_STATIC_NSENTER
 usrbin_exec_PROGRAMS += nsenter.static
index 8a3b25eccb5230817ac5e964ab4287c415b38d90..79fc2e5c6fd3dbbdec41ecfcfa9b05129c965579 100644 (file)
@@ -155,6 +155,11 @@ Do not fork before exec'ing the specified program.  By default, when entering a
 PID namespace, \fBnsenter\fP calls \fBfork\fP before calling \fBexec\fP so that
 any children will also be in the newly entered PID namespace.
 .TP
+\fB\-Z\fR, \fB\-\-follow\-context\fR
+Set the SELinux security context used for executing a new process according to
+already running process specified by \fB\-\-target\fR PID. (The util-linux has
+to be compiled with SELinux support otherwise the option is unavailable.)
+.TP
 \fB\-V\fR, \fB\-\-version\fR
 Display version information and exit.
 .TP
@@ -163,10 +168,14 @@ Display help text and exit.
 .SH SEE ALSO
 .BR setns (2),
 .BR clone (2)
-.SH AUTHOR
-.MT ebiederm@xmission.com
+.SH AUTHORS
+.UR biederm@xmission.com
 Eric Biederman
-.ME
+.UE
+.br
+.UR kzak@redhat.com
+Karel Zak
+.UE
 .SH AVAILABILITY
 The nsenter command is part of the util-linux package and is available from
 .UR ftp://\:ftp.kernel.org\:/pub\:/linux\:/utils\:/util-linux/
index b029f80879971b567794497533d3e9501da635cf..37157258019331703fdc8f34325fda45102d33db 100644 (file)
 #include <sys/wait.h>
 #include <grp.h>
 
+#ifdef HAVE_LIBSELINUX
+# include <selinux/selinux.h>
+#endif
+
 #include "strutils.h"
 #include "nls.h"
 #include "c.h"
@@ -82,6 +86,9 @@ static void usage(int status)
        fputs(_(" -r, --root[=<dir>]     set the root directory\n"), out);
        fputs(_(" -w, --wd[=<dir>]       set the working directory\n"), out);
        fputs(_(" -F, --no-fork          do not fork before exec'ing <program>\n"), out);
+#ifdef HAVE_LIBSELINUX
+       fputs(_(" -Z, --follow-context   set SELinux context according to --target PID\n"), out);
+#endif
 
        fputs(USAGE_SEPARATOR, out);
        fputs(USAGE_HELP, out);
@@ -185,6 +192,9 @@ int main(int argc, char *argv[])
                { "wd", optional_argument, NULL, 'w' },
                { "no-fork", no_argument, NULL, 'F' },
                { "preserve-credentials", no_argument, NULL, OPT_PRESERVE_CRED },
+#ifdef HAVE_LIBSELINUX
+               { "follow-context", no_argument, NULL, 'Z' },
+#endif
                { NULL, 0, NULL, 0 }
        };
 
@@ -194,6 +204,9 @@ int main(int argc, char *argv[])
        int do_fork = -1; /* unknown yet */
        uid_t uid = 0;
        gid_t gid = 0;
+#ifdef HAVE_LIBSELINUX
+       bool selinux = 0;
+#endif
 
        setlocale(LC_ALL, "");
        bindtextdomain(PACKAGE, LOCALEDIR);
@@ -201,7 +214,7 @@ int main(int argc, char *argv[])
        atexit(close_stdout);
 
        while ((c =
-               getopt_long(argc, argv, "+hVt:m::u::i::n::p::U::S:G:r::w::F",
+               getopt_long(argc, argv, "+hVt:m::u::i::n::p::U::S:G:r::w::FZ",
                            longopts, NULL)) != -1) {
                switch (c) {
                case 'h':
@@ -275,11 +288,30 @@ int main(int argc, char *argv[])
                case OPT_PRESERVE_CRED:
                        preserve_cred = 1;
                        break;
+#ifdef HAVE_LIBSELINUX
+               case 'Z':
+                       selinux = 1;
+                       break;
+#endif
                default:
                        usage(EXIT_FAILURE);
                }
        }
 
+#ifdef HAVE_LIBSELINUX
+       if (selinux && is_selinux_enabled() > 0) {
+               char *scon = NULL;
+
+               if (!namespace_target_pid)
+                       errx(EXIT_FAILURE, _("no target PID specified for --follow-context"));
+               if (getpidcon(namespace_target_pid, &scon) < 0)
+                       errx(EXIT_FAILURE, _("failed to get %d SELinux context"),
+                                       (int) namespace_target_pid);
+               if (setexeccon(scon) < 0)
+                       errx(EXIT_FAILURE, _("failed to set exec context to '%s'"), scon);
+               freecon(scon);
+       }
+#endif
        /*
         * Open remaining namespace and directory descriptors.
         */