113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle#include <stdlib.h>
213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle#include "debug.h"
413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle#include <sepol/policydb/policydb.h>
513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle#include "policydb_internal.h"
613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle/* Policy file interfaces. */
813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint sepol_policy_file_create(sepol_policy_file_t ** pf)
1013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{
1113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	*pf = calloc(1, sizeof(sepol_policy_file_t));
1213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	if (!(*pf))
1313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		return -1;
1413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	return 0;
1513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle}
1613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
1713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindlevoid sepol_policy_file_set_mem(sepol_policy_file_t * spf,
1813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle			       char *data, size_t len)
1913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{
2013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	struct policy_file *pf = &spf->pf;
2113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	if (!len) {
2213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		pf->type = PF_LEN;
2313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		return;
2413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	}
2513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	pf->type = PF_USE_MEMORY;
2613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	pf->data = data;
2713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	pf->len = len;
2813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	pf->size = len;
2913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	return;
3013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle}
3113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
3213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindlevoid sepol_policy_file_set_fp(sepol_policy_file_t * spf, FILE * fp)
3313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{
3413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	struct policy_file *pf = &spf->pf;
3513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	pf->type = PF_USE_STDIO;
3613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	pf->fp = fp;
3713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	return;
3813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle}
3913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
4013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint sepol_policy_file_get_len(sepol_policy_file_t * spf, size_t * len)
4113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{
4213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	struct policy_file *pf = &spf->pf;
4313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	if (pf->type != PF_LEN)
4413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		return -1;
4513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	*len = pf->len;
4613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	return 0;
4713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle}
4813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
4913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindlevoid sepol_policy_file_set_handle(sepol_policy_file_t * pf,
5013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle				  sepol_handle_t * handle)
5113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{
5213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	pf->pf.handle = handle;
5313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle}
5413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
5513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindlevoid sepol_policy_file_free(sepol_policy_file_t * pf)
5613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{
5713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	free(pf);
5813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle}
5913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
6013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle/* Policydb interfaces. */
6113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
6213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint sepol_policydb_create(sepol_policydb_t ** sp)
6313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{
6413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	policydb_t *p;
6513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	*sp = malloc(sizeof(sepol_policydb_t));
6613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	if (!(*sp))
6713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		return -1;
6813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	p = &(*sp)->p;
6913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	if (policydb_init(p)) {
7013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		free(*sp);
7113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		return -1;
7213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	}
7313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	return 0;
7413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle}
7513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
7613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindlehidden_def(sepol_policydb_create)
7713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
7813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindlevoid sepol_policydb_free(sepol_policydb_t * p)
7913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{
8013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	if (!p)
8113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		return;
8213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	policydb_destroy(&p->p);
8313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	free(p);
8413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle}
8513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
8613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindlehidden_def(sepol_policydb_free)
8713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
8813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint sepol_policy_kern_vers_min(void)
8913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{
9013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	return POLICYDB_VERSION_MIN;
9113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle}
9213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
9313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint sepol_policy_kern_vers_max(void)
9413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{
9513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	return POLICYDB_VERSION_MAX;
9613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle}
9713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
9813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint sepol_policydb_set_typevers(sepol_policydb_t * sp, unsigned int type)
9913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{
10013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	struct policydb *p = &sp->p;
10113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	switch (type) {
10213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	case POLICY_KERN:
10313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		p->policyvers = POLICYDB_VERSION_MAX;
10413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		break;
10513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	case POLICY_BASE:
10613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	case POLICY_MOD:
10713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		p->policyvers = MOD_POLICYDB_VERSION_MAX;
10813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		break;
10913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	default:
11013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		return -1;
11113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	}
11213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	p->policy_type = type;
11313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	return 0;
11413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle}
11513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
11613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint sepol_policydb_set_vers(sepol_policydb_t * sp, unsigned int vers)
11713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{
11813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	struct policydb *p = &sp->p;
11913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	switch (p->policy_type) {
12013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	case POLICY_KERN:
12113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		if (vers < POLICYDB_VERSION_MIN || vers > POLICYDB_VERSION_MAX)
12213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle			return -1;
12313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		break;
12413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	case POLICY_BASE:
12513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	case POLICY_MOD:
12613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		if (vers < MOD_POLICYDB_VERSION_MIN
12713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		    || vers > MOD_POLICYDB_VERSION_MAX)
12813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle			return -1;
12913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		break;
13013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	default:
13113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		return -1;
13213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	}
13313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	p->policyvers = vers;
13413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	return 0;
13513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle}
13613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
13713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint sepol_policydb_set_handle_unknown(sepol_policydb_t * sp,
13813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle				      unsigned int handle_unknown)
13913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{
14013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	struct policydb *p = &sp->p;
14113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
14213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	switch (handle_unknown) {
14313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	case SEPOL_DENY_UNKNOWN:
14413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	case SEPOL_REJECT_UNKNOWN:
14513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	case SEPOL_ALLOW_UNKNOWN:
14613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		break;
14713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	default:
14813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		return -1;
14913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	}
15013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
15113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	p->handle_unknown = handle_unknown;
15213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	return 0;
15313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle}
15413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
15544a65ed816ea05e3f04872eb78f09c44ec695b21Steve Lawrenceint sepol_policydb_set_target_platform(sepol_policydb_t * sp,
15644a65ed816ea05e3f04872eb78f09c44ec695b21Steve Lawrence				      int target_platform)
15744a65ed816ea05e3f04872eb78f09c44ec695b21Steve Lawrence{
15844a65ed816ea05e3f04872eb78f09c44ec695b21Steve Lawrence	struct policydb *p = &sp->p;
15944a65ed816ea05e3f04872eb78f09c44ec695b21Steve Lawrence
16044a65ed816ea05e3f04872eb78f09c44ec695b21Steve Lawrence	switch (target_platform) {
16144a65ed816ea05e3f04872eb78f09c44ec695b21Steve Lawrence	case SEPOL_TARGET_SELINUX:
16244a65ed816ea05e3f04872eb78f09c44ec695b21Steve Lawrence	case SEPOL_TARGET_XEN:
16344a65ed816ea05e3f04872eb78f09c44ec695b21Steve Lawrence		break;
16444a65ed816ea05e3f04872eb78f09c44ec695b21Steve Lawrence	default:
16544a65ed816ea05e3f04872eb78f09c44ec695b21Steve Lawrence		return -1;
16644a65ed816ea05e3f04872eb78f09c44ec695b21Steve Lawrence	}
16744a65ed816ea05e3f04872eb78f09c44ec695b21Steve Lawrence
16844a65ed816ea05e3f04872eb78f09c44ec695b21Steve Lawrence	p->target_platform = target_platform;
16944a65ed816ea05e3f04872eb78f09c44ec695b21Steve Lawrence	return 0;
17044a65ed816ea05e3f04872eb78f09c44ec695b21Steve Lawrence}
17144a65ed816ea05e3f04872eb78f09c44ec695b21Steve Lawrence
17213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint sepol_policydb_read(sepol_policydb_t * p, sepol_policy_file_t * pf)
17313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{
17413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	return policydb_read(&p->p, &pf->pf, 0);
17513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle}
17613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
17713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint sepol_policydb_write(sepol_policydb_t * p, sepol_policy_file_t * pf)
17813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{
17913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	return policydb_write(&p->p, &pf->pf);
18013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle}
18113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
18213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint sepol_policydb_from_image(sepol_handle_t * handle,
18313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle			      void *data, size_t len, sepol_policydb_t * p)
18413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{
18513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	return policydb_from_image(handle, data, len, &p->p);
18613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle}
18713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
18813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint sepol_policydb_to_image(sepol_handle_t * handle,
18913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle			    sepol_policydb_t * p, void **newdata,
19013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle			    size_t * newlen)
19113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{
19213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	return policydb_to_image(handle, &p->p, newdata, newlen);
19313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle}
19413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
19513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint sepol_policydb_mls_enabled(const sepol_policydb_t * p)
19613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{
19713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
19813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	return p->p.mls;
19913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle}
20013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle
20113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle/*
20213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle * Enable compatibility mode for SELinux network checks iff
20313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle * the packet class is not defined in the policy.
20413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle */
20513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle#define PACKET_CLASS_NAME "packet"
20613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint sepol_policydb_compat_net(const sepol_policydb_t * p)
20713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{
20813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle	return (hashtab_search(p->p.p_classes.table, PACKET_CLASS_NAME) ==
20913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle		NULL);
21013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle}
211