[policycoreutils/f15/master] Fix error message in seunshare, check for tmpdir existance before unlink.

Daniel J Walsh dwalsh at fedoraproject.org
Thu Mar 3 20:51:55 UTC 2011


commit 4d63979d6d49e93f476143b5e4b15c54044dd8a0
Author: Dan Walsh <dwalsh at redhat.com>
Date:   Thu Mar 3 15:51:42 2011 -0500

    Fix error message in seunshare, check for tmpdir existance before unlink.

 policycoreutils-rhat.patch |  135 ++++++++++++++++++++++++++------------------
 policycoreutils.spec       |    7 ++-
 2 files changed, 86 insertions(+), 56 deletions(-)
---
diff --git a/policycoreutils-rhat.patch b/policycoreutils-rhat.patch
index dcc70e4..fa2b034 100644
--- a/policycoreutils-rhat.patch
+++ b/policycoreutils-rhat.patch
@@ -2147,7 +2147,7 @@ index 0000000..6063d6a
 +and
 +.I Thomas Liu <tliu at fedoraproject.org>
 diff --git a/policycoreutils/sandbox/seunshare.c b/policycoreutils/sandbox/seunshare.c
-index ec692e7..995f78a 100644
+index ec692e7..a273d3f 100644
 --- a/policycoreutils/sandbox/seunshare.c
 +++ b/policycoreutils/sandbox/seunshare.c
 @@ -1,28 +1,34 @@
@@ -2190,7 +2190,7 @@ index ec692e7..995f78a 100644
  #ifdef USE_NLS
  #include <locale.h>		/* for setlocale() */
  #include <libintl.h>		/* for gettext() */
-@@ -39,6 +45,12 @@
+@@ -39,6 +45,13 @@
  #define MS_PRIVATE 1<<18
  #endif
  
@@ -2199,11 +2199,12 @@ index ec692e7..995f78a 100644
 +#endif
 +
 +#define BUF_SIZE 1024
++static char template[] = "/tmp/.sandboxXXXXXX";
 +
  /**
   * This function will drop all capabilities 
   * Returns zero on success, non-zero otherwise
-@@ -46,9 +58,9 @@
+@@ -46,9 +59,9 @@
  static int drop_capabilities(uid_t uid)
  {
  	capng_clear(CAPNG_SELECT_BOTH);
@@ -2214,7 +2215,7 @@ index ec692e7..995f78a 100644
  	/* Change uid */
  	if (setresuid(uid, uid, uid)) {
  		fprintf(stderr, _("Error changing uid, aborting.\n"));
-@@ -90,18 +102,37 @@ static int set_signal_handles(void)
+@@ -90,18 +103,37 @@ static int set_signal_handles(void)
   * If so, it returns 0. If it can not figure this out or they are different, it returns -1.
   */
  static int verify_mount(const char *mntdir, struct passwd *pwd) {
@@ -2259,7 +2260,7 @@ index ec692e7..995f78a 100644
  }
  
  /**
-@@ -131,45 +162,330 @@ static int verify_shell(const char *shell_name)
+@@ -131,45 +163,356 @@ static int verify_shell(const char *shell_name)
  	return rc;
  }
  
@@ -2294,8 +2295,9 @@ index ec692e7..995f78a 100644
  		return -1;
 +
 +	return 0;
-+}
-+
+ }
+ 
+-#define USAGE_STRING _("USAGE: seunshare [ -v ] [ -t tmpdir ] [ -h homedir ] -- CONTEXT executable [args] ")
 +static int set_label(char *srcdir) {
 +	int rc = -1;
 +	security_context_t filecon = NULL;
@@ -2306,22 +2308,21 @@ index ec692e7..995f78a 100644
 +	rc =setfilecon("/tmp", filecon);
 +	if (rc < 0) {
 +		fprintf(stderr, _("Failed to set context %s on /tmp: %s\n"), filecon, strerror(errno));
-+		freecon(filecon);
 +		goto err;
 +	}
 +	rc = 0;
 +err:
 +	freecon(filecon);
 +	return rc;
- }
++}
  
--#define USAGE_STRING _("USAGE: seunshare [ -v ] [ -t tmpdir ] [ -h homedir ] -- CONTEXT executable [args] ")
-+static char *seunshare_mount_tmp(void) {
+-int main(int argc, char **argv) {
+-	int rc;
++static int seunshare_mount_tmp(const char *tmpdir) {
 +
-+	char * tmpdir = NULL;
 +	int rc = -1;
 +	if (verbose)
-+		printf("Mount tmpfs on /tmp\n");
++		printf("Mount %s on /tmp\n", tmpdir);
 +
 +	int flags = MS_REC | MS_NODEV | MS_NOSUID | MS_NOEXEC;
 +	if (mount("/tmp", "/tmp",  NULL, MS_BIND | flags, NULL) < 0) {
@@ -2340,23 +2341,7 @@ index ec692e7..995f78a 100644
 +	}
 +
 +	if (mount("/var/tmp", "/var/tmp", NULL, MS_PRIVATE | flags, NULL) < 0) {
-+		fprintf(stderr, _("Failed to make /tmp private: %s\n"), strerror(errno));
-+		goto err;
-+	}
-+
-+	if (seteuid(0)) {
-+		fprintf(stderr, _("Error changing uid, aborting.\n"));
-+		goto err;
-+	}
-+/*	if (setegid(0)) {
-+		fprintf(stderr, _("Error changing gid, aborting.\n"));
-+		goto err;
-+	}
-+*/
-+	char template[] = "/tmp/.sandboxXXXXXX";
-+	tmpdir = mkdtemp(template);
-+	if  (! tmpdir) {
-+		fprintf(stderr, _("Failed to make temporary directory: %s\n"), strerror(errno));
++		fprintf(stderr, _("Failed to make /var/tmp private: %s\n"), strerror(errno));
 +		goto err;
 +	}
 +
@@ -2370,18 +2355,9 @@ index ec692e7..995f78a 100644
 +		goto err;
 +	}
 +
-+	if (chmod("/tmp", strtol("1770",0,8))) {
-+		fprintf(stderr, _("Unable to change mode on /tmp: %s\n"), strerror(errno));
-+		goto err;
-+	}
-+
 +	rc = 0;
 +err:
-+	if (rc < 0) {
-+		unlink(tmpdir);
-+		return NULL;
-+	}
-+	return tmpdir;
++	return rc;
 +}
 +
 +#define USAGE_STRING _("USAGE: seunshare [ -v ] [ -c ] -h homedir [-Z CONTEXT] --  executable [args] ")
@@ -2574,13 +2550,64 @@ index ec692e7..995f78a 100644
 +	free(cpus);
 +	return rc;
 +}
- 
- int main(int argc, char **argv) {
--	int rc;
-+	int rc = -1;
++
++/*
++  seunshare will create a tmpdi  in /tmp, with root ownership
++  Then the process forks and 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 *gen_tmpdir() {
++
++	char * tmpdir = NULL;
  	int status = -1;
--
++	int rootchild = 0;
++
++	if (seteuid(0)) {
++		fprintf(stderr, _("Error changing uid, aborting.\n"));
++		goto err;
++	}
++
++	tmpdir = mkdtemp(template);
++	if  (! tmpdir) {
++		fprintf(stderr, _("Failed to make temporary directory: %s\n"), strerror(errno));
++		goto err;
++	}
+ 
 -	security_context_t scontext;
++	if (chmod(tmpdir, 01770)) {
++		fprintf(stderr, _("Unable to change mode on /tmp: %s\n"), strerror(errno));
++		rmdir(tmpdir);
++		tmpdir=NULL;
++		goto err;
++	}
++
++	rootchild = fork();
++	if (rootchild == -1) {
++		perror(_("Unable to fork"));
++		goto err;
++	}
++
++	if (rootchild) {
++		capng_clear(CAPNG_SELECT_BOTH);
++		if ((capng_lock() != 0) || 
++		    capng_apply(CAPNG_SELECT_BOTH)) {
++			perror(_("Failed to drop all capabilities"));
++			exit(-1);
++		}
++		waitpid(rootchild, &status, 0);
++		if(rmdir(tmpdir) < 0)
++			fprintf(stderr, _("Unlinking %s: %s\n"), tmpdir, strerror(errno));
++		exit(0);
++	}
++err:
++	return tmpdir;
++}
++
++int main(int argc, char **argv) {
++	int rc = -1;
++	int status = -1;
 +	security_context_t execcon = NULL;
 +	char *tmpdir = NULL;
 +	char *cpbuf=NULL;
@@ -2600,7 +2627,7 @@ index ec692e7..995f78a 100644
  		{NULL, 0, 0, 0}
  	};
  
-@@ -180,6 +496,12 @@ int main(int argc, char **argv) {
+@@ -180,6 +523,12 @@ int main(int argc, char **argv) {
  		return -1;
  	}
  
@@ -2613,7 +2640,7 @@ index ec692e7..995f78a 100644
  	struct passwd *pwd=getpwuid(uid);
  	if (!pwd) {
  		perror(_("getpwduid failed"));
-@@ -192,80 +514,99 @@ int main(int argc, char **argv) {
+@@ -192,80 +541,99 @@ int main(int argc, char **argv) {
  	}
  
  	while (1) {
@@ -2690,6 +2717,8 @@ index ec692e7..995f78a 100644
 +	if (verify_mount(pwd->pw_dir, pwd) < 0)	return -1;
 +	if (verify_mount(homedir_s, pwd) < 0)	return -1;
 +
++	if (! (tmpdir = gen_tmpdir())) return -1;
++
          if (unshare(CLONE_NEWNS) < 0) {
  		perror(_("Failed to unshare"));
  		return -1;
@@ -2706,10 +2735,8 @@ index ec692e7..995f78a 100644
 -				
 -		if (tmpdir_s && seunshare_mount(tmpdir_s, "/tmp", pwd) < 0)
 -				return -1;
-+	if ((tmpdir = seunshare_mount_tmp()) == NULL) return -1;
++	if (seunshare_mount_tmp(tmpdir) < 0) return -1;
 +
-+	/* you must mount the homedir first, since the tmpdir will use  
-+	   the file context from the homedir to set its label*/
 +	if (seunshare_mount_home(homedir_s, pwd) < 0) return -1;
 +
 +	if (asprintf(&tmpdir_s, "%s/.sandboxtmp", pwd->pw_dir) < 0) {
@@ -2728,7 +2755,7 @@ index ec692e7..995f78a 100644
 +
 +	/* Since we have dropped capabilities and we have reset the UID,
 +	   the system call below should be safe */
-+	if (asprintf(&cpbuf, "/usr/bin/rsync -r %s/ /tmp", tmpdir_s) < 0) {
++	if (asprintf(&cpbuf, "/usr/bin/rsync -tr %s/ /tmp 2>/dev/null", tmpdir_s) < 0) {
 +		fprintf(stderr, _("Failed to allocate copy command: %s\n"), strerror(errno));
 +		goto err;
 +	}
@@ -2748,7 +2775,7 @@ index ec692e7..995f78a 100644
  	}
  
  	if (!child) {
-@@ -286,11 +627,15 @@ int main(int argc, char **argv) {
+@@ -286,11 +654,15 @@ int main(int argc, char **argv) {
  			exit(-1);
  		}
  		
@@ -2769,7 +2796,7 @@ index ec692e7..995f78a 100644
  		}
  
  		if (display) 
-@@ -305,17 +650,26 @@ int main(int argc, char **argv) {
+@@ -305,17 +677,26 @@ int main(int argc, char **argv) {
  			perror(_("Failed to change dir to homedir"));
  			exit(-1);
  		}
@@ -2780,7 +2807,7 @@ index ec692e7..995f78a 100644
  		exit(-1);
  	} else {
  		waitpid(child, &status, 0);
-+		if (asprintf(&cpbuf, "/usr/bin/rsync --delete -ur /tmp/ %s 2>/dev/null", tmpdir_s) < 0) {
++		if (asprintf(&cpbuf, "/usr/bin/rsync --delete --exclude=.X11-unix -utr /tmp/ %s 2>/dev/null", tmpdir_s) < 0) {
 +			fprintf(stderr, _("Failed to allocate copy command: %s\n"), strerror(errno));
 +		} else {
 +			rc = system(cpbuf);
diff --git a/policycoreutils.spec b/policycoreutils.spec
index 645980d..d816023 100644
--- a/policycoreutils.spec
+++ b/policycoreutils.spec
@@ -7,7 +7,7 @@
 Summary: SELinux policy core utilities
 Name:	 policycoreutils
 Version: 2.0.85
-Release: 13%{?dist}
+Release: 14%{?dist}
 License: GPLv2
 Group:	 System Environment/Base
 # Based on git repository with tag 20101221
@@ -168,7 +168,7 @@ The policycoreutils-python package contains the scripts to create graphical sand
 %defattr(-,root,root,-)
 %{_datadir}/sandbox/sandboxX.sh
 %{_datadir}/sandbox/start
-%attr(0755,root,root) %caps(cap_setpcap,cap_setuid,cap_setgid,cap_fowner,cap_dac_override,cap_sys_admin,cap_sys_nice=pe) %{_sbindir}/seunshare
+%attr(0755,root,root) %caps(cap_setpcap,cap_setuid,cap_fowner,cap_dac_override,cap_sys_admin,cap_sys_nice=pe) %{_sbindir}/seunshare
 %{_mandir}/man8/seunshare.8*
 %{_mandir}/man5/sandbox.conf.5*
 
@@ -329,6 +329,9 @@ fi
 exit 0
 
 %changelog
+* Thu Mar 3 2011 Dan Walsh <dwalsh at redhat.com> 2.0.85-14
+- Fix error message in seunshare, check for tmpdir existance before unlink.
+
 * Fri Feb 25 2011 Dan Walsh <dwalsh at redhat.com> 2.0.85-13
 - Rewrite seunshare to make sure /tmp is mounted stickybit owned by root
 - Only allow names in polgengui that contain letters and numbers


More information about the scm-commits mailing list