/* Authors: Karl MacMillan <kmacmillan@tresys.com>
 *          Frank Mayer <mayerf@tresys.com>
 *
 * Copyright (C) 2003 - 2004 Tresys Technology, LLC
 *	This program is free software; you can redistribute it and/or modify
 *  	it under the terms of the GNU General Public License as published by
 *	the Free Software Foundation, version 2.
 */

#include <linux/kernel.h>
#include <linux/errno.h>
#include <linux/string.h>
#include <linux/spinlock.h>
#include <asm/semaphore.h>
#include <linux/slab.h>

#include "security.h"
#include "conditional.h"

/*
 * cond_evaluate_expr evaluates a conditional expr
 * in reverse polish notation. It returns true (1), false (0),
 * or undefined (-1). Undefined occurs when the expression
 * exceeds the stack depth of COND_EXPR_MAXDEPTH.
 */
static int cond_evaluate_expr(struct policydb *p, struct cond_expr *expr)
{

	struct cond_expr *cur;
	int s[COND_EXPR_MAXDEPTH];
	int sp = -1;

	for (cur = expr; cur != NULL; cur = cur->next) {
		switch (cur->expr_type) {
		case COND_BOOL:
			if (sp == (COND_EXPR_MAXDEPTH - 1))
				return -1;
			sp++;
			s[sp] = p->bool_val_to_struct[cur->bool - 1]->state;
			break;
		case COND_NOT:
			if (sp < 0)
				return -1;
			s[sp] = !s[sp];
			break;
		case COND_OR:
			if (sp < 1)
				return -1;
			sp--;
			s[sp] |= s[sp + 1];
			break;
		case COND_AND:
			if (sp < 1)
				return -1;
			sp--;
			s[sp] &= s[sp + 1];
			break;
		case COND_XOR:
			if (sp < 1)
				return -1;
			sp--;
			s[sp] ^= s[sp + 1];
			break;
		case COND_EQ:
			if (sp < 1)
				return -1;
			sp--;
			s[sp] = (s[sp] == s[sp + 1]);
			break;
		case COND_NEQ:
			if (sp < 1)
				return -1;
			sp--;
			s[sp] = (s[sp] != s[sp + 1]);
			break;
		default:
			return -1;
		}
	}
	return s[0];
}

/*
 * evaluate_cond_node evaluates the conditional stored in
 * a struct cond_node and if the result is different than the
 * current state of the node it sets the rules in the true/false
 * list appropriately. If the result of the expression is undefined
 * all of the rules are disabled for safety.
 */
int evaluate_cond_node(struct policydb *p, struct cond_node *node)
{
	int new_state;
	struct cond_av_list* cur;

	new_state = cond_evaluate_expr(p, node->expr);
	if (new_state != node->cur_state) {
		node->cur_state = new_state;
		if (new_state == -1)
			printk(KERN_ERR "security: expression result was undefined - disabling all rules.\n");
		/* turn the rules on or off */
		for (cur = node->true_list; cur != NULL; cur = cur->next) {
			if (new_state <= 0) {
				cur->node->datum.specified &= ~AVTAB_ENABLED;
			} else {
				cur->node->datum.specified |= AVTAB_ENABLED;
			}
		}

		for (cur = node->false_list; cur != NULL; cur = cur->next) {
			/* -1 or 1 */
			if (new_state) {
				cur->node->datum.specified &= ~AVTAB_ENABLED;
			} else {
				cur->node->datum.specified |= AVTAB_ENABLED;
			}
		}
	}
	return 0;
}

int cond_policydb_init(struct policydb *p)
{
	p->bool_val_to_struct = NULL;
	p->cond_list = NULL;
	if (avtab_init(&p->te_cond_avtab))
		return -1;

	return 0;
}

static void cond_av_list_destroy(struct cond_av_list *list)
{
	struct cond_av_list *cur, *next;
	for (cur = list; cur != NULL; cur = next) {
		next = cur->next;
		/* the avtab_ptr_t node is destroy by the avtab */
		kfree(cur);
	}
}

static void cond_node_destroy(struct cond_node *node)
{
	struct cond_expr *cur_expr, *next_expr;

	for (cur_expr = node->expr; cur_expr != NULL; cur_expr = next_expr) {
		next_expr = cur_expr->next;
		kfree(cur_expr);
	}
	cond_av_list_destroy(node->true_list);
	cond_av_list_destroy(node->false_list);
	kfree(node);
}

static void cond_list_destroy(struct cond_node *list)
{
	struct cond_node *next, *cur;

	if (list == NULL)
		return;

	for (cur = list; cur != NULL; cur = next) {
		next = cur->next;
		cond_node_destroy(cur);
	}
}

void cond_policydb_destroy(struct policydb *p)
{
	if (p->bool_val_to_struct != NULL)
		kfree(p->bool_val_to_struct);
	avtab_destroy(&p->te_cond_avtab);
	cond_list_destroy(p->cond_list);
}

int cond_init_bool_indexes(struct policydb *p)
{
	if (p->bool_val_to_struct)
		kfree(p->bool_val_to_struct);
	p->bool_val_to_struct = (struct cond_bool_datum**)
		kmalloc(p->p_bools.nprim * sizeof(struct cond_bool_datum*), GFP_KERNEL);
	if (!p->bool_val_to_struct)
		return -1;
	return 0;
}

int cond_destroy_bool(void *key, void *datum, void *p)
{
	if (key)
		kfree(key);
	kfree(datum);
	return 0;
}

int cond_index_bool(void *key, void *datum, void *datap)
{
	struct policydb *p;
	struct cond_bool_datum *booldatum;

	booldatum = datum;
	p = datap;

	if (!booldatum->value || booldatum->value > p->p_bools.nprim)
		return -EINVAL;

	p->p_bool_val_to_name[booldatum->value - 1] = key;
	p->bool_val_to_struct[booldatum->value -1] = booldatum;

	return 0;
}

static int bool_isvalid(struct cond_bool_datum *b)
{
	if (!(b->state == 0 || b->state == 1))
		return 0;
	return 1;
}

int cond_read_bool(struct policydb *p, struct hashtab *h, void *fp)
{
	char *key = NULL;
	struct cond_bool_datum *booldatum;
	u32 buf[3], len;
	int rc;

	booldatum = kmalloc(sizeof(struct cond_bool_datum), GFP_KERNEL);
	if (!booldatum)
		return -1;
	memset(booldatum, 0, sizeof(struct cond_bool_datum));

	rc = next_entry(buf, fp, sizeof buf);
	if (rc < 0)
		goto err;

	booldatum->value = le32_to_cpu(buf[0]);
	booldatum->state = le32_to_cpu(buf[1]);

	if (!bool_isvalid(booldatum))
		goto err;

	len = le32_to_cpu(buf[2]);

	key = kmalloc(len + 1, GFP_KERNEL);
	if (!key)
		goto err;
	rc = next_entry(key, fp, len);
	if (rc < 0)
		goto err;
	key[len] = 0;
	if (hashtab_insert(h, key, booldatum))
		goto err;

	return 0;
err:
	cond_destroy_bool(key, booldatum, NULL);
	return -1;
}

static int cond_read_av_list(struct policydb *p, void *fp, struct cond_av_list **ret_list,
			     struct cond_av_list *other)
{
	struct cond_av_list *list, *last = NULL, *cur;
	struct avtab_key key;
	struct avtab_datum datum;
	struct avtab_node *node_ptr;
	int rc;
	u32 buf[1], i, len;
	u8 found;

	*ret_list = NULL;

	len = 0;
	rc = next_entry(buf, fp, sizeof buf);
	if (rc < 0)
		return -1;

	len = le32_to_cpu(buf[0]);
	if (len == 0) {
		return 0;
	}

	for (i = 0; i < len; i++) {
		if (avtab_read_item(fp, &datum, &key))
			goto err;

		/*
		 * For type rules we have to make certain there aren't any
		 * conflicting rules by searching the te_avtab and the
		 * cond_te_avtab.
		 */
		if (datum.specified & AVTAB_TYPE) {
			if (avtab_search(&p->te_avtab, &key, AVTAB_TYPE)) {
				printk("security: type rule already exists outside of a conditional.");
				goto err;
			}
			/*
			 * If we are reading the false list other will be a pointer to
			 * the true list. We can have duplicate entries if there is only
			 * 1 other entry and it is in our true list.
			 *
			 * If we are reading the true list (other == NULL) there shouldn't
			 * be any other entries.
			 */
			if (other) {
				node_ptr = avtab_search_node(&p->te_cond_avtab, &key, AVTAB_TYPE);
				if (node_ptr) {
					if (avtab_search_node_next(node_ptr, AVTAB_TYPE)) {
						printk("security: too many conflicting type rules.");
						goto err;
					}
					found = 0;
					for (cur = other; cur != NULL; cur = cur->next) {
						if (cur->node == node_ptr) {
							found = 1;
							break;
						}
					}
					if (!found) {
						printk("security: conflicting type rules.");
						goto err;
					}
				}
			} else {
				if (avtab_search(&p->te_cond_avtab, &key, AVTAB_TYPE)) {
					printk("security: conflicting type rules when adding type rule for true.");
					goto err;
				}
			}
		}
		node_ptr = avtab_insert_nonunique(&p->te_cond_avtab, &key, &datum);
		if (!node_ptr) {
			printk("security: could not insert rule.");
			goto err;
		}

		list = kmalloc(sizeof(struct cond_av_list), GFP_KERNEL);
		if (!list)
			goto err;
		memset(list, 0, sizeof(struct cond_av_list));

		list->node = node_ptr;
		if (i == 0)
			*ret_list = list;
		else
			last->next = list;
		last = list;

	}

	return 0;
err:
	cond_av_list_destroy(*ret_list);
	*ret_list = NULL;
	return -1;
}

static int expr_isvalid(struct policydb *p, struct cond_expr *expr)
{
	if (expr->expr_type <= 0 || expr->expr_type > COND_LAST) {
		printk("security: conditional expressions uses unknown operator.\n");
		return 0;
	}

	if (expr->bool > p->p_bools.nprim) {
		printk("security: conditional expressions uses unknown bool.\n");
		return 0;
	}
	return 1;
}

static int cond_read_node(struct policydb *p, struct cond_node *node, void *fp)
{
	u32 buf[2], len, i;
	int rc;
	struct cond_expr *expr = NULL, *last = NULL;

	rc = next_entry(buf, fp, sizeof(u32));
	if (rc < 0)
		return -1;

	node->cur_state = le32_to_cpu(buf[0]);

	len = 0;
	rc = next_entry(buf, fp, sizeof(u32));
	if (rc < 0)
		return -1;

	/* expr */
	len = le32_to_cpu(buf[0]);

	for (i = 0; i < len; i++ ) {
		rc = next_entry(buf, fp, sizeof(u32) * 2);
		if (rc < 0)
			goto err;

		expr = kmalloc(sizeof(struct cond_expr), GFP_KERNEL);
		if (!expr) {
			goto err;
		}
		memset(expr, 0, sizeof(struct cond_expr));

		expr->expr_type = le32_to_cpu(buf[0]);
		expr->bool = le32_to_cpu(buf[1]);

		if (!expr_isvalid(p, expr)) {
			kfree(expr);
			goto err;
		}

		if (i == 0) {
			node->expr = expr;
		} else {
			last->next = expr;
		}
		last = expr;
	}

	if (cond_read_av_list(p, fp, &node->true_list, NULL) != 0)
		goto err;
	if (cond_read_av_list(p, fp, &node->false_list, node->true_list) != 0)
		goto err;
	return 0;
err:
	cond_node_destroy(node);
	return -1;
}

int cond_read_list(struct policydb *p, void *fp)
{
	struct cond_node *node, *last = NULL;
	u32 buf[1], i, len;
	int rc;

	rc = next_entry(buf, fp, sizeof buf);
	if (rc < 0)
		return -1;

	len = le32_to_cpu(buf[0]);

	for (i = 0; i < len; i++) {
		node = kmalloc(sizeof(struct cond_node), GFP_KERNEL);
		if (!node)
			goto err;
		memset(node, 0, sizeof(struct cond_node));

		if (cond_read_node(p, node, fp) != 0)
			goto err;

		if (i == 0) {
			p->cond_list = node;
		} else {
			last->next = node;
		}
		last = node;
	}
	return 0;
err:
	cond_list_destroy(p->cond_list);
	return -1;
}

/* Determine whether additional permissions are granted by the conditional
 * av table, and if so, add them to the result
 */
void cond_compute_av(struct avtab *ctab, struct avtab_key *key, struct av_decision *avd)
{
	struct avtab_node *node;

	if(!ctab || !key || !avd)
		return;

	for(node = avtab_search_node(ctab, key, AVTAB_AV); node != NULL;
				node = avtab_search_node_next(node, AVTAB_AV)) {
		if ( (__u32) (AVTAB_ALLOWED|AVTAB_ENABLED) ==
		     (node->datum.specified & (AVTAB_ALLOWED|AVTAB_ENABLED)))
			avd->allowed |= avtab_allowed(&node->datum);
		if ( (__u32) (AVTAB_AUDITDENY|AVTAB_ENABLED) ==
		     (node->datum.specified & (AVTAB_AUDITDENY|AVTAB_ENABLED)))
			/* Since a '0' in an auditdeny mask represents a
			 * permission we do NOT want to audit (dontaudit), we use
			 * the '&' operand to ensure that all '0's in the mask
			 * are retained (much unlike the allow and auditallow cases).
			 */
			avd->auditdeny &= avtab_auditdeny(&node->datum);
		if ( (__u32) (AVTAB_AUDITALLOW|AVTAB_ENABLED) ==
		     (node->datum.specified & (AVTAB_AUDITALLOW|AVTAB_ENABLED)))
			avd->auditallow |= avtab_auditallow(&node->datum);
	}
	return;
}
