aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLeonardo Arena <rnalrd@alpinelinux.org>2018-03-12 10:55:24 +0000
committerLeonardo Arena <rnalrd@alpinelinux.org>2018-03-12 10:56:07 +0000
commit7a017e10fd6de2f5477c69120b540b2cd74652a1 (patch)
treea5f6be0bfe71b26f5926f652b443e1159d4b83d8
parent19539511a24c68d6a70c19ae7f30e6a11736caff (diff)
downloadaports-7a017e10fd6de2f5477c69120b540b2cd74652a1.tar.bz2
aports-7a017e10fd6de2f5477c69120b540b2cd74652a1.tar.xz
main/xen: security fixes
-rw-r--r--main/xen/APKBUILD14
-rw-r--r--main/xen/xsa252-4.9.patch25
-rw-r--r--main/xen/xsa255-4.9-1.patch126
-rw-r--r--main/xen/xsa255-4.9-2.patch186
-rw-r--r--main/xen/xsa256-4.8.patch46
5 files changed, 396 insertions, 1 deletions
diff --git a/main/xen/APKBUILD b/main/xen/APKBUILD
index 987dce584e..cf3165297b 100644
--- a/main/xen/APKBUILD
+++ b/main/xen/APKBUILD
@@ -3,7 +3,7 @@
# Maintainer: William Pitcock <nenolod@dereferenced.org>
pkgname=xen
pkgver=4.8.2
-pkgrel=5
+pkgrel=6
pkgdesc="Xen hypervisor"
url="http://www.xen.org/"
arch="x86_64 armhf"
@@ -104,6 +104,10 @@ options="!strip"
# - CVE-2017-17563 XSA-249
# - CVE-2017-17564 XSA-250
# - CVE-2017-17565 XSA-251
+# 4.8.2-r6:
+# - CVE-2018-7540 XSA-252
+# - CVE-2018-7541 XSA-255
+# - CVE-2018-7542 XSA-256
case "$CARCH" in
x86*)
@@ -193,6 +197,10 @@ source="https://downloads.xenproject.org/release/xen/$pkgver/xen-$pkgver.tar.gz
xsa249.patch
xsa250.patch
xsa251-4.8.patch
+ xsa252-4.9.patch
+ xsa255-4.9-1.patch
+ xsa255-4.9-2.patch
+ xsa256-4.8.patch
0001-x86-entry-Remove-support-for-partial-cpu_user_regs-f.patch
0002-x86-mm-Always-set-_PAGE_ACCESSED-on-L4e-updates.patch
@@ -469,6 +477,10 @@ b00f42d2069f273e204698177d2c36950cee759a92dfe7833c812ddff4dedde2c4a842980927ec4f
05a2e954bab1877500eb5ed3a8c49edb27411ed3ec9dbfb2115b7804a3b03c6d45c9f08a7ed96ff2b586346f321142065a8c5a5d996468496b373637b6ee31b9 xsa249.patch
b3030f09ddb4f9e4a356519c7b74d393e8db085278a1e616788c81d19988699a6efdd8568277c25514f3298ca92e5a09e3cd08b0a308a4d2ddb55374a8445657 xsa250.patch
22ac1c788e5c4c6b03e4d6c04ef97819fda4d5fb22015aa3a79d2f9a7dbac050f0b516401c0392c237576087306a810155a2dcdc6918d3de46f1ceb06b0b8a25 xsa251-4.8.patch
+993febe7ac7d4add0f36a519fe461a40d32f16e23003dfb23e76883ecdd86474cd4a6f9d0a9190cc6bc8cad19afa652556f125a5d5edb4fa2e9f2e6a5e77b2b9 xsa252-4.9.patch
+3af678f3c4271da2bb1515b9a1e76d9b85b391fbb1e9cd521c66ac52d2984a15c6c1bb6fa8a1f408380e4c7462b1ef671f77245fee6eecef274f93ca47bc12bd xsa255-4.9-1.patch
+22bf18c5e0120d787c9ec04d10dfb4684a0849c5d7a80cbe400f8f2ee2ee64789c9e6fe5bedab579ca4928f3168f7a5c0c817f93c73ad1cf7ce702a4afe732ab xsa255-4.9-2.patch
+82d75a5711c6a0521ecd34b220e4830b169aef8a52edf98b3b93e27ece734751d8d47dfdbe6979b6518c683e3f0c623cbf344a5efd893f3fafcc06c8e89a5320 xsa256-4.8.patch
c2b4a036bc9f0b43be40fb52e846bac2aa812f193acd2d58edb074b3a38b65dbb52a133150e574bd6e324fc4c93dc19ae5bafceeef44bd8c3610fd8a0b07072d 0001-x86-entry-Remove-support-for-partial-cpu_user_regs-f.patch
90746468ac83794e1e27fbf9bfb0d7f60ca0b85ceda0561f61f5ec328e2ea1428cc7ede7f1dca4e5a3398a7c27a46d6f9f0d2183c3b71e8ec1ac3ea2833a6a04 0002-x86-mm-Always-set-_PAGE_ACCESSED-on-L4e-updates.patch
287d03637f5ff35b0ec27af268a6f750be0341dd51d40266f17d4581eba9a285dafef65e5420c4f8a8e21ffce98057d8fe0bff1e7008d5df21defd7448c6fb37 0003-x86-Meltdown-band-aid-against-malicious-64-bit-PV-gu.patch
diff --git a/main/xen/xsa252-4.9.patch b/main/xen/xsa252-4.9.patch
new file mode 100644
index 0000000000..4afc22a6f1
--- /dev/null
+++ b/main/xen/xsa252-4.9.patch
@@ -0,0 +1,25 @@
+From: Jan Beulich <jbeulich@suse.com>
+Subject: memory: don't implicitly unpin for decrease-reservation
+
+It very likely was a mistake (copy-and-paste from domain cleanup code)
+to implicitly unpin here: The caller should really unpin itself before
+(or after, if they so wish) requesting the page to be removed.
+
+This is XSA-252.
+
+Reported-by: Jann Horn <jannh@google.com>
+Signed-off-by: Jan Beulich <jbeulich@suse.com>
+Reviewed-by: Andrew Cooper <andrew.cooper3@citrix.com>
+
+--- a/xen/common/memory.c
++++ b/xen/common/memory.c
+@@ -341,9 +341,6 @@ int guest_remove_page(struct domain *d,
+
+ rc = guest_physmap_remove_page(d, _gfn(gmfn), mfn, 0);
+
+- if ( !rc && test_and_clear_bit(_PGT_pinned, &page->u.inuse.type_info) )
+- put_page_and_type(page);
+-
+ /*
+ * With the lack of an IOMMU on some platforms, domains with DMA-capable
+ * device must retrieve the same pfn when the hypercall populate_physmap
diff --git a/main/xen/xsa255-4.9-1.patch b/main/xen/xsa255-4.9-1.patch
new file mode 100644
index 0000000000..0365adf750
--- /dev/null
+++ b/main/xen/xsa255-4.9-1.patch
@@ -0,0 +1,126 @@
+From: Jan Beulich <jbeulich@suse.com>
+Subject: gnttab/ARM: don't corrupt shared GFN array
+
+... by writing status GFNs to it. Introduce a second array instead.
+Also implement gnttab_status_gmfn() properly now that the information is
+suitably being tracked.
+
+While touching it anyway, remove a misguided (but luckily benign) upper
+bound check from gnttab_shared_gmfn(): We should never access beyond the
+bounds of that array.
+
+This is part of XSA-255.
+
+Signed-off-by: Jan Beulich <jbeulich@suse.com>
+Reviewed-by: Stefano Stabellini <sstabellini@kernel.org>
+Reviewed-by: Andrew Cooper <andrew.cooper3@citrix.com>
+
+--- a/xen/arch/arm/domain.c
++++ b/xen/arch/arm/domain.c
+@@ -461,19 +461,37 @@ void startup_cpu_idle_loop(void)
+ struct domain *alloc_domain_struct(void)
+ {
+ struct domain *d;
++ unsigned int i, max_status_frames;
++
+ BUILD_BUG_ON(sizeof(*d) > PAGE_SIZE);
+ d = alloc_xenheap_pages(0, 0);
+ if ( d == NULL )
+ return NULL;
+
+ clear_page(d);
+- d->arch.grant_table_gfn = xzalloc_array(gfn_t, max_grant_frames);
++
++ d->arch.grant_shared_gfn = xmalloc_array(gfn_t, max_grant_frames);
++ max_status_frames = grant_to_status_frames(max_grant_frames);
++ d->arch.grant_status_gfn = xmalloc_array(gfn_t, max_status_frames);
++ if ( !d->arch.grant_shared_gfn || !d->arch.grant_status_gfn )
++ {
++ free_domain_struct(d);
++ return NULL;
++ }
++
++ for ( i = 0; i < max_grant_frames; ++i )
++ d->arch.grant_shared_gfn[i] = INVALID_GFN;
++
++ for ( i = 0; i < max_status_frames; ++i )
++ d->arch.grant_status_gfn[i] = INVALID_GFN;
++
+ return d;
+ }
+
+ void free_domain_struct(struct domain *d)
+ {
+- xfree(d->arch.grant_table_gfn);
++ xfree(d->arch.grant_shared_gfn);
++ xfree(d->arch.grant_status_gfn);
+ free_xenheap_page(d);
+ }
+
+--- a/xen/arch/arm/mm.c
++++ b/xen/arch/arm/mm.c
+@@ -1148,6 +1148,7 @@ int xenmem_add_to_physmap_one(
+ int rc;
+ p2m_type_t t;
+ struct page_info *page = NULL;
++ bool status = false;
+
+ switch ( space )
+ {
+@@ -1165,6 +1166,7 @@ int xenmem_add_to_physmap_one(
+ mfn = virt_to_mfn(d->grant_table->status[idx]);
+ else
+ mfn = mfn_x(INVALID_MFN);
++ status = true;
+ }
+ else
+ {
+@@ -1180,7 +1182,10 @@ int xenmem_add_to_physmap_one(
+
+ if ( mfn != mfn_x(INVALID_MFN) )
+ {
+- d->arch.grant_table_gfn[idx] = gfn;
++ if ( status )
++ d->arch.grant_status_gfn[idx] = gfn;
++ else
++ d->arch.grant_shared_gfn[idx] = gfn;
+
+ t = p2m_ram_rw;
+ }
+--- a/xen/include/asm-arm/domain.h
++++ b/xen/include/asm-arm/domain.h
+@@ -50,7 +50,8 @@ struct arch_domain
+ struct p2m_domain p2m;
+
+ struct hvm_domain hvm_domain;
+- gfn_t *grant_table_gfn;
++ gfn_t *grant_shared_gfn;
++ gfn_t *grant_status_gfn;
+
+ struct vmmio vmmio;
+
+--- a/xen/include/asm-arm/grant_table.h
++++ b/xen/include/asm-arm/grant_table.h
+@@ -14,7 +14,6 @@ int replace_grant_host_mapping(unsigned
+ unsigned long new_gpaddr, unsigned int flags);
+ void gnttab_mark_dirty(struct domain *d, unsigned long l);
+ #define gnttab_create_status_page(d, t, i) do {} while (0)
+-#define gnttab_status_gmfn(d, t, i) (0)
+ #define gnttab_release_host_mappings(domain) 1
+ static inline int replace_grant_supported(void)
+ {
+@@ -29,8 +28,12 @@ static inline int replace_grant_supporte
+ } while ( 0 )
+
+ #define gnttab_shared_gmfn(d, t, i) \
+- ( ((i >= nr_grant_frames(d->grant_table)) && \
+- (i < max_grant_frames)) ? 0 : gfn_x(d->arch.grant_table_gfn[i]))
++ gfn_x(((i) >= nr_grant_frames(t)) ? INVALID_GFN \
++ : (d)->arch.grant_shared_gfn[i])
++
++#define gnttab_status_gmfn(d, t, i) \
++ gfn_x(((i) >= nr_status_frames(t)) ? INVALID_GFN \
++ : (d)->arch.grant_status_gfn[i])
+
+ #define gnttab_need_iommu_mapping(d) \
+ (is_domain_direct_mapped(d) && need_iommu(d))
diff --git a/main/xen/xsa255-4.9-2.patch b/main/xen/xsa255-4.9-2.patch
new file mode 100644
index 0000000000..ce225bde28
--- /dev/null
+++ b/main/xen/xsa255-4.9-2.patch
@@ -0,0 +1,186 @@
+From: Jan Beulich <jbeulich@suse.com>
+Subject: gnttab: don't blindly free status pages upon version change
+
+There may still be active mappings, which would trigger the respective
+BUG_ON(). Split the loop into one dealing with the page attributes and
+the second (when the first fully passed) freeing the pages. Return an
+error if any pages still have pending references.
+
+This is part of XSA-255.
+
+Signed-off-by: Jan Beulich <jbeulich@suse.com>
+Reviewed-by: Stefano Stabellini <sstabellini@kernel.org>
+Reviewed-by: Andrew Cooper <andrew.cooper3@citrix.com>
+
+--- a/xen/arch/arm/mm.c
++++ b/xen/arch/arm/mm.c
+@@ -1180,12 +1180,22 @@ int xenmem_add_to_physmap_one(
+ mfn = mfn_x(INVALID_MFN);
+ }
+
++ if ( mfn != mfn_x(INVALID_MFN) &&
++ !gfn_eq(gnttab_get_frame_gfn(d, status, idx), INVALID_GFN) )
++ {
++ rc = guest_physmap_remove_page(d,
++ gnttab_get_frame_gfn(d, status, idx),
++ _mfn(mfn), 0);
++ if ( rc )
++ {
++ grant_write_unlock(d->grant_table);
++ return rc;
++ }
++ }
++
+ if ( mfn != mfn_x(INVALID_MFN) )
+ {
+- if ( status )
+- d->arch.grant_status_gfn[idx] = gfn;
+- else
+- d->arch.grant_shared_gfn[idx] = gfn;
++ gnttab_set_frame_gfn(d, status, idx, gfn);
+
+ t = p2m_ram_rw;
+ }
+--- a/xen/common/grant_table.c
++++ b/xen/common/grant_table.c
+@@ -1516,23 +1516,74 @@ status_alloc_failed:
+ return -ENOMEM;
+ }
+
+-static void
++static int
+ gnttab_unpopulate_status_frames(struct domain *d, struct grant_table *gt)
+ {
+- int i;
++ unsigned int i;
+
+ for ( i = 0; i < nr_status_frames(gt); i++ )
+ {
+ struct page_info *pg = virt_to_page(gt->status[i]);
++ gfn_t gfn = gnttab_get_frame_gfn(d, true, i);
++
++ /*
++ * For translated domains, recovering from failure after partial
++ * changes were made is more complicated than it seems worth
++ * implementing at this time. Hence respective error paths below
++ * crash the domain in such a case.
++ */
++ if ( paging_mode_translate(d) )
++ {
++ int rc = gfn_eq(gfn, INVALID_GFN)
++ ? 0
++ : guest_physmap_remove_page(d, gfn,
++ _mfn(page_to_mfn(pg)), 0);
++
++ if ( rc )
++ {
++ gprintk(XENLOG_ERR,
++ "Could not remove status frame %u (GFN %#lx) from P2M\n",
++ i, gfn_x(gfn));
++ domain_crash(d);
++ return rc;
++ }
++ gnttab_set_frame_gfn(d, true, i, INVALID_GFN);
++ }
+
+ BUG_ON(page_get_owner(pg) != d);
+ if ( test_and_clear_bit(_PGC_allocated, &pg->count_info) )
+ put_page(pg);
+- BUG_ON(pg->count_info & ~PGC_xen_heap);
++
++ if ( pg->count_info & ~PGC_xen_heap )
++ {
++ if ( paging_mode_translate(d) )
++ {
++ gprintk(XENLOG_ERR,
++ "Wrong page state %#lx of status frame %u (GFN %#lx)\n",
++ pg->count_info, i, gfn_x(gfn));
++ domain_crash(d);
++ }
++ else
++ {
++ if ( get_page(pg, d) )
++ set_bit(_PGC_allocated, &pg->count_info);
++ while ( i-- )
++ gnttab_create_status_page(d, gt, i);
++ }
++ return -EBUSY;
++ }
++
++ page_set_owner(pg, NULL);
++ }
++
++ for ( i = 0; i < nr_status_frames(gt); i++ )
++ {
+ free_xenheap_page(gt->status[i]);
+ gt->status[i] = NULL;
+ }
+ gt->nr_status_frames = 0;
++
++ return 0;
+ }
+
+ /*
+@@ -2774,8 +2825,9 @@ gnttab_set_version(XEN_GUEST_HANDLE_PARA
+ break;
+ }
+
+- if ( op.version < 2 && gt->gt_version == 2 )
+- gnttab_unpopulate_status_frames(currd, gt);
++ if ( op.version < 2 && gt->gt_version == 2 &&
++ (res = gnttab_unpopulate_status_frames(currd, gt)) != 0 )
++ goto out_unlock;
+
+ /* Make sure there's no crud left over from the old version. */
+ for ( i = 0; i < nr_grant_frames(gt); i++ )
+--- a/xen/include/asm-arm/grant_table.h
++++ b/xen/include/asm-arm/grant_table.h
+@@ -20,6 +20,17 @@ static inline int replace_grant_supporte
+ return 1;
+ }
+
++#define gnttab_set_frame_gfn(d, st, idx, gfn) \
++ do { \
++ ((st) ? (d)->arch.grant_status_gfn \
++ : (d)->arch.grant_shared_gfn)[idx] = (gfn); \
++ } while ( 0 )
++
++#define gnttab_get_frame_gfn(d, st, idx) ({ \
++ _gfn((st) ? gnttab_status_gmfn(d, (d)->grant_table, idx) \
++ : gnttab_shared_gmfn(d, (d)->grant_table, idx)); \
++})
++
+ #define gnttab_create_shared_page(d, t, i) \
+ do { \
+ share_xen_page_with_guest( \
+--- a/xen/include/asm-x86/grant_table.h
++++ b/xen/include/asm-x86/grant_table.h
+@@ -18,6 +18,14 @@ int create_grant_host_mapping(uint64_t a
+ int replace_grant_host_mapping(
+ uint64_t addr, unsigned long frame, uint64_t new_addr, unsigned int flags);
+
++#define gnttab_set_frame_gfn(d, st, idx, gfn) do {} while ( 0 )
++#define gnttab_get_frame_gfn(d, st, idx) ({ \
++ unsigned long mfn_ = (st) ? gnttab_status_mfn((d)->grant_table, idx) \
++ : gnttab_shared_mfn((d)->grant_table, idx); \
++ unsigned long gpfn_ = get_gpfn_from_mfn(mfn_); \
++ VALID_M2P(gpfn_) ? _gfn(gpfn_) : INVALID_GFN; \
++})
++
+ #define gnttab_create_shared_page(d, t, i) \
+ do { \
+ share_xen_page_with_guest( \
+@@ -33,11 +41,11 @@ int replace_grant_host_mapping(
+ } while ( 0 )
+
+
+-#define gnttab_shared_mfn(d, t, i) \
++#define gnttab_shared_mfn(t, i) \
+ ((virt_to_maddr((t)->shared_raw[i]) >> PAGE_SHIFT))
+
+ #define gnttab_shared_gmfn(d, t, i) \
+- (mfn_to_gmfn(d, gnttab_shared_mfn(d, t, i)))
++ (mfn_to_gmfn(d, gnttab_shared_mfn(t, i)))
+
+
+ #define gnttab_status_mfn(t, i) \
diff --git a/main/xen/xsa256-4.8.patch b/main/xen/xsa256-4.8.patch
new file mode 100644
index 0000000000..019e6e6b97
--- /dev/null
+++ b/main/xen/xsa256-4.8.patch
@@ -0,0 +1,46 @@
+From: Andrew Cooper <andrew.cooper3@citrix.com>
+Subject: x86/hvm: Disallow the creation of HVM domains without Local APIC emulation
+
+There are multiple problems, not necesserily limited to:
+
+ * Guests which configure event channels via hvmop_set_evtchn_upcall_vector(),
+ or which hit %cr8 emulation will cause Xen to fall over a NULL vlapic->regs
+ pointer.
+
+ * On Intel hardware, disabling the TPR_SHADOW execution control without
+ reenabling CR8_{LOAD,STORE} interception means that the guests %cr8
+ accesses interact with the real TPR. Amongst other things, setting the
+ real TPR to 0xf blocks even IPIs from interrupting this CPU.
+
+ * On hardware which sets up the use of Interrupt Posting, including
+ IOMMU-Posting, guests run without the appropriate non-root configuration,
+ which at a minimum will result in dropped interrupts.
+
+Whether no-LAPIC mode is of any use at all remains to be seen.
+
+This is XSA-256.
+
+Reported-by: Ian Jackson <ian.jackson@eu.citrix.com>
+Reviewed-by: Roger Pau Monné <roger.pau@citrix.com>
+Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
+Reviewed-by: Jan Beulich <jbeulich@suse.com>
+
+diff --git a/xen/arch/x86/domain.c b/xen/arch/x86/domain.c
+index 8817263..91b9ab7 100644
+--- a/xen/arch/x86/domain.c
++++ b/xen/arch/x86/domain.c
+@@ -557,11 +557,9 @@ int arch_domain_create(struct domain *d, unsigned int domcr_flags,
+ return -EINVAL;
+ }
+
+- /* PVHv2 guests can request emulated APIC. */
+- if ( emflags &&
+- (is_hvm_domain(d) ? ((emflags != XEN_X86_EMU_ALL) &&
+- (emflags != XEN_X86_EMU_LAPIC)) :
+- (emflags != XEN_X86_EMU_PIT)) )
++ if ( is_hvm_domain(d) ? ((emflags != XEN_X86_EMU_ALL) &&
++ (emflags != XEN_X86_EMU_LAPIC))
++ : (emflags && emflags != XEN_X86_EMU_PIT) )
+ {
+ printk(XENLOG_G_ERR "d%d: Xen does not allow %s domain creation "
+ "with the current selection of emulators: %#x\n",