* [Xense-devel][RFC][PATCH][1/4] Xen Security Modules: XSM
@ 2006-09-01 16:58 George S. Coker, II
2006-09-01 18:35 ` James Morris
2006-09-01 18:55 ` Chris Wright
0 siblings, 2 replies; 11+ messages in thread
From: George S. Coker, II @ 2006-09-01 16:58 UTC (permalink / raw)
To: xen-devel; +Cc: xense-devel
[-- Attachment #1: Type: text/plain, Size: 1165 bytes --]
The attached patch implements the Xen Security Modules (XSM) framework.
This patch should apply cleanly to changeset 9694:d82a4c4d04d4 Xen
3.0.2-3.
The framework is configured as default-enable in this patch set.
Configuration of XSM is made in Config.mk. The only configuration
option is XSM_ENABLE = y/n. XSM_ENABLE must be y to compile an XSM
module.
XSM provides a generalized hook infrastructure allowing third-party
security modules to interpose on the Xen code path. A default or dummy
module provides basic call/return functionality for hooks not
implemented by a given module. During module initialization, a module
registers its security hooks and the equivalent dummy hooks are
unregistered. If a module does not implement a hook, the equivalent
dummy hook remains in place. Modules also may define and register at
boot time a module specific hypercall through the XSM hook
infrastructure.
Modules may also define at Xen compile time a magic number XSM_MAGIC to
indicate that a policy should be discovered from the images loaded at
boot. The policy file should then be listed in grub as one of the
multi-boot modules after the dom0 kernel.
[-- Attachment #2: xsm-xen-3.0.2-3.diff --]
[-- Type: text/x-patch, Size: 65576 bytes --]
diff -r d82a4c4d04d4 -r a24b5a5f5f5b Config.mk
--- a/Config.mk Fri May 26 09:23:33 2006 +0100
+++ b/Config.mk Thu Aug 31 17:14:49 2006 -0400
@@ -71,6 +71,10 @@ CFLAGS += $(foreach i, $(EXTRA_INCLUDES)
# Choose the best mirror to download linux kernel
KERNEL_REPO = http://www.kernel.org
+#Enable XSM security module. Enabling XSM requires selection of an
+#XSM security module.
+XSM_ENABLE ?= y
+
# If ACM_SECURITY = y, then the access control module is compiled
# into Xen and the policy type can be set by the boot policy file
# y - Build the Xen ACM framework
diff -r d82a4c4d04d4 -r a24b5a5f5f5b linux-2.6-xen-sparse/drivers/xen/privcmd/privcmd.c
--- a/linux-2.6-xen-sparse/drivers/xen/privcmd/privcmd.c Fri May 26 09:23:33 2006 +0100
+++ b/linux-2.6-xen-sparse/drivers/xen/privcmd/privcmd.c Thu Aug 31 17:14:49 2006 -0400
@@ -264,6 +264,7 @@ static int __init privcmd_init(void)
{
/* Set of hypercalls that privileged applications may execute. */
set_bit(__HYPERVISOR_acm_op, hypercall_permission_map);
+ set_bit(__HYPERVISOR_xsm_op, hypercall_permission_map);
set_bit(__HYPERVISOR_dom0_op, hypercall_permission_map);
set_bit(__HYPERVISOR_event_channel_op, hypercall_permission_map);
set_bit(__HYPERVISOR_memory_op, hypercall_permission_map);
diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/Makefile
--- a/xen/Makefile Fri May 26 09:23:33 2006 +0100
+++ b/xen/Makefile Thu Aug 31 17:14:49 2006 -0400
@@ -45,6 +45,7 @@ _clean: delete-unfresh-files
$(MAKE) -f $(BASEDIR)/Rules.mk -C common clean
$(MAKE) -f $(BASEDIR)/Rules.mk -C drivers clean
$(MAKE) -f $(BASEDIR)/Rules.mk -C acm clean
+ $(MAKE) -f $(BASEDIR)/Rules.mk -C xsm clean
$(MAKE) -f $(BASEDIR)/Rules.mk -C arch/$(TARGET_ARCH) clean
rm -f include/asm *.o $(TARGET)* *~ core
rm -f include/asm-*/asm-offsets.h
@@ -122,7 +123,7 @@ include/asm-$(TARGET_ARCH)/asm-offsets.h
echo ""; \
echo "#endif") <$< >$@
-SUBDIRS = acm arch/$(TARGET_ARCH) common drivers
+SUBDIRS = xsm acm arch/$(TARGET_ARCH) common drivers
define all_sources
( find include/asm-$(TARGET_ARCH) -name SCCS -prune -o -name '*.h' -print; \
find include -type d -name SCCS -prune -o \( -name "asm-*" -o \
diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/Rules.mk
--- a/xen/Rules.mk Fri May 26 09:23:33 2006 +0100
+++ b/xen/Rules.mk Thu Aug 31 17:14:49 2006 -0400
@@ -47,10 +47,12 @@ HDRS := $(subst $(BASEDIR)/include/xen/c
# Note that link order matters!
ALL_OBJS-y += $(BASEDIR)/common/built_in.o
ALL_OBJS-y += $(BASEDIR)/drivers/built_in.o
+ALL_OBJS-y += $(BASEDIR)/xsm/built_in.o
ALL_OBJS-$(ACM_SECURITY) += $(BASEDIR)/acm/built_in.o
ALL_OBJS-y += $(BASEDIR)/arch/$(TARGET_ARCH)/built_in.o
CFLAGS-y += -g -D__XEN__
+CFLAGS-y += -DXSM_ENABLE
CFLAGS-$(ACM_SECURITY) += -DACM_SECURITY
CFLAGS-$(verbose) += -DVERBOSE
CFLAGS-$(crash_debug) += -DCRASH_DEBUG
diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/arch/x86/dom0_ops.c
--- a/xen/arch/x86/dom0_ops.c Fri May 26 09:23:33 2006 +0100
+++ b/xen/arch/x86/dom0_ops.c Thu Aug 31 17:14:49 2006 -0400
@@ -25,6 +25,7 @@
#include <asm/hvm/support.h>
#include <asm/processor.h>
#include <public/sched_ctl.h>
+#include <xsm/xsm.h>
#include <asm/mtrr.h>
#include "cpu/mtrr/mtrr.h"
@@ -58,6 +59,10 @@ long arch_do_dom0_op(struct dom0_op *op,
case DOM0_MSR:
{
+ ret = xsm_msr(op->u.msr.write);
+ if (ret)
+ break;
+
if ( op->u.msr.write )
{
msr_cpu_mask = op->u.msr.cpu_mask;
@@ -89,15 +94,25 @@ long arch_do_dom0_op(struct dom0_op *op,
d = find_domain_by_id(op->u.shadow_control.domain);
if ( d != NULL )
{
+ ret = xsm_shadow_control(d, op->u.shadow_control.op);
+ if (ret)
+ goto shadowctrl_out;
+
ret = shadow_mode_control(d, &op->u.shadow_control);
+ copy_to_guest(u_dom0_op, op, 1);
+
+ shadowctrl_out:
put_domain(d);
- copy_to_guest(u_dom0_op, op, 1);
}
}
break;
case DOM0_ADD_MEMTYPE:
{
+ ret= xsm_memtype(op->cmd);
+ if (ret)
+ break;
+
ret = mtrr_add_page(
op->u.add_memtype.mfn,
op->u.add_memtype.nr_mfns,
@@ -115,6 +130,10 @@ long arch_do_dom0_op(struct dom0_op *op,
case DOM0_DEL_MEMTYPE:
{
+ ret= xsm_memtype(op->cmd);
+ if (ret)
+ break;
+
if (op->u.del_memtype.handle == 0
/* mtrr/main.c otherwise does a lookup */
&& (int)op->u.del_memtype.reg >= 0)
@@ -134,6 +153,10 @@ long arch_do_dom0_op(struct dom0_op *op,
unsigned int nr_mfns;
mtrr_type type;
+ ret= xsm_memtype(op->cmd);
+ if (ret)
+ break;
+
ret = -EINVAL;
if ( op->u.read_memtype.reg < num_var_ranges )
{
@@ -150,6 +173,11 @@ long arch_do_dom0_op(struct dom0_op *op,
case DOM0_MICROCODE:
{
extern int microcode_update(void *buf, unsigned long len);
+
+ ret = xsm_microcode();
+ if (ret)
+ break;
+
ret = microcode_update(op->u.microcode.data.p, op->u.microcode.length);
}
break;
@@ -169,6 +197,10 @@ long arch_do_dom0_op(struct dom0_op *op,
op->u.ioport_permission.domain)) == NULL) )
break;
+ ret = xsm_ioport_permission(d, fp, op->u.ioport_permission.allow_access);
+ if (ret)
+ goto ioportperm_out;
+
if ( np == 0 )
ret = 0;
else if ( op->u.ioport_permission.allow_access )
@@ -176,14 +208,20 @@ long arch_do_dom0_op(struct dom0_op *op,
else
ret = ioports_deny_access(d, fp, fp + np - 1);
+ ioportperm_out:
put_domain(d);
}
break;
case DOM0_PHYSINFO:
{
+
dom0_physinfo_t *pi = &op->u.physinfo;
+ ret = xsm_physinfo();
+ if (ret)
+ break;
+
pi->threads_per_core =
cpus_weight(cpu_sibling_map[0]);
pi->cores_per_socket =
@@ -212,6 +250,10 @@ long arch_do_dom0_op(struct dom0_op *op,
ret = -EINVAL;
+ ret = xsm_getpageframeinfo(mfn);
+ if (ret)
+ break;
+
if ( unlikely(!mfn_valid(mfn)) ||
unlikely((d = find_domain_by_id(dom)) == NULL) )
break;
@@ -291,6 +333,10 @@ long arch_do_dom0_op(struct dom0_op *op,
struct page_info *page;
unsigned long mfn = l_arr[j];
+ ret = xsm_getpageframeinfo(mfn);
+ if (ret)
+ break;
+
page = mfn_to_page(mfn);
if ( likely(mfn_valid(mfn) && get_page(page, d)) )
@@ -350,6 +396,10 @@ long arch_do_dom0_op(struct dom0_op *op,
ret = -EINVAL;
if ( d != NULL )
{
+ ret = xsm_getmemlist(d);
+ if (ret)
+ goto getmemlist_out;
+
ret = 0;
spin_lock(&d->page_alloc_lock);
@@ -371,6 +421,7 @@ long arch_do_dom0_op(struct dom0_op *op,
op->u.getmemlist.num_pfns = i;
copy_to_guest(u_dom0_op, op, 1);
+ getmemlist_out:
put_domain(d);
}
}
@@ -380,6 +431,11 @@ long arch_do_dom0_op(struct dom0_op *op,
{
extern int opt_noirqbalance;
int quirk_id = op->u.platform_quirk.quirk_id;
+
+ ret = xsm_platform_quirk(quirk_id);
+ if (ret)
+ break;
+
switch ( quirk_id )
{
case QUIRK_NOIRQBALANCING:
@@ -409,6 +465,10 @@ long arch_do_dom0_op(struct dom0_op *op,
struct dom0_memory_map_entry entry;
int i;
+ ret = xsm_physmemmap();
+ if (ret)
+ break;
+
for ( i = 0; i < e820.nr_map; i++ )
{
if ( i >= op->u.physical_memory_map.max_map_entries )
@@ -436,6 +496,10 @@ long arch_do_dom0_op(struct dom0_op *op,
op->u.hypercall_init.domain)) == NULL) )
break;
+ ret = xsm_hypercall_init(d);
+ if (ret)
+ goto hypercallinit_out;
+
ret = -EACCES;
if ( !mfn_valid(mfn) ||
!get_page_and_type(mfn_to_page(mfn), d, PGT_writable_page) )
@@ -452,6 +516,7 @@ long arch_do_dom0_op(struct dom0_op *op,
put_page_and_type(mfn_to_page(mfn));
+ hypercallinit_out:
put_domain(d);
}
break;
diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/arch/x86/mm.c
--- a/xen/arch/x86/mm.c Fri May 26 09:23:33 2006 +0100
+++ b/xen/arch/x86/mm.c Thu Aug 31 17:14:49 2006 -0400
@@ -105,6 +105,7 @@
#include <asm/ldt.h>
#include <asm/x86_emulate.h>
#include <public/memory.h>
+#include <xsm/xsm.h>
#ifdef VERBOSE
#define MEM_LOG(_f, _a...) \
@@ -2083,6 +2084,10 @@ int do_mmu_update(
*/
case MMU_NORMAL_PT_UPDATE:
+ rc = xsm_mmu_normal_update(d, req.val);
+ if (rc)
+ goto out;
+
gmfn = req.ptr >> PAGE_SHIFT;
mfn = gmfn_to_mfn(d, gmfn);
diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/arch/x86/setup.c
--- a/xen/arch/x86/setup.c Fri May 26 09:23:33 2006 +0100
+++ b/xen/arch/x86/setup.c Thu Aug 31 17:14:49 2006 -0400
@@ -24,6 +24,7 @@
#include <asm/shadow.h>
#include <asm/e820.h>
#include <acm/acm_hooks.h>
+#include <xsm/xsm.h>
extern void dmi_scan_machine(void);
extern void generic_apic_probe(void);
@@ -404,6 +405,8 @@ void __init __start_xen(multiboot_info_t
scheduler_init();
+ xsm_init(&initrdidx, mbi, initial_images_start);
+
idle_domain = domain_create(IDLE_DOMAIN_ID, 0);
BUG_ON(idle_domain == NULL);
@@ -507,6 +510,8 @@ void __init __start_xen(multiboot_info_t
set_bit(_DOMF_privileged, &dom0->domain_flags);
/* post-create hooks sets security label */
acm_post_domain0_create(dom0->domain_id);
+
+ xsm_complete_init(dom0);
/* Grab the DOM0 command line. */
cmdline = (char *)(mod[0].string ? __va(mod[0].string) : NULL);
diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/arch/x86/x86_32/entry.S
--- a/xen/arch/x86/x86_32/entry.S Fri May 26 09:23:33 2006 +0100
+++ b/xen/arch/x86/x86_32/entry.S Thu Aug 31 17:14:49 2006 -0400
@@ -648,6 +648,7 @@ ENTRY(hypercall_table)
.long do_acm_op
.long do_nmi_op
.long do_arch_sched_op
+ .long do_xsm_op /* 30 */
.rept NR_hypercalls-((.-hypercall_table)/4)
.long do_ni_hypercall
.endr
@@ -683,6 +684,7 @@ ENTRY(hypercall_args_table)
.byte 1 /* do_acm_op */
.byte 2 /* do_nmi_op */
.byte 2 /* do_arch_sched_op */
+ .byte 1 /* do_xsm_op */
.rept NR_hypercalls-(.-hypercall_args_table)
.byte 0 /* do_ni_hypercall */
.endr
diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/arch/x86/x86_32/xen.lds.S
--- a/xen/arch/x86/x86_32/xen.lds.S Fri May 26 09:23:33 2006 +0100
+++ b/xen/arch/x86/x86_32/xen.lds.S Thu Aug 31 17:14:49 2006 -0400
@@ -56,6 +56,7 @@ SECTIONS
__initcall_start = .;
.initcall.init : { *(.initcall.init) } :text
__initcall_end = .;
+ .xsm_initcall.init : { __xsm_initcall_start = .; *(.xsm_initcall.init) __xsm_initcall_end = .; }
. = ALIGN(STACK_SIZE);
__init_end = .;
diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/common/dom0_ops.c
--- a/xen/common/dom0_ops.c Fri May 26 09:23:33 2006 +0100
+++ b/xen/common/dom0_ops.c Thu Aug 31 17:14:49 2006 -0400
@@ -22,6 +22,7 @@
#include <public/dom0_ops.h>
#include <public/sched_ctl.h>
#include <acm/acm_hooks.h>
+#include <xsm/xsm.h>
extern long arch_do_dom0_op(
struct dom0_op *op, GUEST_HANDLE(dom0_op_t) u_dom0_op);
@@ -82,6 +83,8 @@ static void getdomaininfo(struct domain
info->ssidref = ((struct acm_ssid_domain *)d->ssid)->ssidref;
else
info->ssidref = ACM_DEFAULT_SSID;
+
+ xsm_security_domaininfo(d, info);
info->tot_pages = d->tot_pages;
info->max_pages = d->max_pages;
@@ -120,7 +123,12 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
ret = -ESRCH;
if ( d != NULL )
{
+ ret = xsm_setvcpucontext(d);
+ if (ret)
+ goto setvcpucontext_out;
+
ret = set_info_guest(d, &op->u.setvcpucontext);
+ setvcpucontext_out:
put_domain(d);
}
}
@@ -132,12 +140,18 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
ret = -ESRCH;
if ( d != NULL )
{
+ ret = xsm_pausedomain(d);
+ if (ret)
+ goto pausedomain_out;
+
ret = -EINVAL;
if ( d != current->domain )
{
domain_pause_by_systemcontroller(d);
ret = 0;
}
+
+ pausedomain_out:
put_domain(d);
}
}
@@ -146,9 +160,14 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
case DOM0_UNPAUSEDOMAIN:
{
struct domain *d = find_domain_by_id(op->u.unpausedomain.domain);
+
ret = -ESRCH;
if ( d != NULL )
{
+ ret = xsm_unpausedomain(d);
+ if (ret)
+ goto unpausedomain_out;
+
ret = -EINVAL;
if ( (d != current->domain) &&
test_bit(_VCPUF_initialised, &d->vcpu[0]->vcpu_flags) )
@@ -156,6 +175,8 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
domain_unpause_by_systemcontroller(d);
ret = 0;
}
+
+ unpausedomain_out:
put_domain(d);
}
}
@@ -178,12 +199,16 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
if ( supervisor_mode_kernel )
return -EINVAL;
+ ret = xsm_createdomain(op);
+ if (ret)
+ goto createdomain_out;
+
dom = op->u.createdomain.domain;
if ( (dom > 0) && (dom < DOMID_FIRST_RESERVED) )
{
ret = -EINVAL;
if ( !is_free_domid(dom) )
- break;
+ goto createdomain_out;
}
else
{
@@ -197,7 +222,7 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
ret = -ENOMEM;
if ( dom == rover )
- break;
+ goto createdomain_out;
rover = dom;
}
@@ -232,7 +257,9 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
ret = -ENOMEM;
if ( (d = domain_create(dom, pro)) == NULL )
- break;
+ goto createdomain_out;
+
+ xsm_createdomain_post(d, op);
memcpy(d->handle, op->u.createdomain.handle,
sizeof(xen_domain_handle_t));
@@ -240,8 +267,13 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
ret = 0;
op->u.createdomain.domain = d->domain_id;
- if ( copy_to_guest(u_dom0_op, op, 1) )
- ret = -EFAULT;
+
+ createdomain_out:
+ if (ret)
+ xsm_createdomain_fail(op);
+
+ if ( copy_to_guest(u_dom0_op, op, 1) )
+ ret = -EFAULT;
}
break;
@@ -258,6 +290,10 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
if ( (d = find_domain_by_id(op->u.max_vcpus.domain)) == NULL )
break;
+ ret = xsm_max_vcpus(d);
+ if (ret)
+ goto maxvcpu_out;
+
/*
* Can only create new VCPUs while the domain is not fully constructed
* (and hence not runnable). Xen needs auditing for races before
@@ -293,17 +329,24 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
case DOM0_DESTROYDOMAIN:
{
struct domain *d = find_domain_by_id(op->u.destroydomain.domain);
+
ret = -ESRCH;
if ( d != NULL )
{
+ ret = xsm_destroydomain(d);
+ if (ret)
+ goto destroydomain_out;
+
ret = -EINVAL;
if ( d != current->domain )
{
domain_kill(d);
ret = 0;
}
- put_domain(d);
- }
+
+ destroydomain_out:
+ put_domain(d);
+ }
}
break;
@@ -320,6 +363,10 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
break;
}
+ ret = xsm_setvcpuaffinity(d);
+ if (ret)
+ goto setvcpuaffinity_out;
+
if ( (op->u.setvcpuaffinity.vcpu >= MAX_VIRT_CPUS) ||
!d->vcpu[op->u.setvcpuaffinity.vcpu] )
{
@@ -350,13 +397,17 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
(int)sizeof(op->u.setvcpuaffinity.cpumap)));
ret = vcpu_set_affinity(v, &new_affinity);
-
+
+ setvcpuaffinity_out:
put_domain(d);
}
break;
case DOM0_SCHEDCTL:
{
+ ret = xsm_schedctl(&op->u.schedctl);
+ if (ret)
+ break;
ret = sched_ctl(&op->u.schedctl);
if ( copy_to_guest(u_dom0_op, op, 1) )
ret = -EFAULT;
@@ -365,6 +416,9 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
case DOM0_ADJUSTDOM:
{
+ ret = xsm_adjustdom(&op->u.adjustdom);
+ if (ret)
+ break;
ret = sched_adjdom(&op->u.adjustdom);
if ( copy_to_guest(u_dom0_op, op, 1) )
ret = -EFAULT;
@@ -397,11 +451,16 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
read_unlock(&domlist_lock);
+ ret = xsm_getdomaininfo(d);
+ if (ret)
+ goto getdomaininfo_out;
+
getdomaininfo(d, &op->u.getdomaininfo);
if ( copy_to_guest(u_dom0_op, op, 1) )
ret = -EFAULT;
+ getdomaininfo_out:
put_domain(d);
}
break;
@@ -426,6 +485,12 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
break;
}
+ ret = xsm_getdomaininfo(d);
+ if (ret) {
+ put_domain(d);
+ continue;
+ }
+
getdomaininfo(d, &info);
put_domain(d);
@@ -461,7 +526,11 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
ret = -ESRCH;
if ( (d = find_domain_by_id(op->u.getvcpucontext.domain)) == NULL )
break;
-
+
+ ret = xsm_getvcpucontext(d);
+ if (ret)
+ goto getvcpucontext_out;
+
ret = -EINVAL;
if ( op->u.getvcpucontext.vcpu >= MAX_VIRT_CPUS )
goto getvcpucontext_out;
@@ -510,6 +579,10 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
if ( (d = find_domain_by_id(op->u.getvcpuinfo.domain)) == NULL )
break;
+ ret = xsm_getvcpuinfo(d);
+ if (ret)
+ goto getvcpuinfo_out;
+
ret = -EINVAL;
if ( op->u.getvcpuinfo.vcpu >= MAX_VIRT_CPUS )
goto getvcpuinfo_out;
@@ -542,6 +615,10 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
case DOM0_SETTIME:
{
+ ret = xsm_settime();
+ if (ret)
+ break;
+
do_settime(op->u.settime.secs,
op->u.settime.nsecs,
op->u.settime.system_time);
@@ -551,6 +628,10 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
case DOM0_TBUFCONTROL:
{
+ ret = xsm_tbufcontrol();
+ if (ret)
+ break;
+
ret = tb_control(&op->u.tbufcontrol);
if ( copy_to_guest(u_dom0_op, op, 1) )
ret = -EFAULT;
@@ -559,6 +640,10 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
case DOM0_READCONSOLE:
{
+ ret = xsm_readconsole(op->u.readconsole.clear);
+ if (ret)
+ break;
+
ret = read_console_ring(
op->u.readconsole.buffer,
&op->u.readconsole.count,
@@ -570,6 +655,10 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
case DOM0_SCHED_ID:
{
+ ret = xsm_sched_id();
+ if (ret)
+ break;
+
op->u.sched_id.sched_id = sched_id();
if ( copy_to_guest(u_dom0_op, op, 1) )
ret = -EFAULT;
@@ -588,6 +677,10 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
if ( d == NULL )
break;
+ xsm_setdomainmaxmem(d);
+ if (ret)
+ goto setdomainmaxmem_out;
+
ret = -EINVAL;
new_max = op->u.setdomainmaxmem.max_memkb >> (PAGE_SHIFT-10);
@@ -599,6 +692,7 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
}
spin_unlock(&d->page_alloc_lock);
+ setdomainmaxmem_out:
put_domain(d);
}
break;
@@ -610,10 +704,16 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
d = find_domain_by_id(op->u.setdomainhandle.domain);
if ( d != NULL )
{
+ ret = xsm_setdomainhandle(d);
+ if (ret)
+ goto setdomainhandle_out;
+
memcpy(d->handle, op->u.setdomainhandle.handle,
sizeof(xen_domain_handle_t));
- put_domain(d);
ret = 0;
+
+ setdomainhandle_out:
+ put_domain(d);
}
}
break;
@@ -625,12 +725,18 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
d = find_domain_by_id(op->u.setdebugging.domain);
if ( d != NULL )
{
+ ret = xsm_setdebugging(d);
+ if (ret)
+ goto setdebugging_out;
+
if ( op->u.setdebugging.enable )
set_bit(_DOMF_debugging, &d->domain_flags);
else
clear_bit(_DOMF_debugging, &d->domain_flags);
- put_domain(d);
ret = 0;
+
+ setdebugging_out:
+ put_domain(d);
}
}
break;
@@ -649,11 +755,16 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
if ( d == NULL )
break;
+ ret = xsm_irq_permission(d, pirq, op->u.irq_permission.allow_access);
+ if (ret)
+ goto irqperm_out;
+
if ( op->u.irq_permission.allow_access )
ret = irq_permit_access(d, pirq);
else
ret = irq_deny_access(d, pirq);
+ irqperm_out:
put_domain(d);
}
break;
@@ -673,11 +784,16 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
if ( d == NULL )
break;
+ ret = xsm_iomem_permission(d, mfn, op->u.iomem_permission.allow_access);
+ if (ret)
+ goto iomemperm_out;
+
if ( op->u.iomem_permission.allow_access )
ret = iomem_permit_access(d, mfn, mfn + nr_mfns - 1);
else
ret = iomem_deny_access(d, mfn, mfn + nr_mfns - 1);
+ iomemperm_out:
put_domain(d);
}
break;
@@ -685,6 +801,10 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
#ifdef PERF_COUNTERS
case DOM0_PERFCCONTROL:
{
+ ret = xsm_perfcontrol(void);
+ if (ret)
+ break;
+
extern int perfc_control(dom0_perfccontrol_t *);
ret = perfc_control(&op->u.perfccontrol);
if ( copy_to_guest(u_dom0_op, op, 1) )
diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/common/domain.c
--- a/xen/common/domain.c Fri May 26 09:23:33 2006 +0100
+++ b/xen/common/domain.c Thu Aug 31 17:14:49 2006 -0400
@@ -24,6 +24,7 @@
#include <public/dom0_ops.h>
#include <public/sched.h>
#include <public/vcpu.h>
+#include <xsm/xsm.h>
/* Both these structures are protected by the domlist_lock. */
rwlock_t domlist_lock = RW_LOCK_UNLOCKED;
@@ -50,6 +51,9 @@ struct domain *domain_create(domid_t dom
INIT_LIST_HEAD(&d->xenpage_list);
rangeset_domain_initialise(d);
+
+ if (xsm_alloc_security_domain(d))
+ goto fail1;
if ( !is_idle_domain(d) )
{
@@ -305,6 +309,8 @@ void domain_destroy(struct domain *d)
arch_domain_destroy(d);
+ xsm_free_security_domain(d);
+
free_domain(d);
send_guest_virq(dom0->vcpu[0], VIRQ_DOM_EXC);
diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/common/event_channel.c
--- a/xen/common/event_channel.c Fri May 26 09:23:33 2006 +0100
+++ b/xen/common/event_channel.c Thu Aug 31 17:14:49 2006 -0400
@@ -29,6 +29,7 @@
#include <public/xen.h>
#include <public/event_channel.h>
#include <acm/acm_hooks.h>
+#include <xsm/xsm.h>
#define bucket_from_port(d,p) \
((d)->evtchn[(p)/EVTCHNS_PER_BUCKET])
@@ -61,9 +62,15 @@ static int get_free_port(struct domain *
chn = xmalloc_array(struct evtchn, EVTCHNS_PER_BUCKET);
if ( unlikely(chn == NULL) )
return -ENOMEM;
+
memset(chn, 0, EVTCHNS_PER_BUCKET * sizeof(*chn));
bucket_from_port(d, port) = chn;
+ if (xsm_alloc_security_evtchn(chn)) {
+ xfree(chn);
+ return -ENOMEM;
+ }
+
return port;
}
@@ -89,6 +96,10 @@ static long evtchn_alloc_unbound(evtchn_
if ( (port = get_free_port(d)) < 0 )
ERROR_EXIT(port);
chn = evtchn_from_port(d, port);
+
+ rc = xsm_evtchn_unbound(d, chn, alloc->remote_dom);
+ if (rc)
+ goto out;
chn->state = ECS_UNBOUND;
if ( (chn->u.unbound.remote_domid = alloc->remote_dom) == DOMID_SELF )
@@ -143,6 +154,10 @@ static long evtchn_bind_interdomain(evtc
(rchn->u.unbound.remote_domid != ld->domain_id) )
ERROR_EXIT(-EINVAL);
+ rc = xsm_evtchn_interdomain(ld, lchn, rd, rchn);
+ if (rc)
+ goto out;
+
lchn->u.interdomain.remote_dom = rd;
lchn->u.interdomain.remote_port = (u16)rport;
lchn->state = ECS_INTERDOMAIN;
@@ -193,6 +208,11 @@ static long evtchn_bind_virq(evtchn_bind
ERROR_EXIT(port);
chn = evtchn_from_port(d, port);
+
+ rc = xsm_evtchn_virq(d, chn, virq, vcpu);
+ if (rc)
+ goto out;
+
chn->state = ECS_VIRQ;
chn->notify_vcpu_id = vcpu;
chn->u.virq = virq;
@@ -222,6 +242,11 @@ static long evtchn_bind_ipi(evtchn_bind_
ERROR_EXIT(port);
chn = evtchn_from_port(d, port);
+
+ rc = xsm_evtchn_ipi(d, chn, vcpu);
+ if (rc)
+ goto out;
+
chn->state = ECS_IPI;
chn->notify_vcpu_id = vcpu;
@@ -257,6 +282,10 @@ static long evtchn_bind_pirq(evtchn_bind
chn = evtchn_from_port(d, port);
+ rc = xsm_evtchn_pirq(d, chn, pirq);
+ if (rc)
+ goto out;
+
d->pirq_to_evtchn[pirq] = port;
rc = pirq_guest_bind(d->vcpu[0], pirq,
!!(bind->flags & BIND_PIRQ__WILL_SHARE));
@@ -296,6 +325,11 @@ static long __evtchn_close(struct domain
}
chn1 = evtchn_from_port(d1, port1);
+
+ rc = xsm_evtchn_close(d1, chn1);
+ if (rc)
+ goto out;
+
switch ( chn1->state )
{
case ECS_FREE:
@@ -415,6 +449,11 @@ long evtchn_send(unsigned int lport)
}
lchn = evtchn_from_port(ld, lport);
+
+ ret = xsm_evtchn_send(ld, lchn);
+ if (ret)
+ goto out;
+
switch ( lchn->state )
{
case ECS_INTERDOMAIN:
@@ -433,6 +472,7 @@ long evtchn_send(unsigned int lport)
ret = -EINVAL;
}
+out:
spin_unlock(&ld->evtchn_lock);
return ret;
@@ -511,6 +551,11 @@ static long evtchn_status(evtchn_status_
}
chn = evtchn_from_port(d, port);
+
+ rc = xsm_evtchn_status(d, chn);
+ if (rc)
+ goto out;
+
switch ( chn->state )
{
case ECS_FREE:
@@ -568,6 +613,11 @@ long evtchn_bind_vcpu(unsigned int port,
}
chn = evtchn_from_port(d, port);
+
+ rc = xsm_evtchn_vcpu(d, chn, vcpu_id);
+ if (rc)
+ goto out;
+
switch ( chn->state )
{
case ECS_UNBOUND:
@@ -591,6 +641,8 @@ static long evtchn_unmask(evtchn_unmask_
shared_info_t *s = d->shared_info;
int port = unmask->port;
struct vcpu *v;
+ int ret = 0;
+ struct evtchn *chn;
spin_lock(&d->evtchn_lock);
@@ -600,8 +652,13 @@ static long evtchn_unmask(evtchn_unmask_
return -EINVAL;
}
- v = d->vcpu[evtchn_from_port(d, port)->notify_vcpu_id];
-
+ chn = evtchn_from_port(d, port);
+ v = d->vcpu[chn->notify_vcpu_id];
+
+ ret = xsm_evtchn_unmask(d, chn);
+ if (ret)
+ goto out;
+
/*
* These operations must happen in strict order. Based on
* include/xen/event.h:evtchn_set_pending().
@@ -615,9 +672,10 @@ static long evtchn_unmask(evtchn_unmask_
evtchn_notify(v);
}
+out:
spin_unlock(&d->evtchn_lock);
- return 0;
+ return ret;
}
long do_event_channel_op(GUEST_HANDLE(evtchn_op_t) uop)
@@ -696,10 +754,16 @@ long do_event_channel_op(GUEST_HANDLE(ev
int evtchn_init(struct domain *d)
{
+ struct evtchn *chn;
+
spin_lock_init(&d->evtchn_lock);
if ( get_free_port(d) != 0 )
return -EINVAL;
- evtchn_from_port(d, 0)->state = ECS_RESERVED;
+ chn = evtchn_from_port(d, 0);
+ chn->state = ECS_RESERVED;
+ if (xsm_evtchn_init(d, chn))
+ return -EACCES;
+
return 0;
}
@@ -711,8 +775,10 @@ void evtchn_destroy(struct domain *d)
for ( i = 0; port_is_valid(d, i); i++ )
(void)__evtchn_close(d, i);
- for ( i = 0; i < NR_EVTCHN_BUCKETS; i++ )
+ for ( i = 0; i < NR_EVTCHN_BUCKETS; i++ ) {
+ xsm_free_security_evtchn(d->evtchn[i]);
xfree(d->evtchn[i]);
+ }
}
/*
diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/common/grant_table.c
--- a/xen/common/grant_table.c Fri May 26 09:23:33 2006 +0100
+++ b/xen/common/grant_table.c Thu Aug 31 17:14:49 2006 -0400
@@ -31,6 +31,7 @@
#include <xen/trace.h>
#include <xen/guest_access.h>
#include <acm/acm_hooks.h>
+#include <xsm/xsm.h>
#define PIN_FAIL(_lbl, _rc, _f, _a...) \
do { \
@@ -120,6 +121,14 @@ __gnttab_map_grant_ref(
return;
}
+ rc = xsm_grant_mapref(ld, rd, op->flags);
+ if (rc)
+ {
+ put_domain(rd);
+ op->status = GNTST_permission_denied;
+ return;
+ }
+
/* Get a maptrack handle. */
if ( unlikely((handle = get_maptrack_handle(ld->grant_table)) == -1) )
{
@@ -361,6 +370,14 @@ __gnttab_unmap_grant_ref(
return;
}
+ rc = xsm_grant_unmapref(ld, rd);
+ if (rc)
+ {
+ put_domain(rd);
+ op->status = GNTST_permission_denied;
+ return;
+ }
+
TRACE_1D(TRC_MEM_PAGE_GRANT_UNMAP, dom);
act = &rd->grant_table->active[ref];
@@ -506,6 +523,13 @@ gnttab_setup_table(
goto out;
}
+ if ( xsm_grant_setup(current->domain, d) )
+ {
+ put_domain(d);
+ op.status = GNTST_permission_denied;
+ goto out;
+ }
+
if ( op.nr_frames <= NR_GRANT_FRAMES )
{
ASSERT(d->grant_table != NULL);
@@ -653,6 +677,12 @@ gnttab_transfer(
goto copyback;
}
+ if ( xsm_grant_transfer(d, e) )
+ {
+ gop.status = GNTST_permission_denied;
+ goto copyback;
+ }
+
spin_lock(&e->page_alloc_lock);
/*
diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/include/public/xen.h
--- a/xen/include/public/xen.h Fri May 26 09:23:33 2006 +0100
+++ b/xen/include/public/xen.h Thu Aug 31 17:14:49 2006 -0400
@@ -60,6 +60,7 @@
#define __HYPERVISOR_acm_op 27
#define __HYPERVISOR_nmi_op 28
#define __HYPERVISOR_sched_op 29
+#define __HYPERVISOR_xsm_op 30
/*
* VIRTUAL INTERRUPTS
diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/include/xen/grant_table.h
--- a/xen/include/xen/grant_table.h Fri May 26 09:23:33 2006 +0100
+++ b/xen/include/xen/grant_table.h Thu Aug 31 17:14:49 2006 -0400
@@ -74,6 +74,7 @@ typedef struct {
grant_entry_t *shared;
/* Active grant table. */
active_grant_entry_t *active;
+ void *security;
/* Mapping tracking table. */
grant_mapping_t *maptrack;
unsigned int maptrack_head;
diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/include/xen/hypercall.h
--- a/xen/include/xen/hypercall.h Fri May 26 09:23:33 2006 +0100
+++ b/xen/include/xen/hypercall.h Thu Aug 31 17:14:49 2006 -0400
@@ -12,6 +12,7 @@
#include <public/acm_ops.h>
#include <public/event_channel.h>
#include <asm/hypercall.h>
+#include <xsm/xsm.h>
extern long
do_ni_hypercall(
@@ -82,6 +83,10 @@ do_acm_op(
GUEST_HANDLE(acm_op_t) u_acm_op);
extern long
+do_xsm_op(
+ GUEST_HANDLE(xsm_op_t) u_xsm_op);
+
+extern long
do_nmi_op(
unsigned int cmd,
GUEST_HANDLE(void) arg);
diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/include/xen/sched.h
--- a/xen/include/xen/sched.h Fri May 26 09:23:33 2006 +0100
+++ b/xen/include/xen/sched.h Thu Aug 31 17:14:49 2006 -0400
@@ -47,6 +47,7 @@ struct evtchn
u16 pirq; /* state == ECS_PIRQ */
u16 virq; /* state == ECS_VIRQ */
} u;
+ void *ssid;
};
int evtchn_init(struct domain *d);
diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/include/xsm/xsm.h
--- /dev/null Thu Jan 1 00:00:00 1970 +0000
+++ b/xen/include/xsm/xsm.h Thu Aug 31 17:14:49 2006 -0400
@@ -0,0 +1,722 @@
+/*
+ * This file contains the Flask hook function implementations for Xen.
+ *
+ * This work is based on the LSM implementation in Linux 2.6.13.4.
+ *
+ * Author: George Coker, <gscoker@alpha.ncsc.mil>
+ *
+ * Contributors: Michael LeMay, <mdlemay@epoch.ncsc.mil>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2,
+ * as published by the Free Software Foundation.
+ */
+
+#ifndef __XSM_H__
+#define __XSM_H__
+
+#include <xen/sched.h>
+#include <xen/multiboot.h>
+
+#ifdef XSM_ENABLE
+
+/* policy magic number (defined by XSM_MAGIC) */
+typedef u32 xsm_magic_t;
+#ifndef XSM_MAGIC
+#define XSM_MAGIC 0x00000000
+#endif
+
+extern char *policy_buffer;
+extern u32 policy_size;
+
+typedef void xsm_op_t;
+DEFINE_GUEST_HANDLE(xsm_op_t);
+
+typedef int (*xsm_initcall_t)(void);
+
+extern xsm_initcall_t __xsm_initcall_start[], __xsm_initcall_end[];
+
+#define xsm_initcall(fn) \
+ static xsm_initcall_t __initcall_##fn \
+ __attribute_used__ __attribute__((__section__(".xsm_initcall.init"))) = fn
+
+struct xsm_operations {
+ void (*security_domaininfo) (struct domain *d, dom0_getdomaininfo_t *info);
+ int (*setvcpucontext) (struct domain *d);
+ int (*pausedomain) (struct domain *d);
+ int (*unpausedomain) (struct domain *d);
+ int (*createdomain) (dom0_op_t *op);
+ void (*createdomain_post) (struct domain *d, dom0_op_t *op);
+ void (*createdomain_fail) (dom0_op_t *op);
+ int (*max_vcpus) (struct domain *d);
+ int (*destroydomain) (struct domain *d);
+ int (*setvcpuaffinity) (struct domain *d);
+ int (*schedctl) (struct sched_ctl_cmd *cmd);
+ int (*adjustdom) (struct sched_adjdom_cmd *cmd);
+ int (*getdomaininfo) (struct domain *d);
+ int (*getvcpucontext) (struct domain *d);
+ int (*getvcpuinfo) (struct domain *d);
+ int (*settime) (void);
+ int (*tbufcontrol) (void);
+ int (*readconsole) (uint32_t clear);
+ int (*sched_id) (void);
+ int (*setdomainmaxmem) (struct domain *d);
+ int (*setdomainhandle) (struct domain *d);
+ int (*setdebugging) (struct domain *d);
+ int (*irq_permission) (struct domain *d, uint8_t pirq, uint8_t access);
+ int (*iomem_permission) (struct domain *d, unsigned long mfn, uint8_t access);
+ int (*perfcontrol) (void);
+
+ int (*msr) (uint32_t);
+ int (*shadow_control) (struct domain *d, uint32_t op);
+ int (*memtype) (uint32_t access);
+ int (*microcode) (void);
+ int (*ioport_permission) (struct domain *d, uint32_t ioport, uint8_t access);
+ int (*physinfo) (void);
+ int (*getpageframeinfo) (unsigned long mfn);
+ int (*getmemlist) (struct domain *d);
+ int (*platform_quirk) (uint32_t);
+ int (*physmemmap) (void);
+ int (*hypercall_init) (struct domain *d);
+
+ int (*evtchn_unbound) (struct domain *d, struct evtchn *chn, domid_t id2);
+ int (*evtchn_interdomain) (struct domain *d1, struct evtchn *chn1,
+ struct domain *d2, struct evtchn *chn2);
+ int (*evtchn_virq) (struct domain *d, struct evtchn *chn, int virq, int vcpu);
+ int (*evtchn_ipi) (struct domain *d, struct evtchn *chn, int vcpu);
+ int (*evtchn_pirq) (struct domain *d, struct evtchn *chn, int pirq);
+ int (*evtchn_close) (struct domain *d, struct evtchn *chn);
+ int (*evtchn_send) (struct domain *d, struct evtchn *chn);
+ int (*evtchn_status) (struct domain *d, struct evtchn *chn);
+ int (*evtchn_vcpu) (struct domain *d, struct evtchn *chn, unsigned int vcpu);
+ int (*evtchn_unmask) (struct domain *d, struct evtchn *chn);
+ int (*evtchn_init) (struct domain *d, struct evtchn *chn);
+
+ int (*grant_mapref) (struct domain *d1, struct domain *d2, uint32_t flags);
+ int (*grant_unmapref) (struct domain *d1, struct domain *d2);
+ int (*grant_setup) (struct domain *d1, struct domain *d2);
+ int (*grant_transfer) (struct domain *d1, struct domain *d2);
+
+ int (*alloc_security_domain) (struct domain *d);
+ void (*free_security_domain) (struct domain *d);
+ int (*alloc_security_evtchn) (struct evtchn *chn);
+ void (*free_security_evtchn) (struct evtchn *chn);
+
+ int (*mmu_normal_update) (struct domain *d, intpte_t fpte);
+
+ long (*__do_xsm_op) (GUEST_HANDLE(xsm_op_t) op);
+ void (*complete_init) (struct domain *d);
+};
+
+extern struct xsm_operations *xsm_ops;
+
+static inline void xsm_security_domaininfo (struct domain *d, dom0_getdomaininfo_t *info)
+{
+ xsm_ops->security_domaininfo(d, info);
+}
+
+static inline int xsm_setvcpucontext(struct domain *d)
+{
+ return xsm_ops->setvcpucontext(d);
+}
+
+static inline int xsm_pausedomain (struct domain *d)
+{
+ return xsm_ops->pausedomain(d);
+}
+
+static inline int xsm_unpausedomain (struct domain *d)
+{
+ return xsm_ops->unpausedomain(d);
+}
+
+static inline int xsm_createdomain (dom0_op_t *op)
+{
+ return xsm_ops->createdomain(op);
+}
+
+static inline void xsm_createdomain_post (struct domain *d, dom0_op_t *op)
+{
+ xsm_ops->createdomain_post(d, op);
+}
+
+static inline void xsm_createdomain_fail (dom0_op_t *op)
+{
+ xsm_ops->createdomain_fail(op);
+}
+
+static inline int xsm_max_vcpus(struct domain *d)
+{
+ return xsm_ops->max_vcpus(d);
+}
+
+static inline int xsm_destroydomain (struct domain *d)
+{
+ return xsm_ops->destroydomain(d);
+}
+
+static inline int xsm_setvcpuaffinity (struct domain *d)
+{
+ return xsm_ops->setvcpuaffinity(d);
+}
+
+static inline int xsm_schedctl (struct sched_ctl_cmd *cmd)
+{
+ return xsm_ops->schedctl(cmd);
+}
+
+static inline int xsm_adjustdom (struct sched_adjdom_cmd *cmd)
+{
+ return xsm_ops->adjustdom(cmd);
+}
+
+static inline int xsm_getdomaininfo (struct domain *d)
+{
+ return xsm_ops->getdomaininfo(d);
+}
+
+static inline int xsm_getvcpucontext (struct domain *d)
+{
+ return xsm_ops->getvcpucontext(d);
+}
+
+static inline int xsm_getvcpuinfo (struct domain *d)
+{
+ return xsm_ops->getvcpuinfo(d);
+}
+
+static inline int xsm_settime (void)
+{
+ return xsm_ops->settime();
+}
+
+static inline int xsm_tbufcontrol (void)
+{
+ return xsm_ops->tbufcontrol();
+}
+
+static inline int xsm_readconsole (uint32_t clear)
+{
+ return xsm_ops->readconsole(clear);
+}
+
+static inline int xsm_sched_id (void)
+{
+ return xsm_ops->sched_id();
+}
+
+static inline int xsm_setdomainmaxmem (struct domain *d)
+{
+ return xsm_ops->setdomainmaxmem(d);
+}
+
+static inline int xsm_setdomainhandle (struct domain *d)
+{
+ return xsm_ops->setdomainhandle(d);
+}
+
+static inline int xsm_setdebugging (struct domain *d)
+{
+ return xsm_ops->setdebugging(d);
+}
+
+static inline int xsm_irq_permission (struct domain *d, uint8_t pirq, uint8_t access)
+{
+ return xsm_ops->irq_permission(d, pirq, access);
+}
+
+static inline int xsm_iomem_permission (struct domain *d, unsigned long mfn, uint8_t access)
+{
+ return xsm_ops->iomem_permission(d, mfn, access);
+}
+
+static inline int xsm_perfconrol (void)
+{
+ return xsm_ops->perfcontrol();
+}
+
+static inline int xsm_msr (uint32_t access)
+{
+ return xsm_ops->msr(access);
+}
+
+static inline int xsm_shadow_control (struct domain *d, uint32_t op)
+{
+ return xsm_ops->shadow_control(d, op);
+}
+
+static inline int xsm_memtype (uint32_t access)
+{
+ return xsm_ops->memtype(access);
+}
+
+static inline int xsm_microcode (void)
+{
+ return xsm_ops->microcode();
+}
+
+static inline int xsm_ioport_permission (struct domain *d, uint32_t ioport, uint8_t access)
+{
+ return xsm_ops->ioport_permission(d, ioport, access);
+}
+
+static inline int xsm_physinfo (void)
+{
+ return xsm_ops->physinfo();
+}
+
+static inline int xsm_getpageframeinfo (unsigned long mfn)
+{
+ return xsm_ops->getpageframeinfo(mfn);
+}
+
+static inline int xsm_getmemlist (struct domain *d)
+{
+ return xsm_ops->getmemlist(d);
+}
+
+static inline int xsm_platform_quirk (uint32_t quirk)
+{
+ return xsm_ops->platform_quirk(quirk);
+}
+
+static inline int xsm_physmemmap (void)
+{
+ return xsm_ops->physmemmap();
+}
+
+static inline int xsm_hypercall_init (struct domain *d)
+{
+ return xsm_ops->hypercall_init(d);
+}
+
+static inline int xsm_evtchn_unbound (struct domain *d1, struct evtchn *chn,
+ domid_t id2)
+{
+ return xsm_ops->evtchn_unbound(d1, chn, id2);
+}
+
+static inline int xsm_evtchn_interdomain (struct domain *d1, struct evtchn
+ *chan1, struct domain *d2, struct evtchn *chan2)
+{
+ return xsm_ops->evtchn_interdomain(d1, chan1, d2, chan2);
+}
+
+static inline int xsm_evtchn_virq (struct domain *d, struct evtchn *chn,
+ int virq, int vcpu)
+{
+ return xsm_ops->evtchn_virq(d, chn, virq, vcpu);
+}
+
+static inline int xsm_evtchn_ipi (struct domain *d, struct evtchn *chn, int vcpu)
+{
+ return xsm_ops->evtchn_ipi(d, chn, vcpu);
+}
+
+static inline int xsm_evtchn_pirq (struct domain *d, struct evtchn *chn, int pirq)
+{
+ return xsm_ops->evtchn_pirq(d, chn, pirq);
+}
+
+static inline int xsm_evtchn_close (struct domain *d, struct evtchn *chn)
+{
+ return xsm_ops->evtchn_close(d, chn);
+}
+
+static inline int xsm_evtchn_send (struct domain *d, struct evtchn *chn)
+{
+ return xsm_ops->evtchn_send(d, chn);
+}
+
+static inline int xsm_evtchn_status (struct domain *d, struct evtchn *chn)
+{
+ return xsm_ops->evtchn_status(d, chn);
+}
+
+static inline int xsm_evtchn_vcpu (struct domain *d, struct evtchn *chn,
+ unsigned int vcpu)
+{
+ return xsm_ops->evtchn_vcpu(d, chn, vcpu);
+}
+
+static inline int xsm_evtchn_unmask (struct domain *d, struct evtchn *chn)
+{
+ return xsm_ops->evtchn_unmask(d, chn);
+}
+
+static inline int xsm_evtchn_init (struct domain *d, struct evtchn *chn)
+{
+ return xsm_ops->evtchn_init(d, chn);
+}
+
+static inline int xsm_grant_mapref (struct domain *d1, struct domain *d2,
+ uint32_t flags)
+{
+ return xsm_ops->grant_mapref(d1, d2, flags);
+}
+
+static inline int xsm_grant_unmapref (struct domain *d1, struct domain *d2)
+{
+ return xsm_ops->grant_unmapref(d1, d2);
+}
+
+static inline int xsm_grant_setup (struct domain *d1, struct domain *d2)
+{
+ return xsm_ops->grant_setup(d1, d2);
+}
+
+static inline int xsm_grant_transfer (struct domain *d1, struct domain *d2)
+{
+ return xsm_ops->grant_transfer(d1, d2);
+}
+
+static inline int xsm_alloc_security_domain (struct domain *d)
+{
+ return xsm_ops->alloc_security_domain(d);
+}
+
+static inline void xsm_free_security_domain (struct domain *d)
+{
+ xsm_ops->free_security_domain(d);
+}
+
+static inline int xsm_alloc_security_evtchn (struct evtchn *chn)
+{
+ return xsm_ops->alloc_security_evtchn(chn);
+}
+
+static inline void xsm_free_security_evtchn (struct evtchn *chn)
+{
+ xsm_ops->free_security_evtchn(chn);
+}
+
+static inline int xsm_mmu_normal_update (struct domain *d, intpte_t fpte)
+{
+ return xsm_ops->mmu_normal_update(d, fpte);
+}
+
+static inline long __do_xsm_op (GUEST_HANDLE(xsm_op_t) op)
+{
+ return xsm_ops->__do_xsm_op(op);
+}
+
+static inline void xsm_complete_init (struct domain *d)
+{
+ xsm_ops->complete_init(d);
+}
+
+extern int xsm_init(unsigned int *initrdidx, const multiboot_info_t *mbi,
+ unsigned long initial_images_start);
+extern int xsm_policy_init(unsigned int *initrdidx, const multiboot_info_t *mbi,
+ unsigned long initial_images_start);
+extern int register_xsm(struct xsm_operations *ops);
+extern int unregister_xsm(struct xsm_operations *ops);
+
+#else
+
+static inline void xsm_security_domaininfo (struct domain *d, dom0_getdomaininfo_t *info)
+{
+ return;
+}
+
+static inline int xsm_setvcpucontext(struct domain *d)
+{
+ return 0;
+}
+
+static inline int xsm_pausedomain (struct domain *d)
+{
+ return 0;
+}
+
+static inline int xsm_unpausedomain (struct domain *d)
+{
+ return 0;
+}
+
+static inline int xsm_createdomain (dom0_op_t *op)
+{
+ return 0;
+}
+
+static inline void xsm_createdomain_post (struct domain *d, dom0_op_t *op)
+{
+ return;
+}
+
+static inline void xsm_createdomain_fail (dom0_op_t *op)
+{
+ return;
+}
+
+static inline int xsm_max_vcpus(struct domain *d)
+{
+ return 0;
+}
+
+static inline int xsm_destroydomain (struct domain *d1, struct domain *d2)
+{
+ return 0;
+}
+
+static inline int xsm_setvcpuaffinity (struct domain *d)
+{
+ return 0;
+}
+
+static inline int xsm_schedctl (struct sched_ctl_cmd *cmd)
+{
+ return 0;
+}
+
+static inline int xsm_adjustdom (struct sched_adjdom_cmd *cmd)
+{
+ return 0;
+}
+
+static inline int xsm_getdomaininfo (struct domain *d)
+{
+ return 0;
+}
+
+static inline int xsm_getvcpucontext (struct domain *d)
+{
+ return 0;
+}
+
+static inline int xsm_getvcpuinfo (struct domain d)
+{
+ return 0;
+}
+
+static inline int xsm_settime (void)
+{
+ return 0;
+}
+
+static inline int xsm_tbufcontrol (void)
+{
+ return 0;
+}
+
+static inline int xsm_readconsole (uint32_t clear)
+{
+ return 0;
+}
+
+static inline int xsm_sched_id (void)
+{
+ return 0;
+}
+
+static inline int xsm_setdomainmaxmem (struct domain d)
+{
+ return 0;
+}
+
+static inline int xsm_setdomainhandle (struct domain *d)
+{
+ return 0;
+}
+
+static inline int xsm_setdebugging (struct domain *d)
+{
+ return 0;
+}
+
+static inline int xsm_irq_permission (struct domain *d, uint8_t pirq, uint8_t access)
+{
+ return 0;
+}
+
+static inline int xsm_iomem_permission (struct domain *d, unsigned long mfn, uint8_t access)
+{
+ return 0;
+}
+
+static inline int xsm_perfconrol (struct domain *d)
+{
+ return 0;
+}
+
+static inline int xsm_msr (uint32_t access)
+{
+ return 0;
+}
+
+static inline int xsm_shadow_control (struct domain *d, uint32_t op)
+{
+ return 0;
+}
+
+static inline int xsm_memtype (uint32_t access)
+{
+ return 0;
+}
+
+static inline int xsm_microcode (void)
+{
+ return 0;
+}
+
+static inline int xsm_ioport_permission (struct domain *d, uint32_t ioport, uint8_t access)
+{
+ return 0;
+}
+
+static inline int xsm_physinfo (void)
+{
+ return 0;
+}
+
+static inline int xsm_getpageframeinfo (unsigned long mfn)
+{
+ return 0;
+}
+
+static inline int xsm_getmemlist (struct domain *d)
+{
+ return 0;
+}
+
+static inline int xsm_platform_quirk (uint32_t quirk)
+{
+ return 0;
+}
+
+static inline int xsm_physmemmap (void)
+{
+ return 0;
+}
+
+static inline int xsm_hypercall_init (struct domain *d)
+{
+ return 0;
+}
+
+static inline int xsm_evtchn_unbound (struct domain *d1, struct evtchn *chn,
+ domid_t id2)
+{
+ return 0;
+}
+
+static inline int xsm_evtchn_interdomain (struct domain *d1, struct evtchn
+ *chan1, struct domain *d2, struct evtchn *chan2)
+{
+ return 0;
+}
+
+static inline int xsm_evtchn_virq (struct domain *d, struct evtchn *chn,
+ int virq, int vcpu)
+{
+ return 0;
+}
+
+static inline int xsm_evtchn_ipi (struct domain *d, struct evtchn *chn, int vcpu)
+{
+ return 0;
+}
+
+static inline int xsm_evtchn_pirq (struct domain *d, struct evtchn *chn, int pirq)
+{
+ return 0;
+}
+
+static inline int xsm_evtchn_close (struct domain *d, struct evtchn *chn)
+{
+ return 0;
+}
+
+static inline int xsm_evtchn_send (struct domain *d, struct evtchn *chn)
+{
+ return 0;
+}
+
+static inline int xsm_evtchn_status (struct domain *d, struct evtchn *chn)
+{
+ return 0;
+}
+
+static inline int xsm_evtchn_vcpu (struct domain *d, struct evtchn *chn,
+ unsigned int vcpu)
+{
+ return 0;
+}
+
+static inline int xsm_evtchn_unmask (struct domain *d, struct evtchn *chn)
+{
+ return 0;
+}
+
+static inline int xsm_evtchn_init (struct domain *d, struct evtchn *chn)
+{
+ return 0;
+}
+
+static inline int xsm_grant_mapref (struct domain *d1, struct domain *d2,
+ uint32_t flags)
+{
+ return 0;
+}
+
+static inline int xsm_grant_unmapref (struct domain *d1, struct domain *d2)
+{
+ return 0;
+}
+
+static inline int xsm_grant_setup (struct domain *d1, struct domain *d2)
+{
+ return 0;
+}
+
+static inline int xsm_grant_transfer (struct domain *d1, struct domain *d2)
+{
+ return 0;
+}
+
+static inline int xsm_alloc_security_domain (struct domain *d)
+{
+ return 0;
+}
+
+static inline void xsm_free_security_domain (struct domain *d)
+{
+ return;
+}
+
+static inline int xsm_alloc_security_evtchn (struct evtchn *chn)
+{
+ return 0;
+}
+
+static inline void xsm_free_security_evtchn (struct evtchn *chn)
+{
+ return;
+}
+
+static inline int xsm_mmu_normal_update (struct domain *d, intpte_t fpte)
+{
+ return 0;
+}
+
+static inline long __do_xsm_op (GUEST_HANDLE(xsm_op_t) op)
+{
+ return -ENOSYS;
+}
+
+static inline int xsm_complete_init (struct domain *d)
+{
+ return 0;
+}
+
+static inline int xsm_init (unsigned int *initrdidx, const multiboot_info_t *mbi,
+ unsigned long initial_images_start)
+{
+ return 0;
+}
+
+#endif
+
+#endif
+
+extern long do_xsm_op (GUEST_HANDLE(xsm_op_t) op);
diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/xsm/Makefile
--- /dev/null Thu Jan 1 00:00:00 1970 +0000
+++ b/xen/xsm/Makefile Thu Aug 31 17:14:49 2006 -0400
@@ -0,0 +1,3 @@
+obj-y += xsm_core.o
+obj-y += xsm_policy.o
+obj-y += dummy.o
diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/xsm/dummy.c
--- /dev/null Thu Jan 1 00:00:00 1970 +0000
+++ b/xen/xsm/dummy.c Thu Aug 31 17:14:49 2006 -0400
@@ -0,0 +1,392 @@
+/*
+ * This file contains the Flask hook function implementations for Xen.
+ *
+ * This work is based on the LSM implementation in Linux 2.6.13.4.
+ *
+ * Author: George Coker, <gscoker@alpha.ncsc.mil>
+ *
+ * Contributors: Michael LeMay, <mdlemay@epoch.ncsc.mil>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2,
+ * as published by the Free Software Foundation.
+ */
+
+#include <xen/sched.h>
+#include <xsm/xsm.h>
+
+#ifdef XSM_ENABLE
+
+static void dummy_security_domaininfo(struct domain *d, dom0_getdomaininfo_t *info) {
+ return;
+}
+
+static int dummy_setvcpucontext(struct domain *d)
+{
+ return 0;
+}
+
+static int dummy_pausedomain (struct domain *d)
+{
+ return 0;
+}
+
+static int dummy_unpausedomain (struct domain *d)
+{
+ return 0;
+}
+
+static int dummy_createdomain(dom0_op_t *op)
+{
+ return 0;
+}
+
+static void dummy_createdomain_post (struct domain *d, dom0_op_t *op)
+{
+ return;
+}
+
+static void dummy_createdomain_fail (dom0_op_t *op)
+{
+ return;
+}
+
+static int dummy_max_vcpus(struct domain *d)
+{
+ return 0;
+}
+
+static int dummy_destroydomain (struct domain *d)
+{
+ return 0;
+}
+
+static int dummy_setvcpuaffinity (struct domain *d)
+{
+ return 0;
+}
+
+static int dummy_schedctl (struct sched_ctl_cmd *cmd)
+{
+ return 0;
+}
+
+static int dummy_adjustdom (struct sched_adjdom_cmd *cmd)
+{
+ return 0;
+}
+
+static int dummy_getdomaininfo (struct domain *d)
+{
+ return 0;
+}
+
+static int dummy_getvcpucontext (struct domain *d)
+{
+ return 0;
+}
+
+static int dummy_getvcpuinfo (struct domain *d)
+{
+ return 0;
+}
+
+static int dummy_settime (void)
+{
+ return 0;
+}
+
+static int dummy_tbufcontrol (void)
+{
+ return 0;
+}
+
+static int dummy_readconsole (uint32_t clear)
+{
+ return 0;
+}
+
+static int dummy_sched_id (void)
+{
+ return 0;
+}
+
+static int dummy_setdomainmaxmem (struct domain *d)
+{
+ return 0;
+}
+
+static int dummy_setdomainhandle (struct domain *d)
+{
+ return 0;
+}
+
+static int dummy_setdebugging (struct domain *d)
+{
+ return 0;
+}
+
+static int dummy_irq_permission (struct domain *d, uint8_t pirq, uint8_t access)
+{
+ return 0;
+}
+
+static int dummy_iomem_permission (struct domain *d, unsigned long mfn, uint8_t access)
+{
+ return 0;
+}
+
+static int dummy_perfcontrol (void)
+{
+ return 0;
+}
+
+static int dummy_msr (uint32_t access)
+{
+ return 0;
+}
+
+static int dummy_shadow_control (struct domain *d, uint32_t op)
+{
+ return 0;
+}
+
+static int dummy_memtype (uint32_t access)
+{
+ return 0;
+}
+
+static int dummy_microcode (void)
+{
+ return 0;
+}
+
+static int dummy_ioport_permission (struct domain *d, uint32_t ioport, uint8_t access)
+{
+ return 0;
+}
+
+static int dummy_physinfo (void)
+{
+ return 0;
+}
+
+static int dummy_getpageframeinfo (unsigned long mfn)
+{
+ return 0;
+}
+
+static int dummy_getmemlist (struct domain *d)
+{
+ return 0;
+}
+
+static int dummy_platform_quirk (uint32_t quirk)
+{
+ return 0;
+}
+
+static int dummy_physmemmap (void)
+{
+ return 0;
+}
+
+static int dummy_hypercall_init (struct domain *d)
+{
+ return 0;
+}
+
+static int dummy_alloc_security_domain (struct domain *d)
+{
+ return 0;
+}
+
+static void dummy_free_security_domain (struct domain *d)
+{
+ return;
+}
+
+static int dummy_grant_mapref (struct domain *d1, struct domain *d2,
+ uint32_t flags)
+{
+ return 0;
+}
+
+static int dummy_grant_unmapref (struct domain *d1, struct domain *d2)
+{
+ return 0;
+}
+
+static int dummy_grant_setup (struct domain *d1, struct domain *d2)
+{
+ return 0;
+}
+
+static int dummy_grant_transfer (struct domain *d1, struct domain *d2)
+{
+ return 0;
+}
+
+static int dummy_mmu_normal_update (struct domain *d, intpte_t fpte)
+{
+ return 0;
+}
+
+static int dummy_evtchn_unbound (struct domain *d, struct evtchn *chn,
+ domid_t id2)
+{
+ return 0;
+}
+
+static int dummy_evtchn_interdomain (struct domain *d1, struct evtchn
+ *chan1, struct domain *d2, struct evtchn *chan2)
+{
+ return 0;
+}
+
+static int dummy_evtchn_virq (struct domain *d, struct evtchn *chn,
+ int virq, int vcpu)
+{
+ return 0;
+}
+
+static int dummy_evtchn_ipi (struct domain *d, struct evtchn *chn, int vcpu)
+{
+ return 0;
+}
+
+static int dummy_evtchn_pirq (struct domain *d, struct evtchn *chn, int pirq)
+{
+ return 0;
+}
+
+static int dummy_evtchn_close (struct domain *d, struct evtchn *chn)
+{
+ return 0;
+}
+
+static int dummy_evtchn_send (struct domain *d, struct evtchn *chn)
+{
+ return 0;
+}
+
+static int dummy_evtchn_status (struct domain *d, struct evtchn *chn)
+{
+ return 0;
+}
+
+static int dummy_evtchn_vcpu (struct domain *d, struct evtchn *chn,
+ unsigned int vcpu_id)
+{
+ return 0;
+}
+
+static int dummy_evtchn_unmask (struct domain *d, struct evtchn *chn)
+{
+ return 0;
+}
+
+static int dummy_alloc_security_evtchn (struct evtchn *chn)
+{
+ return 0;
+}
+
+static void dummy_free_security_evtchn (struct evtchn *chn)
+{
+ return;
+}
+
+static int dummy_evtchn_init (struct domain *d, struct evtchn *chn)
+{
+ return 0;
+}
+
+static void dummy_complete_init (struct domain *d)
+{
+ return;
+}
+
+static long dummy___do_xsm_op(GUEST_HANDLE(xsm_op_t) op)
+{
+ return -ENOSYS;
+}
+
+struct xsm_operations dummy_xsm_ops;
+
+#define set_to_dummy_if_null(ops, function) \
+ do { \
+ if (!ops->function) { \
+ ops->function = dummy_##function; \
+ DPRINTK("Had to override the " #function \
+ " security operation with the dummy one.\n"); \
+ } \
+ } while (0)
+
+void xsm_fixup_ops (struct xsm_operations *ops)
+{
+ set_to_dummy_if_null(ops, security_domaininfo);
+ set_to_dummy_if_null(ops, setvcpucontext);
+ set_to_dummy_if_null(ops, pausedomain);
+ set_to_dummy_if_null(ops, unpausedomain);
+ set_to_dummy_if_null(ops, createdomain);
+ set_to_dummy_if_null(ops, createdomain_post);
+ set_to_dummy_if_null(ops, createdomain_fail);
+ set_to_dummy_if_null(ops, max_vcpus);
+ set_to_dummy_if_null(ops, destroydomain);
+ set_to_dummy_if_null(ops, setvcpuaffinity);
+ set_to_dummy_if_null(ops, schedctl);
+ set_to_dummy_if_null(ops, adjustdom);
+ set_to_dummy_if_null(ops, getdomaininfo);
+ set_to_dummy_if_null(ops, getvcpucontext);
+ set_to_dummy_if_null(ops, getvcpuinfo);
+ set_to_dummy_if_null(ops, settime);
+ set_to_dummy_if_null(ops, tbufcontrol);
+ set_to_dummy_if_null(ops, readconsole);
+ set_to_dummy_if_null(ops, sched_id);
+ set_to_dummy_if_null(ops, setdomainmaxmem);
+ set_to_dummy_if_null(ops, setdomainhandle);
+ set_to_dummy_if_null(ops, setdebugging);
+ set_to_dummy_if_null(ops, irq_permission);
+ set_to_dummy_if_null(ops, iomem_permission);
+ set_to_dummy_if_null(ops, perfcontrol);
+ set_to_dummy_if_null(ops, msr);
+ set_to_dummy_if_null(ops, shadow_control);
+ set_to_dummy_if_null(ops, memtype);
+ set_to_dummy_if_null(ops, microcode);
+ set_to_dummy_if_null(ops, ioport_permission);
+ set_to_dummy_if_null(ops, physinfo);
+ set_to_dummy_if_null(ops, getpageframeinfo);
+ set_to_dummy_if_null(ops, getmemlist);
+ set_to_dummy_if_null(ops, platform_quirk);
+ set_to_dummy_if_null(ops, physmemmap);
+ set_to_dummy_if_null(ops, hypercall_init);
+
+ set_to_dummy_if_null(ops, evtchn_unbound);
+ set_to_dummy_if_null(ops, evtchn_interdomain);
+ set_to_dummy_if_null(ops, evtchn_virq);
+ set_to_dummy_if_null(ops, evtchn_pirq);
+ set_to_dummy_if_null(ops, evtchn_ipi);
+ set_to_dummy_if_null(ops, evtchn_close);
+ set_to_dummy_if_null(ops, evtchn_send);
+ set_to_dummy_if_null(ops, evtchn_status);
+ set_to_dummy_if_null(ops, evtchn_vcpu);
+ set_to_dummy_if_null(ops, evtchn_unmask);
+ set_to_dummy_if_null(ops, evtchn_init);
+
+ set_to_dummy_if_null(ops, grant_mapref);
+ set_to_dummy_if_null(ops, grant_unmapref);
+ set_to_dummy_if_null(ops, grant_setup);
+ set_to_dummy_if_null(ops, grant_transfer);
+
+ set_to_dummy_if_null(ops, alloc_security_domain);
+ set_to_dummy_if_null(ops, free_security_domain);
+ set_to_dummy_if_null(ops, alloc_security_evtchn);
+ set_to_dummy_if_null(ops, free_security_evtchn);
+
+ set_to_dummy_if_null(ops, mmu_normal_update);
+
+ set_to_dummy_if_null(ops, __do_xsm_op);
+ set_to_dummy_if_null(ops, complete_init);
+}
+
+#endif
diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/xsm/xsm_core.c
--- /dev/null Thu Jan 1 00:00:00 1970 +0000
+++ b/xen/xsm/xsm_core.c Thu Aug 31 17:14:49 2006 -0400
@@ -0,0 +1,114 @@
+/*
+ * This file contains the Flask hook function implementations for Xen.
+ *
+ * This work is based on the LSM implementation in Linux 2.6.13.4.
+ *
+ * Author: George Coker, <gscoker@alpha.ncsc.mil>
+ *
+ * Contributors: Michael LeMay, <mdlemay@epoch.ncsc.mil>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2,
+ * as published by the Free Software Foundation.
+ */
+
+#include <xen/init.h>
+#include <xen/errno.h>
+#include <xen/lib.h>
+
+#include <xsm/xsm.h>
+
+#ifdef XSM_ENABLE
+
+#define XSM_FRAMEWORK_VERSION "1.0.0"
+
+extern struct xsm_operations dummy_xsm_ops;
+extern void xsm_fixup_ops(struct xsm_operations *ops);
+
+struct xsm_operations *xsm_ops;
+
+static inline int verify(struct xsm_operations *ops)
+{
+ /* verify the security_operations structure exists */
+ if (!ops)
+ return -EINVAL;
+ xsm_fixup_ops(ops);
+ return 0;
+}
+
+static void __init do_xsm_initcalls(void)
+{
+ xsm_initcall_t *call;
+ call = __xsm_initcall_start;
+ while (call < __xsm_initcall_end) {
+ (*call) ();
+ call++;
+ }
+}
+
+int __init xsm_init(unsigned int *initrdidx, const multiboot_info_t *mbi,
+ unsigned long initial_images_start)
+{
+ int ret = 0;
+
+ printk("XSM Framework v" XSM_FRAMEWORK_VERSION " initialized\n");
+
+ if (XSM_MAGIC) {
+ ret = xsm_policy_init(initrdidx, mbi, initial_images_start);
+ if (ret) {
+ printk("%s: Error initializing policy.\n", __FUNCTION__);
+ return -EINVAL;
+ }
+ }
+
+ if (verify(&dummy_xsm_ops)) {
+ printk("%s could not verify "
+ "dummy_xsm_ops structure.\n", __FUNCTION__);
+ return -EIO;
+ }
+
+ xsm_ops = &dummy_xsm_ops;
+ do_xsm_initcalls();
+
+ return 0;
+}
+
+int register_xsm(struct xsm_operations *ops)
+{
+ if (verify(ops)) {
+ printk("%s could not verify "
+ "security_operations structure.\n", __FUNCTION__);
+ return -EINVAL;
+ }
+
+ if (xsm_ops != &dummy_xsm_ops)
+ return -EAGAIN;
+
+ xsm_ops = ops;
+
+ return 0;
+}
+
+
+int unregister_xsm(struct xsm_operations *ops)
+{
+ if (ops != xsm_ops) {
+ printk("%s: trying to unregister "
+ "a security_opts structure that is not "
+ "registered, failing.\n", __FUNCTION__);
+ return -EINVAL;
+ }
+
+ xsm_ops = &dummy_xsm_ops;
+
+ return 0;
+}
+
+#endif
+
+long do_xsm_op (GUEST_HANDLE(xsm_op_t) op)
+{
+ return __do_xsm_op(op);
+}
+
+
diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/xsm/xsm_policy.c
--- /dev/null Thu Jan 1 00:00:00 1970 +0000
+++ b/xen/xsm/xsm_policy.c Thu Aug 31 17:14:49 2006 -0400
@@ -0,0 +1,77 @@
+/*
+ * Copyright (C) 2005 IBM Corporation
+ *
+ * Authors:
+ * Reiner Sailer, <sailer@watson.ibm.com>
+ * Stefan Berger, <stefanb@watson.ibm.com>
+ *
+ * Contributors:
+ * Michael LeMay, <mdlemay@epoch.ncsc.mil>
+ * George Coker, <gscoker@alpha.ncsc.mil>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2,
+ * as published by the Free Software Foundation.
+ *
+ *
+ * This file contains the XSM policy init functions for Xen.
+ * This file is based on the ACM functions of the same name.
+ *
+ */
+
+#include <xsm/xsm.h>
+#include <xen/multiboot.h>
+
+char *policy_buffer = NULL;
+u32 policy_size = 0;
+
+int xsm_policy_init(unsigned int *initrdidx, const multiboot_info_t *mbi,
+ unsigned long initial_images_start)
+{
+ int i;
+ module_t *mod = (module_t *)__va(mbi->mods_addr);
+ int rc = 0;
+ u32 *_policy_start;
+ unsigned long _policy_len;
+
+ if (mbi->mods_count > 1)
+ *initrdidx = 1;
+
+ /*
+ * Try all modules and see whichever could be the binary policy.
+ * Adjust the initrdidx if module[1] is the binary policy.
+ */
+ for (i = mbi->mods_count-1; i >= 1; i--) {
+#if defined(__i386__)
+ _policy_start = (u32 *)(initial_images_start + (mod[i].mod_start-mod[0].mod_start));
+#elif defined(__x86_64__)
+ _policy_start = __va(initial_images_start + (mod[i].mod_start-mod[0].mod_start));
+#else
+#error Architecture unsupported by XSM
+#endif
+ _policy_len = mod[i].mod_end - mod[i].mod_start;
+
+ if ((xsm_magic_t)(*_policy_start) == XSM_MAGIC) {
+ policy_buffer = (char *)_policy_start;
+ policy_size = _policy_len;
+
+ printk("Policy len 0x%lx, start at %p.\n",
+ _policy_len,_policy_start);
+
+ if (i == 1) {
+ if (mbi->mods_count > 2) {
+ *initrdidx = 2;
+ } else {
+ *initrdidx = 0;
+ }
+ } else {
+ *initrdidx = 1;
+ }
+
+ break;
+
+ } /* end if a binary policy definition, i.e., (ntohl(pol->magic) == XSM_MAGIC ) */
+ }
+
+ return rc;
+}
[-- Attachment #3: Type: text/plain, Size: 138 bytes --]
_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xensource.com
http://lists.xensource.com/xen-devel
^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [Xense-devel][RFC][PATCH][1/4] Xen Security Modules: XSM
2006-09-01 16:58 [Xense-devel][RFC][PATCH][1/4] Xen Security Modules: XSM George S. Coker, II
@ 2006-09-01 18:35 ` James Morris
2006-09-01 18:47 ` George S. Coker, II
2006-09-01 18:55 ` Chris Wright
1 sibling, 1 reply; 11+ messages in thread
From: James Morris @ 2006-09-01 18:35 UTC (permalink / raw)
To: George S. Coker, II; +Cc: xen-devel, xense-devel
On Fri, 1 Sep 2006, George S. Coker, II wrote:
> XSM provides a generalized hook infrastructure allowing third-party
> security modules to interpose on the Xen code path. A default or dummy
> module provides basic call/return functionality for hooks not
> implemented by a given module.
Do you have any performance figures for the dummy module?
--
James Morris
<jmorris@redhat.com>
^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [Xense-devel][RFC][PATCH][1/4] Xen Security Modules: XSM
2006-09-01 18:35 ` James Morris
@ 2006-09-01 18:47 ` George S. Coker, II
0 siblings, 0 replies; 11+ messages in thread
From: George S. Coker, II @ 2006-09-01 18:47 UTC (permalink / raw)
To: James Morris; +Cc: xen-devel, xense-devel
On Fri, 2006-09-01 at 14:35 -0400, James Morris wrote:
> On Fri, 1 Sep 2006, George S. Coker, II wrote:
>
> > XSM provides a generalized hook infrastructure allowing third-party
> > security modules to interpose on the Xen code path. A default or dummy
> > module provides basic call/return functionality for hooks not
> > implemented by a given module.
>
> Do you have any performance figures for the dummy module?
>
>
No, we do not at this time. Our only performance metric is observation
which isn't prompting us to look further at the moment. However, this
is a fair question to ask.
^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [Xense-devel][RFC][PATCH][1/4] Xen Security Modules: XSM
2006-09-01 16:58 [Xense-devel][RFC][PATCH][1/4] Xen Security Modules: XSM George S. Coker, II
2006-09-01 18:35 ` James Morris
@ 2006-09-01 18:55 ` Chris Wright
2006-09-01 19:00 ` Chris Wright
` (2 more replies)
1 sibling, 3 replies; 11+ messages in thread
From: Chris Wright @ 2006-09-01 18:55 UTC (permalink / raw)
To: George S. Coker, II; +Cc: xen-devel, xense-devel
* George S. Coker, II (gscoker@alpha.ncsc.mil) wrote:
> The attached patch implements the Xen Security Modules (XSM) framework.
> This patch should apply cleanly to changeset 9694:d82a4c4d04d4 Xen
> 3.0.2-3.
Nice to see this all posted. Have any perfomance numbers for default
dummy, or numbers for increase in memory footprint for this + flask +
flask example policy? Just curious to see what the rough cost is.
Some quick comments below.
> Modules may also define at Xen compile time a magic number XSM_MAGIC to
> indicate that a policy should be discovered from the images loaded at
> boot. The policy file should then be listed in grub as one of the
> multi-boot modules after the dom0 kernel.
I like that feature.
> diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/arch/x86/dom0_ops.c
> --- a/xen/arch/x86/dom0_ops.c Fri May 26 09:23:33 2006 +0100
> +++ b/xen/arch/x86/dom0_ops.c Thu Aug 31 17:14:49 2006 -0400
> @@ -25,6 +25,7 @@
> #include <asm/hvm/support.h>
> #include <asm/processor.h>
> #include <public/sched_ctl.h>
> +#include <xsm/xsm.h>
>
> #include <asm/mtrr.h>
> #include "cpu/mtrr/mtrr.h"
> @@ -58,6 +59,10 @@ long arch_do_dom0_op(struct dom0_op *op,
>
> case DOM0_MSR:
> {
> + ret = xsm_msr(op->u.msr.write);
Hmm, this is against 3.0.2, unfortunately you'll have some work to move
to 3.0.3 with the hypercall changes here (IIRC, this one actually
went away). And have you done each arch? I only see x86 here.
<snip>
> diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/arch/x86/setup.c
> --- a/xen/arch/x86/setup.c Fri May 26 09:23:33 2006 +0100
> +++ b/xen/arch/x86/setup.c Thu Aug 31 17:14:49 2006 -0400
> @@ -24,6 +24,7 @@
> #include <asm/shadow.h>
> #include <asm/e820.h>
> #include <acm/acm_hooks.h>
> +#include <xsm/xsm.h>
>
> extern void dmi_scan_machine(void);
> extern void generic_apic_probe(void);
> @@ -404,6 +405,8 @@ void __init __start_xen(multiboot_info_t
>
> scheduler_init();
>
> + xsm_init(&initrdidx, mbi, initial_images_start);
> +
> idle_domain = domain_create(IDLE_DOMAIN_ID, 0);
> BUG_ON(idle_domain == NULL);
>
> @@ -507,6 +510,8 @@ void __init __start_xen(multiboot_info_t
> set_bit(_DOMF_privileged, &dom0->domain_flags);
> /* post-create hooks sets security label */
> acm_post_domain0_create(dom0->domain_id);
> +
> + xsm_complete_init(dom0);
Seems this should drop the acm hook here, no?
> /* Grab the DOM0 command line. */
> cmdline = (char *)(mod[0].string ? __va(mod[0].string) : NULL);
> diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/arch/x86/x86_32/entry.S
> --- a/xen/arch/x86/x86_32/entry.S Fri May 26 09:23:33 2006 +0100
> +++ b/xen/arch/x86/x86_32/entry.S Thu Aug 31 17:14:49 2006 -0400
> @@ -648,6 +648,7 @@ ENTRY(hypercall_table)
> .long do_acm_op
> .long do_nmi_op
> .long do_arch_sched_op
> + .long do_xsm_op /* 30 */
> .rept NR_hypercalls-((.-hypercall_table)/4)
> .long do_ni_hypercall
> .endr
> @@ -683,6 +684,7 @@ ENTRY(hypercall_args_table)
> .byte 1 /* do_acm_op */
> .byte 2 /* do_nmi_op */
> .byte 2 /* do_arch_sched_op */
> + .byte 1 /* do_xsm_op */
> .rept NR_hypercalls-(.-hypercall_args_table)
> .byte 0 /* do_ni_hypercall */
> .endr
> diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/arch/x86/x86_32/xen.lds.S
> --- a/xen/arch/x86/x86_32/xen.lds.S Fri May 26 09:23:33 2006 +0100
> +++ b/xen/arch/x86/x86_32/xen.lds.S Thu Aug 31 17:14:49 2006 -0400
> @@ -56,6 +56,7 @@ SECTIONS
> __initcall_start = .;
> .initcall.init : { *(.initcall.init) } :text
> __initcall_end = .;
> + .xsm_initcall.init : { __xsm_initcall_start = .; *(.xsm_initcall.init) __xsm_initcall_end = .; }
> . = ALIGN(STACK_SIZE);
> __init_end = .;
>
> diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/common/dom0_ops.c
> --- a/xen/common/dom0_ops.c Fri May 26 09:23:33 2006 +0100
> +++ b/xen/common/dom0_ops.c Thu Aug 31 17:14:49 2006 -0400
> @@ -22,6 +22,7 @@
> #include <public/dom0_ops.h>
> #include <public/sched_ctl.h>
> #include <acm/acm_hooks.h>
> +#include <xsm/xsm.h>
>
> extern long arch_do_dom0_op(
> struct dom0_op *op, GUEST_HANDLE(dom0_op_t) u_dom0_op);
> @@ -82,6 +83,8 @@ static void getdomaininfo(struct domain
> info->ssidref = ((struct acm_ssid_domain *)d->ssid)->ssidref;
> else
> info->ssidref = ACM_DEFAULT_SSID;
> +
> + xsm_security_domaininfo(d, info);
>
> info->tot_pages = d->tot_pages;
> info->max_pages = d->max_pages;
> @@ -120,7 +123,12 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
shouldn't this take care of the acm_pre_dom0_op hook here as well?
IOW, at the end there shouldn't be acm specific hooks left, right?
> diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/common/domain.c
> --- a/xen/common/domain.c Fri May 26 09:23:33 2006 +0100
> +++ b/xen/common/domain.c Thu Aug 31 17:14:49 2006 -0400
> @@ -24,6 +24,7 @@
> #include <public/dom0_ops.h>
> #include <public/sched.h>
> #include <public/vcpu.h>
> +#include <xsm/xsm.h>
>
> /* Both these structures are protected by the domlist_lock. */
> rwlock_t domlist_lock = RW_LOCK_UNLOCKED;
> @@ -50,6 +51,9 @@ struct domain *domain_create(domid_t dom
> INIT_LIST_HEAD(&d->xenpage_list);
>
> rangeset_domain_initialise(d);
> +
> + if (xsm_alloc_security_domain(d))
> + goto fail1;
>
> if ( !is_idle_domain(d) )
> {
> @@ -305,6 +309,8 @@ void domain_destroy(struct domain *d)
>
> arch_domain_destroy(d);
>
> + xsm_free_security_domain(d);
> +
> free_domain(d);
>
> send_guest_virq(dom0->vcpu[0], VIRQ_DOM_EXC);
> diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/include/xen/grant_table.h
> --- a/xen/include/xen/grant_table.h Fri May 26 09:23:33 2006 +0100
> +++ b/xen/include/xen/grant_table.h Thu Aug 31 17:14:49 2006 -0400
> @@ -74,6 +74,7 @@ typedef struct {
> grant_entry_t *shared;
> /* Active grant table. */
> active_grant_entry_t *active;
> + void *security;
What's a grant table label look like?
> /* Mapping tracking table. */
> grant_mapping_t *maptrack;
> unsigned int maptrack_head;
> diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/include/xen/hypercall.h
> diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/include/xen/sched.h
> --- a/xen/include/xen/sched.h Fri May 26 09:23:33 2006 +0100
> +++ b/xen/include/xen/sched.h Thu Aug 31 17:14:49 2006 -0400
> @@ -47,6 +47,7 @@ struct evtchn
> u16 pirq; /* state == ECS_PIRQ */
> u16 virq; /* state == ECS_VIRQ */
> } u;
> + void *ssid;
> };
Ah, you must resue the acm domain label? Actually would be nice to see
which objects are labelled, did I miss that list?
> int evtchn_init(struct domain *d);
> diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/include/xsm/xsm.h
> --- /dev/null Thu Jan 1 00:00:00 1970 +0000
> +++ b/xen/include/xsm/xsm.h Thu Aug 31 17:14:49 2006 -0400
> @@ -0,0 +1,722 @@
> +/*
> + * This file contains the Flask hook function implementations for Xen.
> + *
> + * This work is based on the LSM implementation in Linux 2.6.13.4.
> + *
> + * Author: George Coker, <gscoker@alpha.ncsc.mil>
> + *
> + * Contributors: Michael LeMay, <mdlemay@epoch.ncsc.mil>
> + *
> + * This program is free software; you can redistribute it and/or modify
> + * it under the terms of the GNU General Public License version 2,
> + * as published by the Free Software Foundation.
> + */
> +
> +#ifndef __XSM_H__
> +#define __XSM_H__
> +
> +#include <xen/sched.h>
> +#include <xen/multiboot.h>
> +
> +#ifdef XSM_ENABLE
> +
> +/* policy magic number (defined by XSM_MAGIC) */
> +typedef u32 xsm_magic_t;
> +#ifndef XSM_MAGIC
> +#define XSM_MAGIC 0x00000000
> +#endif
> +
> +extern char *policy_buffer;
> +extern u32 policy_size;
> +
> +typedef void xsm_op_t;
> +DEFINE_GUEST_HANDLE(xsm_op_t);
> +
> +typedef int (*xsm_initcall_t)(void);
> +
> +extern xsm_initcall_t __xsm_initcall_start[], __xsm_initcall_end[];
> +
> +#define xsm_initcall(fn) \
> + static xsm_initcall_t __initcall_##fn \
> + __attribute_used__ __attribute__((__section__(".xsm_initcall.init"))) = fn
> +
> +struct xsm_operations {
> + void (*security_domaininfo) (struct domain *d, dom0_getdomaininfo_t *info);
> + int (*setvcpucontext) (struct domain *d);
> + int (*pausedomain) (struct domain *d);
> + int (*unpausedomain) (struct domain *d);
> + int (*createdomain) (dom0_op_t *op);
> + void (*createdomain_post) (struct domain *d, dom0_op_t *op);
> + void (*createdomain_fail) (dom0_op_t *op);
> + int (*max_vcpus) (struct domain *d);
> + int (*destroydomain) (struct domain *d);
> + int (*setvcpuaffinity) (struct domain *d);
> + int (*schedctl) (struct sched_ctl_cmd *cmd);
> + int (*adjustdom) (struct sched_adjdom_cmd *cmd);
> + int (*getdomaininfo) (struct domain *d);
> + int (*getvcpucontext) (struct domain *d);
> + int (*getvcpuinfo) (struct domain *d);
> + int (*settime) (void);
> + int (*tbufcontrol) (void);
> + int (*readconsole) (uint32_t clear);
> + int (*sched_id) (void);
> + int (*setdomainmaxmem) (struct domain *d);
> + int (*setdomainhandle) (struct domain *d);
> + int (*setdebugging) (struct domain *d);
> + int (*irq_permission) (struct domain *d, uint8_t pirq, uint8_t access);
> + int (*iomem_permission) (struct domain *d, unsigned long mfn, uint8_t access);
> + int (*perfcontrol) (void);
> +
> + int (*msr) (uint32_t);
Platform specific code might want ifdefs, or perhaps a just platform
specific set of ops.
> + int (*shadow_control) (struct domain *d, uint32_t op);
> + int (*memtype) (uint32_t access);
> + int (*microcode) (void);
> + int (*ioport_permission) (struct domain *d, uint32_t ioport, uint8_t access);
> + int (*physinfo) (void);
> + int (*getpageframeinfo) (unsigned long mfn);
> + int (*getmemlist) (struct domain *d);
> + int (*platform_quirk) (uint32_t);
> + int (*physmemmap) (void);
> + int (*hypercall_init) (struct domain *d);
> +
> + int (*evtchn_unbound) (struct domain *d, struct evtchn *chn, domid_t id2);
> + int (*evtchn_interdomain) (struct domain *d1, struct evtchn *chn1,
> + struct domain *d2, struct evtchn *chn2);
> + int (*evtchn_virq) (struct domain *d, struct evtchn *chn, int virq, int vcpu);
> + int (*evtchn_ipi) (struct domain *d, struct evtchn *chn, int vcpu);
> + int (*evtchn_pirq) (struct domain *d, struct evtchn *chn, int pirq);
> + int (*evtchn_close) (struct domain *d, struct evtchn *chn);
> + int (*evtchn_send) (struct domain *d, struct evtchn *chn);
> + int (*evtchn_status) (struct domain *d, struct evtchn *chn);
> + int (*evtchn_vcpu) (struct domain *d, struct evtchn *chn, unsigned int vcpu);
> + int (*evtchn_unmask) (struct domain *d, struct evtchn *chn);
> + int (*evtchn_init) (struct domain *d, struct evtchn *chn);
> +
> + int (*grant_mapref) (struct domain *d1, struct domain *d2, uint32_t flags);
> + int (*grant_unmapref) (struct domain *d1, struct domain *d2);
> + int (*grant_setup) (struct domain *d1, struct domain *d2);
> + int (*grant_transfer) (struct domain *d1, struct domain *d2);
> +
> + int (*alloc_security_domain) (struct domain *d);
> + void (*free_security_domain) (struct domain *d);
> + int (*alloc_security_evtchn) (struct evtchn *chn);
> + void (*free_security_evtchn) (struct evtchn *chn);
Heh, well, that's as good as a list ;-)
> + int (*mmu_normal_update) (struct domain *d, intpte_t fpte);
> +
> + long (*__do_xsm_op) (GUEST_HANDLE(xsm_op_t) op);
We very intentionally did not do this in LSM (or more to the point,
we did and it was soundly rejected). It's a free form way to extend the
hypercall interface, which in Linux is frowned upon. Of course, you don't
have the various selinuxfs, /proc/<pid>/attr type of interfaces in the
hypervisor, but it's worth considering if there are other possibilities
(32/64-bit compat is an example of something which is easily lost when
pushing the hypercall interface down a layer into the module).
> diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/xsm/Makefile
> --- /dev/null Thu Jan 1 00:00:00 1970 +0000
> +++ b/xen/xsm/Makefile Thu Aug 31 17:14:49 2006 -0400
> @@ -0,0 +1,3 @@
> +obj-y += xsm_core.o
> +obj-y += xsm_policy.o
> +obj-y += dummy.o
> diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/xsm/dummy.c
> --- /dev/null Thu Jan 1 00:00:00 1970 +0000
> +++ b/xen/xsm/dummy.c Thu Aug 31 17:14:49 2006 -0400
> @@ -0,0 +1,392 @@
> +#include <xen/sched.h>
> +#include <xsm/xsm.h>
> +
> +#ifdef XSM_ENABLE
Can you just conditionally compile in this file using the above Makefile?
> diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/xsm/xsm_core.c
> --- /dev/null Thu Jan 1 00:00:00 1970 +0000
> +++ b/xen/xsm/xsm_core.c Thu Aug 31 17:14:49 2006 -0400
<snip>
> +#ifdef XSM_ENABLE
> +#endif
> +
> +long do_xsm_op (GUEST_HANDLE(xsm_op_t) op)
> +{
> + return __do_xsm_op(op);
> +}
Linux has the cond_syscall() macro, should be enough to do this
if you can't find a better way to do security module specifc
calls.
^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [Xense-devel][RFC][PATCH][1/4] Xen Security Modules: XSM
2006-09-01 18:55 ` Chris Wright
@ 2006-09-01 19:00 ` Chris Wright
2006-09-01 19:39 ` George S. Coker, II
2006-09-01 19:37 ` George S. Coker, II
2006-09-01 19:46 ` James Morris
2 siblings, 1 reply; 11+ messages in thread
From: Chris Wright @ 2006-09-01 19:00 UTC (permalink / raw)
To: George S. Coker, II; +Cc: Chris Wright, xen-devel, xense-devel
* Chris Wright (chrisw@sous-sol.org) wrote:
> > --- a/xen/arch/x86/x86_32/entry.S Fri May 26 09:23:33 2006 +0100
> > +++ b/xen/arch/x86/x86_32/entry.S Thu Aug 31 17:14:49 2006 -0400
> > @@ -648,6 +648,7 @@ ENTRY(hypercall_table)
> > .long do_acm_op
> > .long do_nmi_op
> > .long do_arch_sched_op
> > + .long do_xsm_op /* 30 */
And I forgot to ask, do you change the acm_op entrypoints to
go through this callback?
thanks,
-chris
^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [Xense-devel][RFC][PATCH][1/4] Xen Security Modules: XSM
2006-09-01 18:55 ` Chris Wright
2006-09-01 19:00 ` Chris Wright
@ 2006-09-01 19:37 ` George S. Coker, II
2006-09-02 3:43 ` Reiner Sailer
2006-09-01 19:46 ` James Morris
2 siblings, 1 reply; 11+ messages in thread
From: George S. Coker, II @ 2006-09-01 19:37 UTC (permalink / raw)
To: Chris Wright; +Cc: xen-devel, xense-devel
On Fri, 2006-09-01 at 11:55 -0700, Chris Wright wrote:
> * George S. Coker, II (gscoker@alpha.ncsc.mil) wrote:
> > The attached patch implements the Xen Security Modules (XSM) framework.
> > This patch should apply cleanly to changeset 9694:d82a4c4d04d4 Xen
> > 3.0.2-3.
>
> Nice to see this all posted. Have any perfomance numbers for default
> dummy, or numbers for increase in memory footprint for this + flask +
> flask example policy? Just curious to see what the rough cost is.
> Some quick comments below.
>
> > Modules may also define at Xen compile time a magic number XSM_MAGIC to
> > indicate that a policy should be discovered from the images loaded at
> > boot. The policy file should then be listed in grub as one of the
> > multi-boot modules after the dom0 kernel.
>
> I like that feature.
>
> > diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/arch/x86/dom0_ops.c
> > --- a/xen/arch/x86/dom0_ops.c Fri May 26 09:23:33 2006 +0100
> > +++ b/xen/arch/x86/dom0_ops.c Thu Aug 31 17:14:49 2006 -0400
> > @@ -25,6 +25,7 @@
> > #include <asm/hvm/support.h>
> > #include <asm/processor.h>
> > #include <public/sched_ctl.h>
> > +#include <xsm/xsm.h>
> >
> > #include <asm/mtrr.h>
> > #include "cpu/mtrr/mtrr.h"
> > @@ -58,6 +59,10 @@ long arch_do_dom0_op(struct dom0_op *op,
> >
> > case DOM0_MSR:
> > {
> > + ret = xsm_msr(op->u.msr.write);
>
> Hmm, this is against 3.0.2, unfortunately you'll have some work to move
> to 3.0.3 with the hypercall changes here (IIRC, this one actually
> went away). And have you done each arch? I only see x86 here.
>
We have only done x86 for now.
> <snip>
>
> > diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/arch/x86/setup.c
> > --- a/xen/arch/x86/setup.c Fri May 26 09:23:33 2006 +0100
> > +++ b/xen/arch/x86/setup.c Thu Aug 31 17:14:49 2006 -0400
> > @@ -24,6 +24,7 @@
> > #include <asm/shadow.h>
> > #include <asm/e820.h>
> > #include <acm/acm_hooks.h>
> > +#include <xsm/xsm.h>
> >
> > extern void dmi_scan_machine(void);
> > extern void generic_apic_probe(void);
> > @@ -404,6 +405,8 @@ void __init __start_xen(multiboot_info_t
> >
> > scheduler_init();
> >
> > + xsm_init(&initrdidx, mbi, initial_images_start);
> > +
> > idle_domain = domain_create(IDLE_DOMAIN_ID, 0);
> > BUG_ON(idle_domain == NULL);
> >
> > @@ -507,6 +510,8 @@ void __init __start_xen(multiboot_info_t
> > set_bit(_DOMF_privileged, &dom0->domain_flags);
> > /* post-create hooks sets security label */
> > acm_post_domain0_create(dom0->domain_id);
> > +
> > + xsm_complete_init(dom0);
>
> Seems this should drop the acm hook here, no?
>
We did not want the XSM patch to add XSM and remove ACM because we do
not believe that the community sees ACM and sHype as the distinct
entities that they really are. That's why we have the patch that
removes the duplicated hooks and code and produces a module called ACM.
Hopefully in the future XSM will refer to the security framework and the
the STE/Chinese Wall functionality of ACM will be called the sHype
module.
> > /* Grab the DOM0 command line. */
> > cmdline = (char *)(mod[0].string ? __va(mod[0].string) : NULL);
> > diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/arch/x86/x86_32/entry.S
> > --- a/xen/arch/x86/x86_32/entry.S Fri May 26 09:23:33 2006 +0100
> > +++ b/xen/arch/x86/x86_32/entry.S Thu Aug 31 17:14:49 2006 -0400
> > @@ -648,6 +648,7 @@ ENTRY(hypercall_table)
> > .long do_acm_op
> > .long do_nmi_op
> > .long do_arch_sched_op
> > + .long do_xsm_op /* 30 */
> > .rept NR_hypercalls-((.-hypercall_table)/4)
> > .long do_ni_hypercall
> > .endr
> > @@ -683,6 +684,7 @@ ENTRY(hypercall_args_table)
> > .byte 1 /* do_acm_op */
> > .byte 2 /* do_nmi_op */
> > .byte 2 /* do_arch_sched_op */
> > + .byte 1 /* do_xsm_op */
> > .rept NR_hypercalls-(.-hypercall_args_table)
> > .byte 0 /* do_ni_hypercall */
> > .endr
> > diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/arch/x86/x86_32/xen.lds.S
> > --- a/xen/arch/x86/x86_32/xen.lds.S Fri May 26 09:23:33 2006 +0100
> > +++ b/xen/arch/x86/x86_32/xen.lds.S Thu Aug 31 17:14:49 2006 -0400
> > @@ -56,6 +56,7 @@ SECTIONS
> > __initcall_start = .;
> > .initcall.init : { *(.initcall.init) } :text
> > __initcall_end = .;
> > + .xsm_initcall.init : { __xsm_initcall_start = .; *(.xsm_initcall.init) __xsm_initcall_end = .; }
> > . = ALIGN(STACK_SIZE);
> > __init_end = .;
> >
> > diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/common/dom0_ops.c
> > --- a/xen/common/dom0_ops.c Fri May 26 09:23:33 2006 +0100
> > +++ b/xen/common/dom0_ops.c Thu Aug 31 17:14:49 2006 -0400
> > @@ -22,6 +22,7 @@
> > #include <public/dom0_ops.h>
> > #include <public/sched_ctl.h>
> > #include <acm/acm_hooks.h>
> > +#include <xsm/xsm.h>
> >
> > extern long arch_do_dom0_op(
> > struct dom0_op *op, GUEST_HANDLE(dom0_op_t) u_dom0_op);
> > @@ -82,6 +83,8 @@ static void getdomaininfo(struct domain
> > info->ssidref = ((struct acm_ssid_domain *)d->ssid)->ssidref;
> > else
> > info->ssidref = ACM_DEFAULT_SSID;
> > +
> > + xsm_security_domaininfo(d, info);
> >
> > info->tot_pages = d->tot_pages;
> > info->max_pages = d->max_pages;
> > @@ -120,7 +123,12 @@ long do_dom0_op(GUEST_HANDLE(dom0_op_t)
>
> shouldn't this take care of the acm_pre_dom0_op hook here as well?
> IOW, at the end there shouldn't be acm specific hooks left, right?
>
> > diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/common/domain.c
> > --- a/xen/common/domain.c Fri May 26 09:23:33 2006 +0100
> > +++ b/xen/common/domain.c Thu Aug 31 17:14:49 2006 -0400
> > @@ -24,6 +24,7 @@
> > #include <public/dom0_ops.h>
> > #include <public/sched.h>
> > #include <public/vcpu.h>
> > +#include <xsm/xsm.h>
> >
> > /* Both these structures are protected by the domlist_lock. */
> > rwlock_t domlist_lock = RW_LOCK_UNLOCKED;
> > @@ -50,6 +51,9 @@ struct domain *domain_create(domid_t dom
> > INIT_LIST_HEAD(&d->xenpage_list);
> >
> > rangeset_domain_initialise(d);
> > +
> > + if (xsm_alloc_security_domain(d))
> > + goto fail1;
> >
> > if ( !is_idle_domain(d) )
> > {
> > @@ -305,6 +309,8 @@ void domain_destroy(struct domain *d)
> >
> > arch_domain_destroy(d);
> >
> > + xsm_free_security_domain(d);
> > +
> > free_domain(d);
> >
> > send_guest_virq(dom0->vcpu[0], VIRQ_DOM_EXC);
> > diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/include/xen/grant_table.h
> > --- a/xen/include/xen/grant_table.h Fri May 26 09:23:33 2006 +0100
> > +++ b/xen/include/xen/grant_table.h Thu Aug 31 17:14:49 2006 -0400
> > @@ -74,6 +74,7 @@ typedef struct {
> > grant_entry_t *shared;
> > /* Active grant table. */
> > active_grant_entry_t *active;
> > + void *security;
>
> What's a grant table label look like?
This is detritus in the patch. We have chosen not to put security
structures in grant tables at this time. We were looking into it, but
because the guest has complete control over the contents of the grant
entry, i.e. which page, there is no benefit than to check the
permissions on the domains involved in the grant.
>
> > /* Mapping tracking table. */
> > grant_mapping_t *maptrack;
> > unsigned int maptrack_head;
> > diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/include/xen/hypercall.h
> > diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/include/xen/sched.h
> > --- a/xen/include/xen/sched.h Fri May 26 09:23:33 2006 +0100
> > +++ b/xen/include/xen/sched.h Thu Aug 31 17:14:49 2006 -0400
> > @@ -47,6 +47,7 @@ struct evtchn
> > u16 pirq; /* state == ECS_PIRQ */
> > u16 virq; /* state == ECS_VIRQ */
> > } u;
> > + void *ssid;
> > };
>
> Ah, you must resue the acm domain label? Actually would be nice to see
> which objects are labelled, did I miss that list?
>
We presently have security labels on domains and event channels. We
reuse the security pointer added by ACM for domains. We do not have
labels on other hypervisor objects. The Flask module does use the
policy infrastructure to lookup labels on platform resources such as
physical interrupts.
> > int evtchn_init(struct domain *d);
> > diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/include/xsm/xsm.h
> > --- /dev/null Thu Jan 1 00:00:00 1970 +0000
> > +++ b/xen/include/xsm/xsm.h Thu Aug 31 17:14:49 2006 -0400
> > @@ -0,0 +1,722 @@
> > +/*
> > + * This file contains the Flask hook function implementations for Xen.
> > + *
> > + * This work is based on the LSM implementation in Linux 2.6.13.4.
> > + *
> > + * Author: George Coker, <gscoker@alpha.ncsc.mil>
> > + *
> > + * Contributors: Michael LeMay, <mdlemay@epoch.ncsc.mil>
> > + *
> > + * This program is free software; you can redistribute it and/or modify
> > + * it under the terms of the GNU General Public License version 2,
> > + * as published by the Free Software Foundation.
> > + */
> > +
> > +#ifndef __XSM_H__
> > +#define __XSM_H__
> > +
> > +#include <xen/sched.h>
> > +#include <xen/multiboot.h>
> > +
> > +#ifdef XSM_ENABLE
> > +
> > +/* policy magic number (defined by XSM_MAGIC) */
> > +typedef u32 xsm_magic_t;
> > +#ifndef XSM_MAGIC
> > +#define XSM_MAGIC 0x00000000
> > +#endif
> > +
> > +extern char *policy_buffer;
> > +extern u32 policy_size;
> > +
> > +typedef void xsm_op_t;
> > +DEFINE_GUEST_HANDLE(xsm_op_t);
> > +
> > +typedef int (*xsm_initcall_t)(void);
> > +
> > +extern xsm_initcall_t __xsm_initcall_start[], __xsm_initcall_end[];
> > +
> > +#define xsm_initcall(fn) \
> > + static xsm_initcall_t __initcall_##fn \
> > + __attribute_used__ __attribute__((__section__(".xsm_initcall.init"))) = fn
> > +
> > +struct xsm_operations {
> > + void (*security_domaininfo) (struct domain *d, dom0_getdomaininfo_t *info);
> > + int (*setvcpucontext) (struct domain *d);
> > + int (*pausedomain) (struct domain *d);
> > + int (*unpausedomain) (struct domain *d);
> > + int (*createdomain) (dom0_op_t *op);
> > + void (*createdomain_post) (struct domain *d, dom0_op_t *op);
> > + void (*createdomain_fail) (dom0_op_t *op);
> > + int (*max_vcpus) (struct domain *d);
> > + int (*destroydomain) (struct domain *d);
> > + int (*setvcpuaffinity) (struct domain *d);
> > + int (*schedctl) (struct sched_ctl_cmd *cmd);
> > + int (*adjustdom) (struct sched_adjdom_cmd *cmd);
> > + int (*getdomaininfo) (struct domain *d);
> > + int (*getvcpucontext) (struct domain *d);
> > + int (*getvcpuinfo) (struct domain *d);
> > + int (*settime) (void);
> > + int (*tbufcontrol) (void);
> > + int (*readconsole) (uint32_t clear);
> > + int (*sched_id) (void);
> > + int (*setdomainmaxmem) (struct domain *d);
> > + int (*setdomainhandle) (struct domain *d);
> > + int (*setdebugging) (struct domain *d);
> > + int (*irq_permission) (struct domain *d, uint8_t pirq, uint8_t access);
> > + int (*iomem_permission) (struct domain *d, unsigned long mfn, uint8_t access);
> > + int (*perfcontrol) (void);
> > +
> > + int (*msr) (uint32_t);
>
> Platform specific code might want ifdefs, or perhaps a just platform
> specific set of ops.
Right, because we are x86 specific at this time. But we should be more
careful.
>
> > + int (*shadow_control) (struct domain *d, uint32_t op);
> > + int (*memtype) (uint32_t access);
> > + int (*microcode) (void);
> > + int (*ioport_permission) (struct domain *d, uint32_t ioport, uint8_t access);
> > + int (*physinfo) (void);
> > + int (*getpageframeinfo) (unsigned long mfn);
> > + int (*getmemlist) (struct domain *d);
> > + int (*platform_quirk) (uint32_t);
> > + int (*physmemmap) (void);
> > + int (*hypercall_init) (struct domain *d);
> > +
> > + int (*evtchn_unbound) (struct domain *d, struct evtchn *chn, domid_t id2);
> > + int (*evtchn_interdomain) (struct domain *d1, struct evtchn *chn1,
> > + struct domain *d2, struct evtchn *chn2);
> > + int (*evtchn_virq) (struct domain *d, struct evtchn *chn, int virq, int vcpu);
> > + int (*evtchn_ipi) (struct domain *d, struct evtchn *chn, int vcpu);
> > + int (*evtchn_pirq) (struct domain *d, struct evtchn *chn, int pirq);
> > + int (*evtchn_close) (struct domain *d, struct evtchn *chn);
> > + int (*evtchn_send) (struct domain *d, struct evtchn *chn);
> > + int (*evtchn_status) (struct domain *d, struct evtchn *chn);
> > + int (*evtchn_vcpu) (struct domain *d, struct evtchn *chn, unsigned int vcpu);
> > + int (*evtchn_unmask) (struct domain *d, struct evtchn *chn);
> > + int (*evtchn_init) (struct domain *d, struct evtchn *chn);
> > +
> > + int (*grant_mapref) (struct domain *d1, struct domain *d2, uint32_t flags);
> > + int (*grant_unmapref) (struct domain *d1, struct domain *d2);
> > + int (*grant_setup) (struct domain *d1, struct domain *d2);
> > + int (*grant_transfer) (struct domain *d1, struct domain *d2);
> > +
> > + int (*alloc_security_domain) (struct domain *d);
> > + void (*free_security_domain) (struct domain *d);
> > + int (*alloc_security_evtchn) (struct evtchn *chn);
> > + void (*free_security_evtchn) (struct evtchn *chn);
>
> Heh, well, that's as good as a list ;-)
>
> > + int (*mmu_normal_update) (struct domain *d, intpte_t fpte);
> > +
> > + long (*__do_xsm_op) (GUEST_HANDLE(xsm_op_t) op);
>
> We very intentionally did not do this in LSM (or more to the point,
> we did and it was soundly rejected). It's a free form way to extend the
> hypercall interface, which in Linux is frowned upon. Of course, you don't
> have the various selinuxfs, /proc/<pid>/attr type of interfaces in the
> hypervisor, but it's worth considering if there are other possibilities
> (32/64-bit compat is an example of something which is easily lost when
> pushing the hypercall interface down a layer into the module).
>
> > diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/xsm/Makefile
> > --- /dev/null Thu Jan 1 00:00:00 1970 +0000
> > +++ b/xen/xsm/Makefile Thu Aug 31 17:14:49 2006 -0400
> > @@ -0,0 +1,3 @@
> > +obj-y += xsm_core.o
> > +obj-y += xsm_policy.o
> > +obj-y += dummy.o
> > diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/xsm/dummy.c
> > --- /dev/null Thu Jan 1 00:00:00 1970 +0000
> > +++ b/xen/xsm/dummy.c Thu Aug 31 17:14:49 2006 -0400
> > @@ -0,0 +1,392 @@
> > +#include <xen/sched.h>
> > +#include <xsm/xsm.h>
> > +
> > +#ifdef XSM_ENABLE
>
> Can you just conditionally compile in this file using the above Makefile?
>
yes.
> > diff -r d82a4c4d04d4 -r a24b5a5f5f5b xen/xsm/xsm_core.c
> > --- /dev/null Thu Jan 1 00:00:00 1970 +0000
> > +++ b/xen/xsm/xsm_core.c Thu Aug 31 17:14:49 2006 -0400
> <snip>
> > +#ifdef XSM_ENABLE
> > +#endif
> > +
> > +long do_xsm_op (GUEST_HANDLE(xsm_op_t) op)
> > +{
> > + return __do_xsm_op(op);
> > +}
>
> Linux has the cond_syscall() macro, should be enough to do this
> if you can't find a better way to do security module specifc
> calls.
>
--
George S. Coker, II <gscoker@alpha.ncsc.mil> 443-479-6944
^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [Xense-devel][RFC][PATCH][1/4] Xen Security Modules: XSM
2006-09-01 19:00 ` Chris Wright
@ 2006-09-01 19:39 ` George S. Coker, II
0 siblings, 0 replies; 11+ messages in thread
From: George S. Coker, II @ 2006-09-01 19:39 UTC (permalink / raw)
To: Chris Wright; +Cc: xen-devel, xense-devel
On Fri, 2006-09-01 at 12:00 -0700, Chris Wright wrote:
> * Chris Wright (chrisw@sous-sol.org) wrote:
> > > --- a/xen/arch/x86/x86_32/entry.S Fri May 26 09:23:33 2006 +0100
> > > +++ b/xen/arch/x86/x86_32/entry.S Thu Aug 31 17:14:49 2006 -0400
> > > @@ -648,6 +648,7 @@ ENTRY(hypercall_table)
> > > .long do_acm_op
> > > .long do_nmi_op
> > > .long do_arch_sched_op
> > > + .long do_xsm_op /* 30 */
>
> And I forgot to ask, do you change the acm_op entrypoints to
> go through this callback?
>
In the ACM patch, the only entrypoint to acp_op is through xsm_op.
> thanks,
> -chris
--
George S. Coker, II <gscoker@alpha.ncsc.mil> 443-479-6944
^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [Xense-devel][RFC][PATCH][1/4] Xen Security Modules: XSM
2006-09-01 18:55 ` Chris Wright
2006-09-01 19:00 ` Chris Wright
2006-09-01 19:37 ` George S. Coker, II
@ 2006-09-01 19:46 ` James Morris
2 siblings, 0 replies; 11+ messages in thread
From: James Morris @ 2006-09-01 19:46 UTC (permalink / raw)
To: Chris Wright; +Cc: xen-devel, George S. Coker, II, xense-devel
On Fri, 1 Sep 2006, Chris Wright wrote:
> > + int (*mmu_normal_update) (struct domain *d, intpte_t fpte);
> > +
> > + long (*__do_xsm_op) (GUEST_HANDLE(xsm_op_t) op);
>
> We very intentionally did not do this in LSM (or more to the point,
> we did and it was soundly rejected). It's a free form way to extend the
> hypercall interface, which in Linux is frowned upon.
I agree with Chris here -- it's definitely an architectural issue to
consider, in that you can end up with an arbitrary interface with weak
semantics, which is prone to maintainability & security issues, tasteless
abuse by third party code etc.
> Of course, you don't have the various selinuxfs, /proc/<pid>/attr type
> of interfaces in the hypervisor, but it's worth considering if there are
> other possibilities (32/64-bit compat is an example of something which
> is easily lost when pushing the hypercall interface down a layer into
> the module).
One interface possibility is some kind of extensible message passing
channel (perhaps like Netlink).
George, what did you have in mind as use-cases for this op?
- James
--
James Morris
<jmorris@redhat.com>
^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [Xense-devel][RFC][PATCH][1/4] Xen Security Modules: XSM
2006-09-01 19:37 ` George S. Coker, II
@ 2006-09-02 3:43 ` Reiner Sailer
2006-09-05 16:25 ` John McDermott (U.S. Navy Employee)
0 siblings, 1 reply; 11+ messages in thread
From: Reiner Sailer @ 2006-09-02 3:43 UTC (permalink / raw)
To: xense-devel, George S. Coker, II; +Cc: Chris Wright, xen-devel
[-- Attachment #1.1: Type: text/plain, Size: 1694 bytes --]
xense-devel-bounces@lists.xensource.com wrote on 09/01/2006 03:37:07 PM:
> > > set_bit(_DOMF_privileged, &dom0->domain_flags);
> > > /* post-create hooks sets security label */
> > > acm_post_domain0_create(dom0->domain_id);
> > > +
> > > + xsm_complete_init(dom0);
> >
> > Seems this should drop the acm hook here, no?
> >
>
> We did not want the XSM patch to add XSM and remove ACM because we do
> not believe that the community sees ACM and sHype as the distinct
> entities that they really are. That's why we have the patch that
> removes the duplicated hooks and code and produces a module called ACM.
> Hopefully in the future XSM will refer to the security framework and the
> the STE/Chinese Wall functionality of ACM will be called the sHype
> module.
>
XSM would effectively replace the small set of hooks that the sHype/ACM
module introduced with a more generic mediation framework. sHype would use
the XSM hook framework to control the same operations that it controls
now. The way users interact with sHype(XSM) (tools, policies, labeling,
...) would not be affected by XSM. Instead of being both hooks and
security module, sHype(XSM) would be a security module and XSM would offer
the hooks.
Ideally, XSM would be a standardized and generic Xen interface that offers
the possibility for researchers to easily experiment with proprietary
security modules. At the same time, it must have very low performance
overhead and be effective to support enterprise security on highly
utilized platforms.
It is very good for starting the discussions that George and team
succeeded to submit their code before the Xen Summit. Thank you!
Regards
Reiner
[-- Attachment #1.2: Type: text/html, Size: 2130 bytes --]
[-- Attachment #2: Type: text/plain, Size: 138 bytes --]
_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xensource.com
http://lists.xensource.com/xen-devel
^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [Xense-devel][RFC][PATCH][1/4] Xen Security Modules: XSM
2006-09-02 3:43 ` Reiner Sailer
@ 2006-09-05 16:25 ` John McDermott (U.S. Navy Employee)
2006-09-05 19:00 ` George S. Coker, II
0 siblings, 1 reply; 11+ messages in thread
From: John McDermott (U.S. Navy Employee) @ 2006-09-05 16:25 UTC (permalink / raw)
To: Reiner Sailer; +Cc: Chris Wright, xen-devel, xense-devel, George S. Coker, II
Reiner Sailer wrote:
> <snip>
> XSM would effectively replace the small set of hooks that the
> sHype/ACM module introduced with a more generic mediation framework.
> sHype would use the XSM hook framework to control the same operations
> that it controls now. The way users interact with sHype(XSM) (tools,
> policies, labeling, ...) would not be affected by XSM. Instead of
> being both hooks and security module, sHype(XSM) would be a security
> module and XSM would offer the hooks.
>
> Ideally, XSM would be a standardized and generic Xen interface that
> offers the possibility for researchers to easily experiment with
> proprietary security modules. At the same time, it must have very low
> performance overhead and be effective to support enterprise security
> on highly utilized platforms.
>
> It is very good for starting the discussions that George and team
> succeeded to submit their code before the Xen Summit. Thank you!
The XSM concept looks good for prototyping and research but any
security-related additions to Xen should be done in a way that does not
increase the _minimum_ size of the code base. A small code base is
essential for high assurance; having the flexibility of XSM is good but
it should be possible to build a Xen with something smaller than XSM. If
XSM or other security enhancements become too deeply associated with the
core of Xen then we loose the chance to build high-assurance Xen-based
products.
This is really an issue about what kind of security the hypervisor
should enforce and what should be enforced by trusted or untrusted (wrt
the hypervisor) mechanisms outside the hypervisor.
Sincerely,
John
--
J.P. McDermott building 12
Code 5542 mcdermott@itd.nrl.navy.mil
Naval Research Laboratory voice: +1 202.404.8301
Washington, DC 20375, USA fax: +1 202.404.7942
^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [Xense-devel][RFC][PATCH][1/4] Xen Security Modules: XSM
2006-09-05 16:25 ` John McDermott (U.S. Navy Employee)
@ 2006-09-05 19:00 ` George S. Coker, II
0 siblings, 0 replies; 11+ messages in thread
From: George S. Coker, II @ 2006-09-05 19:00 UTC (permalink / raw)
To: John.McDermott; +Cc: Chris Wright, xen-devel, xense-devel, Reiner Sailer
On Tue, 2006-09-05 at 12:25 -0400, John McDermott (U.S. Navy Employee)
wrote:
> The XSM concept looks good for prototyping and research but any
> security-related additions to Xen should be done in a way that does not
> increase the _minimum_ size of the code base. A small code base is
> essential for high assurance; having the flexibility of XSM is good but
> it should be possible to build a Xen with something smaller than XSM. If
> XSM or other security enhancements become too deeply associated with the
> core of Xen then we loose the chance to build high-assurance Xen-based
> products.
>
> This is really an issue about what kind of security the hypervisor
> should enforce and what should be enforced by trusted or untrusted (wrt
> the hypervisor) mechanisms outside the hypervisor.
I want to make a few points to clarify the value of XSM for Xen. I
think the value goes well beyond prototyping and research.
1) XSM itself is small. Do not confuse XSM with XSM and any particular
security module. XSM has actually made Xen smaller by encapsulating
existing security code into a module that is not part of Xen. XSM
without a module does not add security value to Xen. XSM can only
provide security value in the presence of a security module. In fact,
if you wish to have no security in Xen, XSM allows that too through the
selection of the dummy module.
2) Any arguments about Xen's size and assurance needs to include Xen
with a security module and what the security module is doing for Xen.
Discussion about particular security functionality can now be done in
the context of a particular module not Xen. This adds value because we
can now reason about what a particular security module is doing for Xen.
3) Analysis of Xen as a security kernel is only appropriate in the
context of a particular security model. Whether that model is
implemented in an XSM module or littered about Xen is immaterial.
One might argue that XSM now creates a well defined internal security
interface for Xen and makes it easier to reason about Xen as a security
kernel.
4) Security in user-space needs a secure foundation. XSM allows that to
be created on Xen with an appropriate choice of module. No one is
arguing that all security should be implemented as an XSM module. XSM
modules should only incorporate security functionality appropriate for
the hypervisor; the remainder should be implemented in user-space.
George
> Sincerely,
>
> John
>
^ permalink raw reply [flat|nested] 11+ messages in thread
end of thread, other threads:[~2006-09-05 19:00 UTC | newest]
Thread overview: 11+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2006-09-01 16:58 [Xense-devel][RFC][PATCH][1/4] Xen Security Modules: XSM George S. Coker, II
2006-09-01 18:35 ` James Morris
2006-09-01 18:47 ` George S. Coker, II
2006-09-01 18:55 ` Chris Wright
2006-09-01 19:00 ` Chris Wright
2006-09-01 19:39 ` George S. Coker, II
2006-09-01 19:37 ` George S. Coker, II
2006-09-02 3:43 ` Reiner Sailer
2006-09-05 16:25 ` John McDermott (U.S. Navy Employee)
2006-09-05 19:00 ` George S. Coker, II
2006-09-01 19:46 ` James Morris
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.