/*
 * Authors: Dan Walsh <dwalsh@redhat.com>
 * Authors: Thomas Liu <tliu@fedoraproject.org>
 */

#define _GNU_SOURCE
#include <signal.h>
#include <sys/fsuid.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <syslog.h>
#include <sys/mount.h>
#include <glob.h>
#include <pwd.h>
#include <sched.h>
#include <string.h>
#include <stdio.h>
#include <regex.h>
#include <unistd.h>
#include <stdlib.h>
#include <cap-ng.h>
#include <getopt.h>		/* for getopt_long() form of getopt() */
#include <limits.h>
#include <stdlib.h>
#include <errno.h>
#include <fcntl.h>

#include <selinux/selinux.h>
#include <selinux/context.h>	/* for context-mangling functions */
#include <dirent.h>

#ifdef USE_NLS
#include <locale.h>		/* for setlocale() */
#include <libintl.h>		/* for gettext() */
#define _(msgid) gettext (msgid)
#else
#define _(msgid) (msgid)
#endif

#ifndef MS_REC
#define MS_REC 1<<14
#endif

#ifndef MS_SLAVE
#define MS_SLAVE 1<<19
#endif

#ifndef PACKAGE
#define PACKAGE "policycoreutils"	/* the name of this package lang translation */
#endif

#define BUF_SIZE 1024
#define DEFAULT_PATH "/usr/bin:/bin"
#define USAGE_STRING _("USAGE: seunshare [ -v ] [ -C ] [ -k ] [ -t tmpdir ] [ -h homedir ] [ -Z CONTEXT ] -- executable [args] ")

static int verbose = 0;
static int child = 0;

static capng_select_t cap_set = CAPNG_SELECT_CAPS;

/**
 * This function will drop all capabilities.
 */
static int drop_caps(void)
{
	if (capng_have_capabilities(cap_set) == CAPNG_NONE)
		return 0;
	capng_clear(cap_set);
	if (capng_lock() == -1 || capng_apply(cap_set) == -1) {
		fprintf(stderr, _("Failed to drop all capabilities\n"));
		return -1;
	}
	return 0;
}

/**
 * This function will drop all privileges.
 */
static int drop_privs(uid_t uid)
{
	if (drop_caps() == -1 || setresuid(uid, uid, uid) == -1) {
		fprintf(stderr, _("Failed to drop privileges\n"));
		return -1;
	}
	return 0;
}

/**
 * If the user sends a siginto to seunshare, kill the child's session
 */
void handler(int sig) {
	if (child > 0) kill(-child,sig);
}

/**
 * Take care of any signal setup.
 */
static int set_signal_handles(void)
{
	sigset_t empty;

	/* Empty the signal mask in case someone is blocking a signal */
	if (sigemptyset(&empty)) {
		fprintf(stderr, "Unable to obtain empty signal set\n");
		return -1;
	}

	(void)sigprocmask(SIG_SETMASK, &empty, NULL);

	/* Terminate on SIGHUP */
	if (signal(SIGHUP, SIG_DFL) == SIG_ERR) {
		perror("Unable to set SIGHUP handler");
		return -1;
	}

	if (signal(SIGINT, handler) == SIG_ERR) {
		perror("Unable to set SIGINT handler");
		return -1;
	}

	return 0;
}

#define status_to_retval(status,retval) do { \
	if ((status) == -1) \
		retval = -1; \
	else if (WIFEXITED((status))) \
		retval = WEXITSTATUS((status)); \
	else if (WIFSIGNALED((status))) \
		retval = 128 + WTERMSIG((status)); \
	else \
		retval = -1; \
	} while(0)

/**
 * Spawn external command using system() with dropped privileges.
 * TODO: avoid system() and use exec*() instead
 */
static int spawn_command(const char *cmd, uid_t uid){
	int childpid;
	int status = -1;

	if (verbose > 1)
		printf("spawn_command: %s\n", cmd);

	childpid = fork();
	if (childpid == -1) {
		perror(_("Unable to fork"));
		return status;
	}

	if (childpid == 0) {
		if (drop_privs(uid) != 0) exit(-1);

		status = system(cmd);
		status_to_retval(status, status);
		exit(status);
	}

	waitpid(childpid, &status, 0);
	status_to_retval(status, status);
	return status;
}

/**
 * Check file/directory ownership, struct stat * must be passed to the
 * functions.
 */
static int check_owner_uid(uid_t uid, const char *file, struct stat *st) {
	if (S_ISLNK(st->st_mode)) {
		fprintf(stderr, _("Error: %s must not be a symbolic link\n"), file);
		return -1;
	}
	if (st->st_uid != uid) {
		fprintf(stderr, _("Error: %s not owned by UID %d\n"), file, uid);
		return -1;
	}
	return 0;
}

static int check_owner_gid(gid_t gid, const char *file, struct stat *st) {
	if (S_ISLNK(st->st_mode)) {
		fprintf(stderr, _("Error: %s must not be a symbolic link\n"), file);
		return -1;
	}
	if (st->st_gid != gid) {
		fprintf(stderr, _("Error: %s not owned by GID %d\n"), file, gid);
		return -1;
	}
	return 0;
}

#define equal_stats(one,two) \
	((one)->st_dev == (two)->st_dev && (one)->st_ino == (two)->st_ino && \
	 (one)->st_uid == (two)->st_uid && (one)->st_gid == (two)->st_gid && \
	 (one)->st_mode == (two)->st_mode)

/**
 * Sanity check specified directory.  Store stat info for future comparison, or
 * compare with previously saved info to detect replaced directories.
 * Note: This function does not perform owner checks.
 */
static int verify_directory(const char *dir, struct stat *st_in, struct stat *st_out) {
	struct stat sb;

	if (st_out == NULL) st_out = &sb;

	if (lstat(dir, st_out) == -1) {
		fprintf(stderr, _("Failed to stat %s: %s\n"), dir, strerror(errno));
		return -1;
	}
	if (! S_ISDIR(st_out->st_mode)) {
		fprintf(stderr, _("Error: %s is not a directory: %s\n"), dir, strerror(errno));
		return -1;
	}
	if (st_in && !equal_stats(st_in, st_out)) {
		fprintf(stderr, _("Error: %s was replaced by a different directory\n"), dir);
		return -1;
	}

	return 0;
}

/**
 * This function checks to see if the shell is known in /etc/shells.
 * If so, it returns 0. On error or illegal shell, it returns -1.
 */
static int verify_shell(const char *shell_name)
{
	int rc = -1;
	const char *buf;

	if (!(shell_name && shell_name[0]))
		return rc;

	while ((buf = getusershell()) != NULL) {
		/* ignore comments */
		if (*buf == '#')
			continue;

		/* check the shell skipping newline char */
		if (!strcmp(shell_name, buf)) {
			rc = 0;
			break;
		}
	}
	endusershell();
	return rc;
}

/**
 * Mount directory and check that we mounted the right directory.
 */
static int seunshare_mount(const char *src, const char *dst, struct stat *src_st)
{
	int flags = 0;
	int is_tmp = 0;

	if (verbose)
		printf(_("Mounting %s on %s\n"), src, dst);

	if (strcmp("/tmp", dst) == 0) {
		flags = flags | MS_NODEV | MS_NOSUID | MS_NOEXEC;
		is_tmp = 1;
	}

	/* mount directory */
	if (mount(src, dst, NULL, MS_BIND | flags, NULL) < 0) {
		fprintf(stderr, _("Failed to mount %s on %s: %s\n"), src, dst, strerror(errno));
		return -1;
	}

	/* verify whether we mounted what we expected to mount */
	if (verify_directory(dst, src_st, NULL) < 0) return -1;

	/* bind mount /tmp on /var/tmp too */
	if (is_tmp) {
		if (verbose)
			printf(_("Mounting /tmp on /var/tmp\n"));

		if (mount("/tmp", "/var/tmp",  NULL, MS_BIND | flags, NULL) < 0) {
			fprintf(stderr, _("Failed to mount /tmp on /var/tmp: %s\n"), strerror(errno));
			return -1;
		}
	}

	return 0;

}

/*
   If path is empy or ends with  "/." or "/.. return -1 else return 0;
 */
static int bad_path(const char *path) {
	const char *ptr;
	ptr = path;
	while (*ptr) ptr++;
	if (ptr == path) return -1; // ptr null
	ptr--;
	if (ptr != path && *ptr  == '.') {
		ptr--;
		if (*ptr  == '/') return -1; // path ends in /.
		if (*ptr  == '.') {
			if (ptr != path) {
				ptr--;
				if (*ptr  == '/') return -1; // path ends in /..
			}
		}
	}
	return 0;
}

static int rsynccmd(const char * src, const char *dst, char **cmdbuf)
{
	char *buf = NULL;
	char *newbuf = NULL;
	glob_t fglob;
	fglob.gl_offs = 0;
	int flags = GLOB_PERIOD;
	unsigned int i = 0;
	int rc = -1;

	/* match glob for all files in src dir */
	if (asprintf(&buf, "%s/*", src) == -1) {
		fprintf(stderr, "Out of memory\n");
		return -1;
	}

	if (glob(buf, flags, NULL, &fglob) != 0) {
		free(buf); buf = NULL;
		return -1;
	}

	free(buf); buf = NULL;

	for ( i=0; i < fglob.gl_pathc; i++) {
		const char *path = fglob.gl_pathv[i];

		if (bad_path(path)) continue;

		if (!buf) {
			if (asprintf(&newbuf, "\'%s\'", path) == -1) {
				fprintf(stderr, "Out of memory\n");
				goto err;
			}
		} else {
			if (asprintf(&newbuf, "%s  \'%s\'", buf, path) == -1) {
				fprintf(stderr, "Out of memory\n");
				goto err;
			}
		}

		free(buf); buf = newbuf;
		newbuf = NULL;
	}

	if (buf) {
		if (asprintf(&newbuf, "/usr/bin/rsync -trlHDq %s '%s'", buf, dst) == -1) {
			fprintf(stderr, "Out of memory\n");
			goto err;
		}
		*cmdbuf=newbuf;
	}
	else {
		*cmdbuf=NULL;
	}
	rc = 0;

err:
	free(buf); buf = NULL;
	globfree(&fglob);
	return rc;
}

/**
 * Clean up runtime temporary directory.  Returns 0 if no problem was detected,
 * >0 if some error was detected, but errors here are treated as non-fatal and
 * left to tmpwatch to finish incomplete cleanup.
 */
static int cleanup_tmpdir(const char *tmpdir, const char *src,
	struct passwd *pwd, int copy_content)
{
	char *cmdbuf = NULL;
	int rc = 0;

	/* rsync files back */
	if (copy_content) {
		if (asprintf(&cmdbuf, "/usr/bin/rsync --exclude=.X11-unix -utrlHDq --delete '%s/' '%s/'", tmpdir, src) == -1) {
			fprintf(stderr, _("Out of memory\n"));
			cmdbuf = NULL;
			rc++;
		}
		if (cmdbuf && spawn_command(cmdbuf, pwd->pw_uid) != 0) {
			fprintf(stderr, _("Failed to copy files from the runtime temporary directory\n"));
			rc++;
		}
		free(cmdbuf); cmdbuf = NULL;
	}

	/* remove files from the runtime temporary directory */
	if (asprintf(&cmdbuf, "/bin/rm -r '%s/' 2>/dev/null", tmpdir) == -1) {
		fprintf(stderr, _("Out of memory\n"));
		cmdbuf = NULL;
		rc++;
	}
	/* this may fail if there's root-owned file left in the runtime tmpdir */
	if (cmdbuf && spawn_command(cmdbuf, pwd->pw_uid) != 0) rc++;
	free(cmdbuf); cmdbuf = NULL;

	/* remove runtime temporary directory */
	if ((uid_t)setfsuid(0) != 0) {
		/* setfsuid does not return errror, but this check makes code checkers happy */
		rc++;
	}

	if (rmdir(tmpdir) == -1)
		fprintf(stderr, _("Failed to remove directory %s: %s\n"), tmpdir, strerror(errno));
	if ((uid_t)setfsuid(pwd->pw_uid) != 0) {
		fprintf(stderr, _("unable to switch back to user after clearing tmp dir\n"));
		rc++;
	}

	return rc;
}

/**
 * seunshare will create a tmpdir in /tmp, with root ownership.  The parent
 * process waits for it child to exit to attempt to remove the directory.  If
 * it fails to remove the directory, we will need to rely on tmpreaper/tmpwatch
 * to clean it up.
 */
static char *create_tmpdir(const char *src, struct stat *src_st,
	struct stat *out_st, struct passwd *pwd, security_context_t execcon)
{
	char *tmpdir = NULL;
	char *cmdbuf = NULL;
	int fd_t = -1, fd_s = -1;
	struct stat tmp_st;
	security_context_t con = NULL;

	/* get selinux context */
	if (execcon) {
		if ((uid_t)setfsuid(pwd->pw_uid) != 0)
			goto err;

		if ((fd_s = open(src, O_RDONLY)) < 0) {
			fprintf(stderr, _("Failed to open directory %s: %s\n"), src, strerror(errno));
			goto err;
		}
		if (fstat(fd_s, &tmp_st) == -1) {
			fprintf(stderr, _("Failed to stat directory %s: %s\n"), src, strerror(errno));
			goto err;
		}
		if (!equal_stats(src_st, &tmp_st)) {
			fprintf(stderr, _("Error: %s was replaced by a different directory\n"), src);
			goto err;
		}
		if (fgetfilecon(fd_s, &con) == -1) {
			fprintf(stderr, _("Failed to get context of the directory %s: %s\n"), src, strerror(errno));
			goto err;
		}

		/* ok to not reach this if there is an error */
		if ((uid_t)setfsuid(0) != pwd->pw_uid)
			goto err;
	}

	if (asprintf(&tmpdir, "/tmp/.sandbox-%s-XXXXXX", pwd->pw_name) == -1) {
		fprintf(stderr, _("Out of memory\n"));
		tmpdir = NULL;
		goto err;
	}
	if (mkdtemp(tmpdir) == NULL) {
		fprintf(stderr, _("Failed to create temporary directory: %s\n"), strerror(errno));
		goto err;
	}

	/* temporary directory must be owned by root:user */
	if (verify_directory(tmpdir, NULL, out_st) < 0) {
		goto err;
	}

	if (check_owner_uid(0, tmpdir, out_st) < 0)
		goto err;

	if (check_owner_gid(getgid(), tmpdir, out_st) < 0)
		goto err;

	/* change permissions of the temporary directory */
	if ((fd_t = open(tmpdir, O_RDONLY)) < 0) {
		fprintf(stderr, _("Failed to open directory %s: %s\n"), tmpdir, strerror(errno));
		goto err;
	}
	if (fstat(fd_t, &tmp_st) == -1) {
		fprintf(stderr, _("Failed to stat directory %s: %s\n"), tmpdir, strerror(errno));
		goto err;
	}
	if (!equal_stats(out_st, &tmp_st)) {
		fprintf(stderr, _("Error: %s was replaced by a different directory\n"), tmpdir);
		goto err;
	}
	if (fchmod(fd_t, 01770) == -1) {
		fprintf(stderr, _("Unable to change mode on %s: %s\n"), tmpdir, strerror(errno));
		goto err;
	}
	/* re-stat again to pick change mode */
	if (fstat(fd_t, out_st) == -1) {
		fprintf(stderr, _("Failed to stat directory %s: %s\n"), tmpdir, strerror(errno));
		goto err;
	}

	/* copy selinux context */
	if (execcon) {
		if (fsetfilecon(fd_t, con) == -1) {
			fprintf(stderr, _("Failed to set context of the directory %s: %s\n"), tmpdir, strerror(errno));
			goto err;
		}
	}

	if ((uid_t)setfsuid(pwd->pw_uid) != 0)
		goto err;

	if (rsynccmd(src, tmpdir, &cmdbuf) < 0) {
		goto err;
	}

	/* ok to not reach this if there is an error */
	if ((uid_t)setfsuid(0) != pwd->pw_uid)
		goto err;

	if (cmdbuf && spawn_command(cmdbuf, pwd->pw_uid) != 0) {
		fprintf(stderr, _("Failed to populate runtime temporary directory\n"));
		cleanup_tmpdir(tmpdir, src, pwd, 0);
		goto err;
	}

	goto good;
err:
	free(tmpdir); tmpdir = NULL;
good:
	free(cmdbuf); cmdbuf = NULL;
	freecon(con); con = NULL;
	if (fd_t >= 0) close(fd_t);
	if (fd_s >= 0) close(fd_s);
	return tmpdir;
}

#define PROC_BASE "/proc"

static int
killall (security_context_t execcon)
{
	DIR *dir;
	security_context_t scon;
	struct dirent *de;
	pid_t *pid_table, pid, self;
	int i;
	int pids, max_pids;
	int running = 0;
	self = getpid();
	if (!(dir = opendir(PROC_BASE))) {
		return -1;
	}
	max_pids = 256;
	pid_table = malloc(max_pids * sizeof (pid_t));
	if (!pid_table) {
		(void)closedir(dir);
		return -1;
	}
	pids = 0;
	context_t con;
	con = context_new(execcon);
	const char *mcs = context_range_get(con);
	printf("mcs=%s\n", mcs);
	while ((de = readdir (dir)) != NULL) {
		if (!(pid = (pid_t)atoi(de->d_name)) || pid == self)
			continue;

		if (pids == max_pids) {
			pid_t *new_pid_table = realloc(pid_table, 2*pids*sizeof(pid_t));
			if (!new_pid_table) {
				free(pid_table);
				(void)closedir(dir);
				return -1;
			}
			pid_table = new_pid_table;
			max_pids *= 2;
		}
		pid_table[pids++] = pid;
	}

	(void)closedir(dir);

	for (i = 0; i < pids; i++) {
		pid_t id = pid_table[i];

		if (getpidcon(id, &scon) == 0) {

			context_t pidcon = context_new(scon);
			/* Attempt to kill remaining processes */
			if (strcmp(context_range_get(pidcon), mcs) == 0)
				kill(id, SIGKILL);

			context_free(pidcon);
			freecon(scon);
		}
		running++;
	}

	context_free(con);
	free(pid_table);
	return running;
}

int main(int argc, char **argv) {
	int status = -1;
	security_context_t execcon = NULL;

	int clflag;		/* holds codes for command line flags */
	int kill_all = 0;

	char *homedir_s = NULL;	/* homedir spec'd by user in argv[] */
	char *tmpdir_s = NULL;	/* tmpdir spec'd by user in argv[] */
	char *tmpdir_r = NULL;	/* tmpdir created by seunshare */

	struct stat st_curhomedir;
	struct stat st_homedir;
	struct stat st_tmpdir_s;
	struct stat st_tmpdir_r;

	const struct option long_options[] = {
		{"homedir", 1, 0, 'h'},
		{"tmpdir", 1, 0, 't'},
		{"kill", 1, 0, 'k'},
		{"verbose", 1, 0, 'v'},
		{"context", 1, 0, 'Z'},
		{"capabilities", 1, 0, 'C'},
		{NULL, 0, 0, 0}
	};

	uid_t uid = getuid();
/*
	if (!uid) {
		fprintf(stderr, _("Must not be root"));
		return -1;
	}
*/

#ifdef USE_NLS
	setlocale(LC_ALL, "");
	bindtextdomain(PACKAGE, LOCALEDIR);
	textdomain(PACKAGE);
#endif

	struct passwd *pwd=getpwuid(uid);
	if (!pwd) {
		perror(_("getpwduid failed"));
		return -1;
	}

	if (verify_shell(pwd->pw_shell) < 0) {
		fprintf(stderr, _("Error: User shell is not valid\n"));
		return -1;
	}

	while (1) {
		clflag = getopt_long(argc, argv, "Ccvh:t:Z:", long_options, NULL);
		if (clflag == -1)
			break;

		switch (clflag) {
		case 't':
			tmpdir_s = optarg;
			break;
		case 'k':
			kill_all = 1;
			break;
		case 'h':
			homedir_s = optarg;
			break;
		case 'v':
			verbose++;
			break;
		case 'C':
			cap_set = CAPNG_SELECT_CAPS;
			break;
		case 'Z':
			execcon = optarg;
			break;
		default:
			fprintf(stderr, "%s\n", USAGE_STRING);
			return -1;
		}
	}

	if (! homedir_s && ! tmpdir_s) {
		fprintf(stderr, _("Error: tmpdir and/or homedir required\n %s\n"), USAGE_STRING);
		return -1;
	}

	if (argc - optind < 1) {
		fprintf(stderr, _("Error: executable required\n %s\n"), USAGE_STRING);
		return -1;
	}

	if (execcon && is_selinux_enabled() != 1) {
		fprintf(stderr, _("Error: execution context specified, but SELinux is not enabled\n"));
		return -1;
	}

	if (set_signal_handles())
		return -1;

	/* set fsuid to ruid */
	/* Changing fsuid is usually required when user-specified directory is
	 * on an NFS mount.  It's also desired to avoid leaking info about
	 * existence of the files not accessible to the user. */
	if (((uid_t)setfsuid(uid) != 0)   && (errno != 0)) {
		fprintf(stderr, _("Error: unable to setfsuid %m\n"));

		return -1;
	}

	/* verify homedir and tmpdir */
	if (homedir_s && (
		verify_directory(homedir_s, NULL, &st_homedir) < 0 ||
		check_owner_uid(uid, homedir_s, &st_homedir))) return -1;
	if (tmpdir_s && (
		verify_directory(tmpdir_s, NULL, &st_tmpdir_s) < 0 ||
		check_owner_uid(uid, tmpdir_s, &st_tmpdir_s))) return -1;
	if ((uid_t)setfsuid(0) != uid) return -1;

	/* create runtime tmpdir */
	if (tmpdir_s && (tmpdir_r = create_tmpdir(tmpdir_s, &st_tmpdir_s,
						  &st_tmpdir_r, pwd, execcon)) == NULL) {
		fprintf(stderr, _("Failed to create runtime temporary directory\n"));
		return -1;
	}

	/* spawn child process */
	child = fork();
	if (child == -1) {
		perror(_("Unable to fork"));
		goto err;
	}

	if (child == 0) {
		char *display = NULL;
		char *LANG = NULL;
		char *RUNTIME_DIR = NULL;
		int rc = -1;
		char *resolved_path = NULL;

		if (unshare(CLONE_NEWNS) < 0) {
			perror(_("Failed to unshare"));
			goto childerr;
		}

		/* Remount / as SLAVE so that nothing mounted in the namespace 
		   shows up in the parent */
		if (mount("none", "/", NULL, MS_SLAVE | MS_REC , NULL) < 0) {
			perror(_("Failed to make / a SLAVE mountpoint\n"));
			goto childerr;
		}

		/* assume fsuid==ruid after this point */
		if ((uid_t)setfsuid(uid) != 0) goto childerr;

		resolved_path = realpath(pwd->pw_dir,NULL);
		if (! resolved_path) goto childerr;

		if (verify_directory(resolved_path, NULL, &st_curhomedir) < 0)
			goto childerr;
		if (check_owner_uid(uid, resolved_path, &st_curhomedir) < 0)
			goto childerr;

		/* mount homedir and tmpdir, in this order */
		if (homedir_s && seunshare_mount(homedir_s, resolved_path,
			&st_homedir) != 0) goto childerr;
		if (tmpdir_s &&	seunshare_mount(tmpdir_r, "/tmp",
			&st_tmpdir_r) != 0) goto childerr;

		if (drop_privs(uid) != 0) goto childerr;

		/* construct a new environment */
		if ((display = getenv("DISPLAY")) != NULL) {
			if ((display = strdup(display)) == NULL) {
				perror(_("Out of memory"));
				goto childerr;
			}
		}

		/* construct a new environment */
		if ((LANG = getenv("LANG")) != NULL) {
			if ((LANG = strdup(LANG)) == NULL) {
				perror(_("Out of memory"));
				goto childerr;
			}
		}

		if ((RUNTIME_DIR = getenv("XDG_RUNTIME_DIR")) != NULL) {
			if ((RUNTIME_DIR = strdup(RUNTIME_DIR)) == NULL) {
				perror(_("Out of memory"));
				goto childerr;
			}
		}

		if ((rc = clearenv()) != 0) {
			perror(_("Failed to clear environment"));
			goto childerr;
		}
		if (display)
			rc |= setenv("DISPLAY", display, 1);
		if (LANG)
			rc |= setenv("LANG", LANG, 1);
		if (RUNTIME_DIR)
			rc |= setenv("XDG_RUNTIME_DIR", RUNTIME_DIR, 1);
		rc |= setenv("HOME", pwd->pw_dir, 1);
		rc |= setenv("SHELL", pwd->pw_shell, 1);
		rc |= setenv("USER", pwd->pw_name, 1);
		rc |= setenv("LOGNAME", pwd->pw_name, 1);
		rc |= setenv("PATH", DEFAULT_PATH, 1);
		if (rc != 0) {
			fprintf(stderr, _("Failed to construct environment\n"));
			goto childerr;
		}

		if (chdir(pwd->pw_dir)) {
			perror(_("Failed to change dir to homedir"));
			goto childerr;
		}
		setsid();

		/* selinux context */
		if (execcon) {
			/* try dyntransition, since no_new_privs can interfere
			 * with setexeccon */
			if (setcon(execcon) != 0) {
				/* failed; fall back to setexeccon */
				if (setexeccon(execcon) != 0) {
					fprintf(stderr, _("Could not set exec context to %s. %s\n"), execcon, strerror(errno));
					goto childerr;
				}
			}
		}

		execv(argv[optind], argv + optind);
		fprintf(stderr, _("Failed to execute command %s: %s\n"), argv[optind], strerror(errno));
childerr:
		free(resolved_path);
		free(display);
		free(LANG);
		free(RUNTIME_DIR);
		exit(-1);
	}

	drop_caps();

	/* parent waits for child exit to do the cleanup */
	waitpid(child, &status, 0);
	status_to_retval(status, status);

	/* Make sure all child processes exit */
	kill(-child,SIGTERM);

	if (execcon && kill_all)
		killall(execcon);

	if (tmpdir_r) cleanup_tmpdir(tmpdir_r, tmpdir_s, pwd, 1);

err:
	free(tmpdir_r);
	return status;
}
