All of lore.kernel.org
 help / color / mirror / Atom feed
From: Andrew Cooper <andrew.cooper3@citrix.com>
To: Xen-devel <xen-devel@lists.xenproject.org>
Cc: "Andrew Cooper" <andrew.cooper3@citrix.com>,
	"Jan Beulich" <JBeulich@suse.com>,
	"Roger Pau Monné" <roger.pau@citrix.com>, "Wei Liu" <wl@xen.org>,
	"Stefano Stabellini" <sstabellini@kernel.org>,
	"Julien Grall" <julien@xen.org>,
	"Volodymyr Babchuk" <Volodymyr_Babchuk@epam.com>,
	"Paul Durrant" <paul@xen.org>,
	"Oleksandr Tyshchenko" <oleksandr_tyshchenko@epam.com>
Subject: [PATCH] xen/memory: Reject out-of-range resource 'frame' values
Date: Thu, 28 Jan 2021 16:06:16 +0000	[thread overview]
Message-ID: <20210128160616.17608-1-andrew.cooper3@citrix.com> (raw)

The ABI is unfortunate, and frame being 64 bits leads to all kinds of problems
performing correct overflow checks.

Furthermore, the mixed use of unsigned int and unsigned long in the call tree
is buggy on arm32 where the two are the same size, and certain out-of-range
combinations will truncated and be permitted.

Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
---
CC: Jan Beulich <JBeulich@suse.com>
CC: Roger Pau Monné <roger.pau@citrix.com>
CC: Wei Liu <wl@xen.org>
CC: Stefano Stabellini <sstabellini@kernel.org>
CC: Julien Grall <julien@xen.org>
CC: Volodymyr Babchuk <Volodymyr_Babchuk@epam.com>
CC: Paul Durrant <paul@xen.org>
CC: Oleksandr Tyshchenko <oleksandr_tyshchenko@epam.com>

Posted ahead of my full v8 series, in the hope that it catches some people
before the end of the day.
---
 xen/arch/x86/mm.c        |  2 +-
 xen/common/memory.c      | 15 ++++++++++++++-
 xen/include/asm-x86/mm.h |  2 +-
 xen/include/xen/mm.h     |  2 +-
 4 files changed, 17 insertions(+), 4 deletions(-)

diff --git a/xen/arch/x86/mm.c b/xen/arch/x86/mm.c
index 63e9fae919..2ce00a8ece 100644
--- a/xen/arch/x86/mm.c
+++ b/xen/arch/x86/mm.c
@@ -4588,7 +4588,7 @@ static int handle_iomem_range(unsigned long s, unsigned long e, void *p)
 }
 
 int arch_acquire_resource(struct domain *d, unsigned int type,
-                          unsigned int id, unsigned long frame,
+                          unsigned int id, unsigned int frame,
                           unsigned int nr_frames, xen_pfn_t mfn_list[])
 {
     int rc;
diff --git a/xen/common/memory.c b/xen/common/memory.c
index ccb4d49fc6..33ab36eb72 100644
--- a/xen/common/memory.c
+++ b/xen/common/memory.c
@@ -1054,7 +1054,7 @@ static long xatp_permission_check(struct domain *d, unsigned int space)
 }
 
 static int acquire_grant_table(struct domain *d, unsigned int id,
-                               unsigned long frame,
+                               unsigned int frame,
                                unsigned int nr_frames,
                                xen_pfn_t mfn_list[])
 {
@@ -1134,6 +1134,19 @@ static int acquire_resource(
     if ( xmar.nr_frames > ARRAY_SIZE(mfn_list) )
         return -E2BIG;
 
+    /*
+     * The ABI is rather unfortunate.  nr_frames (and therefore the total size
+     * of the resource) is 32bit, while frame (the offset within the resource
+     * we'd like to start at) is 64bit.
+     *
+     * Reject values oustide the of the range of nr_frames, as well as
+     * combinations of frame and nr_frame which overflow, to simplify the rest
+     * of the logic.
+     */
+    if ( (xmar.frame >> 32) ||
+         ((xmar.frame + xmar.nr_frames) >> 32) )
+        return -EINVAL;
+
     rc = rcu_lock_remote_domain_by_id(xmar.domid, &d);
     if ( rc )
         return rc;
diff --git a/xen/include/asm-x86/mm.h b/xen/include/asm-x86/mm.h
index 1fdb4eb835..3fe47dcd8d 100644
--- a/xen/include/asm-x86/mm.h
+++ b/xen/include/asm-x86/mm.h
@@ -641,7 +641,7 @@ static inline bool arch_mfn_in_directmap(unsigned long mfn)
 }
 
 int arch_acquire_resource(struct domain *d, unsigned int type,
-                          unsigned int id, unsigned long frame,
+                          unsigned int id, unsigned int frame,
                           unsigned int nr_frames, xen_pfn_t mfn_list[]);
 
 #endif /* __ASM_X86_MM_H__ */
diff --git a/xen/include/xen/mm.h b/xen/include/xen/mm.h
index 636a1254ae..66a4d10695 100644
--- a/xen/include/xen/mm.h
+++ b/xen/include/xen/mm.h
@@ -614,7 +614,7 @@ static inline void put_page_alloc_ref(struct page_info *page)
 
 #ifndef CONFIG_ARCH_ACQUIRE_RESOURCE
 static inline int arch_acquire_resource(
-    struct domain *d, unsigned int type, unsigned int id, unsigned long frame,
+    struct domain *d, unsigned int type, unsigned int id, unsigned int frame,
     unsigned int nr_frames, xen_pfn_t mfn_list[])
 {
     return -EOPNOTSUPP;
-- 
2.11.0



             reply	other threads:[~2021-01-28 16:07 UTC|newest]

Thread overview: 10+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2021-01-28 16:06 Andrew Cooper [this message]
2021-01-28 17:13 ` [PATCH] xen/memory: Reject out-of-range resource 'frame' values Paul Durrant
2021-01-29  9:15 ` Jan Beulich
2021-01-29  9:32   ` Andrew Cooper
2021-01-29  9:40     ` Jan Beulich
2021-01-29  9:47       ` Andrew Cooper
2021-01-29 10:01         ` Jan Beulich
2021-01-29 10:04           ` Andrew Cooper
2021-01-29 10:09             ` Jan Beulich
2021-01-29 11:43 ` Julien Grall

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20210128160616.17608-1-andrew.cooper3@citrix.com \
    --to=andrew.cooper3@citrix.com \
    --cc=JBeulich@suse.com \
    --cc=Volodymyr_Babchuk@epam.com \
    --cc=julien@xen.org \
    --cc=oleksandr_tyshchenko@epam.com \
    --cc=paul@xen.org \
    --cc=roger.pau@citrix.com \
    --cc=sstabellini@kernel.org \
    --cc=wl@xen.org \
    --cc=xen-devel@lists.xenproject.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
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.