| 
      
      
      From: <mad...@us...> - 2007-10-05 14:05:53
      
     | 
| Revision: 2639
          http://selinux.svn.sourceforge.net/selinux/?rev=2639&view=rev
Author:   madmethod
Date:     2007-10-05 07:05:52 -0700 (Fri, 05 Oct 2007)
Log Message:
-----------
merge r2545:HEAD from trunk
Modified Paths:
--------------
    branches/policyrep/Makefile
    branches/policyrep/checkpolicy/ChangeLog
    branches/policyrep/checkpolicy/VERSION
    branches/policyrep/checkpolicy/checkmodule.c
    branches/policyrep/checkpolicy/checkpolicy.c
    branches/policyrep/checkpolicy/policy_parse.y
    branches/policyrep/checkpolicy/test/dismod.c
    branches/policyrep/checkpolicy/test/dispol.c
    branches/policyrep/libpolicyrep/include/policyrep/policy_base.hpp
    branches/policyrep/libpolicyrep/src/Makefile
    branches/policyrep/libpolicyrep/tests/Makefile
    branches/policyrep/libpolicyrep/tests/libpolicyrep-test.cpp
    branches/policyrep/libselinux/ChangeLog
    branches/policyrep/libselinux/VERSION
    branches/policyrep/libselinux/include/selinux/avc.h
    branches/policyrep/libselinux/include/selinux/selinux.h
    branches/policyrep/libselinux/src/Makefile
    branches/policyrep/libselinux/src/avc.c
    branches/policyrep/libselinux/src/avc_internal.c
    branches/policyrep/libselinux/src/avc_internal.h
    branches/policyrep/libselinux/src/callbacks.c
    branches/policyrep/libselinux/src/fgetfilecon.c
    branches/policyrep/libselinux/src/getfilecon.c
    branches/policyrep/libselinux/src/lgetfilecon.c
    branches/policyrep/libselinux/src/mapping.c
    branches/policyrep/libselinux/src/matchpathcon.c
    branches/policyrep/libselinux/src/selinux.py
    branches/policyrep/libselinux/src/selinuxswig.i
    branches/policyrep/libselinux/src/selinuxswig_python.i
    branches/policyrep/libselinux/src/selinuxswig_wrap.c
    branches/policyrep/libselinux/src/setrans_client.c
    branches/policyrep/libselinux/src/setrans_internal.h
    branches/policyrep/libselinux/src/stringrep.c
    branches/policyrep/libselinux/utils/togglesebool.c
    branches/policyrep/libsemanage/ChangeLog
    branches/policyrep/libsemanage/Makefile
    branches/policyrep/libsemanage/VERSION
    branches/policyrep/libsemanage/src/Makefile
    branches/policyrep/libsemanage/src/debug.c
    branches/policyrep/libsemanage/src/direct_api.c
    branches/policyrep/libsemanage/src/genhomedircon.c
    branches/policyrep/libsemanage/src/genhomedircon.h
    branches/policyrep/libsemanage/src/semanage.py
    branches/policyrep/libsemanage/src/semanage_store.c
    branches/policyrep/libsemanage/src/semanage_store.h
    branches/policyrep/libsemanage/src/semanageswig_wrap.c
    branches/policyrep/libsemanage/src/utilities.c
    branches/policyrep/libsepol/ChangeLog
    branches/policyrep/libsepol/VERSION
    branches/policyrep/libsepol/include/sepol/policydb/policydb.h
    branches/policyrep/libsepol/src/Makefile
    branches/policyrep/libsepol/src/policydb.c
    branches/policyrep/libsepol/src/private.h
    branches/policyrep/libsepol/src/write.c
    branches/policyrep/policycoreutils/ChangeLog
    branches/policyrep/policycoreutils/VERSION
    branches/policyrep/policycoreutils/semanage/semanage
    branches/policyrep/policycoreutils/semanage/seobject.py
    branches/policyrep/policycoreutils/semodule/semodule.8
    branches/policyrep/policycoreutils/semodule/semodule.c
    branches/policyrep/policycoreutils/setfiles/setfiles.c
    branches/policyrep/sepolgen/ChangeLog
    branches/policyrep/sepolgen/VERSION
    branches/policyrep/sepolgen/src/sepolgen/audit.py
    branches/policyrep/sepolgen/src/sepolgen/refparser.py
    branches/policyrep/sepolgen/src/sepolgen/refpolicy.py
    branches/policyrep/sepolgen/tests/test_audit.py
Modified: branches/policyrep/Makefile
===================================================================
--- branches/policyrep/Makefile	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/Makefile	2007-10-05 14:05:52 UTC (rev 2639)
@@ -1,5 +1,5 @@
-SUBDIRS=libsepol libselinux libsemanage libpolicyrep sepolgen checkpolicy policycoreutils # policy
-PYSUBDIRS=libselinux libsemanage
+SUBDIRS=libsepol libselinux libpolicyrep sepolgen policycoreutils # policy checkpolicy
+PYSUBDIRS=libselinux 
 
 ifeq ($(DEBUG),1)
 	export CFLAGS = -g3 -O0 -gdwarf-2 -fno-strict-aliasing -Wall -Wshadow
Modified: branches/policyrep/checkpolicy/ChangeLog
===================================================================
--- branches/policyrep/checkpolicy/ChangeLog	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/checkpolicy/ChangeLog	2007-10-05 14:05:52 UTC (rev 2639)
@@ -1,3 +1,8 @@
+2.0.4 2007-09-18
+	* Merged handle unknown policydb flag support from Eric Paris.
+	  Adds new command line options -U {allow, reject, deny} for selecting
+	  the flag when a base module or kernel policy is built.
+
 2.0.3 2007-05-31
 	* Merged fix for segfault on duplicate require of sensitivity from Caleb Case.
 	* Merged fix for dead URLs in checkpolicy man pages from Dan Walsh.
Modified: branches/policyrep/checkpolicy/VERSION
===================================================================
--- branches/policyrep/checkpolicy/VERSION	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/checkpolicy/VERSION	2007-10-05 14:05:52 UTC (rev 2639)
@@ -1 +1 @@
-2.0.3
+2.0.4
Modified: branches/policyrep/checkpolicy/checkmodule.c
===================================================================
--- branches/policyrep/checkpolicy/checkmodule.c	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/checkpolicy/checkmodule.c	2007-10-05 14:05:52 UTC (rev 2639)
@@ -39,6 +39,7 @@
 static sidtab_t sidtab;
 
 extern int mlspol;
+extern int handle_unknown;
 
 static char *txtfile = "policy.conf";
 static char *binfile = "policy";
@@ -121,6 +122,7 @@
 
 	p->policy_type = policy_type;
 	p->policyvers = policyvers;
+	p->handle_unknown = handle_unknown;
 
 	pf.type = PF_USE_STDIO;
 	pf.fp = outfp;
@@ -135,13 +137,17 @@
 
 static void usage(char *progname)
 {
-	printf("usage:  %s [-V] [-b] [-m] [-M] [-o FILE] [INPUT]\n", progname);
+	printf("usage:  %s [-V] [-b] [-U handle_unknown] [-m] [-M] [-o FILE] [INPUT]\n", progname);
 	printf("Build base and policy modules.\n");
 	printf("Options:\n");
 	printf("  INPUT      build module from INPUT (else read from \"%s\")\n",
 	       txtfile);
 	printf("  -V         show policy versions created by this program\n");
 	printf("  -b         treat input as a binary policy file\n");
+	printf("  -U OPTION  How to handle unknown classes and permissions\n");
+	printf("               deny: Deny unknown kernel checks\n");
+	printf("               reject: Reject loading of policy with unknowns\n");
+	printf("               allow: Allow unknown kernel checks\n");
 	printf("  -m         build a policy module instead of a base module\n");
 	printf("  -M         enable MLS policy\n");
 	printf("  -o FILE    write module to FILE (else just check syntax)\n");
@@ -156,7 +162,7 @@
 	int show_version = 0;
 	policydb_t modpolicydb;
 
-	while ((ch = getopt(argc, argv, "ho:dbVmM")) != EOF) {
+	while ((ch = getopt(argc, argv, "ho:dbVU:mM")) != EOF) {
 		switch (ch) {
 		case 'h':
 			usage(argv[0]);
@@ -171,6 +177,20 @@
 		case 'V':
 			show_version = 1;
 			break;
+		case 'U':
+			if (!strcasecmp(optarg, "deny")) {
+				handle_unknown = DENY_UNKNOWN;
+				break;
+			}
+			if (!strcasecmp(optarg, "reject")) {
+				handle_unknown = REJECT_UNKNOWN;
+				break;
+			}
+			if (!strcasecmp(optarg, "allow")) {
+				handle_unknown = ALLOW_UNKNOWN;
+				break;
+			}
+			usage(argv[0]);
 		case 'm':
 			policy_type = POLICY_MOD;
 			policyvers = MOD_POLICYDB_VERSION_MAX;
@@ -189,6 +209,12 @@
 		exit(0);
 	}
 
+	if (handle_unknown && (policy_type != POLICY_BASE)) {
+		printf("Handling of unknown classes and permissions is only ");
+		printf("valid in the base module\n");
+		exit(1);
+	}
+
 	if (optind != argc) {
 		file = argv[optind++];
 		if (optind != argc)
@@ -214,6 +240,7 @@
 
 		modpolicydb.policy_type = policy_type;
 		modpolicydb.mls = mlspol;
+		modpolicydb.handle_unknown = handle_unknown;
 
 		if (read_source_policy(&modpolicydb, file, argv[0]) == -1) {
 			exit(1);
Modified: branches/policyrep/checkpolicy/checkpolicy.c
===================================================================
--- branches/policyrep/checkpolicy/checkpolicy.c	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/checkpolicy/checkpolicy.c	2007-10-05 14:05:52 UTC (rev 2639)
@@ -90,6 +90,7 @@
 
 extern policydb_t *policydbp;
 extern int mlspol;
+extern int handle_unknown;
 
 static char *txtfile = "policy.conf";
 static char *binfile = "policy";
@@ -99,7 +100,7 @@
 void usage(char *progname)
 {
 	printf
-	    ("usage:  %s [-b] [-d] [-M] [-c policyvers (%d-%d)] [-o output_file] [input_file]\n",
+	    ("usage:  %s [-b] [-d] [-U handle_unknown (allow,deny,reject) [-M] [-c policyvers (%d-%d)] [-o output_file] [input_file]\n",
 	     progname, POLICYDB_VERSION_MIN, POLICYDB_VERSION_MAX);
 	exit(1);
 }
@@ -390,7 +391,7 @@
 	int show_version = 0;
 	struct policy_file pf;
 
-	while ((ch = getopt(argc, argv, "o:dbMVc:")) != EOF) {
+	while ((ch = getopt(argc, argv, "o:dbU:MVc:")) != EOF) {
 		switch (ch) {
 		case 'o':
 			outfile = optarg;
@@ -405,6 +406,20 @@
 		case 'V':
 			show_version = 1;
 			break;
+		case 'U':
+			if (!strcasecmp(optarg, "deny")) {
+				handle_unknown = DENY_UNKNOWN;
+				break;
+			}
+			if (!strcasecmp(optarg, "allow")) {
+				handle_unknown = ALLOW_UNKNOWN;
+				break;
+			}
+			if (!strcasecmp(optarg, "reject")) {
+				handle_unknown = REJECT_UNKNOWN;
+				break;
+			}
+			usage(argv[0]);
 		case 'M':
 			mlspol = 1;
 			break;
@@ -515,6 +530,7 @@
 
 		/* Let sepol know if we are dealing with MLS support */
 		parse_policy.mls = mlspol;
+		parse_policy.handle_unknown = handle_unknown;
 
 		policydbp = &parse_policy;
 
Modified: branches/policyrep/checkpolicy/policy_parse.y
===================================================================
--- branches/policyrep/checkpolicy/policy_parse.y	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/checkpolicy/policy_parse.y	2007-10-05 14:05:52 UTC (rev 2639)
@@ -67,6 +67,7 @@
 static unsigned int pass;
 char *curfile = 0;
 int mlspol = 0;
+int handle_unknown = 0;
 
 extern unsigned long policydb_lineno;
 extern unsigned long source_lineno;
Modified: branches/policyrep/checkpolicy/test/dismod.c
===================================================================
--- branches/policyrep/checkpolicy/test/dismod.c	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/checkpolicy/test/dismod.c	2007-10-05 14:05:52 UTC (rev 2639)
@@ -665,6 +665,17 @@
 	return 0;
 }
 
+int display_handle_unknown(policydb_t * policydb, FILE * out_fp)
+{
+	if (policydb->handle_unknown == ALLOW_UNKNOWN)
+		fprintf(out_fp, "Allow unknown classes and perms\n");
+	else if (policydb->handle_unknown == DENY_UNKNOWN)
+		fprintf(out_fp, "Deny unknown classes and perms\n");
+	else if (policydb->handle_unknown == REJECT_UNKNOWN)
+		fprintf(out_fp, "Reject unknown classes and perms\n");
+	return 0;
+}
+
 static int read_policy(char *filename, policydb_t * policy)
 {
 	FILE *in_fp;
@@ -771,6 +782,7 @@
 	printf("a)  Display avrule requirements\n");
 	printf("b)  Display avrule declarations\n");
 	printf("l)  Link in a module\n");
+	printf("u)  Display the unknown handling setting\n");
 	printf("\n");
 	printf("f)  set output file\n");
 	printf("m)  display menu\n");
@@ -879,6 +891,10 @@
 			fprintf(out_fp, "avrule block declarations:\n");
 			display_avblock(6, 0, &policydb, out_fp);
 			break;
+		case 'u':
+		case 'U':
+			display_handle_unknown(&policydb, out_fp);
+			break;
 		case 'f':
 			printf
 			    ("\nFilename for output (<CR> for screen output): ");
Modified: branches/policyrep/checkpolicy/test/dispol.c
===================================================================
--- branches/policyrep/checkpolicy/test/dispol.c	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/checkpolicy/test/dispol.c	2007-10-05 14:05:52 UTC (rev 2639)
@@ -273,6 +273,17 @@
 	return 1;
 }
 
+int display_handle_unknown(policydb_t * policydb, FILE * out_fp)
+{
+	if (policydb->handle_unknown == ALLOW_UNKNOWN)
+		fprintf(out_fp, "Allow unknown classes and permisions\n");
+	else if (policydb->handle_unknown == DENY_UNKNOWN)
+		fprintf(out_fp, "Deny unknown classes and permisions\n");
+	else if (policydb->handle_unknown == REJECT_UNKNOWN)
+		fprintf(out_fp, "Reject unknown classes and permisions\n");
+	return 0;
+}
+
 int change_bool(char *name, int state, policydb_t * p, FILE * fp)
 {
 	cond_bool_datum_t *bool;
@@ -298,6 +309,7 @@
 	printf("6)  display conditional expressions\n");
 	printf("7)  change a boolean value\n");
 	printf("\n");
+	printf("u)  display unknown handling setting\n");
 	printf("f)  set output file\n");
 	printf("m)  display menu\n");
 	printf("q)  quit\n");
@@ -409,6 +421,10 @@
 			change_bool(name, state, &policydb, out_fp);
 			free(name);
 			break;
+		case 'u':
+		case 'U':
+			display_handle_unknown(&policydb, out_fp);
+			break;
 		case 'f':
 			printf
 			    ("\nFilename for output (<CR> for screen output): ");
Modified: branches/policyrep/libpolicyrep/include/policyrep/policy_base.hpp
===================================================================
--- branches/policyrep/libpolicyrep/include/policyrep/policy_base.hpp	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libpolicyrep/include/policyrep/policy_base.hpp	2007-10-05 14:05:52 UTC (rev 2639)
@@ -24,6 +24,8 @@
         typedef boost::shared_ptr<Parent> ParentPtr;
 
 	class TreeIterator;
+
+	class Policydb;
         
 	// Convenience typedefs
         typedef std::vector<NodePtr> NodeVector;
Modified: branches/policyrep/libpolicyrep/src/Makefile
===================================================================
--- branches/policyrep/libpolicyrep/src/Makefile	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libpolicyrep/src/Makefile	2007-10-05 14:05:52 UTC (rev 2639)
@@ -32,20 +32,20 @@
 	ranlib $@
 
 $(LIBSO): $(LOBJS)
-	g++ $(LDFLAGS) -shared -o $@ $^ -Wl,-soname,$(LIBSO)
+	$(CXX) $(LDFLAGS) -shared -o $@ $^ -Wl,-soname,$(LIBSO)
 	ln -sf $@ $(TARGET) 
 
 $(PYTHONSO): $(PYTHONLOBJ)
-	g++ $(LDFLAGS) -lboost_python -shared -o $@ $< $(LOBJS) -Wl,-soname,$@
+	$(CXX) $(LDFLAGS) -lboost_python -shared -o $@ $< $(LOBJS) -Wl,-soname,$@
 
 $(PYTHONLOBJ): $(PYTHONCPP)
-	g++ $(CFLAGS) -I$(PYINC) -fPIC -DSHARED -c -o $@ $<
+	$(CXX) $(CFLAGS) -I$(PYINC) -fPIC -DSHARED -c -o $@ $<
 
 %.o:  %.cpp
-	g++ $(CFLAGS) -fPIC -c -o $@ $<
+	$(CXX) $(CFLAGS) -fPIC -c -o $@ $<
 
 %.lo:  %.cpp
-	g++ $(CFLAGS) -fPIC -DSHARED -c -o $@ $<
+	$(CXX) $(CFLAGS) -fPIC -DSHARED -c -o $@ $<
 
 policy_parse.cpp: policy_parse.y
 	bison -o policy_parse.cpp -p policyrep -d policy_parse.y
Modified: branches/policyrep/libpolicyrep/tests/Makefile
===================================================================
--- branches/policyrep/libpolicyrep/tests/Makefile	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libpolicyrep/tests/Makefile	2007-10-05 14:05:52 UTC (rev 2639)
@@ -4,7 +4,7 @@
 
 CFLAGS += -g3 -gdwarf-2 -o0 -Wall -W -Wundef -Wmissing-noreturn -Wmissing-format-attribute -Wno-unused-parameter -Werror -I../include
 
-LIBPOLICYREP := ../src/libpolicyrep.a
+LIBPOLICYREP := ../src/libpolicyrep.a ../../libsepol/src/libsepol.a
 
 # test program object files
 objs := $(patsubst %.cpp,%.o,$(wildcard *.cpp))
Modified: branches/policyrep/libpolicyrep/tests/libpolicyrep-test.cpp
===================================================================
--- branches/policyrep/libpolicyrep/tests/libpolicyrep-test.cpp	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libpolicyrep/tests/libpolicyrep-test.cpp	2007-10-05 14:05:52 UTC (rev 2639)
@@ -20,6 +20,7 @@
 
 #include <policyrep/policy.hpp>
 #include <policyrep/parse.hpp>
+#include <policyrep/generate.hpp>
 
 #include <sstream>
 #include <iostream>
@@ -79,6 +80,10 @@
 
 	parsed_mod->append_children(mod->children().begin(), mod->children().end());
 
+
+	Policydb *poldb = new Policydb();
+	poldb->generate(pol);	
+
 }
 
 int main(int argc, char **argv)
Modified: branches/policyrep/libselinux/ChangeLog
===================================================================
--- branches/policyrep/libselinux/ChangeLog	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/ChangeLog	2007-10-05 14:05:52 UTC (rev 2639)
@@ -1,3 +1,20 @@
+2.0.36 2007-09-27
+	* Fix segfault resulting from missing file_contexts file.
+
+2.0.35 2007-09-24
+	* Make netlink socket close-on-exec to avoid descriptor leakage from Dan Walsh.
+	* Pass CFLAGS when using gcc for linking from Dennis Gilmore. 
+
+2.0.34 2007-09-18
+	* Fix selabel option flag setting for 64-bit from Stephen Smalley.
+
+2.0.33 2007-09-12
+	* Re-map a getxattr return value of 0 to a getfilecon return value of -1 with errno EOPNOTSUPP from Stephen Smalley.
+	* Fall back to the compat code for security_class_to_string and security_av_perm_to_string from Stephen Smalley.
+
+2.0.32 2007-09-10
+	* Fix swig binding for rpm_execcon from James Athey.
+
 2.0.31 2007-08-23
 	* Fix file_contexts.homedirs path from Todd Miller.
 
Modified: branches/policyrep/libselinux/VERSION
===================================================================
--- branches/policyrep/libselinux/VERSION	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/VERSION	2007-10-05 14:05:52 UTC (rev 2639)
@@ -1 +1 @@
-2.0.31
+2.0.36
Modified: branches/policyrep/libselinux/include/selinux/avc.h
===================================================================
--- branches/policyrep/libselinux/include/selinux/avc.h	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/include/selinux/avc.h	2007-10-05 14:05:52 UTC (rev 2639)
@@ -182,6 +182,17 @@
 	     const struct avc_lock_callback *lock_callbacks);
 
 /**
+ * avc_open - Initialize the AVC.
+ * @opts: array of selabel_opt structures specifying AVC options or NULL.
+ * @nopts: number of elements in opts array or zero for no options.
+ *
+ * This function is identical to avc_init(), except the message prefix
+ * is set to "avc" and any callbacks desired should be specified via
+ * selinux_set_callback().  No options are currently supported.
+ */
+int avc_open(struct selinux_opt *opts, unsigned nopts);
+
+/**
  * avc_cleanup - Remove unused SIDs and AVC entries.
  *
  * Search the SID table for SID structures with zero
Modified: branches/policyrep/libselinux/include/selinux/selinux.h
===================================================================
--- branches/policyrep/libselinux/include/selinux/selinux.h	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/include/selinux/selinux.h	2007-10-05 14:05:52 UTC (rev 2639)
@@ -142,7 +142,8 @@
 union selinux_callback {
 	/* log the printf-style format and arguments,
 	   with the type code indicating the type of message */
-	int (*func_log) (int type, const char *fmt, ...);
+	int __attribute__((format(printf, 2, 3)))
+	(*func_log) (int type, const char *fmt, ...);
 	/* store a string representation of auditdata (corresponding
 	   to the given security class) into msgbuf. */
 	int (*func_audit) (void *auditdata, security_class_t cls,
@@ -155,6 +156,7 @@
 #define SELINUX_CB_AUDIT	1
 #define SELINUX_CB_VALIDATE	2
 
+extern union selinux_callback selinux_get_callback(int type);
 extern void selinux_set_callback(int type, union selinux_callback cb);
 
 	/* Logging type codes, passed to the logging callback */
Modified: branches/policyrep/libselinux/src/Makefile
===================================================================
--- branches/policyrep/libselinux/src/Makefile	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/src/Makefile	2007-10-05 14:05:52 UTC (rev 2639)
@@ -57,10 +57,10 @@
 	$(CC) $(CFLAGS) -I$(PYINC) -fPIC -DSHARED -c -o $@ $<
 
 $(SWIGSO): $(SWIGLOBJ)
-	$(CC) $(LDFLAGS) -shared -o $@ $< -L. -lselinux -L$(LIBDIR) -Wl,-soname,$@
+	$(CC) $(CFLAGS) $(LDFLAGS) -shared -o $@ $< -L. -lselinux -L$(LIBDIR) -Wl,-soname,$@
 
 $(LIBSO): $(LOBJS)
-	$(CC) $(LDFLAGS) -shared -o $@ $^ -ldl -L$(LIBDIR) -Wl,-soname,$(LIBSO),-z,defs,-z,relro
+	$(CC) $(CFLAGS) $(LDFLAGS) -shared -o $@ $^ -ldl -L$(LIBDIR) -Wl,-soname,$(LIBSO),-z,defs,-z,relro
 	ln -sf $@ $(TARGET) 
 
 %.o:  %.c policy.h
Modified: branches/policyrep/libselinux/src/avc.c
===================================================================
--- branches/policyrep/libselinux/src/avc.c	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/src/avc.c	2007-10-05 14:05:52 UTC (rev 2639)
@@ -157,6 +157,12 @@
 	return rc;
 }
 
+int avc_open(struct selinux_opt *opts __attribute__((unused)),
+	     unsigned nopts __attribute__((unused)))
+{
+    return avc_init("avc", NULL, NULL, NULL, NULL);
+}
+
 int avc_init(const char *prefix,
 	     const struct avc_memory_callback *mem_cb,
 	     const struct avc_log_callback *log_cb,
Modified: branches/policyrep/libselinux/src/avc_internal.c
===================================================================
--- branches/policyrep/libselinux/src/avc_internal.c	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/src/avc_internal.c	2007-10-05 14:05:52 UTC (rev 2639)
@@ -61,7 +61,8 @@
 		rc = fd;
 		goto out;
 	}
-
+	
+	fcntl(fd, F_SETFD, FD_CLOEXEC);
 	if (!blocking && fcntl(fd, F_SETFL, O_NONBLOCK)) {
 		close(fd);
 		rc = -1;
Modified: branches/policyrep/libselinux/src/avc_internal.h
===================================================================
--- branches/policyrep/libselinux/src/avc_internal.h	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/src/avc_internal.h	2007-10-05 14:05:52 UTC (rev 2639)
@@ -13,6 +13,7 @@
 #include <stdlib.h>
 #include <string.h>
 #include <selinux/avc.h>
+#include "callbacks.h"
 #include "dso.h"
 
 /* SID reference counter manipulation */
@@ -93,13 +94,15 @@
   if (avc_func_log) \
     avc_func_log(format); \
   else \
-    fprintf(stderr, format)
+    selinux_log(SELINUX_ERROR, format);
 
 static inline void avc_suppl_audit(void *ptr, security_class_t class,
 				   char *buf, size_t len)
 {
 	if (avc_func_audit)
 		avc_func_audit(ptr, class, buf, len);
+	else
+		selinux_audit(ptr, class, buf, len);
 }
 
 static inline void *avc_create_thread(void (*run) (void))
Modified: branches/policyrep/libselinux/src/callbacks.c
===================================================================
--- branches/policyrep/libselinux/src/callbacks.c	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/src/callbacks.c	2007-10-05 14:05:52 UTC (rev 2639)
@@ -6,6 +6,7 @@
 #include <stdio.h>
 #include <stdlib.h>
 #include <stdarg.h>
+#include <errno.h>
 #include <selinux/selinux.h>
 #include "callbacks.h"
 
@@ -65,3 +66,27 @@
 		break;
 	}
 }
+
+/* callback getting function */
+union selinux_callback
+selinux_get_callback(int type)
+{
+	union selinux_callback cb;
+
+	switch (type) {
+	case SELINUX_CB_LOG:
+		cb.func_log = selinux_log;
+		break;
+	case SELINUX_CB_AUDIT:
+		cb.func_audit = selinux_audit;
+		break;
+	case SELINUX_CB_VALIDATE:
+		cb.func_validate = selinux_validate;
+		break;
+	default:
+		memset(&cb, 0, sizeof(cb));
+		errno = EINVAL;
+		break;
+	}
+	return cb;
+}
Modified: branches/policyrep/libselinux/src/fgetfilecon.c
===================================================================
--- branches/policyrep/libselinux/src/fgetfilecon.c	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/src/fgetfilecon.c	2007-10-05 14:05:52 UTC (rev 2639)
@@ -37,6 +37,11 @@
 		ret = fgetxattr(fd, XATTR_NAME_SELINUX, buf, size - 1);
 	}
       out:
+	if (ret == 0) {
+		/* Re-map empty attribute values to errors. */
+		errno = EOPNOTSUPP;
+		ret = -1;
+	}
 	if (ret < 0)
 		free(buf);
 	else
Modified: branches/policyrep/libselinux/src/getfilecon.c
===================================================================
--- branches/policyrep/libselinux/src/getfilecon.c	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/src/getfilecon.c	2007-10-05 14:05:52 UTC (rev 2639)
@@ -37,6 +37,11 @@
 		ret = getxattr(path, XATTR_NAME_SELINUX, buf, size - 1);
 	}
       out:
+	if (ret == 0) {
+		/* Re-map empty attribute values to errors. */
+		errno = EOPNOTSUPP;
+		ret = -1;
+	}
 	if (ret < 0)
 		free(buf);
 	else
Modified: branches/policyrep/libselinux/src/lgetfilecon.c
===================================================================
--- branches/policyrep/libselinux/src/lgetfilecon.c	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/src/lgetfilecon.c	2007-10-05 14:05:52 UTC (rev 2639)
@@ -37,6 +37,11 @@
 		ret = lgetxattr(path, XATTR_NAME_SELINUX, buf, size - 1);
 	}
       out:
+	if (ret == 0) {
+		/* Re-map empty attribute values to errors. */
+		errno = EOPNOTSUPP;
+		ret = -1;
+	}
 	if (ret < 0)
 		free(buf);
 	else
Modified: branches/policyrep/libselinux/src/mapping.c
===================================================================
--- branches/policyrep/libselinux/src/mapping.c	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/src/mapping.c	2007-10-05 14:05:52 UTC (rev 2639)
@@ -68,6 +68,11 @@
 
 		k = 0;
 		while (p_in->perms && p_in->perms[k]) {
+			/* An empty permission string skips ahead */
+			if (!*p_in->perms[k]) {
+				k++;
+				continue;
+			}
 			p_out->perms[k] = string_to_av_perm(p_out->value,
 							    p_in->perms[k]);
 			if (!p_out->perms[k])
@@ -111,6 +116,7 @@
 
 		for (i=0; i<current_mapping[tclass].num_perms; i++)
 			if (tperm & (1<<i)) {
+				assert(current_mapping[tclass].perms[i]);
 				kperm |= current_mapping[tclass].perms[i];
 				tperm &= ~(1<<i);
 			}
Modified: branches/policyrep/libselinux/src/matchpathcon.c
===================================================================
--- branches/policyrep/libselinux/src/matchpathcon.c	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/src/matchpathcon.c	2007-10-05 14:05:52 UTC (rev 2639)
@@ -119,10 +119,10 @@
 	memset(options, 0, sizeof(options));
 	i = SELABEL_OPT_BASEONLY;
 	options[i].type = i;
-	options[i].value = (char *)(flags & MATCHPATHCON_BASEONLY);
+	options[i].value = (flags & MATCHPATHCON_BASEONLY) ? (char*)1 : NULL;
 	i = SELABEL_OPT_VALIDATE;
 	options[i].type = i;
-	options[i].value = (char *)(flags & MATCHPATHCON_VALIDATE);
+	options[i].value = (flags & MATCHPATHCON_VALIDATE) ? (char*)1 : NULL;
 	notrans = flags & MATCHPATHCON_NOTRANS;
 }
 
@@ -305,8 +305,10 @@
 
 void matchpathcon_fini(void)
 {
-	selabel_close(hnd);
-	hnd = NULL;
+	if (hnd) {
+		selabel_close(hnd);
+		hnd = NULL;
+	}
 }
 
 int matchpathcon(const char *name, mode_t mode, security_context_t * con)
Modified: branches/policyrep/libselinux/src/selinux.py
===================================================================
--- branches/policyrep/libselinux/src/selinux.py	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/src/selinux.py	2007-10-05 14:05:52 UTC (rev 2639)
@@ -277,6 +277,7 @@
 selinux_file_context_local_path = _selinux.selinux_file_context_local_path
 selinux_homedir_context_path = _selinux.selinux_homedir_context_path
 selinux_media_context_path = _selinux.selinux_media_context_path
+selinux_x_context_path = _selinux.selinux_x_context_path
 selinux_contexts_path = _selinux.selinux_contexts_path
 selinux_securetty_types_path = _selinux.selinux_securetty_types_path
 selinux_booleans_path = _selinux.selinux_booleans_path
Modified: branches/policyrep/libselinux/src/selinuxswig.i
===================================================================
--- branches/policyrep/libselinux/src/selinuxswig.i	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/src/selinuxswig.i	2007-10-05 14:05:52 UTC (rev 2639)
@@ -1,22 +1,5 @@
 /* Authors: Dan Walsh
  *          James Athey
- *
- * Copyright (C) 2004-2005 Red Hat
- * Copyright (C) 2007 Tresys Technology, LLC
- *
- *  This library is free software; you can redistribute it and/or
- *  modify it under the terms of the GNU Lesser General Public
- *  License as published by the Free Software Foundation; either
- *  version 2.1 of the License, or (at your option) any later version.
- *
- *  This library 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
- *  Lesser General Public License for more details.
- *
- *  You should have received a copy of the GNU Lesser General Public
- *  License along with this library; if not, write to the Free Software
- *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
  */
 
 %module selinux
Modified: branches/policyrep/libselinux/src/selinuxswig_python.i
===================================================================
--- branches/policyrep/libselinux/src/selinuxswig_python.i	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/src/selinuxswig_python.i	2007-10-05 14:05:52 UTC (rev 2639)
@@ -1,20 +1,4 @@
 /* Author: James Athey
- *
- * Copyright (C) 2007 Tresys Technology, LLC
- *
- *  This library is free software; you can redistribute it and/or
- *  modify it under the terms of the GNU Lesser General Public
- *  License as published by the Free Software Foundation; either
- *  version 2.1 of the License, or (at your option) any later version.
- *
- *  This library 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
- *  Lesser General Public License for more details.
- *
- *  You should have received a copy of the GNU Lesser General Public
- *  License along with this library; if not, write to the Free Software
- *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
  */
 
 %module selinux
@@ -98,4 +82,41 @@
 	}
 }
 
+%typemap(in) char * const [] {
+	int i, size;
+	PyObject * s;
+
+	if (!PySequence_Check($input)) {
+		PyErr_SetString(PyExc_ValueError, "Expected a sequence");
+		return NULL;
+	}
+
+	size = PySequence_Size($input);
+	
+	$1 = (char**) malloc(size + 1);
+
+	for(i = 0; i < size; i++) {
+		if (!PyString_Check(PySequence_GetItem($input, i))) {
+			PyErr_SetString(PyExc_ValueError, "Sequence must contain only strings");
+			return NULL;
+		}
+	}
+		
+	for(i = 0; i < size; i++) {
+		s = PySequence_GetItem($input, i);
+		$1[i] = (char*) malloc(PyString_Size(s) + 1);
+		strcpy($1[i], PyString_AsString(s));
+	}
+	$1[size] = NULL;
+}
+
+%typemap(freearg,match="in") char * const [] {
+	int i = 0;
+	while($1[i]) {
+		free($1[i]);
+		i++;
+	}
+	free($1);
+}
+
 %include "selinuxswig.i"
Modified: branches/policyrep/libselinux/src/selinuxswig_wrap.c
===================================================================
--- branches/policyrep/libselinux/src/selinuxswig_wrap.c	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/src/selinuxswig_wrap.c	2007-10-05 14:05:52 UTC (rev 2639)
@@ -6856,6 +6856,19 @@
 }
 
 
+SWIGINTERN PyObject *_wrap_selinux_x_context_path(PyObject *SWIGUNUSEDPARM(self), PyObject *args) {
+  PyObject *resultobj = 0;
+  char *result = 0 ;
+  
+  if (!PyArg_ParseTuple(args,(char *)":selinux_x_context_path")) SWIG_fail;
+  result = (char *)selinux_x_context_path();
+  resultobj = SWIG_FromCharPtr((const char *)result);
+  return resultobj;
+fail:
+  return NULL;
+}
+
+
 SWIGINTERN PyObject *_wrap_selinux_contexts_path(PyObject *SWIGUNUSEDPARM(self), PyObject *args) {
   PyObject *resultobj = 0;
   char *result = 0 ;
@@ -7078,10 +7091,6 @@
   int res2 ;
   char *buf2 = 0 ;
   int alloc2 = 0 ;
-  void *argp3 = 0 ;
-  int res3 = 0 ;
-  void *argp4 = 0 ;
-  int res4 = 0 ;
   PyObject * obj0 = 0 ;
   PyObject * obj1 = 0 ;
   PyObject * obj2 = 0 ;
@@ -7098,22 +7107,98 @@
     SWIG_exception_fail(SWIG_ArgError(res2), "in method '" "rpm_execcon" "', argument " "2"" of type '" "char const *""'");
   }
   arg2 = (char *)(buf2);
-  res3 = SWIG_ConvertPtr(obj2, &argp3,SWIGTYPE_p_p_char, 0 |  0 );
-  if (!SWIG_IsOK(res3)) {
-    SWIG_exception_fail(SWIG_ArgError(res3), "in method '" "rpm_execcon" "', argument " "3"" of type '" "char *const []""'"); 
-  } 
-  arg3 = (char **)(argp3);
-  res4 = SWIG_ConvertPtr(obj3, &argp4,SWIGTYPE_p_p_char, 0 |  0 );
-  if (!SWIG_IsOK(res4)) {
-    SWIG_exception_fail(SWIG_ArgError(res4), "in method '" "rpm_execcon" "', argument " "4"" of type '" "char *const []""'"); 
-  } 
-  arg4 = (char **)(argp4);
+  {
+    int i, size;
+    PyObject * s;
+    
+    if (!PySequence_Check(obj2)) {
+      PyErr_SetString(PyExc_ValueError, "Expected a sequence");
+      return NULL;
+    }
+    
+    size = PySequence_Size(obj2);
+    
+    arg3 = (char**) malloc(size + 1);
+    
+    for(i = 0; i < size; i++) {
+      if (!PyString_Check(PySequence_GetItem(obj2, i))) {
+        PyErr_SetString(PyExc_ValueError, "Sequence must contain only strings");
+        return NULL;
+      }
+    }
+    
+    for(i = 0; i < size; i++) {
+      s = PySequence_GetItem(obj2, i);
+      arg3[i] = (char*) malloc(PyString_Size(s) + 1);
+      strcpy(arg3[i], PyString_AsString(s));
+    }
+    arg3[size] = NULL;
+  }
+  {
+    int i, size;
+    PyObject * s;
+    
+    if (!PySequence_Check(obj3)) {
+      PyErr_SetString(PyExc_ValueError, "Expected a sequence");
+      return NULL;
+    }
+    
+    size = PySequence_Size(obj3);
+    
+    arg4 = (char**) malloc(size + 1);
+    
+    for(i = 0; i < size; i++) {
+      if (!PyString_Check(PySequence_GetItem(obj3, i))) {
+        PyErr_SetString(PyExc_ValueError, "Sequence must contain only strings");
+        return NULL;
+      }
+    }
+    
+    for(i = 0; i < size; i++) {
+      s = PySequence_GetItem(obj3, i);
+      arg4[i] = (char*) malloc(PyString_Size(s) + 1);
+      strcpy(arg4[i], PyString_AsString(s));
+    }
+    arg4[size] = NULL;
+  }
   result = (int)rpm_execcon(arg1,(char const *)arg2,(char *const (*))arg3,(char *const (*))arg4);
   resultobj = SWIG_From_int((int)(result));
   if (alloc2 == SWIG_NEWOBJ) free((char*)buf2);
+  {
+    int i = 0;
+    while(arg3[i]) {
+      free(arg3[i]);
+      i++;
+    }
+    free(arg3);
+  }
+  {
+    int i = 0;
+    while(arg4[i]) {
+      free(arg4[i]);
+      i++;
+    }
+    free(arg4);
+  }
   return resultobj;
 fail:
   if (alloc2 == SWIG_NEWOBJ) free((char*)buf2);
+  {
+    int i = 0;
+    while(arg3[i]) {
+      free(arg3[i]);
+      i++;
+    }
+    free(arg3);
+  }
+  {
+    int i = 0;
+    while(arg4[i]) {
+      free(arg4[i]);
+      i++;
+    }
+    free(arg4);
+  }
   return NULL;
 }
 
@@ -8002,6 +8087,7 @@
 	 { (char *)"selinux_file_context_local_path", _wrap_selinux_file_context_local_path, METH_VARARGS, NULL},
 	 { (char *)"selinux_homedir_context_path", _wrap_selinux_homedir_context_path, METH_VARARGS, NULL},
 	 { (char *)"selinux_media_context_path", _wrap_selinux_media_context_path, METH_VARARGS, NULL},
+	 { (char *)"selinux_x_context_path", _wrap_selinux_x_context_path, METH_VARARGS, NULL},
 	 { (char *)"selinux_contexts_path", _wrap_selinux_contexts_path, METH_VARARGS, NULL},
 	 { (char *)"selinux_securetty_types_path", _wrap_selinux_securetty_types_path, METH_VARARGS, NULL},
 	 { (char *)"selinux_booleans_path", _wrap_selinux_booleans_path, METH_VARARGS, NULL},
Modified: branches/policyrep/libselinux/src/setrans_client.c
===================================================================
--- branches/policyrep/libselinux/src/setrans_client.c	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/src/setrans_client.c	2007-10-05 14:05:52 UTC (rev 2639)
@@ -1,4 +1,4 @@
-/* Copyright (c) 2006 Trusted Computer Solutions, Inc. 
+/* Author: Trusted Computer Solutions, Inc. 
  * 
  * Modified:
  * Yuichi Nakamura <yn...@hi...> 
Modified: branches/policyrep/libselinux/src/setrans_internal.h
===================================================================
--- branches/policyrep/libselinux/src/setrans_internal.h	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/src/setrans_internal.h	2007-10-05 14:05:52 UTC (rev 2639)
@@ -1,4 +1,4 @@
-/* Copyright (c) 2006 Trusted Computer Solutions, Inc. */
+/* Author: Trusted Computer Solutions, Inc. */
 
 #define SETRANS_UNIX_SOCKET "/var/run/setrans/.setrans-unix"
 
Modified: branches/policyrep/libselinux/src/stringrep.c
===================================================================
--- branches/policyrep/libselinux/src/stringrep.c	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/src/stringrep.c	2007-10-05 14:05:52 UTC (rev 2639)
@@ -471,10 +471,9 @@
 
 	tclass = unmap_class(tclass);
 	node = get_class_cache_entry_value(tclass);
-	if (node == NULL) {
-		errno = EINVAL;
-		return NULL;
-	} else
+	if (node == NULL)
+		return security_class_to_string_compat(tclass);
+	else
 		return node->name;
 }
 
@@ -495,8 +494,7 @@
 			if ((1<<i) & av)
 				return node->perms[i];
 
-	errno = EINVAL;
-	return NULL;
+	return security_av_perm_to_string_compat(tclass,av);
 }
 
 int security_av_string(security_class_t tclass, access_vector_t av, char **res)
Modified: branches/policyrep/libselinux/utils/togglesebool.c
===================================================================
--- branches/policyrep/libselinux/utils/togglesebool.c	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libselinux/utils/togglesebool.c	2007-10-05 14:05:52 UTC (rev 2639)
@@ -1,8 +1,3 @@
-/*
- * Copyright 1999-2004 Gentoo Technologies, Inc.
- * Distributed under the terms of the GNU General Public License v2
- * $Header: /var/cvsroot/gentoo-projects/hardened/policycoreutils-extra/src/toggle_bool.c,v 1.2 2004/06/18 04:09:04 pebenito Exp $
- */
 #include <unistd.h>
 #include <stdio.h>
 #include <stdlib.h>
Modified: branches/policyrep/libsemanage/ChangeLog
===================================================================
--- branches/policyrep/libsemanage/ChangeLog	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libsemanage/ChangeLog	2007-10-05 14:05:52 UTC (rev 2639)
@@ -1,3 +1,25 @@
+2.0.11 2007-09-28
+	* Fix ordering of file_contexts.homedirs from Todd Miller and Dan Walsh.
+
+2.0.10 2007-09-28
+	* Fix error checking on getpw*_r functions from Todd Miller.
+	* Make genhomedircon skip invalid homedir contexts from Todd Miller.
+	* Set default user and prefix from seusers from Dan Walsh.
+	* Add swigify Makefile target from Dan Walsh.
+
+2.0.9 2007-09-24
+	* Pass CFLAGS to CC even on link command, per Dennis Gilmore.
+
+2.0.8 2007-09-19
+	* Clear errno on non-fatal errors to avoid reporting them upon a
+	  later error that does not set errno.
+
+2.0.7 2007-09-19
+	* Improve reporting of system errors, e.g. full filesystem or read-only filesystem from Stephen Smalley.
+
+2.0.6 2007-09-10
+	* Change to use getpw* function calls to the _r versions from Todd Miller.
+
 2.0.5 2007-08-23
 	* Replace genhomedircon script with equivalent functionality within
 	  libsemanage and introduce disable-genhomedircon option in
Modified: branches/policyrep/libsemanage/Makefile
===================================================================
--- branches/policyrep/libsemanage/Makefile	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libsemanage/Makefile	2007-10-05 14:05:52 UTC (rev 2639)
@@ -1,6 +1,9 @@
 all: 
 	$(MAKE) -C src all
 
+swigify:
+	$(MAKE) -C src swigify
+
 pywrap: 
 	$(MAKE) -C src pywrap
 
Modified: branches/policyrep/libsemanage/VERSION
===================================================================
--- branches/policyrep/libsemanage/VERSION	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libsemanage/VERSION	2007-10-05 14:05:52 UTC (rev 2639)
@@ -1 +1 @@
-2.0.5
+2.0.11
Modified: branches/policyrep/libsemanage/src/Makefile
===================================================================
--- branches/policyrep/libsemanage/src/Makefile	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libsemanage/src/Makefile	2007-10-05 14:05:52 UTC (rev 2639)
@@ -47,14 +47,14 @@
 	$(CC) $(CFLAGS) -I$(PYINC) -fPIC -DSHARED -c -o $@ $<
 
 $(SWIGSO): $(SWIGLOBJ)
-	$(CC) $(LDFLAGS) -shared -o $@ $< -L. -lsemanage -l$(PYLIBVER) -L$(LIBDIR) -Wl,-soname,$@,-z,defs
+	$(CC) $(CFLAGS) $(LDFLAGS) -shared -o $@ $< -L. -lsemanage -l$(PYLIBVER) -L$(LIBDIR) -Wl,-soname,$@,-z,defs
 
 $(LIBA): $(OBJS)
 	$(AR) rcs $@ $^
 	ranlib $@
 
 $(LIBSO): $(LOBJS)
-	$(CC) $(LDFLAGS) -shared -o $@ $^ -lsepol -lselinux -lustr -L$(LIBDIR) -Wl,-soname,$(LIBSO),--version-script=libsemanage.map,-z,defs
+	$(CC) $(CFLAGS) $(LDFLAGS) -shared -o $@ $^ -lsepol -lselinux -lustr -L$(LIBDIR) -Wl,-soname,$(LIBSO),--version-script=libsemanage.map,-z,defs
 	ln -sf $@ $(TARGET)
 
 conf-scan.c: conf-scan.l conf-parse.h
Modified: branches/policyrep/libsemanage/src/debug.c
===================================================================
--- branches/policyrep/libsemanage/src/debug.c	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libsemanage/src/debug.c	2007-10-05 14:05:52 UTC (rev 2639)
@@ -23,6 +23,8 @@
 #include <stdarg.h>
 #include <stdlib.h>
 #include <stdio.h>
+#include <errno.h>
+#include <string.h>
 #include "handle.h"
 #include "debug.h"
 
@@ -55,10 +57,12 @@
 {
 
 	FILE *stream = NULL;
+	int errsv = 0;
 
 	switch (semanage_msg_get_level(handle)) {
 
 	case SEMANAGE_MSG_ERR:
+		errsv = errno;
 	case SEMANAGE_MSG_WARN:
 		stream = stderr;
 		break;
@@ -77,6 +81,9 @@
 	vfprintf(stream, fmt, ap);
 	va_end(ap);
 
+	if (errsv)
+		fprintf(stream, " %s.", strerror(errsv));
+
 	fprintf(stream, "\n");
 
 	varg = NULL;
Modified: branches/policyrep/libsemanage/src/direct_api.c
===================================================================
--- branches/policyrep/libsemanage/src/direct_api.c	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libsemanage/src/direct_api.c	2007-10-05 14:05:52 UTC (rev 2639)
@@ -32,6 +32,7 @@
 #include <sys/stat.h>
 #include <sys/types.h>
 #include <limits.h>
+#include <errno.h>
 
 #include "user_internal.h"
 #include "seuser_internal.h"
@@ -540,6 +541,7 @@
 			 * checking is done because this is likely to fail because
 			 * the file does not exist - which is not an error. */
 			unlink(linked_filename);
+			errno = 0;
 		}
 
 		/* ==================== File-backed ================== */
@@ -700,7 +702,7 @@
 		goto cleanup;
 
 	if (sh->do_rebuild || modified) {
-		retval = semanage_install_sandbox(sh);
+		retval = semanage_install_sandbox(sh, out);
 	}
 
       cleanup:
Modified: branches/policyrep/libsemanage/src/genhomedircon.c
===================================================================
--- branches/policyrep/libsemanage/src/genhomedircon.c	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libsemanage/src/genhomedircon.c	2007-10-05 14:05:52 UTC (rev 2639)
@@ -1,5 +1,6 @@
-/* Author: Mark Goldman   <mgo...@tr...>
- * 			Paul Rosenfeld	<pro...@tr...>
+/* Author: Mark Goldman	  <mgo...@tr...>
+ * 	   Paul Rosenfeld <pro...@tr...>
+ * 	   Todd C. Miller <tm...@tr...>
  *
  * Copyright (C) 2007 Tresys Technology, LLC
  *
@@ -23,6 +24,8 @@
 #include <semanage/seusers_policy.h>
 #include <semanage/users_policy.h>
 #include <semanage/user_record.h>
+#include <sepol/context.h>
+#include <sepol/context_record.h>
 #include "semanage_store.h"
 #include "seuser_internal.h"
 #include "debug.h"
@@ -41,6 +44,7 @@
 #include <fcntl.h>
 #include <pwd.h>
 #include <errno.h>
+#include <unistd.h>
 
 /* paths used in get_home_dirs() */
 #define PATH_ETC_USERADD "/etc/default/useradd"
@@ -78,7 +82,10 @@
 	const char *fcfilepath;
 	int usepasswd;
 	const char *homedir_template_path;
+	char *fallback_user;
+	char *fallback_user_prefix;
 	semanage_handle_t *h_semanage;
+	sepol_policydb_t *policydb;
 } genhomedircon_settings_t;
 
 typedef struct user_entry {
@@ -145,12 +152,15 @@
 {
 	semanage_list_t *homedir_list = NULL;
 	semanage_list_t *shells = NULL;
+	char *rbuf = NULL;
 	char *path = NULL;
+	long rbuflen;
 	size_t minuid = 0;
 	size_t minuid_set = 0;
 	size_t temp;
-	struct passwd *pwbuf;
+	struct passwd pwstorage, *pwbuf;
 	struct stat buf;
+	int retval;
 
 	shells = get_shell_list();
 	assert(shells);
@@ -215,8 +225,14 @@
 		minuid_set = 1;
 	}
 
+	rbuflen = sysconf(_SC_GETPW_R_SIZE_MAX);
+	if (rbuflen <= 0)
+		goto fail;
+	rbuf = malloc(rbuflen);
+	if (rbuf == NULL)
+		goto fail;
 	setpwent();
-	for (errno = 0; (pwbuf = getpwent()); errno = 0) {
+	while ((retval = getpwent_r(&pwstorage, rbuf, rbuflen, &pwbuf)) == 0) {
 		if (pwbuf->pw_uid < minuid)
 			continue;
 		if (!semanage_list_find(shells, pwbuf->pw_shell))
@@ -239,11 +255,12 @@
 		free(path);
 	}
 
-	if (errno) {
+	if (retval && retval != ENOENT) {
 		WARN(s->h_semanage, "Error while fetching users.  "
 		     "Returning list so far.");
 	}
 	endpwent();
+	free(rbuf);
 	semanage_list_destroy(&shells);
 	if (semanage_list_sort(&homedir_list))
 		goto fail;
@@ -251,6 +268,8 @@
 	return homedir_list;
 
       fail:
+	endpwent();
+	free(rbuf);
 	semanage_list_destroy(&homedir_list);
 	semanage_list_destroy(&shells);
 	return NULL;
@@ -322,7 +341,7 @@
 static Ustr *replace_all(const char *str, const replacement_pair_t * repl)
 {
 	Ustr *retval = USTR_NULL;
-	int i, num_replaced = 0;
+	int i;
 
 	if (!str || !repl)
 		goto done;
@@ -330,20 +349,60 @@
 		goto done;
 
 	for (i = 0; repl[i].search_for; i++) {
-		num_replaced += ustr_replace_cstr(&retval, repl[i].search_for,
-						  repl[i].replace_with, 0);
+		ustr_replace_cstr(&retval, repl[i].search_for,
+				  repl[i].replace_with, 0);
 	}
-	if (!num_replaced)
+	if (ustr_enomem(retval))
 		ustr_sc_free(&retval);
 
       done:
 	return retval;
 }
 
-static int write_home_dir_context(FILE * out, semanage_list_t * tpl,
-				  const char *user, const char *seuser,
-				  const char *home, const char *role_prefix)
+static const char * extract_context(Ustr *line)
 {
+	const char whitespace[] = " \t\n";
+	size_t off, len;
+
+	/* check for trailing whitespace */
+	off = ustr_spn_chrs_rev(line, 0, whitespace, strlen(whitespace));
+
+	/* find the length of the last field in line */
+	len = ustr_cspn_chrs_rev(line, off, whitespace, strlen(whitespace));
+
+	if (len == 0)
+		return NULL;
+	return ustr_cstr(line) + ustr_len(line) - (len + off);
+}
+
+static int check_line(genhomedircon_settings_t * s, Ustr *line)
+{
+	sepol_context_t *ctx_record = NULL;
+	const char *ctx_str;
+	int result;
+
+	ctx_str = extract_context(line);
+	if (!ctx_str)
+		return STATUS_ERR;
+
+	result = sepol_context_from_string(s->h_semanage->sepolh,
+					   ctx_str, &ctx_record);
+	if (result == STATUS_SUCCESS && ctx_record != NULL) {
+		sepol_msg_set_callback(s->h_semanage->sepolh, NULL, NULL);
+		result = sepol_context_check(s->h_semanage->sepolh,
+					     s->policydb, ctx_record);
+		sepol_msg_set_callback(s->h_semanage->sepolh,
+				       semanage_msg_relay_handler, s->h_semanage);
+		sepol_context_free(ctx_record);
+	}
+	return result;
+}
+
+static int write_home_dir_context(genhomedircon_settings_t * s, FILE * out,
+				  semanage_list_t * tpl, const char *user,
+				  const char *seuser, const char *home,
+				  const char *role_prefix)
+{
 	replacement_pair_t repl[] = {
 		{.search_for = TEMPLATE_SEUSER,.replace_with = seuser},
 		{.search_for = TEMPLATE_HOME_DIR,.replace_with = home},
@@ -357,8 +416,12 @@
 
 	for (; tpl; tpl = tpl->next) {
 		line = replace_all(tpl->data, repl);
-		if (!line || !ustr_io_putfileline(&line, out))
+		if (!line)
 			goto fail;
+		if (check_line(s, line) == STATUS_SUCCESS) {
+			if (!ustr_io_putfileline(&line, out))
+				goto fail;
+		}
 		ustr_sc_free(&line);
 	}
 	return STATUS_SUCCESS;
@@ -368,8 +431,8 @@
 	return STATUS_ERR;
 }
 
-static int write_home_root_context(FILE * out, semanage_list_t * tpl,
-				   char *homedir)
+static int write_home_root_context(genhomedircon_settings_t * s, FILE * out,
+				   semanage_list_t * tpl, char *homedir)
 {
 	replacement_pair_t repl[] = {
 		{.search_for = TEMPLATE_HOME_ROOT,.replace_with = homedir},
@@ -379,8 +442,12 @@
 
 	for (; tpl; tpl = tpl->next) {
 		line = replace_all(tpl->data, repl);
-		if (!line || !ustr_io_putfileline(&line, out))
+		if (!line)
 			goto fail;
+		if (check_line(s, line) == STATUS_SUCCESS) {
+			if (!ustr_io_putfileline(&line, out))
+				goto fail;
+		}
 		ustr_sc_free(&line);
 	}
 	return STATUS_SUCCESS;
@@ -390,8 +457,9 @@
 	return STATUS_ERR;
 }
 
-static int write_user_context(FILE * out, semanage_list_t * tpl, char *user,
-			      char *seuser, char *role_prefix)
+static int write_user_context(genhomedircon_settings_t * s, FILE * out,
+			      semanage_list_t * tpl, const char *user,
+			      const char *seuser, const char *role_prefix)
 {
 	replacement_pair_t repl[] = {
 		{.search_for = TEMPLATE_USER,.replace_with = user},
@@ -403,8 +471,12 @@
 
 	for (; tpl; tpl = tpl->next) {
 		line = replace_all(tpl->data, repl);
-		if (!line || !ustr_io_putfileline(&line, out))
+		if (!line)
 			goto fail;
+		if (check_line(s, line) == STATUS_SUCCESS) {
+			if (!ustr_io_putfileline(&line, out))
+				goto fail;
+		}
 		ustr_sc_free(&line);
 	}
 	return STATUS_SUCCESS;
@@ -484,6 +556,76 @@
 	free(temp);
 }
 
+static int set_fallback_user(genhomedircon_settings_t *s,
+			     const char *user, const char *prefix)
+{
+	char *fallback_user = strdup(user);
+	char *fallback_user_prefix = strdup(prefix);
+
+	if (fallback_user == NULL || fallback_user_prefix == NULL) {
+		free(fallback_user);
+		free(fallback_user_prefix);
+		return STATUS_ERR;
+	}
+
+	free(s->fallback_user);
+	free(s->fallback_user_prefix);
+	s->fallback_user = fallback_user;
+	s->fallback_user_prefix = fallback_user_prefix;
+	return STATUS_SUCCESS;
+}
+
+static int setup_fallback_user(genhomedircon_settings_t * s)
+{
+	semanage_seuser_t **seuser_list = NULL;
+	unsigned int nseusers = 0;
+	semanage_user_key_t *key = NULL;
+	semanage_user_t *u = NULL;
+	const char *name = NULL;
+	const char *seuname = NULL;
+	const char *prefix = NULL;
+	unsigned int i;
+	int retval;
+	int errors = 0;
+
+	retval = semanage_seuser_list(s->h_semanage, &seuser_list, &nseusers);
+	if (retval < 0 || (nseusers < 1)) {
+		/* if there are no users, this function can't do any other work */
+		return errors;
+	}
+
+	for (i = 0; i < nseusers; i++) {
+		name = semanage_seuser_get_name(seuser_list[i]);
+		if (strcmp(name, DEFAULT_LOGIN) == 0) {
+			seuname = semanage_seuser_get_sename(seuser_list[i]);
+
+			/* find the user structure given the name */
+			if (semanage_user_key_create(s->h_semanage, seuname,
+						     &key) < 0) {
+				errors = STATUS_ERR;
+				break;
+			}
+			if (semanage_user_query(s->h_semanage, key, &u) < 0)
+				prefix = name;
+			else
+				prefix = semanage_user_get_prefix(u);
+
+			if (set_fallback_user(s, seuname, prefix) != 0)
+				errors = STATUS_ERR;
+			semanage_user_key_free(key);
+			if (u)
+				semanage_user_free(u);
+			break;
+		}
+	}
+
+	for (i = 0; i < nseusers; i++)
+		semanage_seuser_free(seuser_list[i]);
+	free(seuser_list);
+
+	return errors;
+}
+
 static genhomedircon_user_entry_t *get_users(genhomedircon_settings_t * s,
 					     int *errors)
 {
@@ -496,8 +638,10 @@
 	const char *name = NULL;
 	const char *seuname = NULL;
 	const char *prefix = NULL;
-	struct passwd *pwent = NULL;
+	struct passwd pwstorage, *pwent = NULL;
 	unsigned int i;
+	long rbuflen;
+	char *rbuf = NULL;
 	int retval;
 
 	*errors = 0;
@@ -514,15 +658,25 @@
 	qsort(user_list, nusers, sizeof(semanage_user_t *),
 	      (int (*)(const void *, const void *))&user_sort_func);
 
+	/* Allocate space for the getpwnam_r buffer */
+	rbuflen = sysconf(_SC_GETPW_R_SIZE_MAX);
+	if (rbuflen <= 0)
+		goto cleanup;
+	rbuf = malloc(rbuflen);
+	if (rbuf == NULL)
+		goto cleanup;
+
 	for (i = 0; i < nseusers; i++) {
+		seuname = semanage_seuser_get_sename(seuser_list[i]);
 		name = semanage_seuser_get_name(seuser_list[i]);
-		seuname = semanage_seuser_get_sename(seuser_list[i]);
 
-		if (strcmp(seuname, FALLBACK_USER) == 0)
+		if (strcmp(name,"root") && strcmp(seuname, s->fallback_user) == 0)
 			continue;
-		if (strcmp(seuname, DEFAULT_LOGIN) == 0)
+
+		if (strcmp(name, DEFAULT_LOGIN) == 0)
 			continue;
-		if (strcmp(seuname, TEMPLATE_SEUSER) == 0)
+
+		if (strcmp(name, TEMPLATE_SEUSER) == 0)
 			continue;
 
 		/* find the user structure given the name */
@@ -535,13 +689,13 @@
 			prefix = name;
 		}
 
-		errno = 0;
-		pwent = getpwnam(name);
-		if (!pwent) {
-			if (errno != 0) {
+		retval = getpwnam_r(name, &pwstorage, rbuf, rbuflen, &pwent);
+		if (retval != 0 || pwent == NULL) {
+			if (retval != 0 && retval != ENOENT) {
 				*errors = STATUS_ERR;
 				goto cleanup;
 			}
+
 			WARN(s->h_semanage,
 			     "user %s not in password file", name);
 			continue;
@@ -561,6 +715,7 @@
 	}
 
       cleanup:
+	free(rbuf);
 	if (*errors) {
 		for (; head; pop_user_entry(&head)) {
 			/* the pop function takes care of all the cleanup
@@ -580,7 +735,7 @@
 	return head;
 }
 
-static int write_gen_home_dir_context(FILE * out, genhomedircon_settings_t * s,
+static int write_gen_home_dir_context(genhomedircon_settings_t * s, FILE * out,
 				      semanage_list_t * user_context_tpl,
 				      semanage_list_t * homedir_context_tpl)
 {
@@ -593,13 +748,13 @@
 	}
 
 	for (; users; pop_user_entry(&users)) {
-		if (write_home_dir_context(out, homedir_context_tpl,
+		if (write_home_dir_context(s, out, homedir_context_tpl,
 					   users->name,
 					   users->sename, users->home,
 					   users->prefix)) {
 			return STATUS_ERR;
 		}
-		if (write_user_context(out, user_context_tpl, users->name,
+		if (write_user_context(s, out, user_context_tpl, users->name,
 				       users->sename, users->prefix)) {
 			return STATUS_ERR;
 		}
@@ -640,6 +795,10 @@
 		goto done;
 	}
 
+	if (setup_fallback_user(s) != 0) {
+		retval = STATUS_ERR;
+		goto done;
+	}
 	for (h = homedirs; h; h = h->next) {
 		Ustr *temp = ustr_dup_cstr(h->data);
 
@@ -649,16 +808,17 @@
 			goto done;
 		}
 
-		if (write_home_dir_context(out,
-					   homedir_context_tpl, FALLBACK_USER,
-					   FALLBACK_USER, ustr_cstr(temp),
-					   FALLBACK_USER_PREFIX) !=
+		if (write_home_dir_context(s, out,
+					   homedir_context_tpl,
+					   s->fallback_user, s->fallback_user,
+					   ustr_cstr(temp),
+					   s->fallback_user_prefix) !=
 		    STATUS_SUCCESS) {
 			ustr_sc_free(&temp);
 			retval = STATUS_ERR;
 			goto done;
 		}
-		if (write_home_root_context(out,
+		if (write_home_root_context(s, out,
 					    homeroot_context_tpl,
 					    h->data) != STATUS_SUCCESS) {
 			ustr_sc_free(&temp);
@@ -668,13 +828,14 @@
 
 		ustr_sc_free(&temp);
 	}
-	if (write_user_context(out, user_context_tpl,
-			       ".*", FALLBACK_USER,
-			       FALLBACK_USER_PREFIX) != STATUS_SUCCESS) {
+	if (write_user_context(s, out, user_context_tpl,
+			       ".*", s->fallback_user,
+			       s->fallback_user_prefix) != STATUS_SUCCESS) {
 		retval = STATUS_ERR;
 		goto done;
 	}
-	if (write_gen_home_dir_context(out, s, user_context_tpl,
+
+	if (write_gen_home_dir_context(s, out, user_context_tpl,
 				       homedir_context_tpl) != STATUS_SUCCESS) {
 		retval = STATUS_ERR;
 	}
@@ -689,7 +850,9 @@
 	return retval;
 }
 
-int semanage_genhomedircon(semanage_handle_t * sh, int usepasswd)
+int semanage_genhomedircon(semanage_handle_t * sh,
+			   sepol_policydb_t * policydb,
+			   int usepasswd)
 {
 	genhomedircon_settings_t s;
 	FILE *out = NULL;
@@ -701,8 +864,14 @@
 	    semanage_path(SEMANAGE_TMP, SEMANAGE_HOMEDIR_TMPL);
 	s.fcfilepath = semanage_path(SEMANAGE_TMP, SEMANAGE_FC_HOMEDIRS);
 
+	s.fallback_user = strdup(FALLBACK_USER);
+	s.fallback_user_prefix = strdup(FALLBACK_USER_PREFIX);
+	if (s.fallback_user == NULL || s.fallback_user_prefix == NULL)
+		return STATUS_ERR;
+
 	s.usepasswd = usepasswd;
 	s.h_semanage = sh;
+	s.policydb = policydb;
 
 	if (!(out = fopen(s.fcfilepath, "w"))) {
 		/* couldn't open output file */
@@ -713,5 +882,9 @@
 	retval = write_context_file(&s, out);
 
 	fclose(out);
+
+	free(s.fallback_user);
+	free(s.fallback_user_prefix);
+
 	return retval;
 }
Modified: branches/policyrep/libsemanage/src/genhomedircon.h
===================================================================
--- branches/policyrep/libsemanage/src/genhomedircon.h	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libsemanage/src/genhomedircon.h	2007-10-05 14:05:52 UTC (rev 2639)
@@ -22,6 +22,7 @@
 
 #include "utilities.h"
 
-int semanage_genhomedircon(semanage_handle_t * sh, int usepasswd);
+int semanage_genhomedircon(semanage_handle_t * sh,
+			   sepol_policydb_t * policydb, int usepasswd);
 
 #endif
Modified: branches/policyrep/libsemanage/src/semanage.py
===================================================================
--- branches/policyrep/libsemanage/src/semanage.py	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libsemanage/src/semanage.py	2007-10-05 14:05:52 UTC (rev 2639)
@@ -1,10 +1,16 @@
-# This file was created automatically by SWIG 1.3.29.
+# This file was automatically generated by SWIG (http://www.swig.org).
+# Version 1.3.31
+#
 # Don't modify this file, modify the SWIG interface instead.
 # This file is compatible with both classic and new-style classes.
 
 import _semanage
 import new
 new_instancemethod = new.instancemethod
+try:
+    _swig_property = property
+except NameError:
+    pass # Python < 2.2 doesn't have 'property'.
 def _swig_setattr_nondynamic(self,class_type,name,value,static=1):
     if (name == "thisown"): return self.this.own(value)
     if (name == "this"):
@@ -60,6 +66,7 @@
 semanage_set_reload = _semanage.semanage_set_reload
 semanage_set_rebuild = _semanage.semanage_set_rebuild
 semanage_set_create_store = _semanage.semanage_set_create_store
+semanage_set_disable_dontaudit = _semanage.semanage_set_disable_dontaudit
 semanage_is_managed = _semanage.semanage_is_managed
 semanage_connect = _semanage.semanage_connect
 semanage_disconnect = _semanage.semanage_disconnect
Modified: branches/policyrep/libsemanage/src/semanage_store.c
===================================================================
--- branches/policyrep/libsemanage/src/semanage_store.c	2007-10-05 14:04:01 UTC (rev 2638)
+++ branches/policyrep/libsemanage/src/semanage_store.c	2007-10-05 14:05:52 UTC (rev 2639)
@@ -437,7 +437,7 @@
  * overwrite it.  Returns 0 on success, -1 on error. */
 static int semanage_copy_file(const char *src, const char *dst, mode_t mode)
 {
-	int in, out, retval = 0, amount_read, n;
+	int in, out, retval = 0, amount_read, n, errsv = errno;
 	char tmp[PATH_MAX];
 	char buf[4192];
 
@@ -453,23 +453,32 @@
 		mode = S_IRUSR | S_IWUSR;
 
 	if ((out = open(tmp, O_WRONLY | O_CREAT | O_TRUNC, mode)) == -1) {
+		errsv = errno;
 		close(in);
-		return -1;
+		retval = -1;
+		goto out;
 	}
 	while (retval == 0 && (amount_read = read(in, buf, sizeof(buf))) > 0) {
-		if (write(out, buf, amount_read) != amount_read) {
+		if (write(out, buf, amount_read) < 0) {
+			errsv = errno;
 			retval = -1;
 		}
 	}
-	if (amount_read < 0)
+	if (amount_read < 0) {
+		errsv = errno;
 		retval = -1;
+	}
 	close(in);
-	if (close(out) < 0)
+	if (close(out) < 0) {
+		errsv = errno;
 		retval = -1;
+	}
 
 	if (!retval && rename(tmp, dst) == -1)
 		return -1;
 
+out:
+	errno = errsv;
 	return retval;
 }
 
@@ -558,12 +567,14 @@
 {
 	const char *sandbox = semanage_path(SEMANAGE_TMP, SEMANAGE_TOPLEVEL);
 	struct stat buf;
+	int errsv;
 
 	if (stat(sandbox, &buf) == -1) {
 		if (errno != ENOENT) {
 			ERR(sh, "Error scanning directory %s.", sandbox);
 			return -1;
 		}
+		errno = 0;
 	} else {
 		/* remove the old sandbox */
 		if (semanage_remove_directory(sandbox) != 0) {
@@ -582,7 +593,9 @@
 	return 0;
 
       cleanup:
+	errsv = errno;
 	semanage_remove_directory(sandbox);
+	errno = errsv;
 	return -1;
 }
 
@@ -973,14 +986,14 @@
 		if (!strncmp(buf, "HOME_DIR", 8) ||
 		    !strncmp(buf, "HOME_ROOT", 9) || strstr(buf, "ROLE")) {
 			/* This contains one of the template variables, write it to homedir.template */
-			if (write(hd, buf, strlen(buf)) == 0) {
+			if (write(hd, buf, strlen(buf)) < 0) {
 				ERR(sh, "Write to %s failed.",
 				    semanage_path(SEMANAGE_TMP,
 						  SEMANAGE_HOMEDIR_TMPL));
 				goto cleanup;
 			}
 		} else {
-			if (write(fc, buf, strlen(buf)) == 0) {
+			if (write(fc, buf, strlen(buf)) < 0) {
 				ERR(sh, "Write to %s failed.",
 				    semanage_path(SEMANAGE_TMP, SEMANAGE_FC));
 				goto cleanup;
@@ -1084,6 +1097,7 @@
 		    store_fc_loc);
 		goto cleanup;
 	}
+	errno = 0;
 
 	snprintf(store_seusers, PATH_MAX, "%s%s", storepath, running_seusers);
 	if (semanage_copy_file
@@ -1093,6 +1107,7 @@
 		    store_seusers);
 		goto cleanup;
 	}
+	errno = 0;
 
 	snprintf(store_nc, PATH_MAX, "%s%s", storepath, running_nc);
 	if (semanage_copy_file(active_nc, store_nc, sh->conf->file_mode) == -1
@@ -1100,6 +1115,7 @@
 		ERR(sh, "Could not copy %s ...
 
[truncated message content] |