/*
 * setpriv(1) - set various kernel privilege bits and run something
 *
 * Copyright (C) 2012 Andy Lutomirski <luto@amacapital.net>
 *
 * This program is free software; you can redistribute it and/or modify it
 * under the terms of the GNU General Public License as published by the
 * Free Software Foundation; either version 2, or (at your option) any
 * later version.
 *
 * This program is distributed in the hope that it will be useful, but
 * WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License along
 * with this program; if not, write to the Free Software Foundation, Inc.,
 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
 */

#include <cap-ng.h>
#include <errno.h>
#include <getopt.h>
#include <grp.h>
#include <linux/securebits.h>
#include <pwd.h>
#include <stdarg.h>
#include <stdio.h>
#include <stdlib.h>
#include <sys/prctl.h>
#include <sys/types.h>
#include <unistd.h>

#include "c.h"
#include "closestream.h"
#include "nls.h"
#include "optutils.h"
#include "strutils.h"
#include "xalloc.h"
#include "pathnames.h"
#include "signames.h"

#ifndef PR_SET_NO_NEW_PRIVS
# define PR_SET_NO_NEW_PRIVS 38
#endif
#ifndef PR_GET_NO_NEW_PRIVS
# define PR_GET_NO_NEW_PRIVS 39
#endif

#ifndef PR_CAP_AMBIENT
# define PR_CAP_AMBIENT		47
#  define PR_CAP_AMBIENT_IS_SET	1
#  define PR_CAP_AMBIENT_RAISE	2
#  define PR_CAP_AMBIENT_LOWER	3
#endif

#define SETPRIV_EXIT_PRIVERR 127	/* how we exit when we fail to set privs */

enum cap_type {
	CAP_TYPE_EFFECTIVE   = CAPNG_EFFECTIVE,
	CAP_TYPE_PERMITTED   = CAPNG_PERMITTED,
	CAP_TYPE_INHERITABLE = CAPNG_INHERITABLE,
	CAP_TYPE_BOUNDING    = CAPNG_BOUNDING_SET,
	CAP_TYPE_AMBIENT     = (1 << 4)
};

/*
 * Note: We are subject to https://bugzilla.redhat.com/show_bug.cgi?id=895105
 * and we will therefore have problems if new capabilities are added.  Once
 * that bug is fixed, I'll (Andy Lutomirski) submit a corresponding fix to
 * setpriv.  In the mean time, the code here tries to work reasonably well.
 */

struct privctx {
	unsigned int
		nnp:1,			/* no_new_privs */
		have_ruid:1,		/* real uid */
		have_euid:1,		/* effective uid */
		have_rgid:1,		/* real gid */
		have_egid:1,		/* effective gid */
		have_passwd:1,		/* passwd entry */
		have_groups:1,		/* add groups */
		keep_groups:1,		/* keep groups */
		clear_groups:1,		/* remove groups */
		init_groups:1,		/* initialize groups */
		have_securebits:1;	/* remove groups */

	/* uids and gids */
	uid_t ruid, euid;
	gid_t rgid, egid;

	/* real user passwd entry */
	struct passwd passwd;

	/* supplementary groups */
	size_t num_groups;
	gid_t *groups;

	/* caps */
	const char *caps_to_inherit;
	const char *ambient_caps;
	const char *bounding_set;

	/* securebits */
	int securebits;
	/* parent death signal (<0 clear, 0 nothing, >0 signal) */
	int pdeathsig;

	/* LSMs */
	const char *selinux_label;
	const char *apparmor_profile;
};

static void __attribute__((__noreturn__)) usage(void)
{
	FILE *out = stdout;
	fputs(USAGE_HEADER, out);
	fprintf(out, _(" %s [options] <program> [<argument>...]\n"),
		program_invocation_short_name);

	fputs(USAGE_SEPARATOR, out);
	fputs(_("Run a program with different privilege settings.\n"), out);

	fputs(USAGE_OPTIONS, out);
	fputs(_(" -d, --dump                  show current state (and do not exec)\n"), out);
	fputs(_(" --nnp, --no-new-privs       disallow granting new privileges\n"), out);
	fputs(_(" --ambient-caps <caps,...>   set ambient capabilities\n"), out);
	fputs(_(" --inh-caps <caps,...>       set inheritable capabilities\n"), out);
	fputs(_(" --bounding-set <caps>       set capability bounding set\n"), out);
	fputs(_(" --ruid <uid>                set real uid\n"), out);
	fputs(_(" --euid <uid>                set effective uid\n"), out);
	fputs(_(" --rgid <gid>                set real gid\n"), out);
	fputs(_(" --egid <gid>                set effective gid\n"), out);
	fputs(_(" --reuid <uid>               set real and effective uid\n"), out);
	fputs(_(" --regid <gid>               set real and effective gid\n"), out);
	fputs(_(" --clear-groups              clear supplementary groups\n"), out);
	fputs(_(" --keep-groups               keep supplementary groups\n"), out);
	fputs(_(" --init-groups               initialize supplementary groups\n"), out);
	fputs(_(" --groups <group,...>        set supplementary groups\n"), out);
	fputs(_(" --securebits <bits>         set securebits\n"), out);
	fputs(_(" --pdeathsig keep|clear|<signame>\n"
	        "                             set or clear parent death signal\n"), out);
	fputs(_(" --selinux-label <label>     set SELinux label\n"), out);
	fputs(_(" --apparmor-profile <pr>     set AppArmor profile\n"), out);

	fputs(USAGE_SEPARATOR, out);
	printf(USAGE_HELP_OPTIONS(29));
	fputs(USAGE_SEPARATOR, out);
	fputs(_(" This tool can be dangerous.  Read the manpage, and be careful.\n"), out);
	printf(USAGE_MAN_TAIL("setpriv(1)"));

	exit(EXIT_SUCCESS);
}

static int real_cap_last_cap(void)
{
	/* CAP_LAST_CAP is untrustworthy. */
	static int ret = -1;
	int matched;
	FILE *f;

	if (ret != -1)
		return ret;

	f = fopen(_PATH_PROC_CAPLASTCAP, "r");
	if (!f) {
		ret = CAP_LAST_CAP;	/* guess */
		return ret;
	}

	matched = fscanf(f, "%d", &ret);
	fclose(f);

	if (matched != 1)
		ret = CAP_LAST_CAP;	/* guess */

	return ret;
}

static int has_cap(enum cap_type which, unsigned int i)
{
	switch (which) {
	case CAP_TYPE_EFFECTIVE:
	case CAP_TYPE_BOUNDING:
	case CAP_TYPE_INHERITABLE:
	case CAP_TYPE_PERMITTED:
		return capng_have_capability((capng_type_t)which, i);
	case CAP_TYPE_AMBIENT:
		return prctl(PR_CAP_AMBIENT, PR_CAP_AMBIENT_IS_SET,
				(unsigned long) i, 0UL, 0UL);
	default:
		warnx(_("invalid capability type"));
		return -1;
	}
}

/* Returns the number of capabilities printed. */
static int print_caps(FILE *f, enum cap_type which)
{
	int i, n = 0, max = real_cap_last_cap();

	for (i = 0; i <= max; i++) {
		int ret = has_cap(which, i);

		if (i == 0 && ret < 0)
			return -1;

		if (ret == 1) {
			const char *name = capng_capability_to_name(i);
			if (n)
				fputc(',', f);
			if (name)
				fputs(name, f);
			else
				/* cap-ng has very poor handling of
				 * CAP_LAST_CAP changes.  This is the
				 * best we can do. */
				printf("cap_%d", i);
			n++;
		}
	}

	return n;
}

static void dump_one_secbit(int *first, int *bits, int bit, const char *name)
{
	if (*bits & bit) {
		if (*first)
			*first = 0;
		else
			printf(",");
		fputs(name, stdout);
		*bits &= ~bit;
	}
}

static void dump_securebits(void)
{
	int first = 1;
	int bits = prctl(PR_GET_SECUREBITS, 0, 0, 0, 0);

	if (bits < 0) {
		warnx(_("getting process secure bits failed"));
		return;
	}

	printf(_("Securebits: "));

	dump_one_secbit(&first, &bits, SECBIT_NOROOT, "noroot");
	dump_one_secbit(&first, &bits, SECBIT_NOROOT_LOCKED, "noroot_locked");
	dump_one_secbit(&first, &bits, SECBIT_NO_SETUID_FIXUP,
			"no_setuid_fixup");
	dump_one_secbit(&first, &bits, SECBIT_NO_SETUID_FIXUP_LOCKED,
			"no_setuid_fixup_locked");
	bits &= ~SECBIT_KEEP_CAPS;
	dump_one_secbit(&first, &bits, SECBIT_KEEP_CAPS_LOCKED,
			"keep_caps_locked");
	if (bits) {
		if (first)
			first = 0;
		else
			printf(",");
		printf("0x%x", (unsigned)bits);
	}

	if (first)
		printf(_("[none]\n"));
	else
		printf("\n");
}

static void dump_label(const char *name)
{
	char buf[4097];
	ssize_t len;
	int fd, e;

	fd = open(_PATH_PROC_ATTR_CURRENT, O_RDONLY);
	if (fd == -1) {
		warn(_("cannot open %s"), _PATH_PROC_ATTR_CURRENT);
		return;
	}

	len = read(fd, buf, sizeof(buf));
	e = errno;
	close(fd);
	if (len < 0) {
		errno = e;
		warn(_("cannot read %s"), name);
		return;
	}
	if (sizeof(buf) - 1 <= (size_t)len) {
		warnx(_("%s: too long"), name);
		return;
	}

	buf[len] = 0;
	if (0 < len && buf[len - 1] == '\n')
		buf[len - 1] = 0;
	printf("%s: %s\n", name, buf);
}

static void dump_groups(void)
{
	int n = getgroups(0, NULL);
	gid_t *groups;

	if (n < 0) {
		warn("getgroups failed");
		return;
	}

	groups = xmalloc(n * sizeof(gid_t));
	n = getgroups(n, groups);
	if (n < 0) {
		free(groups);
		warn("getgroups failed");
		return;
	}

	printf(_("Supplementary groups: "));
	if (n == 0)
		printf(_("[none]"));
	else {
		int i;
		for (i = 0; i < n; i++) {
			if (0 < i)
				printf(",");
			printf("%ld", (long)groups[i]);
		}
	}
	printf("\n");
	free(groups);
}

static void dump_pdeathsig(void)
{
	int pdeathsig;

	if (prctl(PR_GET_PDEATHSIG, &pdeathsig) != 0) {
		warn(_("get pdeathsig failed"));
		return;
	}

	printf("Parent death signal: ");
	if (pdeathsig && signum_to_signame(pdeathsig) != NULL)
		printf("%s\n", signum_to_signame(pdeathsig));
	else if (pdeathsig)
		printf("%d\n", pdeathsig);
	else
		printf("[none]\n");
}

static void dump(int dumplevel)
{
	int x;
	uid_t ru, eu, su;
	gid_t rg, eg, sg;

	if (getresuid(&ru, &eu, &su) == 0) {
		printf(_("uid: %u\n"), ru);
		printf(_("euid: %u\n"), eu);
		/* Saved and fs uids always equal euid. */
		if (3 <= dumplevel)
			printf(_("suid: %u\n"), su);
	} else
		warn(_("getresuid failed"));

	if (getresgid(&rg, &eg, &sg) == 0) {
		printf("gid: %ld\n", (long)rg);
		printf("egid: %ld\n", (long)eg);
		/* Saved and fs gids always equal egid. */
		if (dumplevel >= 3)
			printf("sgid: %ld\n", (long)sg);
	} else
		warn(_("getresgid failed"));

	dump_groups();

	x = prctl(PR_GET_NO_NEW_PRIVS, 0, 0, 0, 0);
	if (0 <= x)
		printf("no_new_privs: %d\n", x);
	else
		warn("setting no_new_privs failed");

	if (2 <= dumplevel) {
		printf(_("Effective capabilities: "));
		if (print_caps(stdout, CAP_TYPE_EFFECTIVE) == 0)
			printf(_("[none]"));
		printf("\n");

		printf(_("Permitted capabilities: "));
		if (print_caps(stdout, CAP_TYPE_PERMITTED) == 0)
			printf(_("[none]"));
		printf("\n");
	}

	printf(_("Inheritable capabilities: "));
	if (print_caps(stdout, CAP_TYPE_INHERITABLE) == 0)
		printf(_("[none]"));
	printf("\n");

	printf(_("Ambient capabilities: "));
	x = print_caps(stdout, CAP_TYPE_AMBIENT);
	if (x == 0)
		printf(_("[none]"));
	if (x < 0)
		printf(_("[unsupported]"));
	printf("\n");

	printf(_("Capability bounding set: "));
	if (print_caps(stdout, CAP_TYPE_BOUNDING) == 0)
		printf(_("[none]"));
	printf("\n");

	dump_securebits();
	dump_pdeathsig();

	if (access(_PATH_SYS_SELINUX, F_OK) == 0)
		dump_label(_("SELinux label"));

	if (access(_PATH_SYS_APPARMOR, F_OK) == 0) {
		dump_label(_("AppArmor profile"));
	}
}

static void list_known_caps(void)
{
	int i, max = real_cap_last_cap();

	for (i = 0; i <= max; i++) {
		const char *name = capng_capability_to_name(i);
		if (name)
			printf("%s\n", name);
		else
			warnx(_("cap %d: libcap-ng is broken"), i);
	}
}

static void parse_groups(struct privctx *opts, const char *str)
{
	char *groups = xstrdup(str);
	char *buf = groups;	/* We'll reuse it */
	char *c;
	size_t i = 0;

	opts->have_groups = 1;
	opts->num_groups = 0;
	while ((c = strsep(&groups, ",")))
		opts->num_groups++;

	/* Start again */
	strcpy(buf, str);	/* It's exactly the right length */
	groups = buf;

	opts->groups = xcalloc(opts->num_groups, sizeof(gid_t));
	while ((c = strsep(&groups, ",")))
		opts->groups[i++] = (gid_t) strtol_or_err(c,
						  _("Invalid supplementary group id"));

	free(groups);
}

static void parse_pdeathsig(struct privctx *opts, const char *str)
{
	if (!strcmp(str, "keep")) {
		if (prctl(PR_GET_PDEATHSIG, &opts->pdeathsig) != 0)
			errx(SETPRIV_EXIT_PRIVERR,
				 _("failed to get parent death signal"));
	} else if (!strcmp(str, "clear")) {
		opts->pdeathsig = -1;
	} else if ((opts->pdeathsig = signame_to_signum(str)) < 0) {
		errx(EXIT_FAILURE, _("unknown signal: %s"), str);
	}
}

static void do_setresuid(const struct privctx *opts)
{
	uid_t ruid, euid, suid;
	if (getresuid(&ruid, &euid, &suid) != 0)
		err(SETPRIV_EXIT_PRIVERR, _("getresuid failed"));
	if (opts->have_ruid)
		ruid = opts->ruid;
	if (opts->have_euid)
		euid = opts->euid;

	/* Also copy effective to saved (for paranoia). */
	if (setresuid(ruid, euid, euid) != 0)
		err(SETPRIV_EXIT_PRIVERR, _("setresuid failed"));
}

static void do_setresgid(const struct privctx *opts)
{
	gid_t rgid, egid, sgid;
	if (getresgid(&rgid, &egid, &sgid) != 0)
		err(SETPRIV_EXIT_PRIVERR, _("getresgid failed"));
	if (opts->have_rgid)
		rgid = opts->rgid;
	if (opts->have_egid)
		egid = opts->egid;

	/* Also copy effective to saved (for paranoia). */
	if (setresgid(rgid, egid, egid) != 0)
		err(SETPRIV_EXIT_PRIVERR, _("setresgid failed"));
}

static void bump_cap(unsigned int cap)
{
	if (capng_have_capability(CAPNG_PERMITTED, cap))
		capng_update(CAPNG_ADD, CAPNG_EFFECTIVE, cap);
}

static int cap_update(capng_act_t action,
		enum cap_type type, unsigned int cap)
{
	switch (type) {
		case CAP_TYPE_EFFECTIVE:
		case CAP_TYPE_BOUNDING:
		case CAP_TYPE_INHERITABLE:
		case CAP_TYPE_PERMITTED:
			return capng_update(action, (capng_type_t) type, cap);
		case CAP_TYPE_AMBIENT:
		{
			int ret;

			if (action == CAPNG_ADD)
				ret = prctl(PR_CAP_AMBIENT, PR_CAP_AMBIENT_RAISE,
						(unsigned long) cap, 0UL, 0UL);
			else
				ret = prctl(PR_CAP_AMBIENT, PR_CAP_AMBIENT_LOWER,
						(unsigned long) cap, 0UL, 0UL);

			return ret;
		}
		default:
			errx(EXIT_FAILURE, _("unsupported capability type"));
			return -1;
	}
}

static void do_caps(enum cap_type type, const char *caps)
{
	char *my_caps = xstrdup(caps);
	char *c;

	while ((c = strsep(&my_caps, ","))) {
		capng_act_t action;
		if (*c == '+')
			action = CAPNG_ADD;
		else if (*c == '-')
			action = CAPNG_DROP;
		else
			errx(EXIT_FAILURE, _("bad capability string"));

		if (!strcmp(c + 1, "all")) {
			int i;
			/* It would be really bad if -all didn't drop all
			 * caps.  It's better to just fail. */
			if (real_cap_last_cap() > CAP_LAST_CAP)
				errx(SETPRIV_EXIT_PRIVERR,
				     _("libcap-ng is too old for \"all\" caps"));
			for (i = 0; i <= CAP_LAST_CAP; i++)
				cap_update(action, type, i);
		} else {
			int cap = capng_name_to_capability(c + 1);
			if (0 <= cap)
				cap_update(action, type, cap);
			else if (sscanf(c + 1, "cap_%d", &cap) == 1
			    && 0 <= cap && cap <= real_cap_last_cap())
				cap_update(action, type, cap);
			else
				errx(EXIT_FAILURE,
				     _("unknown capability \"%s\""), c + 1);
		}
	}

	free(my_caps);
}

static void parse_securebits(struct privctx *opts, const char *arg)
{
	char *buf = xstrdup(arg);
	char *c;

	opts->have_securebits = 1;
	opts->securebits = prctl(PR_GET_SECUREBITS, 0, 0, 0, 0);
	if (opts->securebits < 0)
		err(SETPRIV_EXIT_PRIVERR, _("getting process secure bits failed"));

	if (opts->securebits & ~(int)(SECBIT_NOROOT |
				      SECBIT_NOROOT_LOCKED |
				      SECBIT_NO_SETUID_FIXUP |
				      SECBIT_NO_SETUID_FIXUP_LOCKED |
				      SECBIT_KEEP_CAPS |
				      SECBIT_KEEP_CAPS_LOCKED))
		errx(SETPRIV_EXIT_PRIVERR,
		     _("unrecognized securebit set -- refusing to adjust"));

	while ((c = strsep(&buf, ","))) {
		if (*c != '+' && *c != '-')
			errx(EXIT_FAILURE, _("bad securebits string"));

		if (!strcmp(c + 1, "all")) {
			if (*c == '-')
				opts->securebits = 0;
			else
				errx(EXIT_FAILURE,
				     _("+all securebits is not allowed"));
		} else {
			int bit;
			if (!strcmp(c + 1, "noroot"))
				bit = SECBIT_NOROOT;
			else if (!strcmp(c + 1, "noroot_locked"))
				bit = SECBIT_NOROOT_LOCKED;
			else if (!strcmp(c + 1, "no_setuid_fixup"))
				bit = SECBIT_NO_SETUID_FIXUP;
			else if (!strcmp(c + 1, "no_setuid_fixup_locked"))
				bit = SECBIT_NO_SETUID_FIXUP_LOCKED;
			else if (!strcmp(c + 1, "keep_caps"))
				errx(EXIT_FAILURE,
				     _("adjusting keep_caps does not make sense"));
			else if (!strcmp(c + 1, "keep_caps_locked"))
				bit = SECBIT_KEEP_CAPS_LOCKED;	/* sigh */
			else
				errx(EXIT_FAILURE, _("unrecognized securebit"));

			if (*c == '+')
				opts->securebits |= bit;
			else
				opts->securebits &= ~bit;
		}
	}

	opts->securebits |= SECBIT_KEEP_CAPS;	/* We need it, and it's reset on exec */

	free(buf);
}

static void do_selinux_label(const char *label)
{
	int fd;
	size_t len;

	if (access(_PATH_SYS_SELINUX, F_OK) != 0)
		errx(SETPRIV_EXIT_PRIVERR, _("SELinux is not running"));

	fd = open(_PATH_PROC_ATTR_EXEC, O_RDWR);
	if (fd == -1)
		err(SETPRIV_EXIT_PRIVERR,
		    _("cannot open %s"), _PATH_PROC_ATTR_EXEC);

	len = strlen(label);
	errno = 0;
	if (write(fd, label, len) != (ssize_t) len)
		err(SETPRIV_EXIT_PRIVERR,
		    _("write failed: %s"), _PATH_PROC_ATTR_EXEC);

	if (close(fd) != 0)
		err(SETPRIV_EXIT_PRIVERR,
		    _("close failed: %s"), _PATH_PROC_ATTR_EXEC);
}

static void do_apparmor_profile(const char *label)
{
	FILE *f;

	if (access(_PATH_SYS_APPARMOR, F_OK) != 0)
		errx(SETPRIV_EXIT_PRIVERR, _("AppArmor is not running"));

	f = fopen(_PATH_PROC_ATTR_EXEC, "r+");
	if (!f)
		err(SETPRIV_EXIT_PRIVERR,
		    _("cannot open %s"), _PATH_PROC_ATTR_EXEC);

	fprintf(f, "exec %s", label);

	if (close_stream(f) != 0)
		err(SETPRIV_EXIT_PRIVERR,
		    _("write failed: %s"), _PATH_PROC_ATTR_EXEC);
}

static uid_t get_user(const char *s, const char *err)
{
	struct passwd *pw;
	long tmp;
	pw = getpwnam(s);
	if (pw)
		return pw->pw_uid;
	tmp = strtol_or_err(s, err);
	return tmp;
}

static gid_t get_group(const char *s, const char *err)
{
	struct group *gr;
	long tmp;
	gr = getgrnam(s);
	if (gr)
		return gr->gr_gid;
	tmp = strtol_or_err(s, err);
	return tmp;
}

static struct passwd *get_passwd(const char *s, uid_t *uid, const char *err)
{
	struct passwd *pw;
	long tmp;
	pw = getpwnam(s);
	if (pw) {
		*uid = pw->pw_uid;
	} else {
		tmp = strtol_or_err(s, err);
		*uid = tmp;
		pw = getpwuid(*uid);
	}
	return pw;
}

static struct passwd *passwd_copy(struct passwd *dst, const struct passwd *src)
{
	struct passwd *rv;
	rv = memcpy(dst, src, sizeof(*dst));
	rv->pw_name = xstrdup(rv->pw_name);
	rv->pw_passwd = xstrdup(rv->pw_passwd);
	rv->pw_gecos = xstrdup(rv->pw_gecos);
	rv->pw_dir = xstrdup(rv->pw_dir);
	rv->pw_shell = xstrdup(rv->pw_shell);
	return rv;
}

int main(int argc, char **argv)
{
	enum {
		NNP = CHAR_MAX + 1,
		RUID,
		EUID,
		RGID,
		EGID,
		REUID,
		REGID,
		CLEAR_GROUPS,
		KEEP_GROUPS,
		INIT_GROUPS,
		GROUPS,
		INHCAPS,
		AMBCAPS,
		LISTCAPS,
		CAPBSET,
		SECUREBITS,
		PDEATHSIG,
		SELINUX_LABEL,
		APPARMOR_PROFILE
	};

	static const struct option longopts[] = {
		{ "dump",             no_argument,       NULL, 'd'              },
		{ "nnp",              no_argument,       NULL, NNP              },
		{ "no-new-privs",     no_argument,       NULL, NNP              },
		{ "inh-caps",         required_argument, NULL, INHCAPS          },
		{ "ambient-caps",     required_argument, NULL, AMBCAPS          },
		{ "list-caps",        no_argument,       NULL, LISTCAPS         },
		{ "ruid",             required_argument, NULL, RUID             },
		{ "euid",             required_argument, NULL, EUID             },
		{ "rgid",             required_argument, NULL, RGID             },
		{ "egid",             required_argument, NULL, EGID             },
		{ "reuid",            required_argument, NULL, REUID            },
		{ "regid",            required_argument, NULL, REGID            },
		{ "clear-groups",     no_argument,       NULL, CLEAR_GROUPS     },
		{ "keep-groups",      no_argument,       NULL, KEEP_GROUPS      },
		{ "init-groups",      no_argument,       NULL, INIT_GROUPS      },
		{ "groups",           required_argument, NULL, GROUPS           },
		{ "bounding-set",     required_argument, NULL, CAPBSET          },
		{ "securebits",       required_argument, NULL, SECUREBITS       },
		{ "pdeathsig",        required_argument, NULL, PDEATHSIG,       },
		{ "selinux-label",    required_argument, NULL, SELINUX_LABEL    },
		{ "apparmor-profile", required_argument, NULL, APPARMOR_PROFILE },
		{ "help",             no_argument,       NULL, 'h'              },
		{ "version",          no_argument,       NULL, 'V'              },
		{ NULL, 0, NULL, 0 }
	};

	static const ul_excl_t excl[] = {
		/* keep in same order with enum definitions */
		{CLEAR_GROUPS, KEEP_GROUPS, INIT_GROUPS, GROUPS},
		{0}
	};
	int excl_st[ARRAY_SIZE(excl)] = UL_EXCL_STATUS_INIT;

	int c;
	struct privctx opts;
	struct passwd *pw = NULL;
	int dumplevel = 0;
	int total_opts = 0;
	int list_caps = 0;

	setlocale(LC_ALL, "");
	bindtextdomain(PACKAGE, LOCALEDIR);
	textdomain(PACKAGE);
	atexit(close_stdout);

	memset(&opts, 0, sizeof(opts));

	while ((c = getopt_long(argc, argv, "+dhV", longopts, NULL)) != -1) {
		err_exclusive_options(c, longopts, excl, excl_st);
		total_opts++;
		switch (c) {
		case 'd':
			dumplevel++;
			break;
		case NNP:
			if (opts.nnp)
				errx(EXIT_FAILURE,
				     _("duplicate --no-new-privs option"));
			opts.nnp = 1;
			break;
		case RUID:
			if (opts.have_ruid)
				errx(EXIT_FAILURE, _("duplicate ruid"));
			opts.have_ruid = 1;
			pw = get_passwd(optarg, &opts.ruid, _("failed to parse ruid"));
			if (pw) {
				passwd_copy(&opts.passwd, pw);
				opts.have_passwd = 1;
			}
			break;
		case EUID:
			if (opts.have_euid)
				errx(EXIT_FAILURE, _("duplicate euid"));
			opts.have_euid = 1;
			opts.euid = get_user(optarg, _("failed to parse euid"));
			break;
		case REUID:
			if (opts.have_ruid || opts.have_euid)
				errx(EXIT_FAILURE, _("duplicate ruid or euid"));
			opts.have_ruid = opts.have_euid = 1;
			pw = get_passwd(optarg, &opts.ruid, _("failed to parse reuid"));
			opts.euid = opts.ruid;
			if (pw) {
				passwd_copy(&opts.passwd, pw);
				opts.have_passwd = 1;
			}
			break;
		case RGID:
			if (opts.have_rgid)
				errx(EXIT_FAILURE, _("duplicate rgid"));
			opts.have_rgid = 1;
			opts.rgid = get_group(optarg, _("failed to parse rgid"));
			break;
		case EGID:
			if (opts.have_egid)
				errx(EXIT_FAILURE, _("duplicate egid"));
			opts.have_egid = 1;
			opts.egid = get_group(optarg, _("failed to parse egid"));
			break;
		case REGID:
			if (opts.have_rgid || opts.have_egid)
				errx(EXIT_FAILURE, _("duplicate rgid or egid"));
			opts.have_rgid = opts.have_egid = 1;
			opts.rgid = opts.egid = get_group(optarg, _("failed to parse regid"));
			break;
		case CLEAR_GROUPS:
			if (opts.clear_groups)
				errx(EXIT_FAILURE,
				     _("duplicate --clear-groups option"));
			opts.clear_groups = 1;
			break;
		case KEEP_GROUPS:
			if (opts.keep_groups)
				errx(EXIT_FAILURE,
				     _("duplicate --keep-groups option"));
			opts.keep_groups = 1;
			break;
		case INIT_GROUPS:
			if (opts.init_groups)
				errx(EXIT_FAILURE,
				     _("duplicate --init-groups option"));
			opts.init_groups = 1;
			break;
		case GROUPS:
			if (opts.have_groups)
				errx(EXIT_FAILURE,
				     _("duplicate --groups option"));
			parse_groups(&opts, optarg);
			break;
		case PDEATHSIG:
			if (opts.pdeathsig)
				errx(EXIT_FAILURE,
				     _("duplicate --keep-pdeathsig option"));
			parse_pdeathsig(&opts, optarg);
			break;
		case LISTCAPS:
			list_caps = 1;
			break;
		case INHCAPS:
			if (opts.caps_to_inherit)
				errx(EXIT_FAILURE,
				     _("duplicate --inh-caps option"));
			opts.caps_to_inherit = optarg;
			break;
		case AMBCAPS:
			if (opts.ambient_caps)
				errx(EXIT_FAILURE,
				     _("duplicate --ambient-caps option"));
			opts.ambient_caps = optarg;
			break;
		case CAPBSET:
			if (opts.bounding_set)
				errx(EXIT_FAILURE,
				     _("duplicate --bounding-set option"));
			opts.bounding_set = optarg;
			break;
		case SECUREBITS:
			if (opts.have_securebits)
				errx(EXIT_FAILURE,
				     _("duplicate --securebits option"));
			parse_securebits(&opts, optarg);
			break;
		case SELINUX_LABEL:
			if (opts.selinux_label)
				errx(EXIT_FAILURE,
				     _("duplicate --selinux-label option"));
			opts.selinux_label = optarg;
			break;
		case APPARMOR_PROFILE:
			if (opts.apparmor_profile)
				errx(EXIT_FAILURE,
				     _("duplicate --apparmor-profile option"));
			opts.apparmor_profile = optarg;
			break;
		case 'h':
			usage();
		case 'V':
			printf(UTIL_LINUX_VERSION);
			return EXIT_SUCCESS;
		default:
			errtryhelp(EXIT_FAILURE);
		}
	}

	if (dumplevel) {
		if (total_opts != dumplevel || optind < argc)
			errx(EXIT_FAILURE,
			     _("--dump is incompatible with all other options"));
		dump(dumplevel);
		return EXIT_SUCCESS;
	}

	if (list_caps) {
		if (total_opts != 1 || optind < argc)
			errx(EXIT_FAILURE,
			     _("--list-caps must be specified alone"));
		list_known_caps();
		return EXIT_SUCCESS;
	}

	if (argc <= optind)
		errx(EXIT_FAILURE, _("No program specified"));

	if ((opts.have_rgid || opts.have_egid)
	    && !opts.keep_groups && !opts.clear_groups && !opts.init_groups
	    && !opts.have_groups)
		errx(EXIT_FAILURE,
		     _("--[re]gid requires --keep-groups, --clear-groups, --init-groups, or --groups"));

	if (opts.init_groups && !opts.have_ruid)
		errx(EXIT_FAILURE,
		     _("--init-groups requires --ruid or --reuid"));

	if (opts.init_groups && !opts.have_passwd)
		errx(EXIT_FAILURE,
		     _("uid %ld not found, --init-groups requires an user that "
		       "can be found on the system"),
		     (long) opts.ruid);

	if (opts.nnp && prctl(PR_SET_NO_NEW_PRIVS, 1, 0, 0, 0) == -1)
		err(EXIT_FAILURE, _("disallow granting new privileges failed"));

	if (opts.selinux_label)
		do_selinux_label(opts.selinux_label);
	if (opts.apparmor_profile)
		do_apparmor_profile(opts.apparmor_profile);

	if (prctl(PR_SET_KEEPCAPS, 1, 0, 0, 0) == -1)
		err(EXIT_FAILURE, _("keep process capabilities failed"));

	/* We're going to want CAP_SETPCAP, CAP_SETUID, and CAP_SETGID if
	 * possible.  */
	bump_cap(CAP_SETPCAP);
	bump_cap(CAP_SETUID);
	bump_cap(CAP_SETGID);
	if (capng_apply(CAPNG_SELECT_CAPS) != 0)
		err(SETPRIV_EXIT_PRIVERR, _("activate capabilities"));

	if (opts.have_ruid || opts.have_euid) {
		do_setresuid(&opts);
		/* KEEPCAPS doesn't work for the effective mask. */
		if (capng_apply(CAPNG_SELECT_CAPS) != 0)
			err(SETPRIV_EXIT_PRIVERR, _("reactivate capabilities"));
	}

	if (opts.have_rgid || opts.have_egid)
		do_setresgid(&opts);

	if (opts.have_groups) {
		if (setgroups(opts.num_groups, opts.groups) != 0)
			err(SETPRIV_EXIT_PRIVERR, _("setgroups failed"));
	} else if (opts.init_groups) {
		if (initgroups(opts.passwd.pw_name, opts.passwd.pw_gid) != 0)
			err(SETPRIV_EXIT_PRIVERR, _("initgroups failed"));
	} else if (opts.clear_groups) {
		gid_t x = 0;
		if (setgroups(0, &x) != 0)
			err(SETPRIV_EXIT_PRIVERR, _("setgroups failed"));
	}

	if (opts.have_securebits && prctl(PR_SET_SECUREBITS, opts.securebits, 0, 0, 0) != 0)
		err(SETPRIV_EXIT_PRIVERR, _("set process securebits failed"));

	if (opts.bounding_set) {
		do_caps(CAP_TYPE_BOUNDING, opts.bounding_set);
		errno = EPERM;	/* capng doesn't set errno if we're missing CAP_SETPCAP */
		if (capng_apply(CAPNG_SELECT_BOUNDS) != 0)
			err(SETPRIV_EXIT_PRIVERR, _("apply bounding set"));
	}

	if (opts.caps_to_inherit) {
		do_caps(CAP_TYPE_INHERITABLE, opts.caps_to_inherit);
		if (capng_apply(CAPNG_SELECT_CAPS) != 0)
			err(SETPRIV_EXIT_PRIVERR, _("apply capabilities"));
	}

	if (opts.ambient_caps) {
		do_caps(CAP_TYPE_AMBIENT, opts.ambient_caps);
	}

	/* Clear or set parent death signal */
	if (opts.pdeathsig && prctl(PR_SET_PDEATHSIG, opts.pdeathsig < 0 ? 0 : opts.pdeathsig) != 0)
		err(SETPRIV_EXIT_PRIVERR, _("set parent death signal failed"));

	execvp(argv[optind], argv + optind);
	errexec(argv[optind]);
}
