PERFORCE change 65787 for review

Andrew Reisse areisse at FreeBSD.org
Wed Nov 24 15:58:36 GMT 2004


http://perforce.freebsd.org/chv.cgi?CH=65787

Change 65787 by areisse at areisse_tislabs on 2004/11/24 15:58:17

	Begin merging checkpolicy changes from selinux version 
	2004081908.

Affected files ...

.. //depot/projects/trustedbsd/sebsd/contrib/sebsd/checkpolicy/checkpolicy.c#7 integrate
.. //depot/projects/trustedbsd/sebsd/contrib/sebsd/checkpolicy/checkpolicy.h#3 integrate
.. //depot/projects/trustedbsd/sebsd/contrib/sebsd/checkpolicy/genpolusers.c#1 branch
.. //depot/projects/trustedbsd/sebsd/contrib/sebsd/checkpolicy/policy_parse.y#4 integrate
.. //depot/projects/trustedbsd/sebsd/contrib/sebsd/checkpolicy/policy_scan.l#3 integrate
.. //depot/projects/trustedbsd/sebsd/contrib/sebsd/checkpolicy/users.l#1 branch
.. //depot/projects/trustedbsd/sebsd/contrib/sebsd/checkpolicy/users.y#1 branch
.. //depot/projects/trustedbsd/sebsd/contrib/sebsd/checkpolicy/write.c#2 integrate

Differences ...

==== //depot/projects/trustedbsd/sebsd/contrib/sebsd/checkpolicy/checkpolicy.c#7 (text+ko) ====

@@ -1,10 +1,21 @@
 
 /*
- * Author : Stephen Smalley (NAI Labs), <ssmalley at nai.com> 
+ * Author : Stephen Smalley, <sds at epoch.ncsc.mil> 
+ */
+
+/* Updated: Karl MacMillan <kmacmillan at tresys.com>
+ *
+ * 	Added conditional policy language extensions
+ *
+ * Updated: James Morris <jmorris at intercode.com.au>
+ *
+ *	Added IPv6 support.
  *
- * The policy compiler was originally written while I was employed by NSA,
- * but I have implemented a number of extensions and revisions since 
- * joining NAI Labs.
+ * Copyright (C) 2003 - 2004 Tresys Technology, LLC
+ * Copyright (C) 2003 Red Hat, Inc., James Morris <jmorris at redhat.com>
+ *	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, version 2.
  */
 
 /* FLASK */
@@ -27,6 +38,11 @@
  * If '-d' is specified, then checkpolicy permits the user 
  * to interactively test the security server functions with 
  * the loaded policy configuration.
+ *
+ * If '-c' is specified, then the supplied parameter is used to
+ * determine which policy version to use for generating binary
+ * policy.  This is for compatibility with older kernels. If any
+ * booleans or conditional rules are thrown away a warning is printed.
  */
 
 #ifdef __FreeBSD__
@@ -59,6 +75,8 @@
 extern queue_t id_queue;
 extern unsigned int policydb_errors;
 extern unsigned long policydb_lineno;
+extern unsigned long source_lineno;
+extern char source_file[];
 extern unsigned int pass;
 
 extern FILE *yyin;
@@ -68,6 +86,7 @@
 char *txtfile = "policy.conf";
 char *binfile = "policy";
 
+unsigned int policyvers = POLICYDB_VERSION_MAX;
 int selinux_enforcing = 1;
 
 int avc_ss_reset(__u32 seqno)
@@ -77,15 +96,16 @@
 
 void usage(char *progname)
 {
-	printf("usage:  %s [-b] [-d] [-o output_file] [input_file]\n", progname);
+	printf("usage:  %s [-b] [-d] [-c policyvers (%d-%d)] [-o output_file] [input_file]\n",
+		progname, POLICYDB_VERSION_MIN, POLICYDB_VERSION_MAX);
 	exit(1);
 }
 
 static int print_sid(security_id_t sid,
-		     context_struct_t * context, void *data)
+		     context_struct_t * context __attribute__ ((unused)), void *data __attribute__ ((unused)))
 {
 	security_context_t scontext;
-	unsigned int scontext_len;
+	size_t scontext_len;
 	int rc;
 
 	rc = security_sid_to_context(sid, &scontext, &scontext_len);
@@ -112,7 +132,7 @@
 	return 0;
 }
 
-static int type_attr_remove(hashtab_key_t key, hashtab_datum_t datum, void *p)
+static int type_attr_remove(hashtab_key_t key __attribute__ ((unused)), hashtab_datum_t datum, void *p __attribute__ ((unused)))
 {
 	type_datum_t *typdatum;
 
@@ -249,14 +269,49 @@
 }
 #endif 
 
-extern char *av_to_string(__u32 tclass, access_vector_t av);
+static void cond_check_type_rules_list(cond_av_list_t *list)
+{
+	cond_av_list_t *cur = list;
+
+	while (cur) {
+		if (cur->node->datum.specified & AVTAB_TYPE) {
+			if (avtab_search(&policydbp->te_avtab, &cur->node->key, AVTAB_TYPE)) {
+				fprintf(stderr, "conditional type rule for (%s, %s : %s) conflicts with entry in base policy; "
+					"conditional rule discarded.\n", policydbp->p_type_val_to_name[cur->node->key.source_type-1],
+					policydbp->p_type_val_to_name[cur->node->key.target_type-1],
+					policydbp->p_class_val_to_name[cur->node->key.target_class-1]);
+				cur->node->parse_context = (void*)0;
+			} else {
+				cur->node->parse_context = (void*)1;
+			}
+		} else {
+			cur->node->parse_context = (void*)1;
+		}
+		cur = cur->next;
+	}
+}
+
+/* check for duplicate type rules - this has to be done after all of
+ * the parsing is finished because the conditional and base type rules
+ * are collected in the same pass */
+static void cond_check_type_rules(void)
+{
+	cond_list_t *node;
+
+	for (node = policydbp->cond_list; node != NULL; node = node->next) {
+		cond_check_type_rules_list(node->true_list);
+		cond_check_type_rules_list(node->false_list);
+	}
+}
+
+extern char *av_to_string(uint32_t tclass, access_vector_t av);
 
-void check_assertion_helper(int stype, int ttype, ebitmap_t *tclasses, 
+void check_assertion_helper(unsigned int stype, unsigned int ttype, ebitmap_t *tclasses, 
 			    access_vector_t *avp, unsigned long line) 
 {
 	avtab_key_t avkey;
 	avtab_datum_t *avdatump;
-	int k;
+	unsigned int k;
 	
 
 	for (k = ebitmap_startbit(tclasses); k < ebitmap_length(tclasses); k++) {
@@ -282,7 +337,7 @@
 void check_assertions(void) 
 {
 	te_assert_t *a, *tmp;
-	int i, j;
+	unsigned int i, j;
 
 	a = te_assertions;
 	while (a) {
@@ -308,6 +363,77 @@
 	}
 }
 
+int display_bools()
+{
+	int i;
+
+	for (i = 0; i < policydbp->p_bools.nprim; i++) {
+		printf("%s : %d\n", policydbp->p_bool_val_to_name[i],
+			policydbp->bool_val_to_struct[i]->state);
+	}
+	return 0;
+}
+
+void display_expr(cond_expr_t *exp)
+{
+
+	cond_expr_t *cur;
+	for (cur = exp; cur != NULL; cur = cur->next) {
+		switch (cur->expr_type) {
+		case COND_BOOL:
+			printf("%s ", policydbp->p_bool_val_to_name[cur->bool - 1]);
+			break;
+		case COND_NOT:
+			printf("! ");
+			break;
+		case COND_OR:
+			printf("|| ");
+			break;
+		case COND_AND:
+			printf("&& ");
+			break;
+		case COND_XOR:
+			printf("^ ");
+			break;
+		case COND_EQ:
+			printf("== ");
+			break;
+		case COND_NEQ:
+			printf("!= ");
+			break;
+		default:
+			printf("error!");
+			break;
+		}
+	}
+}
+
+int display_cond_expressions()
+{
+	cond_node_t *cur;
+
+	for (cur = policydbp->cond_list; cur != NULL; cur = cur->next) {
+		printf("expression: ");
+		display_expr(cur->expr);
+		printf("current state: %d\n", cur->cur_state);
+	}
+	return 0;
+}
+
+int change_bool(char *name, int state)
+{
+	cond_bool_datum_t *bool;
+
+	bool = hashtab_search(policydbp->p_bools.table, name);
+	if (bool == NULL) {
+		printf("Could not find bool %s\n", name);
+		return -1;
+	}
+	bool->state = state;
+	evaluate_conds(policydbp);
+	return 0;
+}
+
 int main(int argc, char **argv)
 {
 	security_class_t tclass;
@@ -327,7 +453,7 @@
 	struct stat sb;
 	size_t filelen;
 
-	while ((ch = getopt(argc, argv, "o:dbV")) != EOF) {
+	while ((ch = getopt(argc, argv, "o:dbVc:")) != EOF) {
 		switch (ch) {
 		case 'o':
 			outfile = optarg;
@@ -340,17 +466,39 @@
 			debug = 1;
 			break;
 		case 'V':
-#ifdef CONFIG_SECURITY_SELINUX_MLS
-			printf("%d-mls\n", POLICYDB_VERSION);
-#else
-			printf("%d\n", POLICYDB_VERSION);
-#endif
-			exit(0);
+			show_version = 1;
+			break;
+		case 'c': {
+			long int n = strtol(optarg, NULL, 10);
+			if (errno) {
+				fprintf(stderr, "Invalid policyvers specified: %s\n", optarg);
+				usage(argv[0]);
+				exit(1);
+			}
+			if (n < POLICYDB_VERSION_MIN || n > POLICYDB_VERSION_MAX) {
+				fprintf(stderr, "policyvers value %ld not in range %d-%d\n",
+					n, POLICYDB_VERSION_MIN, POLICYDB_VERSION_MAX);
+				usage(argv[0]);
+				exit(1);
+			}
+			if (policyvers != n)
+				policyvers = n;
+			break;
+		}
 		default:
 			usage(argv[0]);
 		}
 	}
 
+	if (show_version) {
+#ifdef CONFIG_SECURITY_SELINUX_MLS	
+		printf("%d-mls (compatibility range %d-%d)\n", policyvers, POLICYDB_VERSION_MAX, POLICYDB_VERSION_MIN);
+#else
+		printf("%d (compatibility range %d-%d)\n", policyvers, POLICYDB_VERSION_MAX, POLICYDB_VERSION_MIN);
+#endif
+		exit(0);
+	}
+
 	if (optind != argc) {
 		file = argv[optind++];
 		if (optind != argc)
@@ -402,7 +550,7 @@
 		yyin = fopen(file, "r");
 		if (!yyin) {
 			fprintf(stderr, "%s:  unable to open %s\n", argv[0], 
-			    file);
+				file);
 			exit(1);
 		}
 
@@ -423,6 +571,8 @@
 		}
 		rewind(yyin);
 		policydb_lineno = 1;
+		source_file[0] = '\0';
+		source_lineno = 1;
 		yyrestart(yyin);
 		pass = 2;
 		if (yyparse() || policydb_errors) {
@@ -431,10 +581,19 @@
 		}
 		queue_destroy(id_queue);
 
+		cond_check_type_rules();
+		cond_optimize_lists(policydb.cond_list);
+
 		check_assertions();
 		if (policydb_errors) 
 			exit(1);
 
+		if (policyvers >= POLICYDB_VERSION_NLCLASS &&
+		    policydb.p_classes.nprim < SECCLASS_NETLINK_DNRT_SOCKET) {
+			fprintf(stderr, "%s:  policy lacks new netlink classes, unable to generate policy version %d\n", argv[0], policyvers);
+			exit(1);
+		}
+	    
 		/* remove type attributes */
 		hashtab_map_remove_on_error(policydb.p_types.table, 
 					    type_attr_remove, 0, 0);
@@ -448,7 +607,7 @@
 
 	if (outfile) {
 		printf("%s:  writing binary representation (version %d) to %s\n",
-		       argv[0], POLICYDB_VERSION, outfile);
+		       argv[0], policyvers, outfile);
 		outfp = fopen(outfile, "w");
 		if (!outfp) {
 			perror(outfile);
@@ -484,6 +643,9 @@
 	printf("c)  Call fs_use\n");
 	printf("d)  Call genfs_sid\n");
 	printf("e)  Call get_user_sids\n");
+	printf("f)  display conditional bools\n");
+	printf("g)  display conditional expressions\n");
+	printf("h)  change a boolean value\n");
 #ifdef EQUIVTYPES
 	printf("z)  Show equivalent types\n");
 #endif
@@ -730,14 +892,47 @@
 			printf("if_sid %d default_msg_sid %d\n",
 			       ssid, tsid);
 			break;
-		case 'b':
+		case 'b': {
+			char *p;
+			int family, len;
+			struct in_addr addr4;
+			struct in6_addr addr6;
+			
+			printf("protocol family? ");
+			fgets(ans, sizeof(ans), stdin);
+			ans[strlen(ans) - 1] = 0;
+			if (!strcasecmp(ans, "ipv4"))
+				family = AF_INET;
+			else if (!strcasecmp(ans, "ipv6"))
+				family = AF_INET6;
+			else {
+				printf("unknown protocol family\n");
+				break;
+			}
+			
 			printf("node address?  ");
 			fgets(ans, sizeof(ans), stdin);
 			ans[strlen(ans) - 1] = 0;
+			
+			if (family == AF_INET) {
+				p = (char *)&addr4;
+				len = sizeof(addr4);
+			} else {
+				p = (char *)&addr6;
+				len = sizeof(addr6);
+			}
+			
+			if (inet_pton(family, ans, p) < 1) {
+				printf("error parsing address\n");
+				break;
+			}
+
+			sepol_node_sid(family, p, len, &ssid);
 			addr = inet_addr(ans);
 			security_node_sid(AF_INET, &addr, sizeof addr, &ssid);
 			printf("sid %d\n", ssid);
 			break;
+		}	
 		case 'c':
 			printf("fstype?  ");
 			fgets(ans, sizeof(ans), stdin);
@@ -825,6 +1020,37 @@
 				break;
 			}
 			break;
+		case 'f':
+			display_bools();
+			break;
+		case 'g':
+			display_cond_expressions();
+			break;
+		case 'h':
+			printf("name? ");
+			fgets(ans, sizeof(ans), stdin);
+			ans[strlen(ans) - 1] = 0;
+			
+			name = malloc((strlen(ans) + 1) * sizeof(char));
+			if (name == NULL) {
+				fprintf(stderr, "couldn't malloc string.\n");
+				break;
+			}
+			strcpy(name, ans);
+
+
+			printf("state? ");
+			fgets(ans, sizeof(ans), stdin);
+			ans[strlen(ans) - 1] = 0;
+
+			if (atoi(ans))
+				state = 1;
+			else
+				state = 0;
+
+			change_bool(name, state);
+			free(name);
+			break;
 #ifdef EQUIVTYPES
 		case 'z':
 			identify_equiv_types();

==== //depot/projects/trustedbsd/sebsd/contrib/sebsd/checkpolicy/checkpolicy.h#3 (text+ko) ====


==== //depot/projects/trustedbsd/sebsd/contrib/sebsd/checkpolicy/policy_parse.y#4 (text+ko) ====

@@ -3,6 +3,16 @@
  * Author : Stephen Smalley, <sds at epoch.ncsc.mil> 
  */
 
+/* Updated: David Caplan, <dac at tresys.com>
+ *
+ * 	Added conditional policy language extensions
+ *
+ * Copyright (C) 2003 - 2004 Tresys Technology, LLC
+ *	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, version 2.
+ */
+
 /* FLASK */
 
 %{
@@ -20,12 +30,22 @@
 #include "flask.h"
 #include "security.h"
 
+/* 
+ * We need the following so we have a valid error return code in yacc
+ * when we have a parse error for a conditional rule.  We can't check 
+ * for NULL (ie 0) because that is a potentially valid return.
+ */
+static cond_av_list_t *conditional_unused_error_code;
+#define COND_ERR (cond_av_list_t *)&conditional_unused_error_code
+
 #define TRUE 1
 #define FALSE 0
 
 policydb_t *policydbp;
 queue_t id_queue = 0;
 unsigned int pass;
+char *curfile = 0;
+unsigned int curline; 
 
 extern unsigned long policydb_lineno;
 
@@ -48,6 +68,7 @@
 static int define_common_base(void);
 static int define_av_base(void);
 static int define_attrib(void);
+static int define_typealias(void);
 static int define_type(int alias);
 static int define_compute_type(int which);
 static int define_te_avtab(int which);
@@ -57,24 +78,38 @@
 static int define_role_trans(void);
 static int define_role_allow(void);
 static int define_constraint(constraint_expr_t *expr);
-static constraint_expr_t *define_cexpr(__u32 expr_type, void *arg1, void* arg2);
+static int define_bool();
+static int define_conditional(cond_expr_t *expr,cond_av_list_t *t_list, cond_av_list_t *f_list );
+static cond_expr_t *define_cond_expr(uint32_t expr_type, void *arg1, void* arg2);
+static cond_av_list_t *define_cond_pol_list(cond_av_list_t *avlist, cond_av_list_t *stmt);
+static cond_av_list_t *define_cond_compute_type(int which);
+static cond_av_list_t *define_cond_te_avtab(int which);
+static cond_av_list_t *cond_list_append(cond_av_list_t *sl, avtab_key_t *key, avtab_datum_t *datum);
+static void cond_reduce_insert_list(cond_av_list_t *new, cond_av_list_t **active, cond_av_list_t **inactive, int state ); 
+static uintptr_t define_cexpr(uint32_t expr_type, uintptr_t arg1, uintptr_t arg2);
 static int define_user(void);
 static int parse_security_context(context_struct_t *c);
 static int define_initial_sid_context(void);
 static int define_fs_use(int behavior);
 static int define_genfs_context(int has_type);
-static int define_fs_context(int major, int minor);
-static int define_port_context(int low, int high);
+static int define_fs_context(unsigned int major, unsigned int minor);
+static int define_port_context(unsigned int low, unsigned int high);
 static int define_netif_context(void);
-static int define_node_context(int addr, int mask);
+static int define_ipv4_node_context(unsigned int addr, unsigned int mask);
+static int define_ipv6_node_context(void);
 %}
 
 %union {
-	int val;
+	unsigned int val;
+	uintptr_t valptr;
 	void *ptr;
 }
 
-%type <ptr> role_def roles cexpr cexpr_prim op roleop
+%type <ptr> cond_expr cond_expr_prim cond_pol_list
+%type <ptr> cond_allow_def cond_auditallow_def cond_auditdeny_def cond_dontaudit_def
+%type <ptr> cond_transition_def cond_te_avtab_def cond_rule_def
+%type <ptr> role_def roles
+%type <valptr> cexpr cexpr_prim op roleop
 %type <val> ipv4_addr_def number
 
 %token PATH
@@ -86,10 +121,14 @@
 %token SID
 %token ROLE
 %token ROLES
+%token TYPEALIAS
 %token TYPE
 %token TYPES
 %token ALIAS
 %token ATTRIBUTE
+%token BOOL
+%token IF
+%token ELSE
 %token TYPE_TRANSITION
 %token TYPE_MEMBER
 %token TYPE_CHANGE
@@ -113,22 +152,26 @@
 %token FSUSEXATTR FSUSETASK FSUSETRANS
 %token GENFSCON
 %token U1 U2 R1 R2 T1 T2
-%token NOT AND OR 
+%token NOT AND OR XOR
+%token CTRUE CFALSE
 %token IDENTIFIER
 %token USER_IDENTIFIER
 %token NUMBER
 %token EQUALS
 %token NOTEQUAL
+%token IPV6_ADDR
 
 %left OR
+%left XOR
 %left AND
 %right NOT
 %left EQUALS NOTEQUAL
 %%
-policy			: classes initial_sids access_vectors 
+policy			: classes initial_sids access_vectors
                           { if (pass == 1) { if (policydb_index_classes(policydbp)) return -1; } }
 			  opt_mls te_rbac users opt_constraints 
-			  { if (pass == 2) { if (policydb_index_others(policydbp)) return -1;} } 
+                         { if (pass == 1) { if (policydb_index_bools(policydbp)) return -1;}
+			   if (pass == 2) { if (policydb_index_others(policydbp, 1)) return -1;} } 
 			  initial_sid_contexts opt_fs_contexts fs_uses opt_genfs_contexts net_contexts 
 			;
 classes			: class_def 
@@ -202,7 +245,7 @@
 			{if (define_level()) return -1;}
 			| LEVEL identifier ';' 
 			{if (define_level()) return -1;}
-			;
+						;
 base_perms		: opt_common_base av_base
 			;
 opt_common_base         : common_base
@@ -244,8 +287,11 @@
 			;
 te_decl			: attribute_def
                         | type_def
+                        | typealias_def
+                        | bool_def
                         | transition_def
                         | te_avtab_def
+                        | cond_stmt_def
 			;
 attribute_def           : ATTRIBUTE identifier ';'
                         { if (define_attrib()) return -1;}
@@ -255,9 +301,105 @@
 	                | TYPE identifier opt_attr_list ';'
                         {if (define_type(0)) return -1;}
     			;
+typealias_def           : TYPEALIAS identifier alias_def ';'
+			{if (define_typealias()) return -1;}
+			;
 opt_attr_list           : ',' id_comma_list
 			| 
 			;
+bool_def                : BOOL identifier bool_val ';'
+                        {if (define_bool()) return -1;}
+                        ;
+bool_val                : CTRUE
+ 			{ if (insert_id("T",0)) return -1; }
+                        | CFALSE
+			{ if (insert_id("F",0)) return -1; }
+                        ;
+cond_stmt_def           : IF cond_expr '{' cond_pol_list '}'
+                        { if (pass == 2) { if (define_conditional((cond_expr_t*)$2, (cond_av_list_t*)$4,(cond_av_list_t*) 0) < 0) return -1;  }}
+                        | IF cond_expr '{' cond_pol_list '}' ELSE '{' cond_pol_list '}'
+                        { if (pass == 2) { if (define_conditional((cond_expr_t*)$2,(cond_av_list_t*)$4,(cond_av_list_t*)$8) < 0 ) return -1;  }}       
+                        | IF cond_expr '{' cond_pol_list '}' ELSE '{' '}'
+                        { if (pass == 2) { if (define_conditional((cond_expr_t*)$2,(cond_av_list_t*)$4,(cond_av_list_t*) 0) < 0 ) return -1;  }}       
+                        | IF cond_expr '{' '}' ELSE '{' cond_pol_list '}'
+                        { if (pass == 2) { if (define_conditional((cond_expr_t*)$2,(cond_av_list_t*) 0,(cond_av_list_t*) $7) < 0 ) return -1;  }}       
+                        | IF cond_expr '{' '}' ELSE '{' '}'
+                        /* do nothing */
+                        | IF cond_expr '{' '}' 
+                        /* do nothing */
+                        ;
+cond_expr               : '(' cond_expr ')'
+			{ $$ = $2;}
+			| NOT cond_expr
+			{ $$ = define_cond_expr(COND_NOT, $2, 0);
+			  if ($$ == 0) return -1; }
+			| cond_expr AND cond_expr
+			{ $$ = define_cond_expr(COND_AND, $1, $3);
+			  if ($$ == 0) return  -1; }
+			| cond_expr OR cond_expr
+			{ $$ = define_cond_expr(COND_OR, $1, $3);
+			  if ($$ == 0) return   -1; }
+			| cond_expr XOR cond_expr
+			{ $$ = define_cond_expr(COND_XOR, $1, $3);
+			  if ($$ == 0) return  -1; }
+			| cond_expr EQUALS cond_expr
+			{ $$ = define_cond_expr(COND_EQ, $1, $3);
+			  if ($$ == 0) return  -1; }
+			| cond_expr NOTEQUAL cond_expr
+			{ $$ = define_cond_expr(COND_NEQ, $1, $3);
+			  if ($$ == 0) return  -1; }
+			| cond_expr_prim
+			{ $$ = $1; }
+			;
+cond_expr_prim          : identifier
+                        { $$ = define_cond_expr(COND_BOOL,0, 0);
+			  if ($$ == COND_ERR) return   -1; }
+                        ;
+cond_pol_list           : cond_rule_def
+                        { $$ = define_cond_pol_list((cond_av_list_t *) 0, (cond_av_list_t *)$1);}
+                        | cond_pol_list cond_rule_def 
+                        { $$ = define_cond_pol_list((cond_av_list_t *)$1, (cond_av_list_t *)$2); }
+			;
+cond_rule_def           : cond_transition_def
+                        { $$ = $1; }
+                        | cond_te_avtab_def
+                        { $$ = $1; }
+                        ;
+cond_transition_def	: TYPE_TRANSITION names names ':' names identifier ';'
+                        { $$ = define_cond_compute_type(AVTAB_TRANSITION) ;
+                          if ($$ == COND_ERR) return -1;}
+                        | TYPE_MEMBER names names ':' names identifier ';'
+                        { $$ = define_cond_compute_type(AVTAB_MEMBER) ;
+                          if ($$ ==  COND_ERR) return -1;}
+                        | TYPE_CHANGE names names ':' names identifier ';'
+                        { $$ = define_cond_compute_type(AVTAB_CHANGE) ;
+                          if ($$ == COND_ERR) return -1;}
+    			;
+cond_te_avtab_def	: cond_allow_def
+                          { $$ = $1; }
+			| cond_auditallow_def
+			  { $$ = $1; }
+			| cond_auditdeny_def
+			  { $$ = $1; }
+			| cond_dontaudit_def
+			  { $$ = $1; }
+			;
+cond_allow_def		: ALLOW names names ':' names names  ';'
+			{ $$ = define_cond_te_avtab(AVTAB_ALLOWED) ;
+                          if ($$ == COND_ERR) return -1; }
+		        ;
+cond_auditallow_def	: AUDITALLOW names names ':' names names ';'
+			{ $$ = define_cond_te_avtab(AVTAB_AUDITALLOW) ;
+                          if ($$ == COND_ERR) return -1; }
+		        ;
+cond_auditdeny_def	: AUDITDENY names names ':' names names ';'
+			{ $$ = define_cond_te_avtab(AVTAB_AUDITDENY) ;
+                          if ($$ == COND_ERR) return -1; }
+		        ;
+cond_dontaudit_def	: DONTAUDIT names names ':' names names ';'
+			{ $$ = define_cond_te_avtab(-AVTAB_AUDITDENY);
+                          if ($$ == COND_ERR) return -1; }
+		        ;
 transition_def		: TYPE_TRANSITION names names ':' names identifier ';'
                         {if (define_compute_type(AVTAB_TRANSITION)) return -1;}
                         | TYPE_MEMBER names names ':' names identifier ';'
@@ -331,64 +473,64 @@
 			{ $$ = $1; }
 			;
 cexpr_prim		: U1 op U2
-			{ $$ = define_cexpr(CEXPR_ATTR, (void*)CEXPR_USER, $2);
+			{ $$ = define_cexpr(CEXPR_ATTR, CEXPR_USER, $2);
 			  if ($$ == 0) return -1; }
 			| R1 roleop R2
-			{ $$ = define_cexpr(CEXPR_ATTR, (void*)CEXPR_ROLE, $2);
+			{ $$ = define_cexpr(CEXPR_ATTR, CEXPR_ROLE, $2);
 			  if ($$ == 0) return -1; }
 			| T1 op T2
-			{ $$ = define_cexpr(CEXPR_ATTR, (void*)CEXPR_TYPE, $2);
+			{ $$ = define_cexpr(CEXPR_ATTR, CEXPR_TYPE, $2);
 			  if ($$ == 0) return -1; }
 			| U1 op { if (insert_separator(1)) return -1; } user_names_push
-			{ $$ = define_cexpr(CEXPR_NAMES, (void*)CEXPR_USER, $2);
+			{ $$ = define_cexpr(CEXPR_NAMES, CEXPR_USER, $2);
 			  if ($$ == 0) return -1; }
 			| U2 op { if (insert_separator(1)) return -1; } user_names_push
-			{ $$ = define_cexpr(CEXPR_NAMES, (void*)(CEXPR_USER | CEXPR_TARGET), $2);
+			{ $$ = define_cexpr(CEXPR_NAMES, (CEXPR_USER | CEXPR_TARGET), $2);
 			  if ($$ == 0) return -1; }
 			| R1 op { if (insert_separator(1)) return -1; } names_push
-			{ $$ = define_cexpr(CEXPR_NAMES, (void*)CEXPR_ROLE, $2);
+			{ $$ = define_cexpr(CEXPR_NAMES, CEXPR_ROLE, $2);
 			  if ($$ == 0) return -1; }
 			| R2 op { if (insert_separator(1)) return -1; } names_push
-			{ $$ = define_cexpr(CEXPR_NAMES, (void*)(CEXPR_ROLE | CEXPR_TARGET), $2);
+			{ $$ = define_cexpr(CEXPR_NAMES, (CEXPR_ROLE | CEXPR_TARGET), $2);
 			  if ($$ == 0) return -1; }
 			| T1 op { if (insert_separator(1)) return -1; } names_push
-			{ $$ = define_cexpr(CEXPR_NAMES, (void*)CEXPR_TYPE, $2);
+			{ $$ = define_cexpr(CEXPR_NAMES, CEXPR_TYPE, $2);
 			  if ($$ == 0) return -1; }
 			| T2 op { if (insert_separator(1)) return -1; } names_push
-			{ $$ = define_cexpr(CEXPR_NAMES, (void*)(CEXPR_TYPE | CEXPR_TARGET), $2);
+			{ $$ = define_cexpr(CEXPR_NAMES, (CEXPR_TYPE | CEXPR_TARGET), $2);
 			  if ($$ == 0) return -1; }
 			| SAMEUSER
-			{ $$ = define_cexpr(CEXPR_ATTR, (void*)CEXPR_USER, (void*)CEXPR_EQ);
+			{ $$ = define_cexpr(CEXPR_ATTR, CEXPR_USER, CEXPR_EQ);
 			  if ($$ == 0) return -1; }
 			| SOURCE ROLE { if (insert_separator(1)) return -1; } names_push
-			{ $$ = define_cexpr(CEXPR_NAMES, (void*)CEXPR_ROLE, (void*)CEXPR_EQ);
+			{ $$ = define_cexpr(CEXPR_NAMES, CEXPR_ROLE, CEXPR_EQ);
 			  if ($$ == 0) return -1; }
 			| TARGET ROLE { if (insert_separator(1)) return -1; } names_push
-			{ $$ = define_cexpr(CEXPR_NAMES, (void*)(CEXPR_ROLE | CEXPR_TARGET), (void*)CEXPR_EQ);
+			{ $$ = define_cexpr(CEXPR_NAMES, (CEXPR_ROLE | CEXPR_TARGET), CEXPR_EQ);
 			  if ($$ == 0) return -1; }
 			| ROLE roleop
-			{ $$ = define_cexpr(CEXPR_ATTR, (void*)CEXPR_ROLE, (void*)$2);
+			{ $$ = define_cexpr(CEXPR_ATTR, CEXPR_ROLE, $2);
 			  if ($$ == 0) return -1; }
 			| SOURCE TYPE { if (insert_separator(1)) return -1; } names_push
-			{ $$ = define_cexpr(CEXPR_NAMES, (void*)CEXPR_TYPE, (void*)CEXPR_EQ);
+			{ $$ = define_cexpr(CEXPR_NAMES, CEXPR_TYPE, CEXPR_EQ);
 			  if ($$ == 0) return -1; }
 			| TARGET TYPE { if (insert_separator(1)) return -1; } names_push
-			{ $$ = define_cexpr(CEXPR_NAMES, (void*)(CEXPR_TYPE | CEXPR_TARGET), (void*)CEXPR_EQ);
+			{ $$ = define_cexpr(CEXPR_NAMES, (CEXPR_TYPE | CEXPR_TARGET), CEXPR_EQ);
 			  if ($$ == 0) return -1; }
 			;
 op			: EQUALS
-			{ $$ = (void*)CEXPR_EQ; }
+			{ $$ = CEXPR_EQ; }
 			| NOTEQUAL
-			{ $$ = (void*)CEXPR_NEQ; }
+			{ $$ = CEXPR_NEQ; }
 			;
 roleop			: op 
 			{ $$ = $1; }
 			| DOM
-			{ $$ = (void*)CEXPR_DOM; }
+			{ $$ = CEXPR_DOM; }
 			| DOMBY
-			{ $$ = (void*)CEXPR_DOMBY; }
+			{ $$ = CEXPR_DOMBY; }
 			| INCOMP
-			{ $$ = (void*)CEXPR_INCOMP; }
+			{ $$ = CEXPR_INCOMP; }
 			;
 users			: user_def
 			| users user_def
@@ -452,7 +594,9 @@
 			| node_contexts node_context_def
 			;
 node_context_def	: NODECON ipv4_addr_def ipv4_addr_def security_context_def
-			{if (define_node_context($2,$3)) return -1;}
+			{if (define_ipv4_node_context($2,$3)) return -1;}
+			| NODECON ipv6_addr ipv6_addr security_context_def
+			{if (define_ipv6_node_context()) return -1;}
 			;
 fs_uses                 : fs_use_def
                         | fs_uses fs_use_def
@@ -524,6 +668,8 @@
 			| tilde nested_id_set
 	 		{ if (insert_id("~", 0)) return -1; 
 			  if (insert_separator(0)) return -1; }
+                        | identifier '-' { if (insert_id("-", 0)) return -1; } identifier 
+			{ if (insert_separator(0)) return -1; }
 			;
 tilde_push              : tilde
                         { if (insert_id("~", 1)) return -1; }
@@ -550,7 +696,7 @@
                         ;
 nested_id_list          : nested_id_element | nested_id_list nested_id_element
                         ;
-nested_id_element       : identifier | nested_id_set
+nested_id_element       : identifier | '-' { if (insert_id("-", 0)) return -1; } identifier | nested_id_set
                         ;
 identifier		: IDENTIFIER
 			{ if (insert_id(yytext,0)) return -1; }
@@ -578,7 +724,12 @@
 number			: NUMBER 
 			{ $$ = strtoul(yytext,NULL,0); }
 			;
+ipv6_addr		: IPV6_ADDR
+			{ if (insert_id(yytext,0)) return -1; }
+			;
 %%
+#define DEBUG 1
+
 static int insert_separator(int push)
 {
 	int error;
@@ -1410,16 +1561,12 @@
 		while ((base = queue_remove(id_queue))) {
 			if (!strcmp(base, "read")) {
 				perdatum->base_perms |= MLS_BASE_READ;
-				cladatum->mlsperms.read |= (1 << (perdatum->value - 1));
 			} else if (!strcmp(base, "write")) {
 				perdatum->base_perms |= MLS_BASE_WRITE;
-				cladatum->mlsperms.write |= (1 << (perdatum->value - 1));
 			} else if (!strcmp(base, "readby")) {
 				perdatum->base_perms |= MLS_BASE_READBY;
-				cladatum->mlsperms.readby |= (1 << (perdatum->value - 1));
 			} else if (!strcmp(base, "writeby")) {
 				perdatum->base_perms |= MLS_BASE_WRITEBY;
-				cladatum->mlsperms.writeby |= (1 << (perdatum->value - 1));
 			} else if (strcmp(base, "none")) {
 				sprintf(errormsg, "base permission %s is not defined", base);
 				yyerror(errormsg);
@@ -1432,6 +1579,9 @@
 		free(id);
 	}
 
+	/* Set MLS base permission masks */
+	hashtab_map(cladatum->permissions.table, common_base_set, cladatum);
+
 	return 0;
 #else
 	yyerror("MLS base permission definition in non-MLS configuration");
@@ -1481,7 +1631,62 @@
 	return 0;
 }
 
+static int define_typealias(void)
+{
+	char *id;
+	type_datum_t *t, *aliasdatum;;
+	int ret;
+
+
+	if (pass == 2) {
+		while ((id = queue_remove(id_queue))) 
+			free(id);
+		return 0;
+	}
+
+	id = (char *) queue_remove(id_queue);
+	if (!id) {
+		yyerror("no type name for typealias definition?");
+		return -1;
+	}
 
+	t = hashtab_search(policydbp->p_types.table, id);
+	if (!t || t->isattr) {
+		sprintf(errormsg, "unknown type %s", id);
+		yyerror(errormsg);
+		free(id);
+		return -1;
+	}
+
+	while ((id = queue_remove(id_queue))) {
+		aliasdatum = (type_datum_t *) malloc(sizeof(type_datum_t));
+		if (!aliasdatum) {
+			yyerror("out of memory");
+			return -1;
+		}
+		memset(aliasdatum, 0, sizeof(type_datum_t));
+		aliasdatum->value = t->value;
+
+		ret = hashtab_insert(policydbp->p_types.table,
+				     (hashtab_key_t) id, (hashtab_datum_t) aliasdatum);
+
+		if (ret == HASHTAB_PRESENT) {
+			sprintf(errormsg, "name conflict for type alias %s", id);
+			yyerror(errormsg);
+			free(aliasdatum);
+			free(id);
+			return -1;
+		}
+		if (ret == HASHTAB_OVERFLOW) {
+			yyerror("hash table overflow");
+			free(aliasdatum);
+			free(id);
+			return -1;
+		}
+	}
+	return 0;
+}
+
 static int define_type(int alias)
 {
 	char *id;
@@ -1665,15 +1870,19 @@
 
 
 static int set_types(ebitmap_t *set,
-		     char *id)
+		     ebitmap_t *negset,
+		     char *id,
+		     int *add)
 {
 	type_datum_t *t;
-	int i;
+	unsigned int i;
 
 	if (strcmp(id, "*") == 0) {
-		/* set all types */
-		for (i = 0; i < policydbp->p_types.nprim; i++) 
-			ebitmap_set_bit(set, i, TRUE);
+		/* set all types not in negset */
+		for (i = 0; i < policydbp->p_types.nprim; i++) {
+			if (!ebitmap_get_bit(negset, i))
+				ebitmap_set_bit(set, i, TRUE);
+		}
 		free(id);
 		return 0;
 	}
@@ -1690,6 +1899,12 @@
 		return 0;
 	}
 
+	if (strcmp(id, "-") == 0) {
+		*add = 0;
+		free(id);
+		return 0;
+	}	
+
 	t = hashtab_search(policydbp->p_types.table, id);
 	if (!t) {
 		sprintf(errormsg, "unknown type %s", id);
@@ -1699,18 +1914,42 @@
 	}
 
 	if (t->isattr) {
-		/* set all types with this attribute */
+		/* set or clear all types with this attribute,
+		   but do not set anything explicitly cleared previously */
 		for (i = ebitmap_startbit(&t->types); i < ebitmap_length(&t->types); i++) {
 			if (!ebitmap_get_bit(&t->types, i)) 
 				continue;		
-			ebitmap_set_bit(set, i, TRUE);
+			if (!(*add)) {
+				ebitmap_set_bit(set, i, FALSE);
+				ebitmap_set_bit(negset, i, TRUE);
+			} else if (!ebitmap_get_bit(negset, i)) {
+				ebitmap_set_bit(set, i, TRUE);
+#if VERBOSE
+			} else {
+				char *name = type_val_to_name(i+1);
+				sprintf(errormsg, "ignoring %s due to prior -%s", name, name);
+				yywarn(errormsg);
+#endif
+			}
 		}
 	} else {
-		/* set one type */
-		ebitmap_set_bit(set, t->value - 1, TRUE);
+		/* set or clear one type, but do not set anything
+		   explicitly cleared previously */	
+		if (!(*add)) {
+			ebitmap_set_bit(set, t->value - 1, FALSE);

>>> TRUNCATED FOR MAIL (1000 lines) <<<
To Unsubscribe: send mail to majordomo at trustedbsd.org
with "unsubscribe trustedbsd-cvs" in the body of the message



More information about the trustedbsd-cvs mailing list