Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 3bb56b25 authored by Paul Moore's avatar Paul Moore Committed by James Morris
Browse files

SELinux: Add a capabilities bitmap to SELinux policy version 22



Add a new policy capabilities bitmap to SELinux policy version 22.  This bitmap
will enable the security server to query the policy to determine which features
it supports.

Signed-off-by: default avatarPaul Moore <paul.moore@hp.com>
Signed-off-by: default avatarJames Morris <jmorris@namei.org>
parent 224dfbd8
Loading
Loading
Loading
Loading
+1 −1
Original line number Original line Diff line number Diff line
@@ -145,7 +145,7 @@ config SECURITY_SELINUX_POLICYDB_VERSION_MAX
config SECURITY_SELINUX_POLICYDB_VERSION_MAX_VALUE
config SECURITY_SELINUX_POLICYDB_VERSION_MAX_VALUE
	int "NSA SELinux maximum supported policy format version value"
	int "NSA SELinux maximum supported policy format version value"
	depends on SECURITY_SELINUX_POLICYDB_VERSION_MAX
	depends on SECURITY_SELINUX_POLICYDB_VERSION_MAX
	range 15 21
	range 15 22
	default 19
	default 19
	help
	help
	  This option sets the value for the maximum policy format version
	  This option sets the value for the maximum policy format version
+14 −1
Original line number Original line Diff line number Diff line
@@ -25,13 +25,14 @@
#define POLICYDB_VERSION_MLS		19
#define POLICYDB_VERSION_MLS		19
#define POLICYDB_VERSION_AVTAB		20
#define POLICYDB_VERSION_AVTAB		20
#define POLICYDB_VERSION_RANGETRANS	21
#define POLICYDB_VERSION_RANGETRANS	21
#define POLICYDB_VERSION_POLCAP		22


/* Range of policy versions we understand*/
/* Range of policy versions we understand*/
#define POLICYDB_VERSION_MIN   POLICYDB_VERSION_BASE
#define POLICYDB_VERSION_MIN   POLICYDB_VERSION_BASE
#ifdef CONFIG_SECURITY_SELINUX_POLICYDB_VERSION_MAX
#ifdef CONFIG_SECURITY_SELINUX_POLICYDB_VERSION_MAX
#define POLICYDB_VERSION_MAX	CONFIG_SECURITY_SELINUX_POLICYDB_VERSION_MAX_VALUE
#define POLICYDB_VERSION_MAX	CONFIG_SECURITY_SELINUX_POLICYDB_VERSION_MAX_VALUE
#else
#else
#define POLICYDB_VERSION_MAX	POLICYDB_VERSION_RANGETRANS
#define POLICYDB_VERSION_MAX	POLICYDB_VERSION_POLCAP
#endif
#endif


struct netlbl_lsm_secattr;
struct netlbl_lsm_secattr;
@@ -39,8 +40,19 @@ struct netlbl_lsm_secattr;
extern int selinux_enabled;
extern int selinux_enabled;
extern int selinux_mls_enabled;
extern int selinux_mls_enabled;


/* Policy capabilities */
enum {
	POLICYDB_CAPABILITY_NETPEER,
	__POLICYDB_CAPABILITY_MAX
};
#define POLICYDB_CAPABILITY_MAX (__POLICYDB_CAPABILITY_MAX - 1)

extern int selinux_policycap_netpeer;

int security_load_policy(void * data, size_t len);
int security_load_policy(void * data, size_t len);


int security_policycap_supported(unsigned int req_cap);

#define SEL_VEC_MAX 32
#define SEL_VEC_MAX 32
struct av_decision {
struct av_decision {
	u32 allowed;
	u32 allowed;
@@ -91,6 +103,7 @@ int security_get_classes(char ***classes, int *nclasses);
int security_get_permissions(char *class, char ***perms, int *nperms);
int security_get_permissions(char *class, char ***perms, int *nperms);
int security_get_reject_unknown(void);
int security_get_reject_unknown(void);
int security_get_allow_unknown(void);
int security_get_allow_unknown(void);
int security_get_policycaps(int *len, int **values);


#define SECURITY_FS_USE_XATTR		1 /* use xattr */
#define SECURITY_FS_USE_XATTR		1 /* use xattr */
#define SECURITY_FS_USE_TRANS		2 /* use transition SIDs, e.g. devpts/tmpfs */
#define SECURITY_FS_USE_TRANS		2 /* use transition SIDs, e.g. devpts/tmpfs */
+85 −4
Original line number Original line Diff line number Diff line
@@ -2,6 +2,11 @@
 *
 *
 * 	Added conditional policy language extensions
 * 	Added conditional policy language extensions
 *
 *
 *  Updated: Hewlett-Packard <paul.moore@hp.com>
 *
 *      Added support for the policy capability bitmap
 *
 * Copyright (C) 2007 Hewlett-Packard Development Company, L.P.
 * Copyright (C) 2003 - 2004 Tresys Technology, LLC
 * Copyright (C) 2003 - 2004 Tresys Technology, LLC
 * Copyright (C) 2004 Red Hat, Inc., James Morris <jmorris@redhat.com>
 * Copyright (C) 2004 Red Hat, Inc., James Morris <jmorris@redhat.com>
 *	This program is free software; you can redistribute it and/or modify
 *	This program is free software; you can redistribute it and/or modify
@@ -35,6 +40,11 @@
#include "objsec.h"
#include "objsec.h"
#include "conditional.h"
#include "conditional.h"


/* Policy capability filenames */
static char *policycap_names[] = {
	"network_peer_controls"
};

unsigned int selinux_checkreqprot = CONFIG_SECURITY_SELINUX_CHECKREQPROT_VALUE;
unsigned int selinux_checkreqprot = CONFIG_SECURITY_SELINUX_CHECKREQPROT_VALUE;


#ifdef CONFIG_SECURITY_SELINUX_ENABLE_SECMARK_DEFAULT
#ifdef CONFIG_SECURITY_SELINUX_ENABLE_SECMARK_DEFAULT
@@ -72,6 +82,9 @@ static int *bool_pending_values = NULL;
static struct dentry *class_dir = NULL;
static struct dentry *class_dir = NULL;
static unsigned long last_class_ino;
static unsigned long last_class_ino;


/* global data for policy capabilities */
static struct dentry *policycap_dir = NULL;

extern void selnl_notify_setenforce(int val);
extern void selnl_notify_setenforce(int val);


/* Check whether a task is allowed to use a security operation. */
/* Check whether a task is allowed to use a security operation. */
@@ -114,6 +127,7 @@ static unsigned long sel_last_ino = SEL_INO_NEXT - 1;
#define SEL_INITCON_INO_OFFSET		0x01000000
#define SEL_INITCON_INO_OFFSET		0x01000000
#define SEL_BOOL_INO_OFFSET		0x02000000
#define SEL_BOOL_INO_OFFSET		0x02000000
#define SEL_CLASS_INO_OFFSET		0x04000000
#define SEL_CLASS_INO_OFFSET		0x04000000
#define SEL_POLICYCAP_INO_OFFSET	0x08000000
#define SEL_INO_MASK			0x00ffffff
#define SEL_INO_MASK			0x00ffffff


#define TMPBUFLEN	12
#define TMPBUFLEN	12
@@ -263,6 +277,7 @@ static const struct file_operations sel_policyvers_ops = {
/* declaration for sel_write_load */
/* declaration for sel_write_load */
static int sel_make_bools(void);
static int sel_make_bools(void);
static int sel_make_classes(void);
static int sel_make_classes(void);
static int sel_make_policycap(void);


/* declaration for sel_make_class_dirs */
/* declaration for sel_make_class_dirs */
static int sel_make_dir(struct inode *dir, struct dentry *dentry,
static int sel_make_dir(struct inode *dir, struct dentry *dentry,
@@ -323,6 +338,12 @@ static ssize_t sel_write_load(struct file * file, const char __user * buf,
	}
	}


	ret = sel_make_classes();
	ret = sel_make_classes();
	if (ret) {
		length = ret;
		goto out1;
	}

	ret = sel_make_policycap();
	if (ret)
	if (ret)
		length = ret;
		length = ret;
	else
	else
@@ -1399,6 +1420,24 @@ static const struct file_operations sel_perm_ops = {
	.read		= sel_read_perm,
	.read		= sel_read_perm,
};
};


static ssize_t sel_read_policycap(struct file *file, char __user *buf,
				  size_t count, loff_t *ppos)
{
	int value;
	char tmpbuf[TMPBUFLEN];
	ssize_t length;
	unsigned long i_ino = file->f_path.dentry->d_inode->i_ino;

	value = security_policycap_supported(i_ino & SEL_INO_MASK);
	length = scnprintf(tmpbuf, TMPBUFLEN, "%d", value);

	return simple_read_from_buffer(buf, count, ppos, tmpbuf, length);
}

static const struct file_operations sel_policycap_ops = {
	.read		= sel_read_policycap,
};

static int sel_make_perm_files(char *objclass, int classvalue,
static int sel_make_perm_files(char *objclass, int classvalue,
				struct dentry *dir)
				struct dentry *dir)
{
{
@@ -1545,6 +1584,36 @@ out:
	return rc;
	return rc;
}
}


static int sel_make_policycap(void)
{
	unsigned int iter;
	struct dentry *dentry = NULL;
	struct inode *inode = NULL;

	sel_remove_entries(policycap_dir);

	for (iter = 0; iter <= POLICYDB_CAPABILITY_MAX; iter++) {
		if (iter < ARRAY_SIZE(policycap_names))
			dentry = d_alloc_name(policycap_dir,
					      policycap_names[iter]);
		else
			dentry = d_alloc_name(policycap_dir, "unknown");

		if (dentry == NULL)
			return -ENOMEM;

		inode = sel_make_inode(policycap_dir->d_sb, S_IFREG | S_IRUGO);
		if (inode == NULL)
			return -ENOMEM;

		inode->i_fop = &sel_policycap_ops;
		inode->i_ino = iter | SEL_POLICYCAP_INO_OFFSET;
		d_add(dentry, inode);
	}

	return 0;
}

static int sel_make_dir(struct inode *dir, struct dentry *dentry,
static int sel_make_dir(struct inode *dir, struct dentry *dentry,
			unsigned long *ino)
			unsigned long *ino)
{
{
@@ -1673,6 +1742,18 @@ static int sel_fill_super(struct super_block * sb, void * data, int silent)


	class_dir = dentry;
	class_dir = dentry;


	dentry = d_alloc_name(sb->s_root, "policy_capabilities");
	if (!dentry) {
		ret = -ENOMEM;
		goto err;
	}

	ret = sel_make_dir(root_inode, dentry, &sel_last_ino);
	if (ret)
		goto err;

	policycap_dir = dentry;

out:
out:
	return ret;
	return ret;
err:
err:
+17 −1
Original line number Original line Diff line number Diff line
@@ -13,6 +13,11 @@
 *
 *
 * 	Added conditional policy language extensions
 * 	Added conditional policy language extensions
 *
 *
 * Updated: Hewlett-Packard <paul.moore@hp.com>
 *
 *      Added support for the policy capability bitmap
 *
 * Copyright (C) 2007 Hewlett-Packard Development Company, L.P.
 * Copyright (C) 2004-2005 Trusted Computer Solutions, Inc.
 * Copyright (C) 2004-2005 Trusted Computer Solutions, Inc.
 * Copyright (C) 2003 - 2004 Tresys Technology, LLC
 * Copyright (C) 2003 - 2004 Tresys Technology, LLC
 *	This program is free software; you can redistribute it and/or modify
 *	This program is free software; you can redistribute it and/or modify
@@ -102,6 +107,11 @@ static struct policydb_compat_info policydb_compat[] = {
		.sym_num        = SYM_NUM,
		.sym_num        = SYM_NUM,
		.ocon_num       = OCON_NUM,
		.ocon_num       = OCON_NUM,
	},
	},
	{
		.version	= POLICYDB_VERSION_POLCAP,
		.sym_num	= SYM_NUM,
		.ocon_num	= OCON_NUM,
	}
};
};


static struct policydb_compat_info *policydb_lookup_compat(int version)
static struct policydb_compat_info *policydb_lookup_compat(int version)
@@ -183,6 +193,8 @@ static int policydb_init(struct policydb *p)
	if (rc)
	if (rc)
		goto out_free_symtab;
		goto out_free_symtab;


	ebitmap_init(&p->policycaps);

out:
out:
	return rc;
	return rc;


@@ -673,8 +685,8 @@ void policydb_destroy(struct policydb *p)
			ebitmap_destroy(&p->type_attr_map[i]);
			ebitmap_destroy(&p->type_attr_map[i]);
	}
	}
	kfree(p->type_attr_map);
	kfree(p->type_attr_map);

	kfree(p->undefined_perms);
	kfree(p->undefined_perms);
	ebitmap_destroy(&p->policycaps);


	return;
	return;
}
}
@@ -1554,6 +1566,10 @@ int policydb_read(struct policydb *p, void *fp)
	p->reject_unknown = !!(le32_to_cpu(buf[1]) & REJECT_UNKNOWN);
	p->reject_unknown = !!(le32_to_cpu(buf[1]) & REJECT_UNKNOWN);
	p->allow_unknown = !!(le32_to_cpu(buf[1]) & ALLOW_UNKNOWN);
	p->allow_unknown = !!(le32_to_cpu(buf[1]) & ALLOW_UNKNOWN);


	if (p->policyvers >= POLICYDB_VERSION_POLCAP &&
	    ebitmap_read(&p->policycaps, fp) != 0)
		goto bad;

	info = policydb_lookup_compat(p->policyvers);
	info = policydb_lookup_compat(p->policyvers);
	if (!info) {
	if (!info) {
		printk(KERN_ERR "security:  unable to find policy compat info "
		printk(KERN_ERR "security:  unable to find policy compat info "
+2 −0
Original line number Original line Diff line number Diff line
@@ -241,6 +241,8 @@ struct policydb {
	/* type -> attribute reverse mapping */
	/* type -> attribute reverse mapping */
	struct ebitmap *type_attr_map;
	struct ebitmap *type_attr_map;


	struct ebitmap policycaps;

	unsigned int policyvers;
	unsigned int policyvers;


	unsigned int reject_unknown : 1;
	unsigned int reject_unknown : 1;
Loading