All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH 0/6 v3] libsepol/cil: Add high-level language line marking support
@ 2016-05-05 20:44 James Carter
  2016-05-05 20:44 ` [PATCH 1/6 " James Carter
                   ` (6 more replies)
  0 siblings, 7 replies; 9+ messages in thread
From: James Carter @ 2016-05-05 20:44 UTC (permalink / raw)
  To: selinux

This patch set adds support for tracking original file and line numbers for better
error reporting when a high-level language is translated into CIL. It then uses
that support to provide better error reporting for neverallow rules after
generating CIL with checkpolicy or checkmodule. (Unfortunately, the original line
number information is not saved in the pp file, so there is no benefit for policy
modules.)

Changes in V2:
- Only ";;*" at the beginning of a line indicates an HL line mark.
- When cil_tree_get_next_path() encounters a call or blockinherit it will
continue searching the AST from the associated macro or block.

Changes in V3:
- Changed the format of the message printed by cil_tree_log():
  Before:
    Problem at line 21 of policy.cil (from line 11 of foo.hll) (from line 2 of bar.hll)
  Now:
    Problem at policy.cil:21 from foo.hll:11 from bar.hll:2

James Carter (6):
  libsepol/cil: Add high-level language line marking support
  libsepol/cil: Store CIL filename in parse tree and AST
  libsepol/cil: Add cil_tree_log() and supporting functions
  libsepol/cil: Replace cil_log() calls with cil_tree_log()
  libsepol/cil: Remove path field from cil_tree_node struct
  libsepol: When generating CIL use HLL line mark for neverallows

 libsepol/cil/src/cil.c             |  22 ++-
 libsepol/cil/src/cil_binary.c      |  45 +++---
 libsepol/cil/src/cil_build_ast.c   | 294 +++++++++++++++----------------------
 libsepol/cil/src/cil_build_ast.h   |   2 +
 libsepol/cil/src/cil_copy_ast.c    |  24 ++-
 libsepol/cil/src/cil_flavor.h      |   1 +
 libsepol/cil/src/cil_fqn.c         |   2 +-
 libsepol/cil/src/cil_internal.h    |   9 ++
 libsepol/cil/src/cil_lexer.h       |   6 +-
 libsepol/cil/src/cil_lexer.l       |  15 +-
 libsepol/cil/src/cil_parser.c      | 259 +++++++++++++++++++++++++++-----
 libsepol/cil/src/cil_resolve_ast.c |  51 +++----
 libsepol/cil/src/cil_tree.c        |  96 +++++++++++-
 libsepol/cil/src/cil_tree.h        |   6 +-
 libsepol/cil/src/cil_verify.c      |  83 +++++------
 libsepol/src/module_to_cil.c       |   8 +
 16 files changed, 590 insertions(+), 333 deletions(-)

-- 
2.5.5

^ permalink raw reply	[flat|nested] 9+ messages in thread

* [PATCH 1/6 v3] libsepol/cil: Add high-level language line marking support
  2016-05-05 20:44 [PATCH 0/6 v3] libsepol/cil: Add high-level language line marking support James Carter
@ 2016-05-05 20:44 ` James Carter
  2016-05-05 20:44 ` [PATCH 2/6 v3] libsepol/cil: Store CIL filename in parse tree and AST James Carter
                   ` (5 subsequent siblings)
  6 siblings, 0 replies; 9+ messages in thread
From: James Carter @ 2016-05-05 20:44 UTC (permalink / raw)
  To: selinux

Adds support for tracking original file and line numbers for
better error reporting when a high-level language is translated
into CIL.

This adds a field called "hll_line" to struct cil_tree_node which
increases memory usage by 5%.

Syntax:

;;* lm(s|x) LINENO FILENAME
(CIL STATEMENTS)
;;* lme

lms is used when each of the following CIL statements corresponds
to a line in the original file.

lmx is used when the following CIL statements are all expanded
from a single high-level language line.

lme ends a line mark block.

Example:

;;* lms 1 foo.hll
(CIL-1)
(CIL-2)
;;* lme
;;* lmx 10 bar.hll
(CIL-3)
(CIL-4)
;;* lms 100 baz.hll
(CIL-5)
(CIL-6)
;;* lme
(CIL-7)
;;* lme

CIL-1 is from line   1 of foo.hll
CIL-2 is from line   2 of foo.hll
CIL-3 is from line  10 of bar.hll
CIL-4 is from line  10 of bar.hll
CIL-5 is from line 100 of baz.hll
CIL-6 is from line 101 of baz.hll
CIL-7 is from line  10 of bar.hll

Based on work originally done by Yuli Khodorkovskiy of Tresys.

Signed-off-by: James Carter <jwcart2@tycho.nsa.gov>
---
 libsepol/cil/src/cil.c           |  19 +++-
 libsepol/cil/src/cil_build_ast.c |  29 ++++-
 libsepol/cil/src/cil_build_ast.h |   2 +
 libsepol/cil/src/cil_copy_ast.c  |  19 ++++
 libsepol/cil/src/cil_flavor.h    |   1 +
 libsepol/cil/src/cil_internal.h  |   9 ++
 libsepol/cil/src/cil_lexer.h     |   6 +-
 libsepol/cil/src/cil_lexer.l     |  15 +--
 libsepol/cil/src/cil_parser.c    | 240 ++++++++++++++++++++++++++++++++-------
 libsepol/cil/src/cil_tree.c      |   3 +-
 libsepol/cil/src/cil_tree.h      |   1 +
 11 files changed, 290 insertions(+), 54 deletions(-)

diff --git a/libsepol/cil/src/cil.c b/libsepol/cil/src/cil.c
index de7033a..40d520b 100644
--- a/libsepol/cil/src/cil.c
+++ b/libsepol/cil/src/cil.c
@@ -233,6 +233,9 @@ static void cil_init_keys(void)
 	CIL_KEY_PERMISSIONX = cil_strpool_add("permissionx");
 	CIL_KEY_IOCTL = cil_strpool_add("ioctl");
 	CIL_KEY_UNORDERED = cil_strpool_add("unordered");
+	CIL_KEY_SRC_INFO = cil_strpool_add("<src_info>");
+	CIL_KEY_SRC_CIL = cil_strpool_add("<src_cil>");
+	CIL_KEY_SRC_HLL = cil_strpool_add("<src_hll>");
 }
 
 void cil_db_init(struct cil_db **db)
@@ -757,6 +760,9 @@ void cil_destroy_data(void **data, enum cil_flavor flavor)
 	case CIL_MLS:
 		cil_destroy_mls(*data);
 		break;
+	case CIL_SRC_INFO:
+		cil_destroy_src_info(*data);
+		break;
 	case CIL_OP:
 	case CIL_CONS_OPERAND:
 		break;
@@ -764,8 +770,8 @@ void cil_destroy_data(void **data, enum cil_flavor flavor)
 		cil_log(CIL_INFO, "Unknown data flavor: %d\n", flavor);
 		break;
 	}
-	
-	*data = NULL;		
+
+	*data = NULL;
 }
 
 int cil_flavor_to_symtab_index(enum cil_flavor flavor, enum cil_sym_index *sym_index)
@@ -1109,6 +1115,8 @@ const char * cil_node_to_string(struct cil_tree_node *node)
 		return CIL_KEY_HANDLEUNKNOWN;
 	case CIL_MLS:
 		return CIL_KEY_MLS;
+	case CIL_SRC_INFO:
+		return CIL_KEY_SRC_INFO;
 	case CIL_ALL:
 		return CIL_KEY_ALL;
 	case CIL_RANGE:
@@ -2554,3 +2562,10 @@ void cil_mls_init(struct cil_mls **mls)
 	*mls = cil_malloc(sizeof(**mls));
 	(*mls)->value = 0;
 }
+
+void cil_src_info_init(struct cil_src_info **info)
+{
+	*info = cil_malloc(sizeof(**info));
+	(*info)->is_cil = 0;
+	(*info)->path = NULL;
+}
diff --git a/libsepol/cil/src/cil_build_ast.c b/libsepol/cil/src/cil_build_ast.c
index 90fee8e..86adb4b 100644
--- a/libsepol/cil/src/cil_build_ast.c
+++ b/libsepol/cil/src/cil_build_ast.c
@@ -527,6 +527,7 @@ int cil_gen_perm_nodes(struct cil_db *db, struct cil_tree_node *current_perm, st
 		cil_tree_node_init(&new_ast);
 		new_ast->parent = ast_node;
 		new_ast->line = current_perm->line;
+		new_ast->hll_line = current_perm->hll_line;
 		new_ast->path = current_perm->path;
 
 		rc = cil_gen_perm(db, current_perm, new_ast, flavor, num_perms);
@@ -5881,6 +5882,27 @@ void cil_destroy_mls(struct cil_mls *mls)
 	free(mls);
 }
 
+int cil_gen_src_info(struct cil_tree_node *parse_current, struct cil_tree_node *ast_node)
+{
+	/* No need to check syntax, because this is auto generated */
+	struct cil_src_info *info = NULL;
+
+	cil_src_info_init(&info);
+
+	info->is_cil = (parse_current->next->data == CIL_KEY_SRC_CIL) ? CIL_TRUE : CIL_FALSE;
+	info->path = parse_current->next->next->data;
+
+	ast_node->data = info;
+	ast_node->flavor = CIL_SRC_INFO;
+
+	return SEPOL_OK;
+}
+
+void cil_destroy_src_info(struct cil_src_info *info)
+{
+	free(info);
+}
+
 int __cil_build_ast_node_helper(struct cil_tree_node *parse_current, uint32_t *finished, void *extra_args)
 {
 	struct cil_args_build *args = NULL;
@@ -5981,6 +6003,7 @@ int __cil_build_ast_node_helper(struct cil_tree_node *parse_current, uint32_t *f
 
 	ast_node->parent = ast_current;
 	ast_node->line = parse_current->line;
+	ast_node->hll_line = parse_current->hll_line;
 	ast_node->path = parse_current->path;
 
 	if (parse_current->data == CIL_KEY_BLOCK) {
@@ -6244,8 +6267,10 @@ int __cil_build_ast_node_helper(struct cil_tree_node *parse_current, uint32_t *f
 	} else if (parse_current->data == CIL_KEY_MLS) {
 		rc = cil_gen_mls(parse_current, ast_node);
 		*finished = CIL_TREE_SKIP_NEXT;
+	} else if (parse_current->data == CIL_KEY_SRC_INFO) {
+		rc = cil_gen_src_info(parse_current, ast_node);
 	} else {
-		cil_log(CIL_ERR, "Error: Unknown keyword %s\n", (char*)parse_current->data);
+		cil_log(CIL_ERR, "Error: Unknown keyword %s\n", (char *)parse_current->data);
 		rc = SEPOL_ERR;
 	}
 
@@ -6266,7 +6291,7 @@ int __cil_build_ast_node_helper(struct cil_tree_node *parse_current, uint32_t *f
 			if (ast_current->flavor == CIL_IN) {
 				args->in = ast_current;
 			}
-		
+
 			ast_current->cl_head = ast_node;
 		} else {
 			ast_current->cl_tail->next = ast_node;
diff --git a/libsepol/cil/src/cil_build_ast.h b/libsepol/cil/src/cil_build_ast.h
index f428394..825029e 100644
--- a/libsepol/cil/src/cil_build_ast.h
+++ b/libsepol/cil/src/cil_build_ast.h
@@ -215,6 +215,8 @@ int cil_gen_mls(struct cil_tree_node *parse_current, struct cil_tree_node *ast_n
 void cil_destroy_mls(struct cil_mls *mls);
 int cil_gen_defaultrange(struct cil_tree_node *parse_current, struct cil_tree_node *ast_node);
 void cil_destroy_defaultrange(struct cil_defaultrange *def);
+int cil_gen_src_info(struct cil_tree_node *parse_current, struct cil_tree_node *ast_node);
+void cil_destroy_src_info(struct cil_src_info *info);
 
 int cil_fill_cats(struct cil_tree_node *curr, struct cil_cats **cats);
 void cil_destroy_cats(struct cil_cats *cats);
diff --git a/libsepol/cil/src/cil_copy_ast.c b/libsepol/cil/src/cil_copy_ast.c
index 0be1dda..5615b30 100644
--- a/libsepol/cil/src/cil_copy_ast.c
+++ b/libsepol/cil/src/cil_copy_ast.c
@@ -1666,6 +1666,21 @@ int cil_copy_bounds(__attribute__((unused)) struct cil_db *db, void *data, void
 	return SEPOL_OK;
 }
 
+int cil_copy_src_info(__attribute__((unused)) struct cil_db *db, void *data, void **copy, __attribute__((unused)) symtab_t *symtab)
+{
+	struct cil_src_info *orig = data;
+	struct cil_src_info *new = NULL;
+
+	cil_src_info_init(&new);
+
+	new->is_cil = orig->is_cil;
+	new->path = orig->path;
+
+	*copy = new;
+
+	return SEPOL_OK;
+}
+
 int __cil_copy_node_helper(struct cil_tree_node *orig, __attribute__((unused)) uint32_t *finished, void *extra_args)
 {
 	int rc = SEPOL_ERR;
@@ -1942,6 +1957,9 @@ int __cil_copy_node_helper(struct cil_tree_node *orig, __attribute__((unused)) u
 	case CIL_MLS:
 		copy_func = &cil_copy_mls;
 		break;
+	case CIL_SRC_INFO:
+		copy_func = &cil_copy_src_info;
+		break;
 	default:
 		goto exit;
 	}
@@ -1964,6 +1982,7 @@ int __cil_copy_node_helper(struct cil_tree_node *orig, __attribute__((unused)) u
 
 		new->parent = parent;
 		new->line = orig->line;
+		new->hll_line = orig->hll_line;
 		new->path = orig->path;
 		new->flavor = orig->flavor;
 		new->data = data;
diff --git a/libsepol/cil/src/cil_flavor.h b/libsepol/cil/src/cil_flavor.h
index 9fb5083..cd08b97 100644
--- a/libsepol/cil/src/cil_flavor.h
+++ b/libsepol/cil/src/cil_flavor.h
@@ -111,6 +111,7 @@ enum cil_flavor {
 	CIL_DEFAULTRANGE,
 	CIL_HANDLEUNKNOWN,
 	CIL_MLS,
+	CIL_SRC_INFO,
 
 /*
  *          boolean  constraint  set  catset
diff --git a/libsepol/cil/src/cil_internal.h b/libsepol/cil/src/cil_internal.h
index a75ddf8..5875dc9 100644
--- a/libsepol/cil/src/cil_internal.h
+++ b/libsepol/cil/src/cil_internal.h
@@ -226,6 +226,9 @@ char *CIL_KEY_NEVERALLOWX;
 char *CIL_KEY_PERMISSIONX;
 char *CIL_KEY_IOCTL;
 char *CIL_KEY_UNORDERED;
+char *CIL_KEY_SRC_INFO;
+char *CIL_KEY_SRC_CIL;
+char *CIL_KEY_SRC_HLL;
 
 /*
 	Symbol Table Array Indices
@@ -917,6 +920,11 @@ struct cil_mls {
 	int value;
 };
 
+struct cil_src_info {
+	int is_cil;
+	char *path;
+};
+
 void cil_db_init(struct cil_db **db);
 void cil_db_destroy(struct cil_db **db);
 
@@ -1019,6 +1027,7 @@ void cil_default_init(struct cil_default **def);
 void cil_defaultrange_init(struct cil_defaultrange **def);
 void cil_handleunknown_init(struct cil_handleunknown **unk);
 void cil_mls_init(struct cil_mls **mls);
+void cil_src_info_init(struct cil_src_info **info);
 void cil_userattribute_init(struct cil_userattribute **attribute);
 void cil_userattributeset_init(struct cil_userattributeset **attrset);
 
diff --git a/libsepol/cil/src/cil_lexer.h b/libsepol/cil/src/cil_lexer.h
index 1537d5e..ab555d8 100644
--- a/libsepol/cil/src/cil_lexer.h
+++ b/libsepol/cil/src/cil_lexer.h
@@ -37,8 +37,10 @@
 #define SYMBOL 3
 #define QSTRING 4
 #define COMMENT 5
-#define END_OF_FILE 6
-#define UNKNOWN 7
+#define HLL_LINEMARK 6
+#define NEWLINE 7
+#define END_OF_FILE 8
+#define UNKNOWN 9
 
 struct token {
 	uint32_t type;
diff --git a/libsepol/cil/src/cil_lexer.l b/libsepol/cil/src/cil_lexer.l
index 8e4c207..e28c33e 100644
--- a/libsepol/cil/src/cil_lexer.l
+++ b/libsepol/cil/src/cil_lexer.l
@@ -50,15 +50,17 @@ symbol		({digit}|{alpha}|{spec_char})+
 white		[ \t]
 newline		[\n\r]
 qstring		\"[^"\n]*\"
-comment		;[^\n]*
+hll_lm          ^;;\*
+comment		;
 
 %%
-{newline}	line++; 
+{newline}	line++; return NEWLINE;
+{hll_lm}	value=yytext; return HLL_LINEMARK;
 {comment}	value=yytext; return COMMENT;
 "("		value=yytext; return OPAREN;
-")"		value=yytext; return CPAREN;	
+")"		value=yytext; return CPAREN;
 {symbol}	value=yytext; return SYMBOL;
-{white}		//cil_log(CIL_INFO, "white, ");
+{white}		;
 {qstring}	value=yytext; return QSTRING;
 <<EOF>>		return END_OF_FILE;
 .		value=yytext; return UNKNOWN;
@@ -73,7 +75,7 @@ int cil_lexer_setup(char *buffer, uint32_t size)
 	}
 
 	line = 1;
-	
+
 	return SEPOL_OK;
 }
 
@@ -87,7 +89,6 @@ int cil_lexer_next(struct token *tok)
 	tok->type = yylex();
 	tok->value = value;
 	tok->line = line;
-	
+
 	return SEPOL_OK;
 }
-
diff --git a/libsepol/cil/src/cil_parser.c b/libsepol/cil/src/cil_parser.c
index d0e108c..a92e3bb 100644
--- a/libsepol/cil/src/cil_parser.c
+++ b/libsepol/cil/src/cil_parser.c
@@ -36,9 +36,148 @@
 #include "cil_internal.h"
 #include "cil_log.h"
 #include "cil_mem.h"
-#include "cil_tree.h" 
+#include "cil_tree.h"
 #include "cil_lexer.h"
 #include "cil_strpool.h"
+#include "cil_stack.h"
+
+char *CIL_KEY_HLL_LMS;
+char *CIL_KEY_HLL_LMX;
+char *CIL_KEY_HLL_LME;
+
+struct hll_info {
+	int hll_lineno;
+	int hll_expand;
+};
+
+static void push_hll_info(struct cil_stack *stack, int hll_lineno, int hll_expand)
+{
+	struct hll_info *new = cil_malloc(sizeof(*new));
+
+	new->hll_lineno = hll_lineno;
+	new->hll_expand = hll_expand;
+
+	cil_stack_push(stack, CIL_NONE, new);
+}
+
+static void pop_hll_info(struct cil_stack *stack, int *hll_lineno, int *hll_expand)
+{
+	struct cil_stack_item *curr = cil_stack_pop(stack);
+	struct cil_stack_item *prev = cil_stack_peek(stack);
+	struct hll_info *old;
+
+	free(curr->data);
+
+	if (!prev) {
+		*hll_lineno = -1;
+		*hll_expand = -1;
+	} else {
+		old = prev->data;
+		*hll_lineno = old->hll_lineno;
+		*hll_expand = old->hll_expand;
+	}
+}
+
+static void create_node(struct cil_tree_node **node, struct cil_tree_node *current, int line, int hll_line, char *path, void *value)
+{
+	cil_tree_node_init(node);
+	(*node)->parent = current;
+	(*node)->flavor = CIL_NODE;
+	(*node)->line = line;
+	(*node)->hll_line = hll_line;
+	(*node)->path = path;
+	(*node)->data = value;
+}
+
+static void insert_node(struct cil_tree_node *node, struct cil_tree_node *current)
+{
+	if (current->cl_head == NULL) {
+		current->cl_head = node;
+	} else {
+		current->cl_tail->next = node;
+	}
+	current->cl_tail = node;
+}
+
+static int add_hll_linemark(struct cil_tree_node **current, int *hll_lineno, int *hll_expand, struct cil_stack *stack, char *path)
+{
+	char *hll_type;
+	struct cil_tree_node *node;
+	struct token tok;
+	char *hll_file;
+	char *end = NULL;
+
+	cil_lexer_next(&tok);
+	hll_type = cil_strpool_add(tok.value);
+	if (hll_type == CIL_KEY_HLL_LME) {
+		if (cil_stack_is_empty(stack)) {
+			cil_log(CIL_ERR, "Line mark end without start\n");
+			goto exit;
+		}
+		pop_hll_info(stack, hll_lineno, hll_expand);
+		*current = (*current)->parent;
+	} else {
+		create_node(&node, *current, tok.line, *hll_lineno, path, NULL);
+		insert_node(node, *current);
+		*current = node;
+
+		create_node(&node, *current, tok.line, *hll_lineno, path, CIL_KEY_SRC_INFO);
+		insert_node(node, *current);
+
+		create_node(&node, *current, tok.line, *hll_lineno, path, CIL_KEY_SRC_HLL);
+		insert_node(node, *current);
+
+		if (hll_type == CIL_KEY_HLL_LMS) {
+			*hll_expand = 0;
+		} else if (hll_type == CIL_KEY_HLL_LMX) {
+			*hll_expand = 1;
+		} else {
+			cil_log(CIL_ERR, "Invalid line mark syntax\n");
+			goto exit;
+		}
+
+		cil_lexer_next(&tok);
+		if (tok.type != SYMBOL) {
+			cil_log(CIL_ERR, "Invalid line mark syntax\n");
+			goto exit;
+		}
+		*hll_lineno = strtol(tok.value, &end, 10);
+		if (errno == ERANGE || *end != '\0') {
+			cil_log(CIL_ERR, "Problem parsing line number for line mark\n");
+			goto exit;
+		}
+
+		push_hll_info(stack, *hll_lineno, *hll_expand);
+
+		cil_lexer_next(&tok);
+		if (tok.type != SYMBOL && tok.type != QSTRING) {
+			cil_log(CIL_ERR, "Invalid line mark syntax\n");
+			goto exit;
+		}
+
+		if (tok.type == QSTRING) {
+			tok.value[strlen(tok.value) - 1] = '\0';
+			tok.value = tok.value+1;
+		}
+
+		hll_file = cil_strpool_add(tok.value);
+
+		create_node(&node, *current, tok.line, *hll_lineno, path, hll_file);
+		insert_node(node, *current);
+	}
+
+	cil_lexer_next(&tok);
+	if (tok.type != NEWLINE) {
+		cil_log(CIL_ERR, "Invalid line mark syntax\n");
+		goto exit;
+	}
+
+	return SEPOL_OK;
+
+exit:
+	cil_log(CIL_ERR, "Problem with high-level line mark at line %d of %s\n", tok.line, path);
+	return SEPOL_ERR;
+}
 
 int cil_parser(char *_path, char *buffer, uint32_t size, struct cil_tree **parse_tree)
 {
@@ -47,89 +186,110 @@ int cil_parser(char *_path, char *buffer, uint32_t size, struct cil_tree **parse
 
 	struct cil_tree *tree = NULL;
 	struct cil_tree_node *node = NULL;
-	struct cil_tree_node *item = NULL;
 	struct cil_tree_node *current = NULL;
 	char *path = cil_strpool_add(_path);
-
+	struct cil_stack *stack;
+	int hll_lineno = -1;
+	int hll_expand = -1;
 	struct token tok;
+	int rc = SEPOL_OK;
+
+	CIL_KEY_HLL_LMS = cil_strpool_add("lms");
+	CIL_KEY_HLL_LMX = cil_strpool_add("lmx");
+	CIL_KEY_HLL_LME = cil_strpool_add("lme");
+
+	cil_stack_init(&stack);
 
 	cil_lexer_setup(buffer, size);
 
 	tree = *parse_tree;
-	current = tree->root;	
+	current = tree->root;
 
 	do {
 		cil_lexer_next(&tok);
 		switch (tok.type) {
+		case HLL_LINEMARK:
+			rc = add_hll_linemark(&current, &hll_lineno, &hll_expand, stack, path);
+			if (rc != SEPOL_OK) {
+				goto exit;
+			}
+			break;
 		case OPAREN:
 			paren_count++;
-			cil_tree_node_init(&node);
-			node->parent = current;
-			node->flavor = CIL_NODE;
-			node->line = tok.line;
-			node->path = path;
-			if (current->cl_head == NULL) {
-				current->cl_head = node;
-			} else {
-				current->cl_tail->next = node;
-			}
-			current->cl_tail = node;
+
+			create_node(&node, current, tok.line, hll_lineno, path, NULL);
+			insert_node(node, current);
 			current = node;
 			break;
 		case CPAREN:
 			paren_count--;
 			if (paren_count < 0) {
 				cil_log(CIL_ERR, "Close parenthesis without matching open at line %d of %s\n", tok.line, path);
-				return SEPOL_ERR;
+				goto exit;
 			}
 			current = current->parent;
 			break;
-		case SYMBOL:
 		case QSTRING:
+			tok.value[strlen(tok.value) - 1] = '\0';
+			tok.value = tok.value+1;
+		case SYMBOL:
 			if (paren_count == 0) {
 				cil_log(CIL_ERR, "Symbol not inside parenthesis at line %d of %s\n", tok.line, path);
-				return SEPOL_ERR;
+				goto exit;
 			}
-			cil_tree_node_init(&item);
-			item->parent = current;
-			if (tok.type == QSTRING) {
-				tok.value[strlen(tok.value) - 1] = '\0';
-				item->data = cil_strpool_add(tok.value + 1);
-			} else {
-				item->data = cil_strpool_add(tok.value);
-			}
-			item->flavor = CIL_NODE;
-			item->line = tok.line;
-			item->path = path;
-			if (current->cl_head == NULL) {
-				current->cl_head = item;
-			} else {
-				current->cl_tail->next = item;
+
+			create_node(&node, current, tok.line, hll_lineno, path, cil_strpool_add(tok.value));
+			insert_node(node, current);
+			break;
+		case NEWLINE :
+			if (!hll_expand) {
+				hll_lineno++;
 			}
-			current->cl_tail = item;
 			break;
+		case COMMENT:
+			while (tok.type != NEWLINE && tok.type != END_OF_FILE) {
+				cil_lexer_next(&tok);
+			}
+			if (!hll_expand) {
+				hll_lineno++;
+			}
+			if (tok.type != END_OF_FILE) {
+				break;
+			}
+			// Fall through if EOF
 		case END_OF_FILE:
 			if (paren_count > 0) {
 				cil_log(CIL_ERR, "Open parenthesis without matching close at line %d of %s\n", tok.line, path);
-				return SEPOL_ERR;
+				goto exit;
+			}
+			if (!cil_stack_is_empty(stack)) {
+				cil_log(CIL_ERR, "High-level language line marker start without close at line %d of %s\n", tok.line, path);
+				goto exit;
 			}
-			break;
-		case COMMENT:
-			// ignore
 			break;
 		case UNKNOWN:
 			cil_log(CIL_ERR, "Invalid token '%s' at line %d of %s\n", tok.value, tok.line, path);
-			return SEPOL_ERR;
+			goto exit;
 		default:
 			cil_log(CIL_ERR, "Unknown token type '%d' at line %d of %s\n", tok.type, tok.line, path);
-			return SEPOL_ERR;
+			goto exit;
 		}
 	}
 	while (tok.type != END_OF_FILE);
 
 	cil_lexer_destroy();
 
+	cil_stack_destroy(&stack);
+
 	*parse_tree = tree;
 
 	return SEPOL_OK;
+
+exit:
+	while (!cil_stack_is_empty(stack)) {
+		pop_hll_info(stack, &hll_lineno, &hll_expand);
+	}
+	cil_stack_destroy(&stack);
+
+	return SEPOL_ERR;
 }
diff --git a/libsepol/cil/src/cil_tree.c b/libsepol/cil/src/cil_tree.c
index 563b817..6e56dd1 100644
--- a/libsepol/cil/src/cil_tree.c
+++ b/libsepol/cil/src/cil_tree.c
@@ -128,7 +128,8 @@ void cil_tree_node_init(struct cil_tree_node **node)
 	new_node->data = NULL;
 	new_node->next = NULL;
 	new_node->flavor = CIL_ROOT;
-	new_node->line = 0;	
+	new_node->line = 0;
+	new_node->hll_line = 0;
 	new_node->path = NULL;
 
 	*node = new_node;
diff --git a/libsepol/cil/src/cil_tree.h b/libsepol/cil/src/cil_tree.h
index 9bb602f..43d6b98 100644
--- a/libsepol/cil/src/cil_tree.h
+++ b/libsepol/cil/src/cil_tree.h
@@ -46,6 +46,7 @@ struct cil_tree_node {
 	struct cil_tree_node *next;		//Each element in the list points to the next element
 	enum cil_flavor flavor;
 	uint32_t line;
+	uint32_t hll_line;
 	char *path;
 	void *data;
 };
-- 
2.5.5

^ permalink raw reply related	[flat|nested] 9+ messages in thread

* [PATCH 2/6 v3] libsepol/cil: Store CIL filename in parse tree and AST
  2016-05-05 20:44 [PATCH 0/6 v3] libsepol/cil: Add high-level language line marking support James Carter
  2016-05-05 20:44 ` [PATCH 1/6 " James Carter
@ 2016-05-05 20:44 ` James Carter
  2016-05-05 20:44 ` [PATCH 3/6 v3] libsepol/cil: Add cil_tree_log() and supporting functions James Carter
                   ` (4 subsequent siblings)
  6 siblings, 0 replies; 9+ messages in thread
From: James Carter @ 2016-05-05 20:44 UTC (permalink / raw)
  To: selinux

Use some of the functionality recently added to support high-level
language line marking to track the CIL filename.

The goal is to eventually remove the path field from the tree node
struct and offset the addtion of the hll_line field.

Signed-off-by: James Carter <jwcart2@tycho.nsa.gov>
---
 libsepol/cil/src/cil_parser.c | 20 ++++++++++++++++++++
 1 file changed, 20 insertions(+)

diff --git a/libsepol/cil/src/cil_parser.c b/libsepol/cil/src/cil_parser.c
index a92e3bb..451014a 100644
--- a/libsepol/cil/src/cil_parser.c
+++ b/libsepol/cil/src/cil_parser.c
@@ -179,6 +179,24 @@ exit:
 	return SEPOL_ERR;
 }
 
+static void add_cil_path(struct cil_tree_node **current, char *path)
+{
+	struct cil_tree_node *node;
+
+	create_node(&node, *current, 0, 0, path, NULL);
+	insert_node(node, *current);
+	*current = node;
+
+	create_node(&node, *current, 0, 0, path, CIL_KEY_SRC_INFO);
+	insert_node(node, *current);
+
+	create_node(&node, *current, 0, 0, path, CIL_KEY_SRC_CIL);
+	insert_node(node, *current);
+
+	create_node(&node, *current, 0, 0, path, path);
+	insert_node(node, *current);
+}
+
 int cil_parser(char *_path, char *buffer, uint32_t size, struct cil_tree **parse_tree)
 {
 
@@ -205,6 +223,8 @@ int cil_parser(char *_path, char *buffer, uint32_t size, struct cil_tree **parse
 	tree = *parse_tree;
 	current = tree->root;
 
+	add_cil_path(&current, path);
+
 	do {
 		cil_lexer_next(&tok);
 		switch (tok.type) {
-- 
2.5.5

^ permalink raw reply related	[flat|nested] 9+ messages in thread

* [PATCH 3/6 v3] libsepol/cil: Add cil_tree_log() and supporting functions
  2016-05-05 20:44 [PATCH 0/6 v3] libsepol/cil: Add high-level language line marking support James Carter
  2016-05-05 20:44 ` [PATCH 1/6 " James Carter
  2016-05-05 20:44 ` [PATCH 2/6 v3] libsepol/cil: Store CIL filename in parse tree and AST James Carter
@ 2016-05-05 20:44 ` James Carter
  2016-05-05 20:44 ` [PATCH 4/6 v3] libsepol/cil: Replace cil_log() calls with cil_tree_log() James Carter
                   ` (3 subsequent siblings)
  6 siblings, 0 replies; 9+ messages in thread
From: James Carter @ 2016-05-05 20:44 UTC (permalink / raw)
  To: selinux

Provide more detailed log messages containing all relevant CIL and
high-level language source file information through cil_tree_log().

cil_tree_log() uses two new functions: cil_tree_get_next_path() and
cil_tree_get_cil_path().

cil_tree_get_next_path() traverses up the parse tree or AST until
it finds the next CIL or high-level language source information nodes.
It will return the path and whether or not the path is for a CIL file.

cil_tree_get_cil_path() uses cil_tree_get_next_path() to return
the CIL path.

Example cil_tree_log() message:
    Problem at policy.cil:21 from foo.hll:11 from bar.hll:2

Signed-off-by: James Carter <jwcart2@tycho.nsa.gov>
---
 libsepol/cil/src/cil_tree.c | 86 +++++++++++++++++++++++++++++++++++++++++++++
 libsepol/cil/src/cil_tree.h |  4 +++
 2 files changed, 90 insertions(+)

diff --git a/libsepol/cil/src/cil_tree.c b/libsepol/cil/src/cil_tree.c
index 6e56dd1..33cc4f8 100644
--- a/libsepol/cil/src/cil_tree.c
+++ b/libsepol/cil/src/cil_tree.c
@@ -59,6 +59,92 @@ __attribute__((noreturn)) __attribute__((format (printf, 1, 2))) void cil_tree_e
 	exit(1);
 }
 
+struct cil_tree_node *cil_tree_get_next_path(struct cil_tree_node *node, char **path, int* is_cil)
+{
+	if (!node) {
+		return NULL;
+	}
+
+	node = node->parent;
+
+	while (node) {
+		if (node->flavor == CIL_NODE && node->data == NULL) {
+			if (node->cl_head->data == CIL_KEY_SRC_INFO) {
+				/* Parse Tree */
+				*path = node->cl_head->next->next->data;
+				*is_cil = (node->cl_head->next->data == CIL_KEY_SRC_CIL);
+				return node;
+			}
+			node = node->parent;
+		} else if (node->flavor == CIL_SRC_INFO) {
+				/* AST */
+				struct cil_src_info *info = node->data;
+				*path = info->path;
+				*is_cil = info->is_cil;
+				return node;
+		} else {
+			if (node->flavor == CIL_CALL) {
+				struct cil_call *call = node->data;
+				node = NODE(call->macro);
+			} else if (node->flavor == CIL_BLOCKINHERIT) {
+				struct cil_blockinherit *inherit = node->data;
+				node = NODE(inherit->block);
+			} else {
+				node = node->parent;
+			}
+		}
+	}
+
+	return NULL;
+}
+
+char *cil_tree_get_cil_path(struct cil_tree_node *node)
+{
+	char *path = NULL;
+	int is_cil;
+
+	while (node) {
+		node = cil_tree_get_next_path(node, &path, &is_cil);
+		if (node && is_cil) {
+			return path;
+		}
+	}
+
+	return NULL;
+}
+
+__attribute__((format (printf, 3, 4))) void cil_tree_log(struct cil_tree_node *node, enum cil_log_level lvl, const char* msg, ...)
+{
+	va_list ap;
+
+	va_start(ap, msg);
+	cil_vlog(lvl, msg, ap);
+	va_end(ap);
+
+	if (node) {
+		char *path = NULL;
+		int is_cil;
+		unsigned hll_line = node->hll_line;
+
+		path = cil_tree_get_cil_path(node);
+
+		if (path != NULL) {
+			cil_log(lvl, " at %s:%d", path, node->line);
+		}
+
+		while (node) {
+			node = cil_tree_get_next_path(node, &path, &is_cil);
+			if (node && !is_cil) {
+				cil_log(lvl," from %s:%d", path, hll_line);
+				path = NULL;
+				hll_line = node->hll_line;
+			}
+		}
+	}
+
+	cil_log(lvl,"\n");
+}
+
 int cil_tree_init(struct cil_tree **tree)
 {
 	struct cil_tree *new_tree = cil_malloc(sizeof(*new_tree));
diff --git a/libsepol/cil/src/cil_tree.h b/libsepol/cil/src/cil_tree.h
index 43d6b98..318eecd 100644
--- a/libsepol/cil/src/cil_tree.h
+++ b/libsepol/cil/src/cil_tree.h
@@ -51,6 +51,10 @@ struct cil_tree_node {
 	void *data;
 };
 
+struct cil_tree_node *cil_tree_get_next_path(struct cil_tree_node *node, char **path, int* is_cil);
+char *cil_tree_get_cil_path(struct cil_tree_node *node);
+__attribute__((format (printf, 3, 4))) void cil_tree_log(struct cil_tree_node *node, enum cil_log_level lvl, const char* msg, ...);
+
 int cil_tree_init(struct cil_tree **tree);
 void cil_tree_destroy(struct cil_tree **tree);
 void cil_tree_subtree_destroy(struct cil_tree_node *node);
-- 
2.5.5

^ permalink raw reply related	[flat|nested] 9+ messages in thread

* [PATCH 4/6 v3] libsepol/cil: Replace cil_log() calls with cil_tree_log()
  2016-05-05 20:44 [PATCH 0/6 v3] libsepol/cil: Add high-level language line marking support James Carter
                   ` (2 preceding siblings ...)
  2016-05-05 20:44 ` [PATCH 3/6 v3] libsepol/cil: Add cil_tree_log() and supporting functions James Carter
@ 2016-05-05 20:44 ` James Carter
  2016-05-05 20:44 ` [PATCH 5/6 v3] libsepol/cil: Remove path field from cil_tree_node struct James Carter
                   ` (2 subsequent siblings)
  6 siblings, 0 replies; 9+ messages in thread
From: James Carter @ 2016-05-05 20:44 UTC (permalink / raw)
  To: selinux

Replace all calls to cil_log() that print path information with a
call to cil_tree_log() which will also print information about any
high-level sources.

Signed-off-by: James Carter <jwcart2@tycho.nsa.gov>
---
 libsepol/cil/src/cil.c             |   3 +-
 libsepol/cil/src/cil_binary.c      |  31 ++---
 libsepol/cil/src/cil_build_ast.c   | 263 +++++++++++++------------------------
 libsepol/cil/src/cil_copy_ast.c    |   4 +-
 libsepol/cil/src/cil_fqn.c         |   2 +-
 libsepol/cil/src/cil_resolve_ast.c |  51 ++++---
 libsepol/cil/src/cil_tree.c        |   6 +-
 libsepol/cil/src/cil_verify.c      |  83 ++++++------
 8 files changed, 170 insertions(+), 273 deletions(-)

diff --git a/libsepol/cil/src/cil.c b/libsepol/cil/src/cil.c
index 40d520b..929ab19 100644
--- a/libsepol/cil/src/cil.c
+++ b/libsepol/cil/src/cil.c
@@ -1764,8 +1764,7 @@ int cil_get_symtab(struct cil_tree_node *ast_node, symtab_t **symtab, enum cil_s
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Failed to get symtab from node at line %d of %s\n",
-			ast_node->line, ast_node->path);
+	cil_tree_log(ast_node, CIL_ERR, "Failed to get symtab from node");
 	return SEPOL_ERR;	
 }
 
diff --git a/libsepol/cil/src/cil_binary.c b/libsepol/cil/src/cil_binary.c
index 1cd12d2..a3f9171 100644
--- a/libsepol/cil/src/cil_binary.c
+++ b/libsepol/cil/src/cil_binary.c
@@ -1775,13 +1775,12 @@ int __cil_cond_to_policydb_helper(struct cil_tree_node *node, __attribute__((unu
 		cil_typetrans = (struct cil_nametypetransition*)node->data;
 		if (DATUM(cil_typetrans->name)->fqn != CIL_KEY_STAR) {
 			cil_log(CIL_ERR, "typetransition with file name not allowed within a booleanif block.\n");
-			cil_log(CIL_ERR,"Invalid typetransition statement at line %d of %s\n", 
-			node->line, node->path);
+			cil_tree_log(node, CIL_ERR,"Invalid typetransition statement");
 			goto exit;
 		}
 		rc = __cil_typetransition_to_avtab(pdb, db, cil_typetrans, cond_node, cond_flavor, filename_trans_table);
 		if (rc != SEPOL_OK) {
-			cil_log(CIL_ERR, "Failed to insert type transition into avtab at line %d of %s\n", node->line, node->path);
+			cil_tree_log(node, CIL_ERR, "Failed to insert type transition into avtab");
 			goto exit;
 		}
 		break;
@@ -1789,7 +1788,7 @@ int __cil_cond_to_policydb_helper(struct cil_tree_node *node, __attribute__((unu
 		cil_type_rule = node->data;
 		rc = __cil_type_rule_to_avtab(pdb, db, cil_type_rule, cond_node, cond_flavor);
 		if (rc != SEPOL_OK) {
-			cil_log(CIL_ERR, "Failed to insert typerule into avtab at line %d of %s\n", node->line, node->path);
+			cil_tree_log(node, CIL_ERR, "Failed to insert typerule into avtab");
 			goto exit;
 		}
 		break;
@@ -1797,7 +1796,7 @@ int __cil_cond_to_policydb_helper(struct cil_tree_node *node, __attribute__((unu
 		cil_avrule = node->data;
 		rc = __cil_avrule_to_avtab(pdb, db, cil_avrule, cond_node, cond_flavor);
 		if (rc != SEPOL_OK) {
-			cil_log(CIL_ERR, "Failed to insert avrule into avtab at line %d of %s\n", node->line, node->path);
+			cil_tree_log(node, CIL_ERR, "Failed to insert avrule into avtab");
 			goto exit;
 		}
 		break;
@@ -1805,8 +1804,7 @@ int __cil_cond_to_policydb_helper(struct cil_tree_node *node, __attribute__((unu
 	case CIL_TUNABLEIF:
 		break;
 	default:
-		cil_log(CIL_ERR, "Invalid statement within booleanif at line %d of %s\n", 
-			node->line, node->path);
+		cil_tree_log(node, CIL_ERR, "Invalid statement within booleanif");
 		goto exit;
 	}
 
@@ -2065,14 +2063,13 @@ int cil_booleanif_to_policydb(policydb_t *pdb, const struct cil_db *db, struct c
 	tmp_cond = cond_node_create(pdb, NULL);
 	if (tmp_cond == NULL) {
 		rc = SEPOL_ERR;
-		cil_log(CIL_INFO, "Failed to create sepol conditional node at line %d of %s\n", 
-			node->line, node->path);
+		cil_tree_log(node, CIL_INFO, "Failed to create sepol conditional node");
 		goto exit;
 	}
 	
 	rc = __cil_cond_expr_to_sepol_expr(pdb, cil_boolif->datum_expr, &tmp_cond->expr);
 	if (rc != SEPOL_OK) {
-		cil_log(CIL_INFO, "Failed to convert CIL conditional expression to sepol expression at line %d of %s\n", node->line, node->path);
+		cil_tree_log(node, CIL_INFO, "Failed to convert CIL conditional expression to sepol expression");
 		goto exit;
 	}
 
@@ -2128,7 +2125,7 @@ int cil_booleanif_to_policydb(policydb_t *pdb, const struct cil_db *db, struct c
 		bool_args.cond_flavor = CIL_CONDTRUE;
 		rc = cil_tree_walk(true_node, __cil_cond_to_policydb_helper, NULL, NULL, &bool_args);
 		if (rc != SEPOL_OK) {
-			cil_log(CIL_ERR, "Failure while walking true conditional block at line %d of %s\n", true_node->line, true_node->path);
+			cil_tree_log(true_node, CIL_ERR, "Failure while walking true conditional block");
 			goto exit;
 		}
 	}
@@ -2137,7 +2134,7 @@ int cil_booleanif_to_policydb(policydb_t *pdb, const struct cil_db *db, struct c
 		bool_args.cond_flavor = CIL_CONDFALSE;
 		rc = cil_tree_walk(false_node, __cil_cond_to_policydb_helper, NULL, NULL, &bool_args);
 		if (rc != SEPOL_OK) {
-			cil_log(CIL_ERR, "Failure while walking false conditional block at line %d of %s\n", false_node->line, false_node->path);
+			cil_tree_log(false_node, CIL_ERR, "Failure while walking false conditional block");
 			goto exit;
 		}
 	}
@@ -3591,7 +3588,7 @@ int __cil_node_to_policydb(struct cil_tree_node *node, void *extra_args)
 
 exit:
 	if (rc != SEPOL_OK) {
-		cil_log(CIL_ERR, "Binary policy creation failed at line %d of %s\n", node->line, node->path);
+		cil_tree_log(node, CIL_ERR, "Binary policy creation failed");
 	}
 	return rc;
 }
@@ -4271,10 +4268,8 @@ static void __cil_print_parents(const char *pad, struct cil_tree_node *n)
 
 	__cil_print_parents(pad, n->parent);
 
-	if (!n->path) {
-		cil_log(CIL_ERR,"%s%s\n", pad, cil_node_to_string(n));
-	} else {
-		cil_log(CIL_ERR,"%s%s at line %d of %s\n", pad, cil_node_to_string(n), n->line, n->path);
+	if (n->flavor != CIL_SRC_INFO) {
+		cil_tree_log(n, CIL_ERR,"%s%s", pad, cil_node_to_string(n));
 	}
 }
 
@@ -4365,7 +4360,7 @@ static int __cil_print_neverallow_failure(const struct cil_db *db, struct cil_tr
 		allow_str = CIL_KEY_ALLOWX;
 		avrule_flavor = CIL_AVRULEX;
 	}
-	cil_log(CIL_ERR, "%s check failed at line %d of %s\n", neverallow_str, node->line, node->path);
+	cil_tree_log(node, CIL_ERR, "%s check failed", neverallow_str);
 	__cil_print_rule("  ", neverallow_str, cil_rule);
 	cil_list_init(&matching, CIL_NODE);
 	rc = cil_find_matching_avrule_in_ast(db->ast->root, avrule_flavor, &target, matching, CIL_FALSE);
diff --git a/libsepol/cil/src/cil_build_ast.c b/libsepol/cil/src/cil_build_ast.c
index 86adb4b..5b9754a 100644
--- a/libsepol/cil/src/cil_build_ast.c
+++ b/libsepol/cil/src/cil_build_ast.c
@@ -108,8 +108,7 @@ int cil_gen_node(__attribute__((unused)) struct cil_db *db, struct cil_tree_node
 			if (cil_symtab_get_datum(symtab, key, &datum) == SEPOL_OK) {
 				if (sflavor == CIL_SYM_BLOCKS) {
 					struct cil_tree_node *node = datum->nodes->head->data;
-					cil_log(CIL_ERR, "Previous declaration at line %d of %s\n",
-						node->line, node->path);
+					cil_tree_log(node, CIL_ERR, "Previous declaration");
 				}
 			}
 			goto exit;
@@ -186,8 +185,7 @@ int cil_gen_block(struct cil_db *db, struct cil_tree_node *parse_current, struct
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad block declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad block declaration");
 	cil_destroy_block(block);
 	cil_clear_node(ast_node);
 	return rc;
@@ -236,8 +234,7 @@ int cil_gen_blockinherit(struct cil_db *db, struct cil_tree_node *parse_current,
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad blockinherit declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad blockinherit declaration");
 	cil_destroy_blockinherit(inherit);
 	return rc;
 }
@@ -281,8 +278,7 @@ int cil_gen_blockabstract(struct cil_db *db, struct cil_tree_node *parse_current
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad blockabstract declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad blockabstract declaration");
 	cil_destroy_blockabstract(abstract);
 	return rc;
 }
@@ -326,8 +322,7 @@ int cil_gen_in(struct cil_db *db, struct cil_tree_node *parse_current, struct ci
 
 	return SEPOL_OK;
 exit:
-	cil_log(CIL_ERR, "Bad in statement at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad in statement");
 	cil_destroy_in(in);
 	return rc;
 }
@@ -387,8 +382,7 @@ int cil_gen_class(struct cil_db *db, struct cil_tree_node *parse_current, struct
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad class declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad class declaration");
 	cil_destroy_class(class);
 	cil_clear_node(ast_node);
 	return rc;
@@ -456,8 +450,7 @@ int cil_gen_classorder(struct cil_db *db, struct cil_tree_node *parse_current, s
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad classorder declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad classorder declaration");
 	cil_destroy_classorder(classorder);
 	return rc;
 }
@@ -739,8 +732,7 @@ int cil_gen_classpermission(struct cil_db *db, struct cil_tree_node *parse_curre
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad classpermission declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad classpermission declaration");
 	cil_destroy_classpermission(cp);
 	cil_clear_node(ast_node);
 	return rc;
@@ -801,8 +793,7 @@ int cil_gen_classpermissionset(struct cil_db *db, struct cil_tree_node *parse_cu
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad classpermissionset at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad classpermissionset");
 	cil_destroy_classpermissionset(cps);
 	return rc;
 }
@@ -853,8 +844,7 @@ int cil_gen_map_class(struct cil_db *db, struct cil_tree_node *parse_current, st
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad map class declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad map class declaration");
 	cil_destroy_class(map);
 	cil_clear_node(ast_node);
 	return rc;
@@ -898,8 +888,7 @@ int cil_gen_classmapping(struct cil_db *db, struct cil_tree_node *parse_current,
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad classmapping declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad classmapping declaration");
 	cil_destroy_classmapping(mapping);
 	return rc;
 }
@@ -955,8 +944,7 @@ int cil_gen_common(struct cil_db *db, struct cil_tree_node *parse_current, struc
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad common declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad common declaration");
 	cil_destroy_class(common);
 	cil_clear_node(ast_node);
 	return rc;
@@ -995,8 +983,7 @@ int cil_gen_classcommon(struct cil_db *db, struct cil_tree_node *parse_current,
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad classcommon declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad classcommon declaration");
 	cil_destroy_classcommon(clscom);
 	return rc;
 
@@ -1044,8 +1031,7 @@ int cil_gen_sid(struct cil_db *db, struct cil_tree_node *parse_current, struct c
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad sid declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad sid declaration");
 	cil_destroy_sid(sid);
 	cil_clear_node(ast_node);
 	return rc;
@@ -1103,8 +1089,7 @@ int cil_gen_sidcontext(struct cil_db *db, struct cil_tree_node *parse_current, s
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad sidcontext declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad sidcontext declaration");
 	cil_destroy_sidcontext(sidcon);
 	return rc;
 }
@@ -1164,8 +1149,7 @@ int cil_gen_sidorder(struct cil_db *db, struct cil_tree_node *parse_current, str
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad sidorder declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad sidorder declaration");
 	cil_destroy_sidorder(sidorder);
 	return rc;
 }
@@ -1216,8 +1200,7 @@ int cil_gen_user(struct cil_db *db, struct cil_tree_node *parse_current, struct
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad user declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad user declaration");
 	cil_destroy_user(user);
 	cil_clear_node(ast_node);
 	return rc;
@@ -1266,8 +1249,7 @@ int cil_gen_userattribute(struct cil_db *db, struct cil_tree_node *parse_current
 
 	return SEPOL_OK;
 exit:
-	cil_log(CIL_ERR, "Bad userattribute declaration at line %d of %s\n",
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad userattribute declaration");
 	cil_destroy_userattribute(attr);
 	cil_clear_node(ast_node);
 	return rc;
@@ -1337,8 +1319,7 @@ int cil_gen_userattributeset(struct cil_db *db, struct cil_tree_node *parse_curr
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad userattributeset declaration at line %d of %s\n",
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad userattributeset declaration");
 	cil_destroy_userattributeset(attrset);
 
 	return rc;
@@ -1398,8 +1379,7 @@ int cil_gen_userlevel(struct cil_db *db, struct cil_tree_node *parse_current, st
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad userlevel declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad userlevel declaration");
 	cil_destroy_userlevel(usrlvl);
 	return rc;
 }
@@ -1459,8 +1439,7 @@ int cil_gen_userrange(struct cil_db *db, struct cil_tree_node *parse_current, st
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad userrange declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad userrange declaration");
 	cil_destroy_userrange(userrange);
 	return rc;
 }
@@ -1509,8 +1488,7 @@ int cil_gen_userprefix(struct cil_db *db, struct cil_tree_node *parse_current, s
 
 	return SEPOL_OK;
 exit:
-	cil_log(CIL_ERR, "Bad userprefix declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad userprefix declaration");
 	cil_destroy_userprefix(userprefix);
 	return rc;
 }
@@ -1567,8 +1545,7 @@ int cil_gen_selinuxuser(struct cil_db *db, struct cil_tree_node *parse_current,
 
 	return SEPOL_OK;
 exit:
-	cil_log(CIL_ERR, "Bad selinuxuser declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad selinuxuser declaration");
 	cil_destroy_selinuxuser(selinuxuser);
 	return rc;
 }
@@ -1615,8 +1592,7 @@ int cil_gen_selinuxuserdefault(struct cil_db *db, struct cil_tree_node *parse_cu
 
 	return SEPOL_OK;
 exit:
-	cil_log(CIL_ERR, "Bad selinuxuserdefault declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad selinuxuserdefault declaration");
 	cil_destroy_selinuxuser(selinuxuser);
 	return rc;
 }
@@ -1667,8 +1643,7 @@ int cil_gen_role(struct cil_db *db, struct cil_tree_node *parse_current, struct
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad role declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad role declaration");
 	cil_destroy_role(role);
 	cil_clear_node(ast_node);
 	return rc;
@@ -1718,8 +1693,7 @@ int cil_gen_roletype(struct cil_db *db, struct cil_tree_node *parse_current, str
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad roletype declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad roletype declaration");
 	cil_destroy_roletype(roletype);
 	return rc;
 }
@@ -1765,8 +1739,7 @@ int cil_gen_userrole(struct cil_db *db, struct cil_tree_node *parse_current, str
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad userrole declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad userrole declaration");
 	cil_destroy_userrole(userrole);
 	return rc;
 }
@@ -1816,8 +1789,7 @@ int cil_gen_roletransition(struct cil_tree_node *parse_current, struct cil_tree_
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad roletransition rule at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad roletransition rule");
 	cil_destroy_roletransition(roletrans);
 	return rc;
 }
@@ -1863,8 +1835,7 @@ int cil_gen_roleallow(struct cil_db *db, struct cil_tree_node *parse_current, st
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad roleallow rule at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad roleallow rule");
 	cil_destroy_roleallow(roleallow);
 	return rc;
 }
@@ -1915,8 +1886,7 @@ int cil_gen_roleattribute(struct cil_db *db, struct cil_tree_node *parse_current
 
 	return SEPOL_OK;
 exit:
-	cil_log(CIL_ERR, "Bad roleattribute declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad roleattribute declaration");
 	cil_destroy_roleattribute(attr);
 	cil_clear_node(ast_node);
 	return rc;
@@ -1983,8 +1953,7 @@ int cil_gen_roleattributeset(struct cil_db *db, struct cil_tree_node *parse_curr
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad roleattributeset declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad roleattributeset declaration");
 	cil_destroy_roleattributeset(attrset);
 
 	return rc;
@@ -2043,8 +2012,7 @@ int cil_gen_avrule(struct cil_tree_node *parse_current, struct cil_tree_node *as
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad allow rule at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad allow rule");
 	cil_destroy_avrule(rule);
 	return rc;
 }
@@ -2100,8 +2068,7 @@ int cil_fill_permissionx(struct cil_tree_node *parse_current, struct cil_permiss
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad permissionx content at line %d of %s\n",
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad permissionx content");
 	return rc;
 }
 
@@ -2144,8 +2111,7 @@ int cil_gen_permissionx(struct cil_db *db, struct cil_tree_node *parse_current,
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad permissionx statement at line %d of %s\n",
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad permissionx statement");
 	cil_destroy_permissionx(permx);
 	cil_clear_node(ast_node);
 	return rc;
@@ -2211,8 +2177,7 @@ int cil_gen_avrulex(struct cil_tree_node *parse_current, struct cil_tree_node *a
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad allowx rule at line %d of %s\n",
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad allowx rule");
 	cil_destroy_avrule(rule);
 	return rc;
 }
@@ -2254,8 +2219,7 @@ int cil_gen_type_rule(struct cil_tree_node *parse_current, struct cil_tree_node
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad type rule at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad type rule");
 	cil_destroy_type_rule(rule);
 	return rc;
 }
@@ -2307,8 +2271,7 @@ int cil_gen_type(struct cil_db *db, struct cil_tree_node *parse_current, struct
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad type declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad type declaration");
 	cil_destroy_type(type);
 	cil_clear_node(ast_node);
 	return rc;
@@ -2362,8 +2325,7 @@ int cil_gen_typeattribute(struct cil_db *db, struct cil_tree_node *parse_current
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad typeattribute declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad typeattribute declaration");
 	cil_destroy_typeattribute(attr);
 	cil_clear_node(ast_node);
 	return rc;
@@ -2440,11 +2402,9 @@ int cil_gen_bool(struct cil_db *db, struct cil_tree_node *parse_current, struct
 
 exit:
 	if (tunableif) {
-		cil_log(CIL_ERR, "Bad tunable (treated as a boolean due to preserve-tunables) declaration at line %d of %s\n",
-			parse_current->line, parse_current->path);
+		cil_tree_log(parse_current, CIL_ERR, "Bad tunable (treated as a boolean due to preserve-tunables) declaration");
 	} else {
-		cil_log(CIL_ERR, "Bad boolean declaration at line %d of %s\n",
-			parse_current->line, parse_current->path);
+		cil_tree_log(parse_current, CIL_ERR, "Bad boolean declaration");
 	}
 	cil_destroy_bool(boolean);
 	cil_clear_node(ast_node);
@@ -2505,8 +2465,7 @@ int cil_gen_tunable(struct cil_db *db, struct cil_tree_node *parse_current, stru
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad tunable declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad tunable declaration");
 	cil_destroy_tunable(tunable);
 	cil_clear_node(ast_node);
 	return rc;
@@ -2881,11 +2840,9 @@ int cil_gen_boolif(struct cil_db *db, struct cil_tree_node *parse_current, struc
 
 exit:
 	if (tunableif) {
-		cil_log(CIL_ERR, "Bad tunableif (treated as a booleanif due to preserve-tunables) declaration at line %d of %s\n",
-				parse_current->line, parse_current->path);
+		cil_tree_log(parse_current, CIL_ERR, "Bad tunableif (treated as a booleanif due to preserve-tunables) declaration");
 	} else {
-		cil_log(CIL_ERR, "Bad booleanif declaration at line %d of %s\n",
-				parse_current->line, parse_current->path);
+		cil_tree_log(parse_current, CIL_ERR, "Bad booleanif declaration");
 	}
 	cil_destroy_boolif(bif);
 	return rc;
@@ -2965,8 +2922,7 @@ int cil_gen_tunif(struct cil_db *db, struct cil_tree_node *parse_current, struct
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad tunableif declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad tunableif declaration");
 	cil_destroy_tunif(tif);
 	return rc;
 }
@@ -3019,8 +2975,8 @@ int cil_gen_condblock(struct cil_db *db, struct cil_tree_node *parse_current, st
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad %s condition declaration at line %d of %s\n",
-		(char*)parse_current->data, parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad %s condition declaration",
+		(char*)parse_current->data);
 	cil_destroy_condblock(cb);
 	return rc;
 }
@@ -3080,8 +3036,7 @@ int cil_gen_alias(struct cil_db *db, struct cil_tree_node *parse_current, struct
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad %s declaration at line %d of %s\n",
-		(char*)parse_current->data, parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad %s declaration", (char*)parse_current->data);
 	cil_destroy_alias(alias);
 	cil_clear_node(ast_node);
 	return rc;
@@ -3138,8 +3093,7 @@ int cil_gen_aliasactual(struct cil_db *db, struct cil_tree_node *parse_current,
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad %s association at line %d of %s\n", 
-			cil_node_to_string(parse_current),parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad %s association", cil_node_to_string(parse_current));
 	cil_clear_node(ast_node);
 	return rc;
 }
@@ -3188,8 +3142,7 @@ int cil_gen_typeattributeset(struct cil_db *db, struct cil_tree_node *parse_curr
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad typeattributeset statement at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad typeattributeset statement");
 	cil_destroy_typeattributeset(attrset);
 	return rc;
 }
@@ -3236,8 +3189,7 @@ int cil_gen_typepermissive(struct cil_db *db, struct cil_tree_node *parse_curren
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad typepermissive declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad typepermissive declaration");
 	cil_destroy_typepermissive(typeperm);
 	return rc;
 }
@@ -3320,8 +3272,7 @@ int cil_gen_typetransition(struct cil_db *db, struct cil_tree_node *parse_curren
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad typetransition declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad typetransition declaration");
 	return rc;
 }
 
@@ -3392,8 +3343,7 @@ int cil_gen_rangetransition(struct cil_db *db, struct cil_tree_node *parse_curre
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad rangetransition declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad rangetransition declaration");
 	cil_destroy_rangetransition(rangetrans);
 	return rc;
 }
@@ -3444,8 +3394,7 @@ int cil_gen_sensitivity(struct cil_db *db, struct cil_tree_node *parse_current,
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad sensitivity declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad sensitivity declaration");
 	cil_destroy_sensitivity(sens);
 	cil_clear_node(ast_node);
 	return rc;
@@ -3497,8 +3446,7 @@ int cil_gen_category(struct cil_db *db, struct cil_tree_node *parse_current, str
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad category declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad category declaration");
 	cil_destroy_category(cat);
 	cil_clear_node(ast_node);
 	return rc;
@@ -3553,8 +3501,7 @@ int cil_gen_catset(struct cil_db *db, struct cil_tree_node *parse_current, struc
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad categoryset declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad categoryset declaration");
 	cil_destroy_catset(catset);
 	cil_clear_node(ast_node);
 	return rc;
@@ -3615,8 +3562,7 @@ int cil_gen_catorder(struct cil_db *db, struct cil_tree_node *parse_current, str
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad categoryorder declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad categoryorder declaration");
 	cil_destroy_catorder(catorder);
 	return rc;
 }
@@ -3676,8 +3622,7 @@ int cil_gen_sensitivityorder(struct cil_db *db, struct cil_tree_node *parse_curr
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad sensitivityorder declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad sensitivityorder declaration");
 	cil_destroy_sensitivityorder(sensorder);
 	return rc;
 }
@@ -3731,8 +3676,7 @@ int cil_gen_senscat(struct cil_db *db, struct cil_tree_node *parse_current, stru
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad sensitivitycategory declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad sensitivitycategory declaration");
 	cil_destroy_senscat(senscat);
 	return rc;
 }
@@ -3787,8 +3731,7 @@ int cil_gen_level(struct cil_db *db, struct cil_tree_node *parse_current, struct
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad level declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad level declaration");
 	cil_destroy_level(level);
 	cil_clear_node(ast_node);
 	return rc;
@@ -3894,8 +3837,7 @@ int cil_gen_levelrange(struct cil_db *db, struct cil_tree_node *parse_current, s
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad levelrange declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad levelrange declaration");
 	cil_destroy_levelrange(lvlrange);
 	cil_clear_node(ast_node);
 	return rc;
@@ -3959,8 +3901,7 @@ int cil_gen_constrain(struct cil_db *db, struct cil_tree_node *parse_current, st
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad constrain declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad constrain declaration");
 	cil_destroy_constrain(cons);
 	return rc;
 }
@@ -4014,8 +3955,7 @@ int cil_gen_validatetrans(struct cil_db *db, struct cil_tree_node *parse_current
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad validatetrans declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad validatetrans declaration");
 	cil_destroy_validatetrans(validtrans);
 	return rc;
 
@@ -4119,8 +4059,7 @@ int cil_gen_context(struct cil_db *db, struct cil_tree_node *parse_current, stru
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad context declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad context declaration");
 	cil_destroy_context(context);
 	cil_clear_node(ast_node);
 	return SEPOL_ERR;
@@ -4212,8 +4151,7 @@ int cil_gen_filecon(struct cil_db *db, struct cil_tree_node *parse_current, stru
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad filecon declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad filecon declaration");
 	cil_destroy_filecon(filecon);
 	return rc;
 }
@@ -4314,8 +4252,7 @@ int cil_gen_portcon(struct cil_db *db, struct cil_tree_node *parse_current, stru
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad portcon declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad portcon declaration");
 	cil_destroy_portcon(portcon);
 	return rc;
 }
@@ -4396,8 +4333,7 @@ int cil_gen_nodecon(struct cil_db *db, struct cil_tree_node *parse_current, stru
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad nodecon declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad nodecon declaration");
 	cil_destroy_nodecon(nodecon);
 	return rc;
 }
@@ -4467,8 +4403,7 @@ int cil_gen_genfscon(struct cil_db *db, struct cil_tree_node *parse_current, str
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad genfscon declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad genfscon declaration");
 	cil_destroy_genfscon(genfscon);
 	return SEPOL_ERR;
 }
@@ -4541,8 +4476,7 @@ int cil_gen_netifcon(struct cil_db *db, struct cil_tree_node *parse_current, str
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad netifcon declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad netifcon declaration");
 	cil_destroy_netifcon(netifcon);
 	return SEPOL_ERR;
 }
@@ -4609,8 +4543,7 @@ int cil_gen_pirqcon(struct cil_db *db, struct cil_tree_node *parse_current, stru
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad pirqcon declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad pirqcon declaration");
 	cil_destroy_pirqcon(pirqcon);
 	return rc;
 }
@@ -4695,8 +4628,7 @@ int cil_gen_iomemcon(struct cil_db *db, struct cil_tree_node *parse_current, str
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad iomemcon declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad iomemcon declaration");
 	cil_destroy_iomemcon(iomemcon);
 	return rc;
 }
@@ -4781,8 +4713,7 @@ int cil_gen_ioportcon(struct cil_db *db, struct cil_tree_node *parse_current, st
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad ioportcon declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad ioportcon declaration");
 	cil_destroy_ioportcon(ioportcon);
 	return rc;
 }
@@ -4845,8 +4776,7 @@ int cil_gen_pcidevicecon(struct cil_db *db, struct cil_tree_node *parse_current,
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad pcidevicecon declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad pcidevicecon declaration");
 	cil_destroy_pcidevicecon(pcidevicecon);
 	return rc;
 }
@@ -4906,8 +4836,7 @@ int cil_gen_devicetreecon(struct cil_db *db, struct cil_tree_node *parse_current
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad devicetreecon declaration at line %d of %s\n",
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad devicetreecon declaration");
 	cil_destroy_devicetreecon(devicetreecon);
 	return rc;
 }
@@ -4982,8 +4911,7 @@ int cil_gen_fsuse(struct cil_db *db, struct cil_tree_node *parse_current, struct
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad fsuse declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad fsuse declaration");
 	cil_destroy_fsuse(fsuse);
 	return SEPOL_ERR;
 }
@@ -5140,8 +5068,7 @@ int cil_gen_macro(struct cil_db *db, struct cil_tree_node *parse_current, struct
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad macro declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad macro declaration");
 	cil_destroy_macro(macro);
 	cil_clear_node(ast_node);
 	return SEPOL_ERR;
@@ -5199,8 +5126,7 @@ int cil_gen_call(struct cil_db *db, struct cil_tree_node *parse_current, struct
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad macro call at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad macro call");
 	cil_destroy_call(call);
 	return rc;
 }
@@ -5302,8 +5228,7 @@ int cil_gen_optional(struct cil_db *db, struct cil_tree_node *parse_current, str
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad optional at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad optional");
 	cil_destroy_optional(optional);
 	cil_clear_node(ast_node);
 	return rc;
@@ -5351,8 +5276,7 @@ int cil_gen_policycap(struct cil_db *db, struct cil_tree_node *parse_current, st
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad policycap statement at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad policycap statement");
 	cil_destroy_policycap(polcap);
 	cil_clear_node(ast_node);
 	return rc;
@@ -5407,8 +5331,7 @@ int cil_gen_ipaddr(struct cil_db *db, struct cil_tree_node *parse_current, struc
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad ipaddr statement at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad ipaddr statement");
 	cil_destroy_ipaddr(ipaddr);
 	cil_clear_node(ast_node);
 	return rc;
@@ -5612,8 +5535,7 @@ int cil_gen_bounds(struct cil_db *db, struct cil_tree_node *parse_current, struc
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad bounds declaration at line %d of %s\n", 
-		parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad bounds declaration");
 	cil_destroy_bounds(bounds);
 	return rc;
 }
@@ -5674,8 +5596,7 @@ int cil_gen_default(struct cil_tree_node *parse_current, struct cil_tree_node *a
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad %s declaration at line %d of %s\n", 
-			cil_node_to_string(parse_current), parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad %s declaration", cil_node_to_string(parse_current));
 	cil_destroy_default(def);
 	return rc;
 }
@@ -5761,8 +5682,7 @@ int cil_gen_defaultrange(struct cil_tree_node *parse_current, struct cil_tree_no
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad defaultrange declaration at line %d of %s\n", 
-			parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad defaultrange declaration");
 	cil_destroy_defaultrange(def);
 	return rc;
 }
@@ -5822,8 +5742,7 @@ int cil_gen_handleunknown(struct cil_tree_node *parse_current, struct cil_tree_n
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad handleunknown at line %d of %s\n",
-			parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad handleunknown");
 	cil_destroy_handleunknown(unknown);
 	return rc;
 }
@@ -5871,8 +5790,7 @@ int cil_gen_mls(struct cil_tree_node *parse_current, struct cil_tree_node *ast_n
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad mls at line %d of %s\n",
-			parse_current->line, parse_current->path);
+	cil_tree_log(parse_current, CIL_ERR, "Bad mls");
 	cil_destroy_mls(mls);
 	return rc;
 }
@@ -5937,7 +5855,7 @@ int __cil_build_ast_node_helper(struct cil_tree_node *parse_current, uint32_t *f
 		if (parse_current->parent->parent == NULL) {
 			rc = SEPOL_OK;
 		} else {
-			cil_log(CIL_ERR, "Keyword expected after open parenthesis in line %d of %s\n", parse_current->line, parse_current->path);
+			cil_tree_log(parse_current, CIL_ERR, "Keyword expected after open parenthesis");
 		}
 		goto exit;
 	}
@@ -5950,7 +5868,7 @@ int __cil_build_ast_node_helper(struct cil_tree_node *parse_current, uint32_t *f
 			parse_current->data == CIL_KEY_BLOCKINHERIT ||
 			parse_current->data == CIL_KEY_BLOCKABSTRACT) {
 			rc = SEPOL_ERR;
-			cil_log(CIL_ERR, "%s is not allowed in macros (%s:%d)\n", (char *)parse_current->data, parse_current->path, parse_current->line);
+			cil_tree_log(parse_current, CIL_ERR, "%s is not allowed in macros", (char *)parse_current->data);
 			goto exit;
 		}
 	}
@@ -5966,8 +5884,7 @@ int __cil_build_ast_node_helper(struct cil_tree_node *parse_current, uint32_t *f
 			parse_current->data != CIL_KEY_TYPECHANGE &&
 			parse_current->data != CIL_KEY_CALL) {
 			rc = SEPOL_ERR;
-			cil_log(CIL_ERR, "Found %s at line %d of %s\n",
-				(char*)parse_current->data, parse_current->line, parse_current->path);
+			cil_tree_log(parse_current, CIL_ERR, "Found %s", (char*)parse_current->data);
 			if (((struct cil_booleanif*)boolif->data)->preserved_tunable) {
 				cil_log(CIL_ERR, "%s cannot be defined within tunableif statement (treated as a booleanif due to preserve-tunables)\n",
 						(char*)parse_current->data);
@@ -5982,8 +5899,7 @@ int __cil_build_ast_node_helper(struct cil_tree_node *parse_current, uint32_t *f
 	if (tunif != NULL) {
 		if (parse_current->data == CIL_KEY_TUNABLE) {
 			rc = SEPOL_ERR;
-			cil_log(CIL_ERR, "Found tunable at line %d of %s\n",
-				parse_current->line, parse_current->path);
+			cil_tree_log(parse_current, CIL_ERR, "Found tunable");
 			cil_log(CIL_ERR, "Tunables cannot be defined within tunableif statement\n");
 			goto exit;
 		}
@@ -5992,8 +5908,7 @@ int __cil_build_ast_node_helper(struct cil_tree_node *parse_current, uint32_t *f
 	if (in != NULL) {
 		if (parse_current->data == CIL_KEY_IN) {
 			rc = SEPOL_ERR;
-			cil_log(CIL_ERR, "Found in-statement at line %d of %s\n",
-				parse_current->line, parse_current->path);
+			cil_tree_log(parse_current, CIL_ERR, "Found in-statement");
 			cil_log(CIL_ERR, "in-statements cannot be defined within in-statements\n");
 			goto exit;
 		}
diff --git a/libsepol/cil/src/cil_copy_ast.c b/libsepol/cil/src/cil_copy_ast.c
index 5615b30..ad69781 100644
--- a/libsepol/cil/src/cil_copy_ast.c
+++ b/libsepol/cil/src/cil_copy_ast.c
@@ -2004,8 +2004,8 @@ int __cil_copy_node_helper(struct cil_tree_node *orig, __attribute__((unused)) u
 						param = item->data;
 						if (param->flavor == new->flavor) {
 							if (param->str == ((struct cil_symtab_datum*)new->data)->name) {
-								cil_log(CIL_ERR, "%s %s shadows a macro parameter (%s line:%d)\n", cil_node_to_string(new), ((struct cil_symtab_datum*)orig->data)->name, orig->path, orig->line);
-								cil_log(CIL_ERR, "Note: macro declaration (%s line:%d)\n", namespace->path, namespace->line);
+								cil_tree_log(orig, CIL_ERR, "%s %s shadows a macro parameter", cil_node_to_string(new), ((struct cil_symtab_datum*)orig->data)->name);
+								cil_tree_log(namespace, CIL_ERR, "Note: macro declaration");
 								rc = SEPOL_ERR;
 								goto exit;
 							}
diff --git a/libsepol/cil/src/cil_fqn.c b/libsepol/cil/src/cil_fqn.c
index 865bd7d..dad1347 100644
--- a/libsepol/cil/src/cil_fqn.c
+++ b/libsepol/cil/src/cil_fqn.c
@@ -121,7 +121,7 @@ static int __cil_fqn_qualify_blocks(__attribute__((unused)) hashtab_key_t k, has
 
 exit:
 	if (rc != SEPOL_OK) {
-		cil_log(CIL_ERR,"Problem qualifying names in block at line %d of %s\n", child_args.node->line, child_args.node->path);
+		cil_tree_log(child_args.node, CIL_ERR,"Problem qualifying names in block");
 	}
 
 	return rc;
diff --git a/libsepol/cil/src/cil_resolve_ast.c b/libsepol/cil/src/cil_resolve_ast.c
index 1489680..70e4462 100644
--- a/libsepol/cil/src/cil_resolve_ast.c
+++ b/libsepol/cil/src/cil_resolve_ast.c
@@ -497,7 +497,7 @@ int cil_resolve_alias_to_actual(struct cil_tree_node *current, enum cil_flavor f
 	int limit = 2;
 
 	if (alias->actual == NULL) {
-		cil_log(CIL_ERR, "Alias declared but not used at line %d of %s\n",current->line, current->path);
+		cil_tree_log(current, CIL_ERR, "Alias declared but not used");
 		return SEPOL_ERR;
 	}
 
@@ -1380,7 +1380,7 @@ struct cil_list *__cil_ordered_lists_merge_all(struct cil_list **ordered_lists,
 			cil_list_for_each(curr, *ordered_lists) {
 				struct cil_ordered_list *ordered_list = curr->data;
 				if (ordered_list->merged == CIL_FALSE) {
-					cil_log(CIL_ERR, "Unable to merge ordered list at line %d of %s\n",ordered_list->node->line, ordered_list->node->path);
+					cil_tree_log(ordered_list->node, CIL_ERR, "Unable to merge ordered list");
 				}
 			}
 			goto exit;
@@ -2252,12 +2252,10 @@ void cil_print_recursive_blockinherit(struct cil_tree_node *bi_node, struct cil_
 
 	cil_list_for_each(item, trace) {
 		curr = item->data;
-		cil_log(CIL_ERR, "  %s:%d: ", curr->path, curr->line);
-
 		if (curr->flavor == CIL_BLOCK) {
-			cil_log(CIL_ERR, "block %s\n", DATUM(curr->data)->name);
+			cil_tree_log(curr, CIL_ERR, "block %s", DATUM(curr->data)->name);
 		} else {
-			cil_log(CIL_ERR, "blockinherit %s\n", ((struct cil_blockinherit *)curr->data)->block_str);
+			cil_tree_log(curr, CIL_ERR, "blockinherit %s", ((struct cil_blockinherit *)curr->data)->block_str);
 		}
 	}
 
@@ -2442,7 +2440,7 @@ int cil_resolve_in_list(void *extra_args)
 		}
 
 		if (unresolved > 0 && resolved == 0) {
-			cil_log(CIL_ERR, "Failed to resolve in-statement on line %d of %s\n", last_failed_node->line, last_failed_node->path);
+			cil_tree_log(last_failed_node, CIL_ERR, "Failed to resolve in-statement");
 			rc = SEPOL_ERR;
 			goto exit;
 		}
@@ -2485,7 +2483,7 @@ int cil_resolve_bounds(struct cil_tree_node *current, void *extra_args, enum cil
 
 		if (user->bounds != NULL) {
 			struct cil_tree_node *node = user->bounds->datum.nodes->head->data;
-			cil_log(CIL_ERR, "User %s already bound by parent at line %u of %s\n", bounds->child_str, node->line, node->path);
+			cil_tree_log(node, CIL_ERR, "User %s already bound by parent", bounds->child_str);
 			rc = SEPOL_ERR;
 			goto exit;
 		}
@@ -2498,7 +2496,7 @@ int cil_resolve_bounds(struct cil_tree_node *current, void *extra_args, enum cil
 
 		if (role->bounds != NULL) {
 			struct cil_tree_node *node = role->bounds->datum.nodes->head->data;
-			cil_log(CIL_ERR, "Role %s already bound by parent at line %u of %s\n", bounds->child_str, node->line, node->path);
+			cil_tree_log(node, CIL_ERR, "Role %s already bound by parent", bounds->child_str);
 			rc = SEPOL_ERR;
 			goto exit;
 		}
@@ -2512,8 +2510,8 @@ int cil_resolve_bounds(struct cil_tree_node *current, void *extra_args, enum cil
 
 		if (type->bounds != NULL) {
 			node = ((struct cil_symtab_datum *)type->bounds)->nodes->head->data;
-			cil_log(CIL_ERR, "Type %s already bound by parent at line %u of %s\n", bounds->child_str, node->line, node->path);
-			cil_log(CIL_ERR, "Now being bound to parent %s at line %u of %s\n", bounds->parent_str, current->line, current->path);
+			cil_tree_log(node, CIL_ERR, "Type %s already bound by parent", bounds->child_str);
+			cil_tree_log(current, CIL_ERR, "Now being bound to parent %s", bounds->parent_str);
 			rc = SEPOL_ERR;
 			goto exit;
 		}
@@ -2542,7 +2540,7 @@ int cil_resolve_bounds(struct cil_tree_node *current, void *extra_args, enum cil
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Bad bounds statement at line %u of %s\n", current->line, current->path);
+	cil_tree_log(current, CIL_ERR, "Bad bounds statement");
 	return rc;
 }
 
@@ -2617,12 +2615,10 @@ void cil_print_recursive_call(struct cil_tree_node *call_node, struct cil_tree_n
 
 	cil_list_for_each(item, trace) {
 		curr = item->data;
-		cil_log(CIL_ERR, "  %s:%d: ", curr->path, curr->line);
-
 		if (curr->flavor == CIL_MACRO) {
-			cil_log(CIL_ERR, "macro %s\n", DATUM(curr->data)->name);
+			cil_tree_log(curr, CIL_ERR, "macro %s", DATUM(curr->data)->name);
 		} else {
-			cil_log(CIL_ERR, "call %s\n", ((struct cil_call *)curr->data)->macro_str);
+			cil_tree_log(curr, CIL_ERR, "call %s", ((struct cil_call *)curr->data)->macro_str);
 		}
 	}
 
@@ -2700,7 +2696,7 @@ int cil_resolve_call1(struct cil_tree_node *current, void *extra_args)
 		struct cil_tree_node *pc = NULL;
 
 		if (new_call->args_tree == NULL) {
-			cil_log(CIL_ERR, "Missing arguments (%s, line: %d)\n", current->path, current->line);
+			cil_tree_log(current, CIL_ERR, "Missing arguments");
 			rc = SEPOL_ERR;
 			goto exit;
 		}
@@ -2713,7 +2709,7 @@ int cil_resolve_call1(struct cil_tree_node *current, void *extra_args)
 			enum cil_flavor flavor = ((struct cil_param*)item->data)->flavor;
 
 			if (pc == NULL) {
-				cil_log(CIL_ERR, "Missing arguments (%s, line: %d)\n", current->path, current->line);
+				cil_tree_log(current, CIL_ERR, "Missing arguments");
 				rc = SEPOL_ERR;
 				goto exit;
 			}
@@ -2890,12 +2886,12 @@ int cil_resolve_call1(struct cil_tree_node *current, void *extra_args)
 		}
 
 		if (pc != NULL) {
-			cil_log(CIL_ERR, "Unexpected arguments (%s, line: %d)\n", current->path, current->line);
+			cil_tree_log(current, CIL_ERR, "Unexpected arguments");
 			rc = SEPOL_ERR;
 			goto exit;
 		}
 	} else if (new_call->args_tree != NULL) {
-		cil_log(CIL_ERR, "Unexpected arguments (%s, line: %d)\n", current->path, current->line);
+		cil_tree_log(current, CIL_ERR, "Unexpected arguments");
 		rc = SEPOL_ERR;
 		goto exit;
 	}
@@ -3593,7 +3589,7 @@ int __cil_resolve_ast_node_helper(struct cil_tree_node *node, uint32_t *finished
 	if (optstack != NULL) {
 		if (node->flavor == CIL_TUNABLE || node->flavor == CIL_MACRO) {
 			/* tuanbles and macros are not allowed in optionals*/
-			cil_log(CIL_ERR, "%s statement is not allowed in optionals (%s:%d)\n", cil_node_to_string(node), node->path, node->line);
+			cil_tree_log(node, CIL_ERR, "%s statement is not allowed in optionals", cil_node_to_string(node));
 			rc = SEPOL_ERR;
 			goto exit;
 		}
@@ -3601,7 +3597,7 @@ int __cil_resolve_ast_node_helper(struct cil_tree_node *node, uint32_t *finished
 
 	if (blockstack != NULL) {
 		if (node->flavor == CIL_CAT || node->flavor == CIL_SENS) {
-			cil_log(CIL_ERR, "%s statement is not allowed in blocks (%s:%d)\n", cil_node_to_string(node), node->path, node->line);
+			cil_tree_log(node, CIL_ERR, "%s statement is not allowed in blocks", cil_node_to_string(node));
 			rc = SEPOL_ERR;
 			goto exit;
 		}
@@ -3612,7 +3608,7 @@ int __cil_resolve_ast_node_helper(struct cil_tree_node *node, uint32_t *finished
 			node->flavor == CIL_BLOCK ||
 			node->flavor == CIL_BLOCKABSTRACT ||
 			node->flavor == CIL_MACRO) {
-			cil_log(CIL_ERR, "%s statement is not allowed in macros (%s:%d)\n", cil_node_to_string(node), node->path, node->line);
+			cil_tree_log(node, CIL_ERR, "%s statement is not allowed in macros", cil_node_to_string(node));
 			rc = SEPOL_ERR;
 			goto exit;
 		}
@@ -3626,9 +3622,9 @@ int __cil_resolve_ast_node_helper(struct cil_tree_node *node, uint32_t *finished
 			node->flavor == CIL_TUNABLEIF ||
 			node->flavor == CIL_NAMETYPETRANSITION)) {
 			if (((struct cil_booleanif*)boolif->data)->preserved_tunable) {
-				cil_log(CIL_ERR, "%s statement is not allowed in booleanifs (tunableif treated as a booleanif) (%s:%d)\n", cil_node_to_string(node), node->path, node->line);
+				cil_tree_log(node, CIL_ERR, "%s statement is not allowed in booleanifs (tunableif treated as a booleanif)", cil_node_to_string(node));
 			} else {
-				cil_log(CIL_ERR, "%s statement is not allowed in booleanifs (%s:%d)\n", cil_node_to_string(node), node->path, node->line);
+				cil_tree_log(node, CIL_ERR, "%s statement is not allowed in booleanifs", cil_node_to_string(node));
 			}
 			rc = SEPOL_ERR;
 			goto exit;
@@ -3658,14 +3654,13 @@ int __cil_resolve_ast_node_helper(struct cil_tree_node *node, uint32_t *finished
 
 			struct cil_optional *opt = (struct cil_optional *)optstack->data;
 			struct cil_tree_node *opt_node = opt->datum.nodes->head->data;
-			cil_log(lvl, "Disabling optional '%s' at line %d of %s: ", opt->datum.name, opt_node->line, opt_node->path);
+			cil_tree_log(opt_node, lvl, "Disabling optional '%s'", opt->datum.name);
 			/* disable an optional if something failed to resolve */
 			opt->enabled = CIL_FALSE;
 			rc = SEPOL_OK;
 		}
 
-		cil_log(lvl, "Failed to resolve '%s' in %s statement at line %d of %s\n",
-		        args->last_resolved_name, cil_node_to_string(node), node->line, node->path);
+		cil_tree_log(node, lvl, "Failed to resolve '%s' in %s statement", args->last_resolved_name, cil_node_to_string(node));
 		goto exit;
 	}
 
diff --git a/libsepol/cil/src/cil_tree.c b/libsepol/cil/src/cil_tree.c
index 33cc4f8..7dc1a1e 100644
--- a/libsepol/cil/src/cil_tree.c
+++ b/libsepol/cil/src/cil_tree.c
@@ -272,7 +272,7 @@ int cil_tree_walk_core(struct cil_tree_node *node,
 		if (process_node != NULL) {
 			rc = (*process_node)(node, &finished, extra_args);
 			if (rc != SEPOL_OK) {
-				cil_log(CIL_INFO, "Problem at line %d of %s\n", node->line, node->path);
+				cil_tree_log(node, CIL_INFO, "Problem");
 				return rc;
 			}
 		}
@@ -309,7 +309,7 @@ int cil_tree_walk(struct cil_tree_node *node,
 	if (first_child != NULL) {
 		rc = (*first_child)(node->cl_head, extra_args);
 		if (rc != SEPOL_OK) {
-			cil_log(CIL_INFO, "Problem at line %d of %s\n", node->line, node->path);
+			cil_tree_log(node, CIL_INFO, "Problem");
 			return rc;
 		}
 	}
@@ -322,7 +322,7 @@ int cil_tree_walk(struct cil_tree_node *node,
 	if (last_child != NULL) {
 		rc = (*last_child)(node->cl_tail, extra_args);
 		if (rc != SEPOL_OK) {
-			cil_log(CIL_INFO, "Problem at line %d of %s\n",node->line, node->path);
+			cil_tree_log(node, CIL_INFO, "Problem");
 			return rc;
 		}
 	}
diff --git a/libsepol/cil/src/cil_verify.c b/libsepol/cil/src/cil_verify.c
index 36ec45a..038f77a 100644
--- a/libsepol/cil/src/cil_verify.c
+++ b/libsepol/cil/src/cil_verify.c
@@ -377,25 +377,25 @@ int __cil_verify_ordered_node_helper(struct cil_tree_node *node, __attribute__((
 		if (node->flavor == CIL_SID) {
 			struct cil_sid *sid = node->data;
 			if (sid->ordered == CIL_FALSE) {
-				cil_log(CIL_ERR, "SID %s not in sidorder statement at line %d of %s\n", sid->datum.name, node->line, node->path);
+				cil_tree_log(node, CIL_ERR, "SID %s not in sidorder statement", sid->datum.name);
 				return SEPOL_ERR;
 			}
 		} else if (node->flavor == CIL_CLASS) {
 			struct cil_class *class = node->data;
 			if (class->ordered == CIL_FALSE) {
-				cil_log(CIL_ERR, "Class %s not in classorder statement at line %d of %s\n", class->datum.name, node->line, node->path);
+				cil_tree_log(node, CIL_ERR, "Class %s not in classorder statement", class->datum.name);
 				return SEPOL_ERR;
 			}
 		} else if (node->flavor == CIL_CAT) {
 			struct cil_cat *cat = node->data;
 			if (cat->ordered == CIL_FALSE) {
-				cil_log(CIL_ERR, "Category %s not in categoryorder statement at line %d of %s\n", cat->datum.name, node->line, node->path);
+				cil_tree_log(node, CIL_ERR, "Category %s not in categoryorder statement", cat->datum.name);
 				return SEPOL_ERR;
 			}
 		} else if (node->flavor == CIL_SENS) {
 			struct cil_sens *sens = node->data;
 			if (sens->ordered == CIL_FALSE) {
-				cil_log(CIL_ERR, "Sensitivity %s not in sensitivityorder statement at line %d of %s\n", sens->datum.name, node->line, node->path);
+				cil_tree_log(node, CIL_ERR, "Sensitivity %s not in sensitivityorder statement", sens->datum.name);
 				return SEPOL_ERR;
 			}
 		}
@@ -430,7 +430,7 @@ int __cil_verify_initsids(struct cil_list *sids)
 		struct cil_sid *sid = i->data;
 		if (sid->context == NULL) {
 			struct cil_tree_node *node = sid->datum.nodes->head->data;
-			cil_log(CIL_ERR, "No context assigned to SID %s declared at line %d in %s\n",sid->datum.name, node->line, node->path);
+			cil_tree_log(node, CIL_ERR, "No context assigned to SID %s declared",sid->datum.name);
 			rc = SEPOL_ERR;
 		}
 	}
@@ -598,7 +598,7 @@ int __cil_verify_named_levelrange(struct cil_db *db, struct cil_tree_node *node)
 
 	return SEPOL_OK;
 exit:
-	cil_log(CIL_ERR, "Invalid named range at line %d of %s\n", node->line, node->path);
+	cil_tree_log(node, CIL_ERR, "Invalid named range");
 	return rc;
 }
 
@@ -638,7 +638,7 @@ static int __cil_verify_user_pre_eval(struct cil_tree_node *node)
 
 	return SEPOL_OK;
 exit:
-	cil_log(CIL_ERR, "Invalid user at line %d of %s\n", node->line, node->path);
+	cil_tree_log(node, CIL_ERR, "Invalid user");
 	return rc;
 }
 
@@ -657,7 +657,7 @@ static int __cil_verify_user_post_eval(struct cil_db *db, struct cil_tree_node *
 
 	return SEPOL_OK;
 exit:
-	cil_log(CIL_ERR, "Invalid user at line %d of %s\n", node->line, node->path);
+	cil_tree_log(node, CIL_ERR, "Invalid user");
 	return rc;
 }
 
@@ -688,7 +688,7 @@ int __cil_verify_role(struct cil_tree_node *node)
 
 	return SEPOL_OK;
 exit:
-	cil_log(CIL_ERR, "Invalid role at line %d of %s\n", node->line, node->path);
+	cil_tree_log(node, CIL_ERR, "Invalid role");
 	return rc;
 }
 
@@ -719,7 +719,7 @@ int __cil_verify_type(struct cil_tree_node *node)
 
 	return SEPOL_OK;
 exit:
-	cil_log(CIL_ERR, "Invalid type at line %d of %s\n", node->line, node->path);
+	cil_tree_log(node, CIL_ERR, "Invalid type");
 	return rc;
 }
 
@@ -813,7 +813,7 @@ int __cil_verify_named_context(struct cil_db *db, struct cil_tree_node *node)
 
 	return SEPOL_OK;
 exit:
-	cil_log(CIL_ERR, "Invalid named context at line %d of %s\n", node->line, node->path);
+	cil_tree_log(node, CIL_ERR, "Invalid named context");
 	return rc;
 }
 
@@ -852,8 +852,7 @@ int __cil_verify_rule(struct cil_tree_node *node, struct cil_complex_symtab *sym
 		struct cil_complex_symtab_datum *datum = NULL;
 		cil_complex_symtab_search(symtab, &ckey, &datum);
 		if (datum == NULL) {
-			cil_log(CIL_ERR, "Duplicate rule defined on line %d of %s\n", 
-				node->line, node->path);
+			cil_tree_log(node, CIL_ERR, "Duplicate rule defined");
 			rc = SEPOL_ERR;
 			goto exit;
 		}
@@ -861,7 +860,7 @@ int __cil_verify_rule(struct cil_tree_node *node, struct cil_complex_symtab *sym
 
 	return SEPOL_OK;
 exit:
-	cil_log(CIL_ERR, "Invalid rule at line %d of %s\n", node->line, node->path);
+	cil_tree_log(node, CIL_ERR, "Invalid rule");
 	return rc;
 }
 
@@ -877,11 +876,9 @@ int __cil_verify_booleanif_helper(struct cil_tree_node *node, __attribute__((unu
 		avrule = rule_node->data;
 		if (avrule->rule_kind == CIL_AVRULE_NEVERALLOW) {
 			if (bif->preserved_tunable) {
-				cil_log(CIL_ERR, "Neverallow found in tunableif block (treated as a booleanif due to preserve-tunables) at line %d or %s\n",
-					node->line, node->path);
+				cil_tree_log(node, CIL_ERR, "Neverallow found in tunableif block (treated as a booleanif due to preserve-tunables)");
 			} else {
-				cil_log(CIL_ERR, "Neverallow found in booleanif block at line %d or %s\n",
-					node->line, node->path);
+				cil_tree_log(node, CIL_ERR, "Neverallow found in booleanif block");
 			}
 			rc = SEPOL_ERR;
 			goto exit;
@@ -942,11 +939,9 @@ int __cil_verify_booleanif_helper(struct cil_tree_node *node, __attribute__((unu
 	default: {
 		const char * flavor = cil_node_to_string(node);
 		if (bif->preserved_tunable) {
-			cil_log(CIL_ERR, "Invalid %s statement in tunableif (treated as a booleanif due to preserve-tunables) at line %d of %s\n",
-					flavor, node->line, node->path);
+			cil_tree_log(node, CIL_ERR, "Invalid %s statement in tunableif (treated as a booleanif due to preserve-tunables)", flavor);
 		} else {
-			cil_log(CIL_ERR, "Invalid %s statement in booleanif at line %d of %s\n",
-					flavor, node->line, node->path);
+			cil_tree_log(node, CIL_ERR, "Invalid %s statement in booleanif", flavor);
 		}
 		goto exit;
 	}
@@ -974,9 +969,9 @@ int __cil_verify_booleanif(struct cil_tree_node *node, struct cil_complex_symtab
 	return SEPOL_OK;
 exit:
 	if (bif->preserved_tunable) {
-		cil_log(CIL_ERR, "Invalid tunableif (treated as a booleanif due to preserve-tunables) at line %d of %s\n", node->line, node->path);
+		cil_tree_log(node, CIL_ERR, "Invalid tunableif (treated as a booleanif due to preserve-tunables)");
 	} else {
-		cil_log(CIL_ERR, "Invalid booleanif at line %d of %s\n", node->line, node->path);
+		cil_tree_log(node, CIL_ERR, "Invalid booleanif");
 	}
 	return rc;
 }
@@ -1007,7 +1002,7 @@ int __cil_verify_netifcon(struct cil_db *db, struct cil_tree_node *node)
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Invalid netifcon at line %d of %s\n", node->line, node->path);
+	cil_tree_log(node, CIL_ERR, "Invalid netifcon");
 	return rc;
 }
 
@@ -1028,7 +1023,7 @@ int __cil_verify_genfscon(struct cil_db *db, struct cil_tree_node *node)
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Invalid genfscon at line %d of %s\n", node->line, node->path);
+	cil_tree_log(node, CIL_ERR, "Invalid genfscon");
 	return rc;
 }
 
@@ -1047,8 +1042,7 @@ int __cil_verify_filecon(struct cil_db *db, struct cil_tree_node *node)
 	if (ctx->datum.name == NULL) {
 		rc = __cil_verify_context(db, ctx);
 		if (rc != SEPOL_OK) {
-			cil_log(CIL_ERR, "Invalid filecon at line %d of %s\n", 
-				node->line, node->path);
+			cil_tree_log(node, CIL_ERR, "Invalid filecon");
 			goto exit;
 		}
 	}
@@ -1076,7 +1070,7 @@ int __cil_verify_nodecon(struct cil_db *db, struct cil_tree_node *node)
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Invalid nodecon at line %d of %s\n", node->line, node->path);
+	cil_tree_log(node, CIL_ERR, "Invalid nodecon");
 	return rc;
 }
 
@@ -1097,7 +1091,7 @@ int __cil_verify_portcon(struct cil_db *db, struct cil_tree_node *node)
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Invalid portcon at line %d of %s\n", node->line, node->path);
+	cil_tree_log(node, CIL_ERR, "Invalid portcon");
 	return rc;
 }
 
@@ -1118,7 +1112,7 @@ int __cil_verify_pirqcon(struct cil_db *db, struct cil_tree_node *node)
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Invalid pirqcon at line %d of %s\n", node->line, node->path);
+	cil_tree_log(node, CIL_ERR, "Invalid pirqcon");
 	return rc;
 }
 
@@ -1139,7 +1133,7 @@ int __cil_verify_iomemcon(struct cil_db *db, struct cil_tree_node *node)
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Invalid iomemcon at line %d of %s\n", node->line, node->path);
+	cil_tree_log(node, CIL_ERR, "Invalid iomemcon");
 	return rc;
 }
 
@@ -1160,7 +1154,7 @@ int __cil_verify_ioportcon(struct cil_db *db, struct cil_tree_node *node)
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Invalid ioportcon at line %d of %s\n", node->line, node->path);
+	cil_tree_log(node, CIL_ERR, "Invalid ioportcon");
 	return rc;
 }
 
@@ -1181,7 +1175,7 @@ int __cil_verify_pcidevicecon(struct cil_db *db, struct cil_tree_node *node)
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Invalid pcidevicecon at line %d of %s\n", node->line, node->path);
+	cil_tree_log(node, CIL_ERR, "Invalid pcidevicecon");
 	return rc;
 }
 
@@ -1202,7 +1196,7 @@ int __cil_verify_devicetreecon(struct cil_db *db, struct cil_tree_node *node)
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Invalid devicetreecon at line %d of %s\n", node->line, node->path);
+	cil_tree_log(node, CIL_ERR, "Invalid devicetreecon");
 	return rc;
 }
 
@@ -1223,7 +1217,7 @@ int __cil_verify_fsuse(struct cil_db *db, struct cil_tree_node *node)
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Invalid fsuse at line %d of %s\n", node->line, node->path);
+	cil_tree_log(node, CIL_ERR, "Invalid fsuse");
 	return rc;
 }
 
@@ -1241,7 +1235,7 @@ int __cil_verify_permissionx(struct cil_permissionx *permx, struct cil_tree_node
 			kind_str = CIL_KEY_IOCTL;
 			break;
 		default:
-			cil_log(CIL_ERR, "Invalid permissionx kind (%d) at line %d of %s\n", permx->kind, node->line, node->path);
+			cil_tree_log(node, CIL_ERR, "Invalid permissionx kind (%d)", permx->kind);
 			rc = SEPOL_ERR;
 			goto exit;
 	}
@@ -1257,7 +1251,7 @@ int __cil_verify_permissionx(struct cil_permissionx *permx, struct cil_tree_node
 			}
 
 			if (rc == SEPOL_ENOENT) {
-				cil_log(CIL_ERR, "Invalid permissionx at line %d of %s: %s is not a permission of class %s\n", node->line, node->path, kind_str, class->datum.name);
+				cil_tree_log(node, CIL_ERR, "Invalid permissionx: %s is not a permission of class %s", kind_str, class->datum.name);
 				rc = SEPOL_ERR;
 				goto exit;
 			}
@@ -1312,7 +1306,7 @@ int __cil_verify_class(struct cil_tree_node *node)
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Invalid class at line %d of %s\n", node->line, node->path);
+	cil_tree_log(node, CIL_ERR, "Invalid class");
 	return rc;
 }
 
@@ -1329,8 +1323,7 @@ int __cil_verify_policycap(struct cil_tree_node *node)
 	return SEPOL_OK;
 
 exit:
-	cil_log(CIL_ERR, "Invalid policycap (%s) at line %d of %s\n", 
-		(const char*)polcap->datum.name, node->line, node->path);
+	cil_tree_log(node, CIL_ERR, "Invalid policycap (%s)", (const char*)polcap->datum.name);
 	return rc;
 }
 
@@ -1547,14 +1540,14 @@ static int __cil_verify_classpermission(struct cil_tree_node *node)
 	struct cil_classpermission *cp = node->data;
 
 	if (cp->classperms == NULL) {
-		cil_log(CIL_ERR, "Classpermission %s does not have a classpermissionset at line %d of %s\n", cp->datum.name, node->line, node->path);
+		cil_tree_log(node, CIL_ERR, "Classpermission %s does not have a classpermissionset", cp->datum.name);
 		rc = SEPOL_ERR;
 		goto exit;
 	}
 
 	rc = __cil_verify_classperms(cp->classperms, &cp->datum);
 	if (rc != SEPOL_OK) {
-		cil_log(CIL_ERR, "Found circular class permissions involving the set %s at line %d of %s\n",cp->datum.name, node->line, node->path);
+		cil_tree_log(node, CIL_ERR, "Found circular class permissions involving the set %s",cp->datum.name);
 		goto exit;
 	}
 
@@ -1577,14 +1570,14 @@ static int __verify_map_perm_classperms(__attribute__((unused)) hashtab_key_t k,
 	struct cil_perm *cmp = (struct cil_perm *)d;
 
 	if (cmp->classperms == NULL) {
-		cil_log(CIL_ERR, "Map class %s does not have a classmapping for %s at line %d of %s\n", map_args->class->datum.name, cmp->datum.name, map_args->node->line, map_args->node->path);
+		cil_tree_log(map_args->node, CIL_ERR, "Map class %s does not have a classmapping for %s", map_args->class->datum.name, cmp->datum.name);
 		map_args->rc = SEPOL_ERR;
 		goto exit;
 	}
 
 	rc = __cil_verify_classperms(cmp->classperms, &cmp->datum);
 	if (rc != SEPOL_OK) {
-		cil_log(CIL_ERR, "Found circular class permissions involving the map class %s and permission %s at line %d of %s\n", map_args->class->datum.name, cmp->datum.name, map_args->node->line, map_args->node->path);
+		cil_tree_log(map_args->node, CIL_ERR, "Found circular class permissions involving the map class %s and permission %s", map_args->class->datum.name, cmp->datum.name);
 		map_args->rc = SEPOL_ERR;
 		goto exit;
 	}
-- 
2.5.5

^ permalink raw reply related	[flat|nested] 9+ messages in thread

* [PATCH 5/6 v3] libsepol/cil: Remove path field from cil_tree_node struct
  2016-05-05 20:44 [PATCH 0/6 v3] libsepol/cil: Add high-level language line marking support James Carter
                   ` (3 preceding siblings ...)
  2016-05-05 20:44 ` [PATCH 4/6 v3] libsepol/cil: Replace cil_log() calls with cil_tree_log() James Carter
@ 2016-05-05 20:44 ` James Carter
  2016-05-05 20:44 ` [PATCH 6/6 v3] libsepol: When generating CIL use HLL line mark for neverallows James Carter
  2016-05-06 12:34 ` [PATCH 0/6 v3] libsepol/cil: Add high-level language line marking support Steve Lawrence
  6 siblings, 0 replies; 9+ messages in thread
From: James Carter @ 2016-05-05 20:44 UTC (permalink / raw)
  To: selinux

Remove path field from cil_tree_node struct and all references
to it in CIL. This will reduce memory usage by 5%.

Signed-off-by: James Carter <jwcart2@tycho.nsa.gov>
---
 libsepol/cil/src/cil_binary.c    | 14 +++++++++++++-
 libsepol/cil/src/cil_build_ast.c |  2 --
 libsepol/cil/src/cil_copy_ast.c  |  1 -
 libsepol/cil/src/cil_parser.c    | 23 +++++++++++------------
 libsepol/cil/src/cil_tree.c      |  1 -
 libsepol/cil/src/cil_tree.h      |  1 -
 6 files changed, 24 insertions(+), 18 deletions(-)

diff --git a/libsepol/cil/src/cil_binary.c b/libsepol/cil/src/cil_binary.c
index a3f9171..5d03127 100644
--- a/libsepol/cil/src/cil_binary.c
+++ b/libsepol/cil/src/cil_binary.c
@@ -4232,6 +4232,9 @@ exit:
 static avrule_t *__cil_init_sepol_avrule(uint32_t kind, struct cil_tree_node *node)
 {
 	avrule_t *avrule;
+	struct cil_tree_node *source_node;
+	char *source_path;
+	int is_cil;
 
 	avrule = cil_malloc(sizeof(avrule_t));
 	avrule->specified = kind;
@@ -4240,8 +4243,17 @@ static avrule_t *__cil_init_sepol_avrule(uint32_t kind, struct cil_tree_node *no
 	__cil_init_sepol_type_set(&avrule->ttypes);
 	avrule->perms = NULL;
 	avrule->line = node->line;
-	avrule->source_filename = node->path;
+
+	avrule->source_filename = NULL;
 	avrule->source_line = node->line;
+	source_node = cil_tree_get_next_path(node, &source_path, &is_cil);
+	if (source_node) {
+		avrule->source_filename = source_path;
+		if (!is_cil) {
+			avrule->source_line = node->hll_line;
+		}
+	}
+
 	avrule->next = NULL;
 	return avrule;
 }
diff --git a/libsepol/cil/src/cil_build_ast.c b/libsepol/cil/src/cil_build_ast.c
index 5b9754a..1505873 100644
--- a/libsepol/cil/src/cil_build_ast.c
+++ b/libsepol/cil/src/cil_build_ast.c
@@ -521,7 +521,6 @@ int cil_gen_perm_nodes(struct cil_db *db, struct cil_tree_node *current_perm, st
 		new_ast->parent = ast_node;
 		new_ast->line = current_perm->line;
 		new_ast->hll_line = current_perm->hll_line;
-		new_ast->path = current_perm->path;
 
 		rc = cil_gen_perm(db, current_perm, new_ast, flavor, num_perms);
 		if (rc != SEPOL_OK) {
@@ -5919,7 +5918,6 @@ int __cil_build_ast_node_helper(struct cil_tree_node *parse_current, uint32_t *f
 	ast_node->parent = ast_current;
 	ast_node->line = parse_current->line;
 	ast_node->hll_line = parse_current->hll_line;
-	ast_node->path = parse_current->path;
 
 	if (parse_current->data == CIL_KEY_BLOCK) {
 		rc = cil_gen_block(db, parse_current, ast_node, 0);
diff --git a/libsepol/cil/src/cil_copy_ast.c b/libsepol/cil/src/cil_copy_ast.c
index ad69781..5debd0d 100644
--- a/libsepol/cil/src/cil_copy_ast.c
+++ b/libsepol/cil/src/cil_copy_ast.c
@@ -1983,7 +1983,6 @@ int __cil_copy_node_helper(struct cil_tree_node *orig, __attribute__((unused)) u
 		new->parent = parent;
 		new->line = orig->line;
 		new->hll_line = orig->hll_line;
-		new->path = orig->path;
 		new->flavor = orig->flavor;
 		new->data = data;
 
diff --git a/libsepol/cil/src/cil_parser.c b/libsepol/cil/src/cil_parser.c
index 451014a..101520c 100644
--- a/libsepol/cil/src/cil_parser.c
+++ b/libsepol/cil/src/cil_parser.c
@@ -78,14 +78,13 @@ static void pop_hll_info(struct cil_stack *stack, int *hll_lineno, int *hll_expa
 	}
 }
 
-static void create_node(struct cil_tree_node **node, struct cil_tree_node *current, int line, int hll_line, char *path, void *value)
+static void create_node(struct cil_tree_node **node, struct cil_tree_node *current, int line, int hll_line, void *value)
 {
 	cil_tree_node_init(node);
 	(*node)->parent = current;
 	(*node)->flavor = CIL_NODE;
 	(*node)->line = line;
 	(*node)->hll_line = hll_line;
-	(*node)->path = path;
 	(*node)->data = value;
 }
 
@@ -117,14 +116,14 @@ static int add_hll_linemark(struct cil_tree_node **current, int *hll_lineno, int
 		pop_hll_info(stack, hll_lineno, hll_expand);
 		*current = (*current)->parent;
 	} else {
-		create_node(&node, *current, tok.line, *hll_lineno, path, NULL);
+		create_node(&node, *current, tok.line, *hll_lineno, NULL);
 		insert_node(node, *current);
 		*current = node;
 
-		create_node(&node, *current, tok.line, *hll_lineno, path, CIL_KEY_SRC_INFO);
+		create_node(&node, *current, tok.line, *hll_lineno, CIL_KEY_SRC_INFO);
 		insert_node(node, *current);
 
-		create_node(&node, *current, tok.line, *hll_lineno, path, CIL_KEY_SRC_HLL);
+		create_node(&node, *current, tok.line, *hll_lineno, CIL_KEY_SRC_HLL);
 		insert_node(node, *current);
 
 		if (hll_type == CIL_KEY_HLL_LMS) {
@@ -162,7 +161,7 @@ static int add_hll_linemark(struct cil_tree_node **current, int *hll_lineno, int
 
 		hll_file = cil_strpool_add(tok.value);
 
-		create_node(&node, *current, tok.line, *hll_lineno, path, hll_file);
+		create_node(&node, *current, tok.line, *hll_lineno, hll_file);
 		insert_node(node, *current);
 	}
 
@@ -183,17 +182,17 @@ static void add_cil_path(struct cil_tree_node **current, char *path)
 {
 	struct cil_tree_node *node;
 
-	create_node(&node, *current, 0, 0, path, NULL);
+	create_node(&node, *current, 0, 0, NULL);
 	insert_node(node, *current);
 	*current = node;
 
-	create_node(&node, *current, 0, 0, path, CIL_KEY_SRC_INFO);
+	create_node(&node, *current, 0, 0, CIL_KEY_SRC_INFO);
 	insert_node(node, *current);
 
-	create_node(&node, *current, 0, 0, path, CIL_KEY_SRC_CIL);
+	create_node(&node, *current, 0, 0, CIL_KEY_SRC_CIL);
 	insert_node(node, *current);
 
-	create_node(&node, *current, 0, 0, path, path);
+	create_node(&node, *current, 0, 0, path);
 	insert_node(node, *current);
 }
 
@@ -237,7 +236,7 @@ int cil_parser(char *_path, char *buffer, uint32_t size, struct cil_tree **parse
 		case OPAREN:
 			paren_count++;
 
-			create_node(&node, current, tok.line, hll_lineno, path, NULL);
+			create_node(&node, current, tok.line, hll_lineno, NULL);
 			insert_node(node, current);
 			current = node;
 			break;
@@ -258,7 +257,7 @@ int cil_parser(char *_path, char *buffer, uint32_t size, struct cil_tree **parse
 				goto exit;
 			}
 
-			create_node(&node, current, tok.line, hll_lineno, path, cil_strpool_add(tok.value));
+			create_node(&node, current, tok.line, hll_lineno, cil_strpool_add(tok.value));
 			insert_node(node, current);
 			break;
 		case NEWLINE :
diff --git a/libsepol/cil/src/cil_tree.c b/libsepol/cil/src/cil_tree.c
index 7dc1a1e..9ff9d4b 100644
--- a/libsepol/cil/src/cil_tree.c
+++ b/libsepol/cil/src/cil_tree.c
@@ -216,7 +216,6 @@ void cil_tree_node_init(struct cil_tree_node **node)
 	new_node->flavor = CIL_ROOT;
 	new_node->line = 0;
 	new_node->hll_line = 0;
-	new_node->path = NULL;
 
 	*node = new_node;
 }
diff --git a/libsepol/cil/src/cil_tree.h b/libsepol/cil/src/cil_tree.h
index 318eecd..aeded56 100644
--- a/libsepol/cil/src/cil_tree.h
+++ b/libsepol/cil/src/cil_tree.h
@@ -47,7 +47,6 @@ struct cil_tree_node {
 	enum cil_flavor flavor;
 	uint32_t line;
 	uint32_t hll_line;
-	char *path;
 	void *data;
 };
 
-- 
2.5.5

^ permalink raw reply related	[flat|nested] 9+ messages in thread

* [PATCH 6/6 v3] libsepol: When generating CIL use HLL line mark for neverallows
  2016-05-05 20:44 [PATCH 0/6 v3] libsepol/cil: Add high-level language line marking support James Carter
                   ` (4 preceding siblings ...)
  2016-05-05 20:44 ` [PATCH 5/6 v3] libsepol/cil: Remove path field from cil_tree_node struct James Carter
@ 2016-05-05 20:44 ` James Carter
  2016-05-06 12:34 ` [PATCH 0/6 v3] libsepol/cil: Add high-level language line marking support Steve Lawrence
  6 siblings, 0 replies; 9+ messages in thread
From: James Carter @ 2016-05-05 20:44 UTC (permalink / raw)
  To: selinux

When converting pp files to CIL or generating CIL using checkpolicy
or checkmodule use CIL's HLL line mark annotations to record the
original file and line numbers for neverallow rules so that CIL can
produce more informative error messages. (Unfortunately, the original
line number information is not saved in pp files, so there is no benefit
for policy modules.)

This is only done for neverallow rules currently.

Signed-off-by: James Carter <jwcart2@tycho.nsa.gov>
---
 libsepol/src/module_to_cil.c | 8 ++++++++
 1 file changed, 8 insertions(+)

diff --git a/libsepol/src/module_to_cil.c b/libsepol/src/module_to_cil.c
index 38f0dc3..b9a4af7 100644
--- a/libsepol/src/module_to_cil.c
+++ b/libsepol/src/module_to_cil.c
@@ -1073,6 +1073,10 @@ static int avrule_list_to_cil(int indent, struct policydb *pdb, struct avrule *a
 	struct type_set *ts;
 
 	for (avrule = avrule_list; avrule != NULL; avrule = avrule->next) {
+		if (avrule->specified == AVRULE_NEVERALLOW && avrule->source_filename) {
+			cil_println(0, ";;* lmx %lu %s\n",avrule->source_line, avrule->source_filename);
+		}
+
 		ts = &avrule->stypes;
 		rc = process_typeset(indent, pdb, ts, attr_list, &snames, &num_snames);
 		if (rc != 0) {
@@ -1103,6 +1107,10 @@ static int avrule_list_to_cil(int indent, struct policydb *pdb, struct avrule *a
 
 		names_destroy(&snames, &num_snames);
 		names_destroy(&tnames, &num_tnames);
+
+		if (avrule->specified == AVRULE_NEVERALLOW && avrule->source_filename) {
+			cil_println(0, ";;* lme\n");
+		}
 	}
 
 	return 0;
-- 
2.5.5

^ permalink raw reply related	[flat|nested] 9+ messages in thread

* Re: [PATCH 0/6 v3] libsepol/cil: Add high-level language line marking support
  2016-05-05 20:44 [PATCH 0/6 v3] libsepol/cil: Add high-level language line marking support James Carter
                   ` (5 preceding siblings ...)
  2016-05-05 20:44 ` [PATCH 6/6 v3] libsepol: When generating CIL use HLL line mark for neverallows James Carter
@ 2016-05-06 12:34 ` Steve Lawrence
  2016-05-06 13:46   ` James Carter
  6 siblings, 1 reply; 9+ messages in thread
From: Steve Lawrence @ 2016-05-06 12:34 UTC (permalink / raw)
  To: James Carter, selinux

On 05/05/2016 04:44 PM, James Carter wrote:
> This patch set adds support for tracking original file and line numbers for better
> error reporting when a high-level language is translated into CIL. It then uses
> that support to provide better error reporting for neverallow rules after
> generating CIL with checkpolicy or checkmodule. (Unfortunately, the original line
> number information is not saved in the pp file, so there is no benefit for policy
> modules.)
> 
> Changes in V2:
> - Only ";;*" at the beginning of a line indicates an HL line mark.
> - When cil_tree_get_next_path() encounters a call or blockinherit it will
> continue searching the AST from the associated macro or block.
> 
> Changes in V3:
> - Changed the format of the message printed by cil_tree_log():
>   Before:
>     Problem at line 21 of policy.cil (from line 11 of foo.hll) (from line 2 of bar.hll)
>   Now:
>     Problem at policy.cil:21 from foo.hll:11 from bar.hll:2
> 
> James Carter (6):
>   libsepol/cil: Add high-level language line marking support
>   libsepol/cil: Store CIL filename in parse tree and AST
>   libsepol/cil: Add cil_tree_log() and supporting functions
>   libsepol/cil: Replace cil_log() calls with cil_tree_log()
>   libsepol/cil: Remove path field from cil_tree_node struct
>   libsepol: When generating CIL use HLL line mark for neverallows

Acked-by: Steve Lawrence <slawrence@tresys.com>

>  libsepol/cil/src/cil.c             |  22 ++-
>  libsepol/cil/src/cil_binary.c      |  45 +++---
>  libsepol/cil/src/cil_build_ast.c   | 294 +++++++++++++++----------------------
>  libsepol/cil/src/cil_build_ast.h   |   2 +
>  libsepol/cil/src/cil_copy_ast.c    |  24 ++-
>  libsepol/cil/src/cil_flavor.h      |   1 +
>  libsepol/cil/src/cil_fqn.c         |   2 +-
>  libsepol/cil/src/cil_internal.h    |   9 ++
>  libsepol/cil/src/cil_lexer.h       |   6 +-
>  libsepol/cil/src/cil_lexer.l       |  15 +-
>  libsepol/cil/src/cil_parser.c      | 259 +++++++++++++++++++++++++++-----
>  libsepol/cil/src/cil_resolve_ast.c |  51 +++----
>  libsepol/cil/src/cil_tree.c        |  96 +++++++++++-
>  libsepol/cil/src/cil_tree.h        |   6 +-
>  libsepol/cil/src/cil_verify.c      |  83 +++++------
>  libsepol/src/module_to_cil.c       |   8 +
>  16 files changed, 590 insertions(+), 333 deletions(-)
> 

^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: [PATCH 0/6 v3] libsepol/cil: Add high-level language line marking support
  2016-05-06 12:34 ` [PATCH 0/6 v3] libsepol/cil: Add high-level language line marking support Steve Lawrence
@ 2016-05-06 13:46   ` James Carter
  0 siblings, 0 replies; 9+ messages in thread
From: James Carter @ 2016-05-06 13:46 UTC (permalink / raw)
  To: Steve Lawrence, selinux

On 05/06/2016 08:34 AM, Steve Lawrence wrote:
> On 05/05/2016 04:44 PM, James Carter wrote:
>> This patch set adds support for tracking original file and line numbers for better
>> error reporting when a high-level language is translated into CIL. It then uses
>> that support to provide better error reporting for neverallow rules after
>> generating CIL with checkpolicy or checkmodule. (Unfortunately, the original line
>> number information is not saved in the pp file, so there is no benefit for policy
>> modules.)
>>
>> Changes in V2:
>> - Only ";;*" at the beginning of a line indicates an HL line mark.
>> - When cil_tree_get_next_path() encounters a call or blockinherit it will
>> continue searching the AST from the associated macro or block.
>>
>> Changes in V3:
>> - Changed the format of the message printed by cil_tree_log():
>>   Before:
>>     Problem at line 21 of policy.cil (from line 11 of foo.hll) (from line 2 of bar.hll)
>>   Now:
>>     Problem at policy.cil:21 from foo.hll:11 from bar.hll:2
>>
>> James Carter (6):
>>   libsepol/cil: Add high-level language line marking support
>>   libsepol/cil: Store CIL filename in parse tree and AST
>>   libsepol/cil: Add cil_tree_log() and supporting functions
>>   libsepol/cil: Replace cil_log() calls with cil_tree_log()
>>   libsepol/cil: Remove path field from cil_tree_node struct
>>   libsepol: When generating CIL use HLL line mark for neverallows
>
> Acked-by: Steve Lawrence <slawrence@tresys.com>

Thanks for the review.

Applied.

>
>>  libsepol/cil/src/cil.c             |  22 ++-
>>  libsepol/cil/src/cil_binary.c      |  45 +++---
>>  libsepol/cil/src/cil_build_ast.c   | 294 +++++++++++++++----------------------
>>  libsepol/cil/src/cil_build_ast.h   |   2 +
>>  libsepol/cil/src/cil_copy_ast.c    |  24 ++-
>>  libsepol/cil/src/cil_flavor.h      |   1 +
>>  libsepol/cil/src/cil_fqn.c         |   2 +-
>>  libsepol/cil/src/cil_internal.h    |   9 ++
>>  libsepol/cil/src/cil_lexer.h       |   6 +-
>>  libsepol/cil/src/cil_lexer.l       |  15 +-
>>  libsepol/cil/src/cil_parser.c      | 259 +++++++++++++++++++++++++++-----
>>  libsepol/cil/src/cil_resolve_ast.c |  51 +++----
>>  libsepol/cil/src/cil_tree.c        |  96 +++++++++++-
>>  libsepol/cil/src/cil_tree.h        |   6 +-
>>  libsepol/cil/src/cil_verify.c      |  83 +++++------
>>  libsepol/src/module_to_cil.c       |   8 +
>>  16 files changed, 590 insertions(+), 333 deletions(-)
>>


-- 
James Carter <jwcart2@tycho.nsa.gov>
National Security Agency

^ permalink raw reply	[flat|nested] 9+ messages in thread

end of thread, other threads:[~2016-05-06 13:46 UTC | newest]

Thread overview: 9+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2016-05-05 20:44 [PATCH 0/6 v3] libsepol/cil: Add high-level language line marking support James Carter
2016-05-05 20:44 ` [PATCH 1/6 " James Carter
2016-05-05 20:44 ` [PATCH 2/6 v3] libsepol/cil: Store CIL filename in parse tree and AST James Carter
2016-05-05 20:44 ` [PATCH 3/6 v3] libsepol/cil: Add cil_tree_log() and supporting functions James Carter
2016-05-05 20:44 ` [PATCH 4/6 v3] libsepol/cil: Replace cil_log() calls with cil_tree_log() James Carter
2016-05-05 20:44 ` [PATCH 5/6 v3] libsepol/cil: Remove path field from cil_tree_node struct James Carter
2016-05-05 20:44 ` [PATCH 6/6 v3] libsepol: When generating CIL use HLL line mark for neverallows James Carter
2016-05-06 12:34 ` [PATCH 0/6 v3] libsepol/cil: Add high-level language line marking support Steve Lawrence
2016-05-06 13:46   ` James Carter

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.