- bnc#797285 - VUL-0: Xen: XSA-34 (CVE-2013-0151) - nested

virtualization on 32-bit exposes host crash
  CVE-2013-0151-xsa34.patch
- bnc#797287 - VUL-0: Xen: XSA-35 (CVE-2013-0152) - Nested HVM
  exposes host to being driven out of memory by guest
  CVE-2013-0152-xsa35.patch

- bnc#793717 - NetWare will not boot on Xen 4.2 
  xnloader.py
  domUloader.py
  pygrub-netware-xnloader.patch
  Removed reverse-24757-use-grant-references.patch

- bnc#797523 - VUL-1: CVE-2012-6075: qemu / kvm-qemu: e1000
  overflows under some conditions
  CVE-2012-6075-xsa41.patch

- Mask the floating point exceptions for guests like NetWare on
  machines that support XSAVE.
  x86-fpu-context-conditional.patch 

- fate##313584: pass bios information to XEN HVM guest 
  26341-hvm-firmware-passthrough.patch
  26342-hvm-firmware-passthrough.patch
  26343-hvm-firmware-passthrough.patch
  26344-hvm-firmware-passthrough.patch

OBS-URL: https://build.opensuse.org/package/show/Virtualization/xen?expand=0&rev=223
This commit is contained in:
Charles Arnold 2013-01-22 15:40:06 +00:00 committed by Git OBS Bridge
parent b48642e0b8
commit 598a3740c6
14 changed files with 1429 additions and 150 deletions

View File

@ -0,0 +1,99 @@
fate#313584: pass bios information to XEN HVM guest
# HG changeset patch
# User Ross Philipson <ross.philipson@citrix.com>
# Date 1357838188 0
# Node ID 07bf59a7ce837bd795e2df2f28166cfe41990d3d
# Parent 19fd1237ff0dfa3d97a896d6ed6fbbd33f816a9f
HVM xenstore strings and firmware passthrough header
Add public HVM definitions header for xenstore strings used in
HVMLOADER. In addition this header describes the use of the firmware
passthrough values set using xenstore.
Signed-off-by: Ross Philipson <ross.philipson@citrix.com>
Committed-by: Keir Fraser <keir@xen.org>
diff -r 19fd1237ff0d -r 07bf59a7ce83 xen/include/public/hvm/hvm_xs_strings.h
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/xen/include/public/hvm/hvm_xs_strings.h Thu Jan 10 17:16:28 2013 +0000
@@ -0,0 +1,79 @@
+/******************************************************************************
+ * hvm/hvm_xs_strings.h
+ *
+ * HVM xenstore strings used in HVMLOADER.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to
+ * deal in the Software without restriction, including without limitation the
+ * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+ * sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef __XEN_PUBLIC_HVM_HVM_XS_STRINGS_H__
+#define __XEN_PUBLIC_HVM_HVM_XS_STRINGS_H__
+
+#define HVM_XS_HVMLOADER "hvmloader"
+#define HVM_XS_BIOS "hvmloader/bios"
+#define HVM_XS_GENERATION_ID_ADDRESS "hvmloader/generation-id-address"
+
+/* The following values allow additional ACPI tables to be added to the
+ * virtual ACPI BIOS that hvmloader constructs. The values specify the guest
+ * physical address and length of a block of ACPI tables to add. The format of
+ * the block is simply concatenated raw tables (which specify their own length
+ * in the ACPI header).
+ */
+#define HVM_XS_ACPI_PT_ADDRESS "hvmloader/acpi/address"
+#define HVM_XS_ACPI_PT_LENGTH "hvmloader/acpi/length"
+
+/* Any number of SMBIOS types can be passed through to an HVM guest using
+ * the following xenstore values. The values specify the guest physical
+ * address and length of a block of SMBIOS structures for hvmloader to use.
+ * The block is formatted in the following way:
+ *
+ * <length><struct><length><struct>...
+ *
+ * Each length separator is a 32b integer indicating the length of the next
+ * SMBIOS structure. For DMTF defined types (0 - 121), the passed in struct
+ * will replace the default structure in hvmloader. In addition, any
+ * OEM/vendortypes (128 - 255) will all be added.
+ */
+#define HVM_XS_SMBIOS_PT_ADDRESS "hvmloader/smbios/address"
+#define HVM_XS_SMBIOS_PT_LENGTH "hvmloader/smbios/length"
+
+/* Set to 1 to enable SMBIOS default portable battery (type 22) values. */
+#define HVM_XS_SMBIOS_DEFAULT_BATTERY "hvmloader/smbios/default_battery"
+
+/* The following xenstore values are used to override some of the default
+ * string values in the SMBIOS table constructed in hvmloader.
+ */
+#define HVM_XS_BIOS_STRINGS "bios-strings"
+#define HVM_XS_BIOS_VENDOR "bios-strings/bios-vendor"
+#define HVM_XS_BIOS_VERSION "bios-strings/bios-version"
+#define HVM_XS_SYSTEM_MANUFACTURER "bios-strings/system-manufacturer"
+#define HVM_XS_SYSTEM_PRODUCT_NAME "bios-strings/system-product-name"
+#define HVM_XS_SYSTEM_VERSION "bios-strings/system-version"
+#define HVM_XS_SYSTEM_SERIAL_NUMBER "bios-strings/system-serial-number"
+#define HVM_XS_ENCLOSURE_MANUFACTURER "bios-strings/enclosure-manufacturer"
+#define HVM_XS_ENCLOSURE_SERIAL_NUMBER "bios-strings/enclosure-serial-number"
+#define HVM_XS_BATTERY_MANUFACTURER "bios-strings/battery-manufacturer"
+#define HVM_XS_BATTERY_DEVICE_NAME "bios-strings/battery-device-name"
+
+/* 1 to 99 OEM strings can be set in xenstore using values of the form
+ * below. These strings will be loaded into the SMBIOS type 11 structure.
+ */
+#define HVM_XS_OEM_STRINGS "bios-strings/oem-%02d"
+
+#endif /* __XEN_PUBLIC_HVM_HVM_XS_STRINGS_H__ */

View File

@ -0,0 +1,282 @@
fate#313584: pass bios information to XEN HVM guest
# HG changeset patch
# User Ross Philipson <ross.philipson@citrix.com>
# Date 1357838241 0
# Node ID cabf395a6c849cc65e56f1640b18db0c3e0faf5d
# Parent 07bf59a7ce837bd795e2df2f28166cfe41990d3d
HVM firmware passthrough control tools support
Xen control tools support for loading the firmware passthrough blocks
during domain construction. SMBIOS and ACPI blocks are passed in using
the new xc_hvm_build_args structure. Each block is read and loaded
into the new domain address space behind the HVMLOADER image. The base
address for the two blocks is returned as an out parameter to the
caller via the args structure.
Signed-off-by: Ross Philipson <ross.philipson@citrix.com>
Committed-by: Keir Fraser <keir@xen.org>
diff -r 07bf59a7ce83 -r cabf395a6c84 tools/libxc/xc_hvm_build_arm.c
--- a/tools/libxc/xc_hvm_build_arm.c Thu Jan 10 17:16:28 2013 +0000
+++ b/tools/libxc/xc_hvm_build_arm.c Thu Jan 10 17:17:21 2013 +0000
@@ -22,7 +22,7 @@
#include <xenguest.h>
int xc_hvm_build(xc_interface *xch, uint32_t domid,
- const struct xc_hvm_build_args *hvm_args)
+ struct xc_hvm_build_args *hvm_args)
{
errno = ENOSYS;
return -1;
diff -r 07bf59a7ce83 -r cabf395a6c84 tools/libxc/xc_hvm_build_x86.c
--- a/tools/libxc/xc_hvm_build_x86.c Thu Jan 10 17:16:28 2013 +0000
+++ b/tools/libxc/xc_hvm_build_x86.c Thu Jan 10 17:17:21 2013 +0000
@@ -49,6 +49,40 @@
#define NR_SPECIAL_PAGES 8
#define special_pfn(x) (0xff000u - NR_SPECIAL_PAGES + (x))
+static int modules_init(struct xc_hvm_build_args *args,
+ uint64_t vend, struct elf_binary *elf,
+ uint64_t *mstart_out, uint64_t *mend_out)
+{
+#define MODULE_ALIGN 1UL << 7
+#define MB_ALIGN 1UL << 20
+#define MKALIGN(x, a) (((uint64_t)(x) + (a) - 1) & ~(uint64_t)((a) - 1))
+ uint64_t total_len = 0, offset1 = 0;
+
+ if ( (args->acpi_module.length == 0)&&(args->smbios_module.length == 0) )
+ return 0;
+
+ /* Find the total length for the firmware modules with a reasonable large
+ * alignment size to align each the modules.
+ */
+ total_len = MKALIGN(args->acpi_module.length, MODULE_ALIGN);
+ offset1 = total_len;
+ total_len += MKALIGN(args->smbios_module.length, MODULE_ALIGN);
+
+ /* Want to place the modules 1Mb+change behind the loader image. */
+ *mstart_out = MKALIGN(elf->pend, MB_ALIGN) + (MB_ALIGN);
+ *mend_out = *mstart_out + total_len;
+
+ if ( *mend_out > vend )
+ return -1;
+
+ if ( args->acpi_module.length != 0 )
+ args->acpi_module.guest_addr_out = *mstart_out;
+ if ( args->smbios_module.length != 0 )
+ args->smbios_module.guest_addr_out = *mstart_out + offset1;
+
+ return 0;
+}
+
static void build_hvm_info(void *hvm_info_page, uint64_t mem_size,
uint64_t mmio_start, uint64_t mmio_size)
{
@@ -86,9 +120,8 @@ static void build_hvm_info(void *hvm_inf
hvm_info->checksum = -sum;
}
-static int loadelfimage(
- xc_interface *xch,
- struct elf_binary *elf, uint32_t dom, unsigned long *parray)
+static int loadelfimage(xc_interface *xch, struct elf_binary *elf,
+ uint32_t dom, unsigned long *parray)
{
privcmd_mmap_entry_t *entries = NULL;
unsigned long pfn_start = elf->pstart >> PAGE_SHIFT;
@@ -126,6 +159,66 @@ static int loadelfimage(
return rc;
}
+static int loadmodules(xc_interface *xch,
+ struct xc_hvm_build_args *args,
+ uint64_t mstart, uint64_t mend,
+ uint32_t dom, unsigned long *parray)
+{
+ privcmd_mmap_entry_t *entries = NULL;
+ unsigned long pfn_start;
+ unsigned long pfn_end;
+ size_t pages;
+ uint32_t i;
+ uint8_t *dest;
+ int rc = -1;
+
+ if ( (mstart == 0)||(mend == 0) )
+ return 0;
+
+ pfn_start = (unsigned long)(mstart >> PAGE_SHIFT);
+ pfn_end = (unsigned long)((mend + PAGE_SIZE - 1) >> PAGE_SHIFT);
+ pages = pfn_end - pfn_start;
+
+ /* Map address space for module list. */
+ entries = calloc(pages, sizeof(privcmd_mmap_entry_t));
+ if ( entries == NULL )
+ goto error_out;
+
+ for ( i = 0; i < pages; i++ )
+ entries[i].mfn = parray[(mstart >> PAGE_SHIFT) + i];
+
+ dest = xc_map_foreign_ranges(
+ xch, dom, pages << PAGE_SHIFT, PROT_READ | PROT_WRITE, 1 << PAGE_SHIFT,
+ entries, pages);
+ if ( dest == NULL )
+ goto error_out;
+
+ /* Zero the range so padding is clear between modules */
+ memset(dest, 0, pages << PAGE_SHIFT);
+
+ /* Load modules into range */
+ if ( args->acpi_module.length != 0 )
+ {
+ memcpy(dest,
+ args->acpi_module.data,
+ args->acpi_module.length);
+ }
+ if ( args->smbios_module.length != 0 )
+ {
+ memcpy(dest + (args->smbios_module.guest_addr_out - mstart),
+ args->smbios_module.data,
+ args->smbios_module.length);
+ }
+
+ munmap(dest, pages << PAGE_SHIFT);
+ rc = 0;
+
+ error_out:
+ free(entries);
+
+ return rc;
+}
+
/*
* Check whether there exists mmio hole in the specified memory range.
* Returns 1 if exists, else returns 0.
@@ -140,7 +233,7 @@ static int check_mmio_hole(uint64_t star
}
static int setup_guest(xc_interface *xch,
- uint32_t dom, const struct xc_hvm_build_args *args,
+ uint32_t dom, struct xc_hvm_build_args *args,
char *image, unsigned long image_size)
{
xen_pfn_t *page_array = NULL;
@@ -153,6 +246,7 @@ static int setup_guest(xc_interface *xch
uint32_t *ident_pt;
struct elf_binary elf;
uint64_t v_start, v_end;
+ uint64_t m_start = 0, m_end = 0;
int rc;
xen_capabilities_info_t caps;
unsigned long stat_normal_pages = 0, stat_2mb_pages = 0,
@@ -178,11 +272,19 @@ static int setup_guest(xc_interface *xch
goto error_out;
}
+ if ( modules_init(args, v_end, &elf, &m_start, &m_end) != 0 )
+ {
+ ERROR("Insufficient space to load modules.");
+ goto error_out;
+ }
+
IPRINTF("VIRTUAL MEMORY ARRANGEMENT:\n"
" Loader: %016"PRIx64"->%016"PRIx64"\n"
+ " Modules: %016"PRIx64"->%016"PRIx64"\n"
" TOTAL: %016"PRIx64"->%016"PRIx64"\n"
" ENTRY ADDRESS: %016"PRIx64"\n",
elf.pstart, elf.pend,
+ m_start, m_end,
v_start, v_end,
elf_uval(&elf, elf.ehdr, e_entry));
@@ -337,6 +439,9 @@ static int setup_guest(xc_interface *xch
if ( loadelfimage(xch, &elf, dom, page_array) != 0 )
goto error_out;
+ if ( loadmodules(xch, args, m_start, m_end, dom, page_array) != 0 )
+ goto error_out;
+
if ( (hvm_info_page = xc_map_foreign_range(
xch, dom, PAGE_SIZE, PROT_READ | PROT_WRITE,
HVM_INFO_PFN)) == NULL )
@@ -413,7 +518,7 @@ static int setup_guest(xc_interface *xch
* Create a domain for a virtualized Linux, using files/filenames.
*/
int xc_hvm_build(xc_interface *xch, uint32_t domid,
- const struct xc_hvm_build_args *hvm_args)
+ struct xc_hvm_build_args *hvm_args)
{
struct xc_hvm_build_args args = *hvm_args;
void *image;
@@ -441,6 +546,15 @@ int xc_hvm_build(xc_interface *xch, uint
sts = setup_guest(xch, domid, &args, image, image_size);
+ if (!sts)
+ {
+ /* Return module load addresses to caller */
+ hvm_args->acpi_module.guest_addr_out =
+ args.acpi_module.guest_addr_out;
+ hvm_args->smbios_module.guest_addr_out =
+ args.smbios_module.guest_addr_out;
+ }
+
free(image);
return sts;
@@ -461,6 +575,7 @@ int xc_hvm_build_target_mem(xc_interface
{
struct xc_hvm_build_args args = {};
+ memset(&args, 0, sizeof(struct xc_hvm_build_args));
args.mem_size = (uint64_t)memsize << 20;
args.mem_target = (uint64_t)target << 20;
args.image_file_name = image_name;
diff -r 07bf59a7ce83 -r cabf395a6c84 tools/libxc/xenguest.h
--- a/tools/libxc/xenguest.h Thu Jan 10 17:16:28 2013 +0000
+++ b/tools/libxc/xenguest.h Thu Jan 10 17:17:21 2013 +0000
@@ -211,11 +211,23 @@ int xc_linux_build_mem(xc_interface *xch
unsigned int console_evtchn,
unsigned long *console_mfn);
+struct xc_hvm_firmware_module {
+ uint8_t *data;
+ uint32_t length;
+ uint64_t guest_addr_out;
+};
+
struct xc_hvm_build_args {
uint64_t mem_size; /* Memory size in bytes. */
uint64_t mem_target; /* Memory target in bytes. */
uint64_t mmio_size; /* Size of the MMIO hole in bytes. */
const char *image_file_name; /* File name of the image to load. */
+
+ /* Extra ACPI tables passed to HVMLOADER */
+ struct xc_hvm_firmware_module acpi_module;
+
+ /* Extra SMBIOS structures passed to HVMLOADER */
+ struct xc_hvm_firmware_module smbios_module;
};
/**
@@ -228,7 +240,7 @@ struct xc_hvm_build_args {
* are optional.
*/
int xc_hvm_build(xc_interface *xch, uint32_t domid,
- const struct xc_hvm_build_args *hvm_args);
+ struct xc_hvm_build_args *hvm_args);
int xc_hvm_build_target_mem(xc_interface *xch,
uint32_t domid,
diff -r 07bf59a7ce83 -r cabf395a6c84 tools/libxc/xg_private.c
--- a/tools/libxc/xg_private.c Thu Jan 10 17:16:28 2013 +0000
+++ b/tools/libxc/xg_private.c Thu Jan 10 17:17:21 2013 +0000
@@ -192,7 +192,7 @@ unsigned long csum_page(void *page)
__attribute__((weak))
int xc_hvm_build(xc_interface *xch,
uint32_t domid,
- const struct xc_hvm_build_args *hvm_args)
+ struct xc_hvm_build_args *hvm_args)
{
errno = ENOSYS;
return -1;

View File

@ -0,0 +1,645 @@
fate#313584: pass bios information to XEN HVM guest
# HG changeset patch
# User Ross Philipson <ross.philipson@citrix.com>
# Date 1357838290 0
# Node ID a7ce196f40444fafbe8f13b2d80e4885d4321806
# Parent cabf395a6c849cc65e56f1640b18db0c3e0faf5d
HVM firmware passthrough SMBIOS processing
Passthrough support for the SMBIOS structures including three new DMTF
defined types and support for OEM defined tables. Passed in SMBIOS
types override the default internal values. Default values can be
enabled for the new type 22 portable battery using a xenstore
flag. All other new DMTF defined and OEM structures will only be added
to the SMBIOS table if passthrough values are present.
Signed-off-by: Ross Philipson <ross.philipson@citrix.com>
Committed-by: Keir Fraser <keir@xen.org>
diff -r cabf395a6c84 -r a7ce196f4044 tools/firmware/hvmloader/smbios.c
--- a/tools/firmware/hvmloader/smbios.c Thu Jan 10 17:17:21 2013 +0000
+++ b/tools/firmware/hvmloader/smbios.c Thu Jan 10 17:18:10 2013 +0000
@@ -26,16 +26,38 @@
#include "smbios_types.h"
#include "util.h"
#include "hypercall.h"
+#include <xen/hvm/hvm_xs_strings.h>
+/* SBMIOS handle base values */
+#define SMBIOS_HANDLE_TYPE0 0x0000
+#define SMBIOS_HANDLE_TYPE1 0x0100
+#define SMBIOS_HANDLE_TYPE2 0x0200
+#define SMBIOS_HANDLE_TYPE3 0x0300
+#define SMBIOS_HANDLE_TYPE4 0x0400
+#define SMBIOS_HANDLE_TYPE11 0x0B00
+#define SMBIOS_HANDLE_TYPE16 0x1000
+#define SMBIOS_HANDLE_TYPE17 0x1100
+#define SMBIOS_HANDLE_TYPE19 0x1300
+#define SMBIOS_HANDLE_TYPE20 0x1400
+#define SMBIOS_HANDLE_TYPE22 0x1600
+#define SMBIOS_HANDLE_TYPE32 0x2000
+#define SMBIOS_HANDLE_TYPE39 0x2700
+#define SMBIOS_HANDLE_TYPE127 0x7f00
+
+static void
+smbios_pt_init(void);
+static void*
+get_smbios_pt_struct(uint8_t type, uint32_t *length_out);
+static void
+get_cpu_manufacturer(char *buf, int len);
static int
write_smbios_tables(void *ep, void *start,
uint32_t vcpus, uint64_t memsize,
uint8_t uuid[16], char *xen_version,
uint32_t xen_major_version, uint32_t xen_minor_version,
unsigned *nr_structs, unsigned *max_struct_size);
-
-static void
-get_cpu_manufacturer(char *buf, int len);
+static uint64_t
+get_memsize(void);
static void
smbios_entry_point_init(void *start,
uint16_t max_structure_size,
@@ -49,6 +71,8 @@ static void *
smbios_type_1_init(void *start, const char *xen_version,
uint8_t uuid[16]);
static void *
+smbios_type_2_init(void *start);
+static void *
smbios_type_3_init(void *start);
static void *
smbios_type_4_init(void *start, unsigned int cpu_number,
@@ -64,10 +88,73 @@ smbios_type_19_init(void *start, uint32_
static void *
smbios_type_20_init(void *start, uint32_t memory_size_mb, int instance);
static void *
+smbios_type_22_init(void *start);
+static void *
smbios_type_32_init(void *start);
static void *
+smbios_type_39_init(void *start);
+static void *
+smbios_type_vendor_oem_init(void *start);
+static void *
smbios_type_127_init(void *start);
+static uint32_t *smbios_pt_addr = NULL;
+static uint32_t smbios_pt_length = 0;
+
+static void
+smbios_pt_init(void)
+{
+ const char *s;
+
+ s = xenstore_read(HVM_XS_SMBIOS_PT_ADDRESS, NULL);
+ if ( s == NULL )
+ goto reset;
+
+ smbios_pt_addr = (uint32_t*)(uint32_t)strtoll(s, NULL, 0);
+ if ( smbios_pt_addr == NULL )
+ goto reset;
+
+ s = xenstore_read(HVM_XS_SMBIOS_PT_LENGTH, NULL);
+ if ( s == NULL )
+ goto reset;
+
+ smbios_pt_length = (uint32_t)strtoll(s, NULL, 0);
+ if ( smbios_pt_length == 0 )
+ goto reset;
+
+ return;
+
+reset:
+ smbios_pt_addr = NULL;
+ smbios_pt_length = 0;
+}
+
+static void*
+get_smbios_pt_struct(uint8_t type, uint32_t *length_out)
+{
+ uint32_t *sep = smbios_pt_addr;
+ uint32_t total = 0;
+ uint8_t *ptr;
+
+ if ( sep == NULL )
+ return NULL;
+
+ while ( total < smbios_pt_length )
+ {
+ ptr = (uint8_t*)(sep + 1);
+ if ( ptr[0] == type )
+ {
+ *length_out = *sep;
+ return ptr;
+ }
+
+ total += (*sep + sizeof(uint32_t));
+ sep = (uint32_t*)(ptr + *sep);
+ }
+
+ return NULL;
+}
+
static void
get_cpu_manufacturer(char *buf, int len)
{
@@ -97,6 +184,8 @@ write_smbios_tables(void *ep, void *star
char cpu_manufacturer[15];
int i, nr_mem_devs;
+ smbios_pt_init();
+
get_cpu_manufacturer(cpu_manufacturer, 15);
p = (char *)start;
@@ -112,6 +201,7 @@ write_smbios_tables(void *ep, void *star
do_struct(smbios_type_0_init(p, xen_version, xen_major_version,
xen_minor_version));
do_struct(smbios_type_1_init(p, xen_version, uuid));
+ do_struct(smbios_type_2_init(p));
do_struct(smbios_type_3_init(p));
for ( cpu_num = 1; cpu_num <= vcpus; cpu_num++ )
do_struct(smbios_type_4_init(p, cpu_num, cpu_manufacturer));
@@ -130,7 +220,10 @@ write_smbios_tables(void *ep, void *star
do_struct(smbios_type_20_init(p, dev_memsize, i));
}
+ do_struct(smbios_type_22_init(p));
do_struct(smbios_type_32_init(p));
+ do_struct(smbios_type_39_init(p));
+ do_struct(smbios_type_vendor_oem_init(p));
do_struct(smbios_type_127_init(p));
#undef do_struct
@@ -289,12 +382,22 @@ smbios_type_0_init(void *start, const ch
struct smbios_type_0 *p = (struct smbios_type_0 *)start;
static const char *smbios_release_date = __SMBIOS_DATE__;
const char *s;
+ void *pts;
+ uint32_t length;
+
+ pts = get_smbios_pt_struct(0, &length);
+ if ( (pts != NULL)&&(length > 0) )
+ {
+ memcpy(start, pts, length);
+ p->header.handle = SMBIOS_HANDLE_TYPE0;
+ return (start + length);
+ }
memset(p, 0, sizeof(*p));
p->header.type = 0;
p->header.length = sizeof(struct smbios_type_0);
- p->header.handle = 0;
+ p->header.handle = SMBIOS_HANDLE_TYPE0;
p->vendor_str = 1;
p->version_str = 2;
@@ -315,11 +418,11 @@ smbios_type_0_init(void *start, const ch
p->embedded_controller_minor = 0xff;
start += sizeof(struct smbios_type_0);
- s = xenstore_read("bios-strings/bios-vendor", "Xen");
+ s = xenstore_read(HVM_XS_BIOS_VENDOR, "Xen");
strcpy((char *)start, s);
start += strlen(s) + 1;
- s = xenstore_read("bios-strings/bios-version", xen_version);
+ s = xenstore_read(HVM_XS_BIOS_VERSION, xen_version);
strcpy((char *)start, s);
start += strlen(s) + 1;
@@ -338,12 +441,22 @@ smbios_type_1_init(void *start, const ch
char uuid_str[37];
struct smbios_type_1 *p = (struct smbios_type_1 *)start;
const char *s;
+ void *pts;
+ uint32_t length;
+
+ pts = get_smbios_pt_struct(1, &length);
+ if ( (pts != NULL)&&(length > 0) )
+ {
+ memcpy(start, pts, length);
+ p->header.handle = SMBIOS_HANDLE_TYPE1;
+ return (start + length);
+ }
memset(p, 0, sizeof(*p));
p->header.type = 1;
p->header.length = sizeof(struct smbios_type_1);
- p->header.handle = 0x100;
+ p->header.handle = SMBIOS_HANDLE_TYPE1;
p->manufacturer_str = 1;
p->product_name_str = 2;
@@ -358,20 +471,20 @@ smbios_type_1_init(void *start, const ch
start += sizeof(struct smbios_type_1);
- s = xenstore_read("bios-strings/system-manufacturer", "Xen");
+ s = xenstore_read(HVM_XS_SYSTEM_MANUFACTURER, "Xen");
strcpy((char *)start, s);
start += strlen(s) + 1;
- s = xenstore_read("bios-strings/system-product-name", "HVM domU");
+ s = xenstore_read(HVM_XS_SYSTEM_PRODUCT_NAME, "HVM domU");
strcpy((char *)start, s);
start += strlen(s) + 1;
- s = xenstore_read("bios-strings/system-version", xen_version);
+ s = xenstore_read(HVM_XS_SYSTEM_VERSION, xen_version);
strcpy((char *)start, s);
start += strlen(s) + 1;
uuid_to_string(uuid_str, uuid);
- s = xenstore_read("bios-strings/system-serial-number", uuid_str);
+ s = xenstore_read(HVM_XS_SYSTEM_SERIAL_NUMBER, uuid_str);
strcpy((char *)start, s);
start += strlen(s) + 1;
@@ -380,17 +493,58 @@ smbios_type_1_init(void *start, const ch
return start+1;
}
+/* Type 2 -- System Board */
+static void *
+smbios_type_2_init(void *start)
+{
+ struct smbios_type_2 *p = (struct smbios_type_2 *)start;
+ uint8_t *ptr;
+ void *pts;
+ uint32_t length;
+
+ pts = get_smbios_pt_struct(2, &length);
+ if ( (pts != NULL)&&(length > 0) )
+ {
+ memcpy(start, pts, length);
+ p->header.handle = SMBIOS_HANDLE_TYPE2;
+
+ /* Set current chassis handle if present */
+ if ( p->header.length > 13 )
+ {
+ ptr = ((uint8_t*)start) + 11;
+ if ( *((uint16_t*)ptr) != 0 )
+ *((uint16_t*)ptr) = SMBIOS_HANDLE_TYPE3;
+ }
+
+ return (start + length);
+ }
+
+ /* Only present when passed in */
+ return start;
+}
+
/* Type 3 -- System Enclosure */
static void *
smbios_type_3_init(void *start)
{
struct smbios_type_3 *p = (struct smbios_type_3 *)start;
+ const char *s;
+ void *pts;
+ uint32_t length;
+
+ pts = get_smbios_pt_struct(3, &length);
+ if ( (pts != NULL)&&(length > 0) )
+ {
+ memcpy(start, pts, length);
+ p->header.handle = SMBIOS_HANDLE_TYPE3;
+ return (start + length);
+ }
memset(p, 0, sizeof(*p));
p->header.type = 3;
p->header.length = sizeof(struct smbios_type_3);
- p->header.handle = 0x300;
+ p->header.handle = SMBIOS_HANDLE_TYPE3;
p->manufacturer_str = 1;
p->type = 0x01; /* other */
@@ -404,8 +558,19 @@ smbios_type_3_init(void *start)
start += sizeof(struct smbios_type_3);
- strcpy((char *)start, "Xen");
- start += strlen("Xen") + 1;
+ s = xenstore_read(HVM_XS_ENCLOSURE_MANUFACTURER, "Xen");
+ strcpy((char *)start, s);
+ start += strlen(s) + 1;
+
+ /* No internal defaults for this if the value is not set */
+ s = xenstore_read(HVM_XS_ENCLOSURE_SERIAL_NUMBER, NULL);
+ if ( (s != NULL)&&(*s != '\0') )
+ {
+ strcpy((char *)start, s);
+ start += strlen(s) + 1;
+ p->serial_number_str = 2;
+ }
+
*((uint8_t *)start) = 0;
return start+1;
}
@@ -423,7 +588,7 @@ smbios_type_4_init(
p->header.type = 4;
p->header.length = sizeof(struct smbios_type_4);
- p->header.handle = 0x400 + cpu_number;
+ p->header.handle = SMBIOS_HANDLE_TYPE4 + cpu_number;
p->socket_designation_str = 1;
p->processor_type = 0x03; /* CPU */
@@ -465,13 +630,23 @@ static void *
smbios_type_11_init(void *start)
{
struct smbios_type_11 *p = (struct smbios_type_11 *)start;
- char path[20] = "bios-strings/oem-XX";
+ char path[20];
const char *s;
int i;
+ void *pts;
+ uint32_t length;
+
+ pts = get_smbios_pt_struct(11, &length);
+ if ( (pts != NULL)&&(length > 0) )
+ {
+ memcpy(start, pts, length);
+ p->header.handle = SMBIOS_HANDLE_TYPE11;
+ return (start + length);
+ }
p->header.type = 11;
p->header.length = sizeof(struct smbios_type_11);
- p->header.handle = 0xB00;
+ p->header.handle = SMBIOS_HANDLE_TYPE11;
p->count = 0;
@@ -480,8 +655,7 @@ smbios_type_11_init(void *start)
/* Pull out as many oem-* strings we find in xenstore */
for ( i = 1; i < 100; i++ )
{
- path[(sizeof path) - 3] = '0' + ((i < 10) ? i : i / 10);
- path[(sizeof path) - 2] = (i < 10) ? '\0' : '0' + (i % 10);
+ snprintf(path, sizeof(path), HVM_XS_OEM_STRINGS, i);
if ( ((s = xenstore_read(path, NULL)) == NULL) || (*s == '\0') )
break;
strcpy((char *)start, s);
@@ -510,7 +684,7 @@ smbios_type_16_init(void *start, uint32_
memset(p, 0, sizeof(*p));
p->header.type = 16;
- p->header.handle = 0x1000;
+ p->header.handle = SMBIOS_HANDLE_TYPE16;
p->header.length = sizeof(struct smbios_type_16);
p->location = 0x01; /* other */
@@ -536,7 +710,7 @@ smbios_type_17_init(void *start, uint32_
p->header.type = 17;
p->header.length = sizeof(struct smbios_type_17);
- p->header.handle = 0x1100 + instance;
+ p->header.handle = SMBIOS_HANDLE_TYPE17 + instance;
p->physical_memory_array_handle = 0x1000;
p->total_width = 64;
@@ -571,7 +745,7 @@ smbios_type_19_init(void *start, uint32_
p->header.type = 19;
p->header.length = sizeof(struct smbios_type_19);
- p->header.handle = 0x1300 + instance;
+ p->header.handle = SMBIOS_HANDLE_TYPE19 + instance;
p->starting_address = instance << 24;
p->ending_address = p->starting_address + (memory_size_mb << 10) - 1;
@@ -593,7 +767,7 @@ smbios_type_20_init(void *start, uint32_
p->header.type = 20;
p->header.length = sizeof(struct smbios_type_20);
- p->header.handle = 0x1400 + instance;
+ p->header.handle = SMBIOS_HANDLE_TYPE20 + instance;
p->starting_address = instance << 24;
p->ending_address = p->starting_address + (memory_size_mb << 10) - 1;
@@ -609,6 +783,71 @@ smbios_type_20_init(void *start, uint32_
return start+2;
}
+/* Type 22 -- Portable Battery */
+static void *
+smbios_type_22_init(void *start)
+{
+ struct smbios_type_22 *p = (struct smbios_type_22 *)start;
+ static const char *smbios_release_date = __SMBIOS_DATE__;
+ const char *s;
+ void *pts;
+ uint32_t length;
+
+ pts = get_smbios_pt_struct(22, &length);
+ if ( (pts != NULL)&&(length > 0) )
+ {
+ memcpy(start, pts, length);
+ p->header.handle = SMBIOS_HANDLE_TYPE22;
+ return (start + length);
+ }
+
+ s = xenstore_read(HVM_XS_SMBIOS_DEFAULT_BATTERY, "0");
+ if ( strncmp(s, "1", 1) != 0 )
+ return start;
+
+ memset(p, 0, sizeof(*p));
+
+ p->header.type = 22;
+ p->header.length = sizeof(struct smbios_type_22);
+ p->header.handle = SMBIOS_HANDLE_TYPE22;
+
+ p->location_str = 1;
+ p->manufacturer_str = 2;
+ p->manufacturer_date_str = 3;
+ p->serial_number_str = 0;
+ p->device_name_str = 4;
+ p->device_chemistry = 0x2; /* unknown */
+ p->device_capacity = 0; /* unknown */
+ p->device_voltage = 0; /* unknown */
+ p->sbds_version_number = 0;
+ p->max_error = 0xff; /* unknown */
+ p->sbds_serial_number = 0;
+ p->sbds_manufacturer_date = 0;
+ p->sbds_device_chemistry = 0;
+ p->design_capacity_multiplier = 0;
+ p->oem_specific = 0;
+
+ start += sizeof(struct smbios_type_22);
+
+ strcpy((char *)start, "Primary");
+ start += strlen("Primary") + 1;
+
+ s = xenstore_read(HVM_XS_BATTERY_MANUFACTURER, "Xen");
+ strcpy((char *)start, s);
+ start += strlen(s) + 1;
+
+ strcpy((char *)start, smbios_release_date);
+ start += strlen(smbios_release_date) + 1;
+
+ s = xenstore_read(HVM_XS_BATTERY_DEVICE_NAME, "XEN-VBAT");
+ strcpy((char *)start, s);
+ start += strlen(s) + 1;
+
+ *((uint8_t *)start) = 0;
+
+ return start+1;
+}
+
/* Type 32 -- System Boot Information */
static void *
smbios_type_32_init(void *start)
@@ -619,7 +858,7 @@ smbios_type_32_init(void *start)
p->header.type = 32;
p->header.length = sizeof(struct smbios_type_32);
- p->header.handle = 0x2000;
+ p->header.handle = SMBIOS_HANDLE_TYPE32;
memset(p->reserved, 0, 6);
p->boot_status = 0; /* no errors detected */
@@ -628,6 +867,58 @@ smbios_type_32_init(void *start)
return start+2;
}
+/* Type 39 -- Power Supply */
+static void *
+smbios_type_39_init(void *start)
+{
+ struct smbios_type_39 *p = (struct smbios_type_39 *)start;
+ void *pts;
+ uint32_t length;
+
+ pts = get_smbios_pt_struct(39, &length);
+ if ( (pts != NULL)&&(length > 0) )
+ {
+ memcpy(start, pts, length);
+ p->header.handle = SMBIOS_HANDLE_TYPE39;
+ return (start + length);
+ }
+
+ /* Only present when passed in */
+ return start;
+}
+
+static void *
+smbios_type_vendor_oem_init(void *start)
+{
+ uint32_t *sep = smbios_pt_addr;
+ uint32_t total = 0;
+ uint8_t *ptr;
+
+ if ( sep == NULL )
+ return start;
+
+ while ( total < smbios_pt_length )
+ {
+ ptr = (uint8_t*)(sep + 1);
+ if ( ptr[0] >= 128 )
+ {
+ /* Vendor/OEM table, copy it in. Note the handle values cannot
+ * be changed since it is unknown what is in each of these tables
+ * but they could contain handle references to other tables. This
+ * means a slight risk of collision with the tables above but that
+ * would have to be dealt with on a case by case basis.
+ */
+ memcpy(start, ptr, *sep);
+ start += *sep;
+ }
+
+ total += (*sep + sizeof(uint32_t));
+ sep = (uint32_t*)(ptr + *sep);
+ }
+
+ return start;
+}
+
/* Type 127 -- End of Table */
static void *
smbios_type_127_init(void *start)
@@ -638,7 +929,7 @@ smbios_type_127_init(void *start)
p->header.type = 127;
p->header.length = sizeof(struct smbios_type_127);
- p->header.handle = 0x7f00;
+ p->header.handle = SMBIOS_HANDLE_TYPE127;
start += sizeof(struct smbios_type_127);
*((uint16_t *)start) = 0;
diff -r cabf395a6c84 -r a7ce196f4044 tools/firmware/hvmloader/smbios_types.h
--- a/tools/firmware/hvmloader/smbios_types.h Thu Jan 10 17:17:21 2013 +0000
+++ b/tools/firmware/hvmloader/smbios_types.h Thu Jan 10 17:18:10 2013 +0000
@@ -84,6 +84,15 @@ struct smbios_type_1 {
uint8_t family_str;
} __attribute__ ((packed));
+/* SMBIOS type 2 - Base Board Information */
+struct smbios_type_2 {
+ struct smbios_structure_header header;
+ uint8_t manufacturer_str;
+ uint8_t product_name_str;
+ uint8_t version_str;
+ uint8_t serial_number_str;
+} __attribute__ ((packed));
+
/* SMBIOS type 3 - System Enclosure */
struct smbios_type_3 {
struct smbios_structure_header header;
@@ -173,6 +182,26 @@ struct smbios_type_20 {
uint8_t interleaved_data_depth;
} __attribute__ ((packed));
+/* SMBIOS type 22 - Portable battery */
+struct smbios_type_22 {
+ struct smbios_structure_header header;
+ uint8_t location_str;
+ uint8_t manufacturer_str;
+ uint8_t manufacturer_date_str;
+ uint8_t serial_number_str;
+ uint8_t device_name_str;
+ uint8_t device_chemistry;
+ uint16_t device_capacity;
+ uint16_t device_voltage;
+ uint8_t sbds_version_number;
+ uint8_t max_error;
+ uint16_t sbds_serial_number;
+ uint16_t sbds_manufacturer_date;
+ uint8_t sbds_device_chemistry;
+ uint8_t design_capacity_multiplier;
+ uint32_t oem_specific;
+} __attribute__ ((packed));
+
/* SMBIOS type 32 - System Boot Information */
struct smbios_type_32 {
struct smbios_structure_header header;
@@ -180,6 +209,24 @@ struct smbios_type_32 {
uint8_t boot_status;
} __attribute__ ((packed));
+/* SMBIOS type 39 - Power Supply */
+struct smbios_type_39 {
+ struct smbios_structure_header header;
+ uint8_t power_unit_group;
+ uint8_t location_str;
+ uint8_t device_name_str;
+ uint8_t manufacturer_str;
+ uint8_t serial_number_str;
+ uint8_t asset_tag_number_str;
+ uint8_t model_part_number_str;
+ uint8_t revision_level_str;
+ uint16_t max_capacity;
+ uint16_t characteristics;
+ uint16_t input_voltage_probe_handle;
+ uint16_t cooling_device_handle;
+ uint16_t input_current_probe_handle;
+} __attribute__ ((packed));
+
/* SMBIOS type 127 -- End-of-table */
struct smbios_type_127 {
struct smbios_structure_header header;

View File

@ -0,0 +1,101 @@
fate#313584: pass bios information to XEN HVM guest
# HG changeset patch
# User Ross Philipson <ross.philipson@citrix.com>
# Date 1357838323 0
# Node ID b9c38bea15b117552ecb51809779c7cfef82dd44
# Parent a7ce196f40444fafbe8f13b2d80e4885d4321806
HVM firmware passthrough ACPI processing
ACPI table passthrough support allowing additional static tables and
SSDTs (AML code) to be loaded. These additional tables are added at
the end of the secondary table list in the RSDT/XSDT tables.
Signed-off-by: Ross Philipson <ross.philipson@citrix.com>
Committed-by: Keir Fraser <keir@xen.org>
diff -r a7ce196f4044 -r b9c38bea15b1 tools/firmware/hvmloader/acpi/build.c
--- a/tools/firmware/hvmloader/acpi/build.c Thu Jan 10 17:18:10 2013 +0000
+++ b/tools/firmware/hvmloader/acpi/build.c Thu Jan 10 17:18:43 2013 +0000
@@ -23,6 +23,9 @@
#include "ssdt_pm.h"
#include "../config.h"
#include "../util.h"
+#include <xen/hvm/hvm_xs_strings.h>
+
+#define ACPI_MAX_SECONDARY_TABLES 16
#define align16(sz) (((sz) + 15) & ~15)
#define fixed_strcpy(d, s) strncpy((d), (s), sizeof(d))
@@ -198,6 +201,52 @@ static struct acpi_20_waet *construct_wa
return waet;
}
+static int construct_passthrough_tables(unsigned long *table_ptrs,
+ int nr_tables)
+{
+ const char *s;
+ uint8_t *acpi_pt_addr;
+ uint32_t acpi_pt_length;
+ struct acpi_header *header;
+ int nr_added;
+ int nr_max = (ACPI_MAX_SECONDARY_TABLES - nr_tables - 1);
+ uint32_t total = 0;
+ uint8_t *buffer;
+
+ s = xenstore_read(HVM_XS_ACPI_PT_ADDRESS, NULL);
+ if ( s == NULL )
+ return 0;
+
+ acpi_pt_addr = (uint8_t*)(uint32_t)strtoll(s, NULL, 0);
+ if ( acpi_pt_addr == NULL )
+ return 0;
+
+ s = xenstore_read(HVM_XS_ACPI_PT_LENGTH, NULL);
+ if ( s == NULL )
+ return 0;
+
+ acpi_pt_length = (uint32_t)strtoll(s, NULL, 0);
+
+ for ( nr_added = 0; nr_added < nr_max; nr_added++ )
+ {
+ if ( (acpi_pt_length - total) < sizeof(struct acpi_header) )
+ break;
+
+ header = (struct acpi_header*)acpi_pt_addr;
+
+ buffer = mem_alloc(header->length, 16);
+ if ( buffer == NULL )
+ break;
+ memcpy(buffer, header, header->length);
+
+ table_ptrs[nr_tables++] = (unsigned long)buffer;
+ total += header->length;
+ acpi_pt_addr += header->length;
+ }
+
+ return nr_added;
+}
+
static int construct_secondary_tables(unsigned long *table_ptrs,
struct acpi_info *info)
{
@@ -293,6 +342,9 @@ static int construct_secondary_tables(un
}
}
+ /* Load any additional tables passed through. */
+ nr_tables += construct_passthrough_tables(table_ptrs, nr_tables);
+
table_ptrs[nr_tables] = 0;
return nr_tables;
}
@@ -327,7 +379,7 @@ void acpi_build_tables(struct acpi_confi
struct acpi_10_fadt *fadt_10;
struct acpi_20_facs *facs;
unsigned char *dsdt;
- unsigned long secondary_tables[16];
+ unsigned long secondary_tables[ACPI_MAX_SECONDARY_TABLES];
int nr_secondaries, i;
unsigned long vm_gid_addr;

88
CVE-2012-6075-xsa41.patch Normal file
View File

@ -0,0 +1,88 @@
Subject: e1000: Discard packets that are too long if !SBP and !LPE
From: Michael Contreras michael@inetric.com Sun Dec 2 20:11:22 2012 -0800
Date: Wed Jan 16 14:12:40 2013 +0000:
Git: b4e9b8169dedc0bcf0d3abe07642f761ac70aeea
The e1000_receive function for the e1000 needs to discard packets longer than
1522 bytes if the SBP and LPE flags are disabled. The linux driver assumes
this behavior and allocates memory based on this assumption.
Signed-off-by: Michael Contreras <michael@inetric.com>
Signed-off-by: Anthony Liguori <aliguori@us.ibm.com>
Subject: e1000: Discard oversized packets based on SBP|LPE
From: Michael Contreras <michael@inetric.com>
Date: Wed, 5 Dec 2012 18:31:30 +0000 (-0500)
e1000: Discard oversized packets based on SBP|LPE
Discard packets longer than 16384 when !SBP to match the hardware behavior.
Signed-off-by: Michael Contreras <michael@inetric.com>
Signed-off-by: Stefan Hajnoczi <stefanha@redhat.com>
[ This is a security vulnerability, CVE-2012-6075 / XSA-41. ]
(cherry picked from commit 4c2cae2a882db4d2a231b27b3b31a5bbec6dacbf)
Index: xen-4.2.1-testing/tools/qemu-xen-traditional-dir-remote/hw/e1000.c
===================================================================
--- xen-4.2.1-testing.orig/tools/qemu-xen-traditional-dir-remote/hw/e1000.c
+++ xen-4.2.1-testing/tools/qemu-xen-traditional-dir-remote/hw/e1000.c
@@ -55,6 +55,11 @@ static int debugflags = DBGBIT(TXERR) |
#define REG_IOADDR 0x0
#define REG_IODATA 0x4
+/* this is the size past which hardware will drop packets when setting LPE=0 */
+#define MAXIMUM_ETHERNET_VLAN_SIZE 1522
+/* this is the size past which hardware will drop packets when setting LPE=1 */
+#define MAXIMUM_ETHERNET_LPE_SIZE 16384
+
/*
* HW models:
* E1000_DEV_ID_82540EM works with Windows and Linux
@@ -628,6 +633,14 @@ e1000_receive(void *opaque, const uint8_
return;
}
+ /* Discard oversized packets if !LPE and !SBP. */
+ if ((size > MAXIMUM_ETHERNET_LPE_SIZE ||
+ (size > MAXIMUM_ETHERNET_VLAN_SIZE
+ && !(s->mac_reg[RCTL] & E1000_RCTL_LPE)))
+ && !(s->mac_reg[RCTL] & E1000_RCTL_SBP)) {
+ return;
+ }
+
if (!receive_filter(s, buf, size))
return;
Index: xen-4.2.1-testing/tools/qemu-xen-dir-remote/hw/e1000.c
===================================================================
--- xen-4.2.1-testing.orig/tools/qemu-xen-dir-remote/hw/e1000.c
+++ xen-4.2.1-testing/tools/qemu-xen-dir-remote/hw/e1000.c
@@ -59,6 +59,11 @@ static int debugflags = DBGBIT(TXERR) |
#define PNPMMIO_SIZE 0x20000
#define MIN_BUF_SIZE 60 /* Min. octets in an ethernet frame sans FCS */
+/* this is the size past which hardware will drop packets when setting LPE=0 */
+#define MAXIMUM_ETHERNET_VLAN_SIZE 1522
+/* this is the size past which hardware will drop packets when setting LPE=1 */
+#define MAXIMUM_ETHERNET_LPE_SIZE 16384
+
/*
* HW models:
* E1000_DEV_ID_82540EM works with Windows and Linux
@@ -693,6 +698,14 @@ e1000_receive(VLANClientState *nc, const
size = sizeof(min_buf);
}
+ /* Discard oversized packets if !LPE and !SBP. */
+ if ((size > MAXIMUM_ETHERNET_LPE_SIZE ||
+ (size > MAXIMUM_ETHERNET_VLAN_SIZE
+ && !(s->mac_reg[RCTL] & E1000_RCTL_LPE)))
+ && !(s->mac_reg[RCTL] & E1000_RCTL_SBP)) {
+ return size;
+ }
+
if (!receive_filter(s, buf, size))
return size;

32
CVE-2013-0151-xsa34.patch Normal file
View File

@ -0,0 +1,32 @@
References: CVE-2013-0151 XSA-34 bnc#797285
x86_32: don't allow use of nested HVM
There are (indirect) uses of map_domain_page() in the nested HVM code
that are unsafe when not just using the 1:1 mapping.
This is XSA-34 / CVE-2013-0151.
Signed-off-by: Jan Beulich <jbeulich@suse.com>
--- a/xen/arch/x86/hvm/hvm.c
+++ b/xen/arch/x86/hvm/hvm.c
@@ -3930,6 +3930,10 @@ long do_hvm_op(unsigned long op, XEN_GUE
rc = -EINVAL;
break;
case HVM_PARAM_NESTEDHVM:
+#ifdef __i386__
+ if ( a.value )
+ rc = -EINVAL;
+#else
if ( a.value > 1 )
rc = -EINVAL;
if ( !is_hvm_domain(d) )
@@ -3944,6 +3948,7 @@ long do_hvm_op(unsigned long op, XEN_GUE
for_each_vcpu(d, v)
if ( rc == 0 )
rc = nestedhvm_vcpu_initialise(v);
+#endif
break;
case HVM_PARAM_BUFIOREQ_EVTCHN:
rc = -EINVAL;

26
CVE-2013-0152-xsa35.patch Normal file
View File

@ -0,0 +1,26 @@
References: CVE-2013-0152 XSA-35 bnc#797287
xen: Do not allow guests to enable nested HVM on themselves
There is no reason for this and doing so exposes a memory leak to
guests. Only toolstacks need write access to this HVM param.
This is XSA-35 / CVE-2013-0152.
Signed-off-by: Ian Campbell <ian.campbell@citrix.com>
Acked-by: Jan Beulich <JBeulich@suse.com>
--- a/xen/arch/x86/hvm/hvm.c
+++ b/xen/arch/x86/hvm/hvm.c
@@ -3930,6 +3930,11 @@ long do_hvm_op(unsigned long op, XEN_GUE
rc = -EINVAL;
break;
case HVM_PARAM_NESTEDHVM:
+ if ( !IS_PRIV(current->domain) )
+ {
+ rc = -EPERM;
+ break;
+ }
#ifdef __i386__
if ( a.value )
rc = -EINVAL;

View File

@ -37,6 +37,7 @@ from stat import *
from xen.xend import sxp
import tempfile
import time
import xnloader
# Global options
quiet = False
@ -447,6 +448,7 @@ def copyKernelAndRamdisk(disk, vdev, kernel, ramdisk):
raise
sxpr += "(ramdisk %s)" % inm
part.umount()
xnloader.patch_netware_loader(knm)
return sxpr
def main(argv):

View File

@ -0,0 +1,21 @@
Index: xen-4.2.1-testing/tools/pygrub/src/pygrub
===================================================================
--- xen-4.2.1-testing.orig/tools/pygrub/src/pygrub
+++ xen-4.2.1-testing/tools/pygrub/src/pygrub
@@ -26,6 +26,7 @@ import fsimage
import grub.GrubConf
import grub.LiloConf
import grub.ExtLinuxConf
+import xnloader
PYGRUB_VER = 0.6
FS_READ_MAX = 1024 * 1024
@@ -734,6 +735,8 @@ if __name__ == "__main__":
if len(data) == 0:
os.close(tfd)
del datafile
+ if file_to_read == "/nwserver/xnloader.sys":
+ xnloader.patch_netware_loader(ret)
return ret
try:
os.write(tfd, data)

View File

@ -1,145 +0,0 @@
Reverse c/s 24757. Breaks booting NetWare.
# HG changeset patch
# User Alex Zeffertt <alex.zeffertt@eu.citrix.com>
# Date 1328812412 0
# Node ID aae516b78fce679f9c367231b7a3891814fcfdbb
# Parent 585caf50a9260d3fc6a4ece0450d10d34e73489f
xenstored: use grant references instead of map_foreign_range
make xenstored use grantref rather than map_foreign_range (which can
only be used by privileged domains)
This patch modifies the xenstore daemon to use xc_gnttab_map_grant_ref
instead of xc_map_foreign_range where available.
Previous versions of this patch have been sent to xen-devel. See
http://lists.xensource.com/archives/html/xen-devel/2008-07/msg00610.html
http://lists.xensource.com/archives/html/xen-devel/2009-03/msg01492.html
Signed-off-by: Diego Ongaro <diego.ongaro@citrix.com>
Signed-off-by: Alex Zeffertt <alex.zeffertt@eu.citrix.com>
Signed-off-by: Daniel De Graaf <dgdegra@tycho.nsa.gov>
Acked-by: Ian Campbell <ian.campbell@citrix.com>
Cc: Ian Jackson <ian.jackson@eu.citrix.com>
Cc: Stefano Stabellini <stefano.stabellini@eu.citrix.com>
Committed-by: Ian Jackson <Ian.Jackson@eu.citrix.com>
Index: xen-4.2.0-testing/tools/xenstore/xenstored_domain.c
===================================================================
--- xen-4.2.0-testing.orig/tools/xenstore/xenstored_domain.c
+++ xen-4.2.0-testing/tools/xenstore/xenstored_domain.c
@@ -32,10 +32,8 @@
#include "xenstored_watch.h"
#include <xenctrl.h>
-#include <xen/grant_table.h>
static xc_interface **xc_handle;
-xc_gnttab **xcg_handle;
static evtchn_port_t virq_port;
xc_evtchn *xce_handle = NULL;
@@ -165,26 +163,6 @@ static int readchn(struct connection *co
return len;
}
-static void *map_interface(domid_t domid, unsigned long mfn)
-{
- if (*xcg_handle != NULL) {
- /* this is the preferred method */
- return xc_gnttab_map_grant_ref(*xcg_handle, domid,
- GNTTAB_RESERVED_XENSTORE, PROT_READ|PROT_WRITE);
- } else {
- return xc_map_foreign_range(*xc_handle, domid,
- getpagesize(), PROT_READ|PROT_WRITE, mfn);
- }
-}
-
-static void unmap_interface(void *interface)
-{
- if (*xcg_handle != NULL)
- xc_gnttab_munmap(*xcg_handle, interface, 1);
- else
- munmap(interface, getpagesize());
-}
-
static int destroy_domain(void *_domain)
{
struct domain *domain = _domain;
@@ -196,14 +174,8 @@ static int destroy_domain(void *_domain)
eprintf("> Unbinding port %i failed!\n", domain->port);
}
- if (domain->interface) {
- /* Domain 0 was mapped by dom0_init, so it must be unmapped
- using munmap() and not the grant unmap call. */
- if (domain->domid == 0)
- unmap_xenbus(domain->interface);
- else
- unmap_interface(domain->interface);
- }
+ if (domain->interface)
+ munmap(domain->interface, getpagesize());
fire_watches(NULL, "@releaseDomain", false);
@@ -372,7 +344,9 @@ void do_introduce(struct connection *con
domain = find_domain_by_domid(domid);
if (domain == NULL) {
- interface = map_interface(domid, mfn);
+ interface = xc_map_foreign_range(
+ *xc_handle, domid,
+ getpagesize(), PROT_READ|PROT_WRITE, mfn);
if (!interface) {
send_error(conn, errno);
return;
@@ -380,7 +354,7 @@ void do_introduce(struct connection *con
/* Hang domain off "in" until we're finished. */
domain = new_domain(in, domid, port);
if (!domain) {
- unmap_interface(interface);
+ munmap(interface, getpagesize());
send_error(conn, errno);
return;
}
@@ -572,18 +546,6 @@ void do_reset_watches(struct connection
send_ack(conn, XS_RESET_WATCHES);
}
-static int close_xc_handle(void *_handle)
-{
- xc_interface_close(*(xc_interface**)_handle);
- return 0;
-}
-
-static int close_xcg_handle(void *_handle)
-{
- xc_gnttab_close(*(xc_gnttab **)_handle);
- return 0;
-}
-
/* Returns the implicit path of a connection (only domains have this) */
const char *get_implicit_path(const struct connection *conn)
{
@@ -633,18 +595,6 @@ void domain_init(void)
if (!*xc_handle)
barf_perror("Failed to open connection to hypervisor");
- talloc_set_destructor(xc_handle, close_xc_handle);
-
- xcg_handle = talloc(talloc_autofree_context(), xc_gnttab*);
- if (!xcg_handle)
- barf_perror("Failed to allocate domain gnttab handle");
-
- *xcg_handle = xc_gnttab_open(NULL, 0);
- if (*xcg_handle < 0)
- xprintf("WARNING: Failed to open connection to gnttab\n");
- else
- talloc_set_destructor(xcg_handle, close_xcg_handle);
-
xce_handle = xc_evtchn_open(NULL, 0);
if (xce_handle == NULL)

View File

@ -0,0 +1,13 @@
--- 2013-01-08.orig/xen/arch/x86/domain.c 2013-01-08 00:00:00.000000000 +0100
+++ 2013-01-08/xen/arch/x86/domain.c 2013-01-15 15:46:17.000000000 +0100
@@ -834,7 +834,9 @@ int arch_set_info_guest(
v->arch.vgc_flags = flags;
- memcpy(v->arch.fpu_ctxt, &c.nat->fpu_ctxt, sizeof(c.nat->fpu_ctxt));
+ if ( flags & VGCF_I387_VALID )
+ memcpy(v->arch.fpu_ctxt, &c.nat->fpu_ctxt, sizeof(c.nat->fpu_ctxt));
+
if ( !compat )
{
memcpy(&v->arch.user_regs, &c.nat->user_regs, sizeof(c.nat->user_regs));

View File

@ -1,3 +1,45 @@
-------------------------------------------------------------------
Tue Jan 22 08:12:39 MST 2013 - carnold@novell.com
- bnc#797285 - VUL-0: Xen: XSA-34 (CVE-2013-0151) - nested
virtualization on 32-bit exposes host crash
CVE-2013-0151-xsa34.patch
- bnc#797287 - VUL-0: Xen: XSA-35 (CVE-2013-0152) - Nested HVM
exposes host to being driven out of memory by guest
CVE-2013-0152-xsa35.patch
-------------------------------------------------------------------
Thu Jan 17 14:13:52 MST 2013 - carnold@novell.com
- bnc#793717 - NetWare will not boot on Xen 4.2
xnloader.py
domUloader.py
pygrub-netware-xnloader.patch
Removed reverse-24757-use-grant-references.patch
-------------------------------------------------------------------
Wed Jan 16 11:26:29 MST 2013
- bnc#797523 - VUL-1: CVE-2012-6075: qemu / kvm-qemu: e1000
overflows under some conditions
CVE-2012-6075-xsa41.patch
-------------------------------------------------------------------
Tue Jan 15 13:19:36 MST 2013 - carnold@novell.com
- Mask the floating point exceptions for guests like NetWare on
machines that support XSAVE.
x86-fpu-context-conditional.patch
-------------------------------------------------------------------
Mon Jan 14 12:01:33 MST 2013 - carnold@novell.com
- fate##313584: pass bios information to XEN HVM guest
26341-hvm-firmware-passthrough.patch
26342-hvm-firmware-passthrough.patch
26343-hvm-firmware-passthrough.patch
26344-hvm-firmware-passthrough.patch
-------------------------------------------------------------------
Tue Jan 8 11:06:04 MST 2013 - carnold@novell.com

View File

@ -15,7 +15,6 @@
# Please submit bugfixes or comments via http://bugs.opensuse.org/
#
Name: xen
ExclusiveArch: %ix86 x86_64
%define xvers 4.2
@ -115,7 +114,7 @@ BuildRequires: kernel-syms
BuildRequires: module-init-tools
BuildRequires: xorg-x11
%endif
Version: 4.2.1_02
Version: 4.2.1_03
Release: 0
PreReq: %insserv_prereq %fillup_prereq
Summary: Xen Virtualization: Hypervisor (aka VMM aka Microkernel)
@ -217,7 +216,14 @@ Patch26330: 26330-VT-d-phantom-MSI.patch
Patch26331: 26331-IOMMU-phantom-dev-quirk.patch
Patch26332: 26332-x86-compat-show-guest-stack-mfn.patch
Patch26333: 26333-x86-get_page_type-assert.patch
Patch26341: 26341-hvm-firmware-passthrough.patch
Patch26342: 26342-hvm-firmware-passthrough.patch
Patch26343: 26343-hvm-firmware-passthrough.patch
Patch26344: 26344-hvm-firmware-passthrough.patch
Patch33: CVE-2012-5634-xsa33.patch
Patch34: CVE-2013-0151-xsa34.patch
Patch35: CVE-2013-0152-xsa35.patch
Patch41: CVE-2012-6075-xsa41.patch
# Upstream qemu patches
Patch100: VNC-Support-for-ExtendedKeyEvent-client-message.patch
# Our patches
@ -311,8 +317,7 @@ Patch458: ipxe-enable-nics.patch
Patch459: blktap-close-fifos.patch
Patch460: blktap-disable-debug-printf.patch
Patch461: xen-glibc217.patch
Patch462: reverse-24757-use-grant-references.patch
Patch463: xen-migration-bridge-check.patch
Patch462: xen-migration-bridge-check.patch
# Jim's domain lock patch
Patch480: xend-domain-lock.patch
Patch481: xend-domain-lock-sfex.patch
@ -725,7 +730,14 @@ tar xfj %{SOURCE6} -C $RPM_BUILD_DIR/%{xen_build_dir}/tools
%patch26331 -p1
%patch26332 -p1
%patch26333 -p1
%patch26341 -p1
%patch26342 -p1
%patch26343 -p1
%patch26344 -p1
%patch33 -p1
%patch34 -p1
%patch35 -p1
%patch41 -p1
# Qemu
%patch100 -p1
# Our patches
@ -817,7 +829,6 @@ tar xfj %{SOURCE6} -C $RPM_BUILD_DIR/%{xen_build_dir}/tools
%patch460 -p1
%patch461 -p1
%patch462 -p1
%patch463 -p1
%patch480 -p1
%patch481 -p1
%patch500 -p1

62
xnloader.py Normal file
View File

@ -0,0 +1,62 @@
# NetWare-specific operations
#
# Copyright (c) 2013 Suse Linux Products.
# Author: Charles Arnold <carnold@suse.com>
#
# This software may be freely redistributed under the terms of the GNU
# general public license.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
# Binary patching of xnloader.sys
# For launching NetWare on Xen 4.2 and newer
import os, sys, base64
CODE_OFFSET=0x49F5
NUMBER_OF_CODE_BYTES=17
ORIGINAL_CODE="BA00080000C786FC1F0000FFFFFFFF31C9"
PATCHED_CODE="BAF8070000834C961CFFB9080000009090"
XNLOADER_SYS_MD5SUM="eb76cce2a2d45928ea2bf26e01430af2"
def patch_netware_loader(loader):
"""Open the given xnloader.sys file and patch the relevant code hunk."""
# domUloader calls this with all kernels so perhaps this is not the NetWare loader
md5sum_cmd = 'md5sum ' + loader
p = os.popen(md5sum_cmd)
sum = p.read().split()[0]
p.close()
if sum != XNLOADER_SYS_MD5SUM:
return
try:
fd = os.open(loader, os.O_RDWR)
except Exception, e:
print >>sys.stderr, e
raise
# Validate minimum size for I/O
stat = os.fstat(fd)
if stat.st_size < CODE_OFFSET+NUMBER_OF_CODE_BYTES:
os.close(fd)
return
# Seek to location of code hunk
os.lseek(fd, CODE_OFFSET, os.SEEK_SET)
# Read code bytes at offset
buf = os.read(fd, NUMBER_OF_CODE_BYTES)
code_as_hex = base64.b16encode(buf)
if code_as_hex == ORIGINAL_CODE:
# Seek back to start location of the code hunk
os.lseek(fd, CODE_OFFSET, os.SEEK_SET)
# Convert the PATCHED_CODE string to raw binary
code_as_bin = base64.b16decode(PATCHED_CODE)
# Write the patched code
os.write(fd, code_as_bin)
os.close(fd)