aboutsummaryrefslogtreecommitdiffstats
path: root/xen/arch/x86/domctl.c
diff options
context:
space:
mode:
authorDaniel De Graaf <dgdegra@tycho.nsa.gov>2012-08-22 22:14:52 +0100
committerDaniel De Graaf <dgdegra@tycho.nsa.gov>2012-08-22 22:14:52 +0100
commitc14bb38304d348b2b39160947b772442a15d03fc (patch)
treefebba903031e096ae42563e51aaa1baef398a788 /xen/arch/x86/domctl.c
parent00e23f230212638718b6ff9214b829a663707a76 (diff)
downloadxen-c14bb38304d348b2b39160947b772442a15d03fc.tar.gz
xen-c14bb38304d348b2b39160947b772442a15d03fc.tar.bz2
xen-c14bb38304d348b2b39160947b772442a15d03fc.zip
xsm/flask: remove page-to-domain lookups from XSM hooks
Doing a reverse lookup from MFN to its owning domain is redundant with the internal checks Xen does on pages. Change the checks to operate directly on the domain owning the pages for normal memory; MMIO areas are still checked with security_iomem_sid. This fixes a hypervisor crash when a domU attempts to map an MFN that is free in Xen's heap: the XSM hook is called before the validity check, and page_get_owner returns garbage when called on these pages. While explicitly checking for such pages using page_get_owner_and_reference is a possible solution, this ends up duplicating parts of get_page_from_l1e. Signed-off-by: Daniel De Graaf <dgdegra@tycho.nsa.gov> Committed-by: Keir Fraser <keir@xen.org>
Diffstat (limited to 'xen/arch/x86/domctl.c')
-rw-r--r--xen/arch/x86/domctl.c23
1 files changed, 15 insertions, 8 deletions
diff --git a/xen/arch/x86/domctl.c b/xen/arch/x86/domctl.c
index 135ea6eca0..97a13fba99 100644
--- a/xen/arch/x86/domctl.c
+++ b/xen/arch/x86/domctl.c
@@ -114,7 +114,7 @@ long arch_do_domctl(
page = mfn_to_page(mfn);
- ret = xsm_getpageframeinfo(page);
+ ret = xsm_getpageframeinfo(d);
if ( ret )
{
rcu_unlock_domain(d);
@@ -170,6 +170,13 @@ long arch_do_domctl(
if ( unlikely((d = rcu_lock_domain_by_id(dom)) == NULL) )
break;
+ ret = xsm_getpageframeinfo(d);
+ if ( ret )
+ {
+ rcu_unlock_domain(d);
+ break;
+ }
+
if ( unlikely(num > 1024) ||
unlikely(num != domctl->u.getpageframeinfo3.num) )
{
@@ -209,8 +216,6 @@ long arch_do_domctl(
if ( unlikely(!page) ||
unlikely(is_xen_heap_page(page)) )
type = XEN_DOMCTL_PFINFO_XTAB;
- else if ( xsm_getpageframeinfo(page) != 0 )
- ;
else
{
switch( page->u.inuse.type_info & PGT_type_mask )
@@ -267,6 +272,13 @@ long arch_do_domctl(
if ( unlikely((d = rcu_lock_domain_by_id(dom)) == NULL) )
break;
+ ret = xsm_getpageframeinfo(d);
+ if ( ret )
+ {
+ rcu_unlock_domain(d);
+ break;
+ }
+
if ( unlikely(num > 1024) )
{
ret = -E2BIG;
@@ -310,11 +322,6 @@ long arch_do_domctl(
if ( unlikely(!page) ||
unlikely(is_xen_heap_page(page)) )
arr32[j] |= XEN_DOMCTL_PFINFO_XTAB;
- else if ( xsm_getpageframeinfo(page) != 0 )
- {
- put_page(page);
- continue;
- }
else
{
unsigned long type = 0;