[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Xen-changelog] [xen-unstable] Merge



# HG changeset patch
# User Tim Deegan <Tim.Deegan@xxxxxxxxxx>
# Date 1307350197 -3600
# Node ID 68947fbeaa76728a14b800132ca3e000dbb519fd
# Parent  840e161428246f0173cb41c2409a0b9481b4a457
# Parent  0c0884fd8b494932a4b707e339cbe1b881d09103
Merge
---


diff -r 840e16142824 -r 68947fbeaa76 
tools/firmware/hvmloader/32bitbios_support.c
--- a/tools/firmware/hvmloader/32bitbios_support.c      Thu Jun 02 13:16:52 
2011 +0100
+++ b/tools/firmware/hvmloader/32bitbios_support.c      Mon Jun 06 09:49:57 
2011 +0100
@@ -67,7 +67,7 @@
      */
     reloc_size = reloc_off;
     printf("%d bytes of ROMBIOS high-memory extensions:\n", reloc_size);
-    highbiosarea = mem_alloc(reloc_size, 0);
+    highbiosarea = mem_alloc(reloc_size, 1024);
     BUG_ON(highbiosarea == NULL);
     printf("  Relocating to 0x%x-0x%x ... ",
            (uint32_t)&highbiosarea[0],
diff -r 840e16142824 -r 68947fbeaa76 tools/firmware/hvmloader/acpi/acpi2_0.h
--- a/tools/firmware/hvmloader/acpi/acpi2_0.h   Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/firmware/hvmloader/acpi/acpi2_0.h   Mon Jun 06 09:49:57 2011 +0100
@@ -98,11 +98,6 @@
 };
 
 /*
- * The maximum number of entrys in RSDT or XSDT.
- */
-#define ACPI_MAX_NUM_TABLES 5
-
-/*
  * Root System Description Table (RSDT).
  */
 struct acpi_20_rsdt {
@@ -383,7 +378,6 @@
 #pragma pack ()
 
 void acpi_build_tables(unsigned int physical);
-extern uint32_t madt_csum_addr, madt_lapic0_addr;
 
 #endif /* _ACPI_2_0_H_ */
 
diff -r 840e16142824 -r 68947fbeaa76 tools/firmware/hvmloader/acpi/build.c
--- a/tools/firmware/hvmloader/acpi/build.c     Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/firmware/hvmloader/acpi/build.c     Mon Jun 06 09:49:57 2011 +0100
@@ -25,9 +25,6 @@
 #define align16(sz)        (((sz) + 15) & ~15)
 #define fixed_strcpy(d, s) strncpy((d), (s), sizeof(d))
 
-/* MADT parameters for filling in bios_info structure for DSDT. */
-uint32_t madt_csum_addr, madt_lapic0_addr;
-
 extern struct acpi_20_rsdp Rsdp;
 extern struct acpi_20_rsdt Rsdt;
 extern struct acpi_20_xsdt Xsdt;
@@ -35,6 +32,21 @@
 extern struct acpi_20_facs Facs;
 
 /*
+ * Located at ACPI_INFO_PHYSICAL_ADDRESS.
+ *
+ * This must match the Field("BIOS"....) definition in the DSDT.
+ */
+struct acpi_info {
+    uint8_t  com1_present:1;    /* 0[0] - System has COM1? */
+    uint8_t  com2_present:1;    /* 0[1] - System has COM2? */
+    uint8_t  lpt1_present:1;    /* 0[2] - System has LPT1? */
+    uint8_t  hpet_present:1;    /* 0[3] - System has HPET? */
+    uint32_t pci_min, pci_len;  /* 4, 8 - PCI I/O hole boundaries */
+    uint32_t madt_csum_addr;    /* 12   - Address of MADT checksum */
+    uint32_t madt_lapic0_addr;  /* 16   - Address of first MADT LAPIC struct */
+};
+
+/*
  * Alternative DSDTs we get linked against. A cover-all DSDT for up to the
  * implementation-defined maximum number of VCPUs, and an alternative for use
  * when a guest can only have up to 15 VCPUs.
@@ -68,12 +80,21 @@
     return (inb(0x88) == 0x1F);
 }
 
-static int construct_madt(struct acpi_20_madt *madt)
+static struct acpi_20_madt *construct_madt(struct acpi_info *info)
 {
+    struct acpi_20_madt           *madt;
     struct acpi_20_madt_intsrcovr *intsrcovr;
     struct acpi_20_madt_ioapic    *io_apic;
     struct acpi_20_madt_lapic     *lapic;
-    int i, offset = 0;
+    int i, sz;
+
+    sz  = sizeof(struct acpi_20_madt);
+    sz += sizeof(struct acpi_20_madt_intsrcovr) * 16;
+    sz += sizeof(struct acpi_20_madt_ioapic);
+    sz += sizeof(struct acpi_20_madt_lapic) * nr_processor_objects;
+
+    madt = mem_alloc(sz, 16);
+    if (!madt) return NULL;
 
     memset(madt, 0, sizeof(*madt));
     madt->header.signature    = ACPI_2_0_MADT_SIGNATURE;
@@ -85,7 +106,6 @@
     madt->header.creator_revision = ACPI_CREATOR_REVISION;
     madt->lapic_addr = LAPIC_BASE_ADDRESS;
     madt->flags      = ACPI_PCAT_COMPAT;
-    offset += sizeof(*madt);
 
     intsrcovr = (struct acpi_20_madt_intsrcovr *)(madt + 1);
     for ( i = 0; i < 16; i++ )
@@ -113,7 +133,6 @@
             continue;
         }
 
-        offset += sizeof(*intsrcovr);
         intsrcovr++;
     }
 
@@ -123,10 +142,9 @@
     io_apic->length      = sizeof(*io_apic);
     io_apic->ioapic_id   = IOAPIC_ID;
     io_apic->ioapic_addr = IOAPIC_BASE_ADDRESS;
-    offset += sizeof(*io_apic);
 
     lapic = (struct acpi_20_madt_lapic *)(io_apic + 1);
-    madt_lapic0_addr = (uint32_t)lapic;
+    info->madt_lapic0_addr = (uint32_t)lapic;
     for ( i = 0; i < nr_processor_objects; i++ )
     {
         memset(lapic, 0, sizeof(*lapic));
@@ -138,20 +156,23 @@
         lapic->flags = ((i < hvm_info->nr_vcpus) &&
                         test_bit(i, hvm_info->vcpu_online)
                         ? ACPI_LOCAL_APIC_ENABLED : 0);
-        offset += sizeof(*lapic);
         lapic++;
     }
 
-    madt->header.length = offset;
-    set_checksum(madt, offsetof(struct acpi_header, checksum), offset);
-    madt_csum_addr = (uint32_t)&madt->header.checksum;
+    madt->header.length = (unsigned char *)lapic - (unsigned char *)madt;
+    set_checksum(madt, offsetof(struct acpi_header, checksum),
+                 madt->header.length);
+    info->madt_csum_addr = (uint32_t)&madt->header.checksum;
 
-    return align16(offset);
+    return madt;
 }
 
-static int construct_hpet(struct acpi_20_hpet *hpet)
+static struct acpi_20_hpet *construct_hpet(void)
 {
-    int offset;
+    struct acpi_20_hpet *hpet;
+
+    hpet = mem_alloc(sizeof(*hpet), 16);
+    if (!hpet) return NULL;
 
     memset(hpet, 0, sizeof(*hpet));
     hpet->header.signature    = ACPI_2_0_HPET_SIGNATURE;
@@ -163,20 +184,21 @@
     hpet->header.creator_revision = ACPI_CREATOR_REVISION;
     hpet->timer_block_id      = 0x8086a201;
     hpet->addr.address        = ACPI_HPET_ADDRESS;
-    offset = sizeof(*hpet);
 
-    hpet->header.length = offset;
-    set_checksum(hpet, offsetof(struct acpi_header, checksum), offset);
-
-    return offset;
+    hpet->header.length = sizeof(*hpet);
+    set_checksum(hpet, offsetof(struct acpi_header, checksum),
+                 hpet->header.length = sizeof(*hpet));
+    return hpet;
 }
 
-static int construct_secondary_tables(uint8_t *buf, unsigned long *table_ptrs)
+static int construct_secondary_tables(unsigned long *table_ptrs,
+                                      struct acpi_info *info)
 {
-    int offset = 0, nr_tables = 0;
+    int nr_tables = 0;
     struct acpi_20_madt *madt;
     struct acpi_20_hpet *hpet;
     struct acpi_20_tcpa *tcpa;
+    unsigned char *ssdt;
     static const uint16_t tis_signature[] = {0x0001, 0x0001, 0x0001};
     uint16_t *tis_hdr;
     void *lasa;
@@ -184,22 +206,23 @@
     /* MADT. */
     if ( (hvm_info->nr_vcpus > 1) || hvm_info->apic_mode )
     {
-        madt = (struct acpi_20_madt *)&buf[offset];
-        offset += construct_madt(madt);
+        madt = construct_madt(info);
+        if (!madt) return -1;
         table_ptrs[nr_tables++] = (unsigned long)madt;
     }
 
     /* HPET. Always included in DSDT, so always include it here too. */
     /* (And it's unconditionally required by Windows SVVP tests.) */
-    hpet = (struct acpi_20_hpet *)&buf[offset];
-    offset += construct_hpet(hpet);
+    hpet = construct_hpet();
+    if (!hpet) return -1;
     table_ptrs[nr_tables++] = (unsigned long)hpet;
 
-    if ( battery_port_exists() ) 
+    if ( battery_port_exists() )
     {
-        table_ptrs[nr_tables++] = (unsigned long)&buf[offset];
-        memcpy(&buf[offset], ssdt_pm, sizeof(ssdt_pm));
-        offset += align16(sizeof(ssdt_pm));
+        ssdt = mem_alloc(sizeof(ssdt_pm), 16);
+        if (!ssdt) return -1;
+        memcpy(ssdt, ssdt_pm, sizeof(ssdt_pm));
+        table_ptrs[nr_tables++] = (unsigned long)ssdt;
     }
 
     /* TPM TCPA and SSDT. */
@@ -208,13 +231,14 @@
          (tis_hdr[1] == tis_signature[1]) &&
          (tis_hdr[2] == tis_signature[2]) )
     {
-        memcpy(&buf[offset], ssdt_tpm, sizeof(ssdt_tpm));
-        table_ptrs[nr_tables++] = (unsigned long)&buf[offset];
-        offset += align16(sizeof(ssdt_tpm));
+        ssdt = mem_alloc(sizeof(ssdt_tpm), 16);
+        if (!ssdt) return -1;
+        memcpy(ssdt, ssdt_tpm, sizeof(ssdt_tpm));
+        table_ptrs[nr_tables++] = (unsigned long)ssdt;
 
-        tcpa = (struct acpi_20_tcpa *)&buf[offset];
+        tcpa = mem_alloc(sizeof(struct acpi_20_tcpa), 16);
+        if (!tcpa) return -1;
         memset(tcpa, 0, sizeof(*tcpa));
-        offset += align16(sizeof(*tcpa));
         table_ptrs[nr_tables++] = (unsigned long)tcpa;
 
         tcpa->header.signature = ACPI_2_0_TCPA_SIGNATURE;
@@ -225,7 +249,7 @@
         tcpa->header.oem_revision = ACPI_OEM_REVISION;
         tcpa->header.creator_id   = ACPI_CREATOR_ID;
         tcpa->header.creator_revision = ACPI_CREATOR_REVISION;
-        if ( (lasa = mem_alloc(ACPI_2_0_TCPA_LAML_SIZE, 0)) != NULL )
+        if ( (lasa = mem_alloc(ACPI_2_0_TCPA_LAML_SIZE, 16)) != NULL )
         {
             tcpa->lasa = virt_to_phys(lasa);
             tcpa->laml = ACPI_2_0_TCPA_LAML_SIZE;
@@ -237,13 +261,12 @@
     }
 
     table_ptrs[nr_tables] = 0;
-    return align16(offset);
+    return nr_tables;
 }
 
-static void __acpi_build_tables(unsigned int physical,
-                                uint8_t *buf,
-                                int *low_sz, int *high_sz)
+void acpi_build_tables(unsigned int physical)
 {
+    struct acpi_info *acpi_info = (struct acpi_info 
*)ACPI_INFO_PHYSICAL_ADDRESS;
     struct acpi_20_rsdp *rsdp;
     struct acpi_20_rsdt *rsdt;
     struct acpi_20_xsdt *xsdt;
@@ -252,27 +275,28 @@
     struct acpi_20_facs *facs;
     unsigned char       *dsdt;
     unsigned long        secondary_tables[16];
-    int                  offset = 0, i;
+    int                  nr_secondaries, i;
 
     /*
      * Fill in high-memory data structures, starting at @buf.
      */
 
-    facs = (struct acpi_20_facs *)&buf[offset];
+    facs = mem_alloc(sizeof(struct acpi_20_facs), 16);
+    if (!facs) goto oom;
     memcpy(facs, &Facs, sizeof(struct acpi_20_facs));
-    offset += align16(sizeof(struct acpi_20_facs));
 
-    dsdt = (unsigned char *)&buf[offset];
     if ( hvm_info->nr_vcpus <= 15 )
     {
+        dsdt = mem_alloc(dsdt_15cpu_len, 16);
+        if (!dsdt) goto oom;
         memcpy(dsdt, &dsdt_15cpu, dsdt_15cpu_len);
-        offset += align16(dsdt_15cpu_len);
         nr_processor_objects = 15;
     }
     else
     {
+        dsdt = mem_alloc(dsdt_anycpu_len, 16);
+        if (!dsdt) goto oom;
         memcpy(dsdt, &dsdt_anycpu, dsdt_anycpu_len);
-        offset += align16(dsdt_anycpu_len);
         nr_processor_objects = HVM_MAX_VCPUS;
     }
 
@@ -284,9 +308,9 @@
      * compatible revision 1 FADT that is linked with the RSDT. Refer to:
      *     http://www.acpi.info/presentations/S01USMOBS169_OS%20new.ppt
      */
-    fadt_10 = (struct acpi_10_fadt *)&buf[offset];
+    fadt_10 = mem_alloc(sizeof(struct acpi_10_fadt), 16);
+    if (!fadt_10) goto oom;
     memcpy(fadt_10, &Fadt, sizeof(struct acpi_10_fadt));
-    offset += align16(sizeof(struct acpi_10_fadt));
     fadt_10->header.length = sizeof(struct acpi_10_fadt);
     fadt_10->header.revision = ACPI_1_0_FADT_REVISION;
     fadt_10->dsdt          = (unsigned long)dsdt;
@@ -295,9 +319,9 @@
                  offsetof(struct acpi_header, checksum),
                  sizeof(struct acpi_10_fadt));
 
-    fadt = (struct acpi_20_fadt *)&buf[offset];
+    fadt = mem_alloc(sizeof(struct acpi_20_fadt), 16);
+    if (!fadt) goto oom;
     memcpy(fadt, &Fadt, sizeof(struct acpi_20_fadt));
-    offset += align16(sizeof(struct acpi_20_fadt));
     fadt->dsdt   = (unsigned long)dsdt;
     fadt->x_dsdt = (unsigned long)dsdt;
     fadt->firmware_ctrl   = (unsigned long)facs;
@@ -306,42 +330,42 @@
                  offsetof(struct acpi_header, checksum),
                  sizeof(struct acpi_20_fadt));
 
-    offset += construct_secondary_tables(&buf[offset], secondary_tables);
+    nr_secondaries = construct_secondary_tables(secondary_tables, acpi_info);
+    if ( nr_secondaries < 0 )
+        goto oom;
 
-    xsdt = (struct acpi_20_xsdt *)&buf[offset];
+    xsdt = mem_alloc(sizeof(struct acpi_20_xsdt)+
+                     sizeof(uint64_t)*nr_secondaries,
+                     16);
+    if (!xsdt) goto oom;
     memcpy(xsdt, &Xsdt, sizeof(struct acpi_header));
     xsdt->entry[0] = (unsigned long)fadt;
     for ( i = 0; secondary_tables[i]; i++ )
         xsdt->entry[i+1] = secondary_tables[i];
     xsdt->header.length = sizeof(struct acpi_header) + (i+1)*sizeof(uint64_t);
-    offset += align16(xsdt->header.length);
     set_checksum(xsdt,
                  offsetof(struct acpi_header, checksum),
                  xsdt->header.length);
 
-    rsdt = (struct acpi_20_rsdt *)&buf[offset];
+    rsdt = mem_alloc(sizeof(struct acpi_20_rsdt)+
+                     sizeof(uint32_t)*nr_secondaries,
+                     16);
+    if (!rsdt) goto oom;
     memcpy(rsdt, &Rsdt, sizeof(struct acpi_header));
     rsdt->entry[0] = (unsigned long)fadt_10;
     for ( i = 0; secondary_tables[i]; i++ )
         rsdt->entry[i+1] = secondary_tables[i];
     rsdt->header.length = sizeof(struct acpi_header) + (i+1)*sizeof(uint32_t);
-    offset += align16(rsdt->header.length);
     set_checksum(rsdt,
                  offsetof(struct acpi_header, checksum),
                  rsdt->header.length);
 
-    *high_sz = offset;
-
     /*
-     * Fill in low-memory data structures: bios_info_table and RSDP.
+     * Fill in low-memory data structures: acpi_info and RSDP.
      */
-    buf = (uint8_t *)physical;
-    offset = 0;
-
-    rsdp = (struct acpi_20_rsdp *)&buf[offset];
+    rsdp = (struct acpi_20_rsdp *)physical;
 
     memcpy(rsdp, &Rsdp, sizeof(struct acpi_20_rsdp));
-    offset += align16(sizeof(struct acpi_20_rsdp));
     rsdp->rsdt_address = (unsigned long)rsdt;
     rsdp->xsdt_address = (unsigned long)xsdt;
     set_checksum(rsdp,
@@ -351,27 +375,19 @@
                  offsetof(struct acpi_20_rsdp, extended_checksum),
                  sizeof(struct acpi_20_rsdp));
 
-    *low_sz = offset;
-}
+    memset(acpi_info, 0, sizeof(*acpi_info));
+    acpi_info->com1_present = uart_exists(0x3f8);
+    acpi_info->com2_present = uart_exists(0x2f8);
+    acpi_info->lpt1_present = lpt_exists(0x378);
+    acpi_info->hpet_present = hpet_exists(ACPI_HPET_ADDRESS);
+    acpi_info->pci_min = pci_mem_start;
+    acpi_info->pci_len = pci_mem_end - pci_mem_start;
 
-void acpi_build_tables(unsigned int physical)
-{
-    int high_sz, low_sz;
-    uint8_t *buf;
+    return;
 
-    /* Find out size of high-memory ACPI data area. */
-    buf = (uint8_t *)&_end;
-    __acpi_build_tables(physical, buf, &low_sz, &high_sz);
-    memset(buf, 0, high_sz);
+oom:
+    printf("unable to build ACPI tables: out of memory\n");
 
-    /* Allocate data area and set up ACPI tables there. */
-    buf = mem_alloc(high_sz, 0);
-    __acpi_build_tables(physical, buf, &low_sz, &high_sz);
-
-    printf(" - Lo data: %08x-%08x\n"
-           " - Hi data: %08lx-%08lx\n",
-           physical, physical + low_sz - 1,
-           (unsigned long)buf, (unsigned long)buf + high_sz - 1);
 }
 
 /*
diff -r 840e16142824 -r 68947fbeaa76 tools/firmware/hvmloader/acpi/dsdt.asl
--- a/tools/firmware/hvmloader/acpi/dsdt.asl    Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/firmware/hvmloader/acpi/dsdt.asl    Mon Jun 06 09:49:57 2011 +0100
@@ -61,8 +61,8 @@
 
     Scope (\_SB)
     {
-       /* BIOS_INFO_PHYSICAL_ADDRESS == 0xEA000 */
-       OperationRegion(BIOS, SystemMemory, 0xEA000, 24)
+       /* ACPI_INFO_PHYSICAL_ADDRESS == 0x9F000 */
+       OperationRegion(BIOS, SystemMemory, 0x9F000, 24)
        Field(BIOS, ByteAcc, NoLock, Preserve) {
            UAR1, 1,
            UAR2, 1,
diff -r 840e16142824 -r 68947fbeaa76 tools/firmware/hvmloader/config.h
--- a/tools/firmware/hvmloader/config.h Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/firmware/hvmloader/config.h Mon Jun 06 09:49:57 2011 +0100
@@ -62,6 +62,7 @@
 /* Memory map. */
 #define SCRATCH_PHYSICAL_ADDRESS      0x00010000
 #define HYPERCALL_PHYSICAL_ADDRESS    0x00080000
+#define ACPI_INFO_PHYSICAL_ADDRESS    0x0009F000
 #define VGABIOS_PHYSICAL_ADDRESS      0x000C0000
 #define HVMLOADER_PHYSICAL_ADDRESS    0x00100000
 
diff -r 840e16142824 -r 68947fbeaa76 tools/firmware/hvmloader/rombios.c
--- a/tools/firmware/hvmloader/rombios.c        Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/firmware/hvmloader/rombios.c        Mon Jun 06 09:49:57 2011 +0100
@@ -67,36 +67,21 @@
 
 static void rombios_setup_bios_info(void)
 {
-    struct bios_info *bios_info;
+    struct rombios_info *info;
 
-    bios_info = (struct bios_info *)BIOS_INFO_PHYSICAL_ADDRESS;
-    memset(bios_info, 0, sizeof(*bios_info));
-    bios_info->com1_present = uart_exists(0x3f8);
-    bios_info->com2_present = uart_exists(0x2f8);
-    bios_info->lpt1_present = lpt_exists(0x378);
-    bios_info->hpet_present = hpet_exists(ACPI_HPET_ADDRESS);
-    bios_info->madt_csum_addr = madt_csum_addr;
-    bios_info->madt_lapic0_addr = madt_lapic0_addr;
+    info = (struct rombios_info *)BIOS_INFO_PHYSICAL_ADDRESS;
+    memset(info, 0, sizeof(*info));
 }
 
 static void rombios_relocate(void)
 {
     uint32_t bioshigh;
-    struct bios_info *bios_info;
+    struct rombios_info *info;
 
     bioshigh = rombios_highbios_setup();
 
-    bios_info = (struct bios_info *)BIOS_INFO_PHYSICAL_ADDRESS;
-    bios_info->bios32_entry = bioshigh;
-}
-
-static void rombios_finish_bios_info(void)
-{
-    struct bios_info *bios_info;
-
-    bios_info = (struct bios_info *)BIOS_INFO_PHYSICAL_ADDRESS;
-    bios_info->pci_min = pci_mem_start;
-    bios_info->pci_len = pci_mem_end - pci_mem_start;
+    info = (struct rombios_info *)BIOS_INFO_PHYSICAL_ADDRESS;
+    info->bios32_entry = bioshigh;
 }
 
 /*
@@ -177,7 +162,7 @@
     .optionrom_end = OPTIONROM_PHYSICAL_END,
 
     .bios_info_setup = rombios_setup_bios_info,
-    .bios_info_finish = rombios_finish_bios_info,
+    .bios_info_finish = NULL,
 
     .bios_relocate = rombios_relocate,
 
diff -r 840e16142824 -r 68947fbeaa76 tools/firmware/hvmloader/util.c
--- a/tools/firmware/hvmloader/util.c   Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/firmware/hvmloader/util.c   Mon Jun 06 09:49:57 2011 +0100
@@ -312,9 +312,9 @@
     xen_pfn_t mfn;
     uint32_t s, e;
 
-    /* Align to at least one kilobyte. */
-    if ( align < 1024 )
-        align = 1024;
+    /* Align to at least 16 bytes. */
+    if ( align < 16 )
+        align = 16;
 
     s = (reserve + align) & ~(align - 1);
     e = s + size - 1;
@@ -366,9 +366,9 @@
 {
     uint32_t s, e;
 
-    /* Align to at least one kilobyte. */
-    if ( align < 1024 )
-        align = 1024;
+    /* Align to at least 16 bytes. */
+    if ( align < 16 )
+        align = 16;
 
     s = (scratch_start + align - 1) & ~(align - 1);
     e = s + size - 1;
diff -r 840e16142824 -r 68947fbeaa76 tools/firmware/rombios/config.h
--- a/tools/firmware/rombios/config.h   Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/firmware/rombios/config.h   Mon Jun 06 09:49:57 2011 +0100
@@ -27,17 +27,10 @@
 #define PFFLAG_ROM_LOCK 1 /* Sets whether ROM memory area is RW or RO */
 
 /* Located at BIOS_INFO_PHYSICAL_ADDRESS. */
-struct bios_info {
-    uint8_t  com1_present:1;    /* 0[0] - System has COM1? */
-    uint8_t  com2_present:1;    /* 0[1] - System has COM2? */
-    uint8_t  lpt1_present:1;    /* 0[2] - System has LPT1? */
-    uint8_t  hpet_present:1;    /* 0[3] - System has HPET? */
-    uint32_t pci_min, pci_len;  /* 4, 8 - PCI I/O hole boundaries */
-    uint32_t madt_csum_addr;    /* 12   - Address of MADT checksum */
-    uint32_t madt_lapic0_addr;  /* 16   - Address of first MADT LAPIC struct */
-    uint32_t bios32_entry;      /* 20   - Entry point for 32-bit BIOS */
+struct rombios_info {
+    uint32_t bios32_entry;      /* 0   - Entry point for 32-bit BIOS */
 };
-#define BIOSINFO_OFF_bios32_entry 20
+#define BIOSINFO_OFF_bios32_entry 0
 
 #endif
 
diff -r 840e16142824 -r 68947fbeaa76 tools/hotplug/Linux/xen-hotplug-common.sh
--- a/tools/hotplug/Linux/xen-hotplug-common.sh Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/hotplug/Linux/xen-hotplug-common.sh Mon Jun 06 09:49:57 2011 +0100
@@ -106,7 +106,7 @@
 #
 call_hooks() {
   for f in /etc/xen/scripts/${1}-${2}.d/*.hook; do
-    [ -x "$f" ] && . "$f"
+    if [ -x "$f" ]; then . "$f"; fi
   done
 }
 
diff -r 840e16142824 -r 68947fbeaa76 tools/libxc/xc_cpufeature.h
--- a/tools/libxc/xc_cpufeature.h       Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxc/xc_cpufeature.h       Mon Jun 06 09:49:57 2011 +0100
@@ -17,128 +17,112 @@
 #ifndef __LIBXC_CPUFEATURE_H
 #define __LIBXC_CPUFEATURE_H
 
-/* Intel-defined CPU features, CPUID level 0x00000001 (edx), word 0 */
-#define X86_FEATURE_FPU                (0*32+ 0) /* Onboard FPU */
-#define X86_FEATURE_VME                (0*32+ 1) /* Virtual Mode Extensions */
-#define X86_FEATURE_DE         (0*32+ 2) /* Debugging Extensions */
-#define X86_FEATURE_PSE        (0*32+ 3) /* Page Size Extensions */
-#define X86_FEATURE_TSC                (0*32+ 4) /* Time Stamp Counter */
-#define X86_FEATURE_MSR                (0*32+ 5) /* Model-Specific Registers, 
RDMSR, WRMSR */
-#define X86_FEATURE_PAE                (0*32+ 6) /* Physical Address 
Extensions */
-#define X86_FEATURE_MCE                (0*32+ 7) /* Machine Check Architecture 
*/
-#define X86_FEATURE_CX8                (0*32+ 8) /* CMPXCHG8 instruction */
-#define X86_FEATURE_APIC       (0*32+ 9) /* Onboard APIC */
-#define X86_FEATURE_SEP                (0*32+11) /* SYSENTER/SYSEXIT */
-#define X86_FEATURE_MTRR       (0*32+12) /* Memory Type Range Registers */
-#define X86_FEATURE_PGE                (0*32+13) /* Page Global Enable */
-#define X86_FEATURE_MCA                (0*32+14) /* Machine Check Architecture 
*/
-#define X86_FEATURE_CMOV       (0*32+15) /* CMOV instruction (FCMOVCC and 
FCOMI too if FPU present) */
-#define X86_FEATURE_PAT                (0*32+16) /* Page Attribute Table */
-#define X86_FEATURE_PSE36      (0*32+17) /* 36-bit PSEs */
-#define X86_FEATURE_PN         (0*32+18) /* Processor serial number */
-#define X86_FEATURE_CLFLSH     (0*32+19) /* Supports the CLFLUSH instruction */
-#define X86_FEATURE_DS         (0*32+21) /* Debug Store */
-#define X86_FEATURE_ACPI       (0*32+22) /* ACPI via MSR */
-#define X86_FEATURE_MMX                (0*32+23) /* Multimedia Extensions */
-#define X86_FEATURE_FXSR       (0*32+24) /* FXSAVE and FXRSTOR instructions 
(fast save and restore */
-                                         /* of FPU context), and CR4.OSFXSR 
available */
-#define X86_FEATURE_XMM                (0*32+25) /* Streaming SIMD Extensions 
*/
-#define X86_FEATURE_XMM2       (0*32+26) /* Streaming SIMD Extensions-2 */
-#define X86_FEATURE_SELFSNOOP  (0*32+27) /* CPU self snoop */
-#define X86_FEATURE_HT         (0*32+28) /* Hyper-Threading */
-#define X86_FEATURE_ACC                (0*32+29) /* Automatic clock control */
-#define X86_FEATURE_IA64       (0*32+30) /* IA-64 processor */
-#define X86_FEATURE_PBE                (0*32+31) /* Pending Break Enable */
+/* Intel-defined CPU features, CPUID level 0x00000001 (edx) */
+#define X86_FEATURE_FPU          0 /* Onboard FPU */
+#define X86_FEATURE_VME          1 /* Virtual Mode Extensions */
+#define X86_FEATURE_DE           2 /* Debugging Extensions */
+#define X86_FEATURE_PSE          3 /* Page Size Extensions */
+#define X86_FEATURE_TSC          4 /* Time Stamp Counter */
+#define X86_FEATURE_MSR          5 /* Model-Specific Registers, RDMSR, WRMSR */
+#define X86_FEATURE_PAE          6 /* Physical Address Extensions */
+#define X86_FEATURE_MCE          7 /* Machine Check Architecture */
+#define X86_FEATURE_CX8          8 /* CMPXCHG8 instruction */
+#define X86_FEATURE_APIC         9 /* Onboard APIC */
+#define X86_FEATURE_SEP         11 /* SYSENTER/SYSEXIT */
+#define X86_FEATURE_MTRR        12 /* Memory Type Range Registers */
+#define X86_FEATURE_PGE         13 /* Page Global Enable */
+#define X86_FEATURE_MCA         14 /* Machine Check Architecture */
+#define X86_FEATURE_CMOV        15 /* CMOV instruction */
+#define X86_FEATURE_PAT         16 /* Page Attribute Table */
+#define X86_FEATURE_PSE36       17 /* 36-bit PSEs */
+#define X86_FEATURE_PN          18 /* Processor serial number */
+#define X86_FEATURE_CLFLSH      19 /* Supports the CLFLUSH instruction */
+#define X86_FEATURE_DS          21 /* Debug Store */
+#define X86_FEATURE_ACPI        22 /* ACPI via MSR */
+#define X86_FEATURE_MMX         23 /* Multimedia Extensions */
+#define X86_FEATURE_FXSR        24 /* FXSAVE and FXRSTOR instructions */
+#define X86_FEATURE_XMM         25 /* Streaming SIMD Extensions */
+#define X86_FEATURE_XMM2        26 /* Streaming SIMD Extensions-2 */
+#define X86_FEATURE_SELFSNOOP   27 /* CPU self snoop */
+#define X86_FEATURE_HT          28 /* Hyper-Threading */
+#define X86_FEATURE_ACC         29 /* Automatic clock control */
+#define X86_FEATURE_IA64        30 /* IA-64 processor */
+#define X86_FEATURE_PBE         31 /* Pending Break Enable */
 
-/* AMD-defined CPU features, CPUID level 0x80000001, word 1 */
+/* AMD-defined CPU features, CPUID level 0x80000001 */
 /* Don't duplicate feature flags which are redundant with Intel! */
-#define X86_FEATURE_SYSCALL    (1*32+11) /* SYSCALL/SYSRET */
-#define X86_FEATURE_MP         (1*32+19) /* MP Capable. */
-#define X86_FEATURE_NX         (1*32+20) /* Execute Disable */
-#define X86_FEATURE_MMXEXT     (1*32+22) /* AMD MMX extensions */
-#define X86_FEATURE_FFXSR       (1*32+25) /* FFXSR instruction optimizations */
-#define X86_FEATURE_PAGE1GB    (1*32+26) /* 1Gb large page support */
-#define X86_FEATURE_RDTSCP     (1*32+27) /* RDTSCP */
-#define X86_FEATURE_LM         (1*32+29) /* Long Mode (x86-64) */
-#define X86_FEATURE_3DNOWEXT   (1*32+30) /* AMD 3DNow! extensions */
-#define X86_FEATURE_3DNOW      (1*32+31) /* 3DNow! */
+#define X86_FEATURE_SYSCALL     11 /* SYSCALL/SYSRET */
+#define X86_FEATURE_MP          19 /* MP Capable. */
+#define X86_FEATURE_NX          20 /* Execute Disable */
+#define X86_FEATURE_MMXEXT      22 /* AMD MMX extensions */
+#define X86_FEATURE_FFXSR       25 /* FFXSR instruction optimizations */
+#define X86_FEATURE_PAGE1GB     26 /* 1Gb large page support */
+#define X86_FEATURE_RDTSCP      27 /* RDTSCP */
+#define X86_FEATURE_LM          29 /* Long Mode (x86-64) */
+#define X86_FEATURE_3DNOWEXT    30 /* AMD 3DNow! extensions */
+#define X86_FEATURE_3DNOW       31 /* 3DNow! */
 
-/* Transmeta-defined CPU features, CPUID level 0x80860001, word 2 */
-#define X86_FEATURE_RECOVERY   (2*32+ 0) /* CPU in recovery mode */
-#define X86_FEATURE_LONGRUN    (2*32+ 1) /* Longrun power control */
-#define X86_FEATURE_LRTI       (2*32+ 3) /* LongRun table interface */
+/* Intel-defined CPU features, CPUID level 0x00000001 (ecx) */
+#define X86_FEATURE_XMM3         0 /* Streaming SIMD Extensions-3 */
+#define X86_FEATURE_PCLMULQDQ    1 /* Carry-less multiplication */
+#define X86_FEATURE_DTES64       2 /* 64-bit Debug Store */
+#define X86_FEATURE_MWAIT        3 /* Monitor/Mwait support */
+#define X86_FEATURE_DSCPL        4 /* CPL Qualified Debug Store */
+#define X86_FEATURE_VMXE         5 /* Virtual Machine Extensions */
+#define X86_FEATURE_SMXE         6 /* Safer Mode Extensions */
+#define X86_FEATURE_EST          7 /* Enhanced SpeedStep */
+#define X86_FEATURE_TM2          8 /* Thermal Monitor 2 */
+#define X86_FEATURE_SSSE3        9 /* Supplemental Streaming SIMD Exts-3 */
+#define X86_FEATURE_CID         10 /* Context ID */
+#define X86_FEATURE_CX16        13 /* CMPXCHG16B */
+#define X86_FEATURE_XTPR        14 /* Send Task Priority Messages */
+#define X86_FEATURE_PDCM        15 /* Perf/Debug Capability MSR */
+#define X86_FEATURE_DCA         18 /* Direct Cache Access */
+#define X86_FEATURE_SSE4_1      19 /* Streaming SIMD Extensions 4.1 */
+#define X86_FEATURE_SSE4_2      20 /* Streaming SIMD Extensions 4.2 */
+#define X86_FEATURE_X2APIC      21 /* x2APIC */
+#define X86_FEATURE_POPCNT      23 /* POPCNT instruction */
+#define X86_FEATURE_TSC_DEADLINE 24 /* "tdt" TSC Deadline Timer */
+#define X86_FEATURE_AES         25 /* AES acceleration instructions */
+#define X86_FEATURE_XSAVE       26 /* XSAVE/XRSTOR/XSETBV/XGETBV */
+#define X86_FEATURE_AVX         28 /* Advanced Vector Extensions */
+#define X86_FEATURE_F16C        29 /* Half-precision convert instruction */
+#define X86_FEATURE_HYPERVISOR  31 /* Running under some hypervisor */
 
-/* Other features, Linux-defined mapping, word 3 */
-/* This range is used for feature bits which conflict or are synthesized */
-#define X86_FEATURE_CXMMX      (3*32+ 0) /* Cyrix MMX extensions */
-#define X86_FEATURE_K6_MTRR    (3*32+ 1) /* AMD K6 nonstandard MTRRs */
-#define X86_FEATURE_CYRIX_ARR  (3*32+ 2) /* Cyrix ARRs (= MTRRs) */
-#define X86_FEATURE_CENTAUR_MCR        (3*32+ 3) /* Centaur MCRs (= MTRRs) */
-/* cpu types for specific tunings: */
-#define X86_FEATURE_K8         (3*32+ 4) /* Opteron, Athlon64 */
-#define X86_FEATURE_K7         (3*32+ 5) /* Athlon */
-#define X86_FEATURE_P3         (3*32+ 6) /* P3 */
-#define X86_FEATURE_P4         (3*32+ 7) /* P4 */
-#define X86_FEATURE_CONSTANT_TSC (3*32+ 8) /* TSC ticks at a constant rate */
+/* VIA/Cyrix/Centaur-defined CPU features, CPUID level 0xC0000001 */
+#define X86_FEATURE_XSTORE       2 /* on-CPU RNG present (xstore insn) */
+#define X86_FEATURE_XSTORE_EN    3 /* on-CPU RNG enabled */
+#define X86_FEATURE_XCRYPT       6 /* on-CPU crypto (xcrypt insn) */
+#define X86_FEATURE_XCRYPT_EN    7 /* on-CPU crypto enabled */
+#define X86_FEATURE_ACE2         8 /* Advanced Cryptography Engine v2 */
+#define X86_FEATURE_ACE2_EN      9 /* ACE v2 enabled */
+#define X86_FEATURE_PHE         10 /* PadLock Hash Engine */
+#define X86_FEATURE_PHE_EN      11 /* PHE enabled */
+#define X86_FEATURE_PMM         12 /* PadLock Montgomery Multiplier */
+#define X86_FEATURE_PMM_EN      13 /* PMM enabled */
 
-/* Intel-defined CPU features, CPUID level 0x00000001 (ecx), word 4 */
-#define X86_FEATURE_XMM3       (4*32+ 0) /* Streaming SIMD Extensions-3 */
-#define X86_FEATURE_PCLMULQDQ  (4*32+ 1) /* Carry-less multiplication */
-#define X86_FEATURE_DTES64     (4*32+ 2) /* 64-bit Debug Store */
-#define X86_FEATURE_MWAIT      (4*32+ 3) /* Monitor/Mwait support */
-#define X86_FEATURE_DSCPL      (4*32+ 4) /* CPL Qualified Debug Store */
-#define X86_FEATURE_VMXE       (4*32+ 5) /* Virtual Machine Extensions */
-#define X86_FEATURE_SMXE       (4*32+ 6) /* Safer Mode Extensions */
-#define X86_FEATURE_EST                (4*32+ 7) /* Enhanced SpeedStep */
-#define X86_FEATURE_TM2                (4*32+ 8) /* Thermal Monitor 2 */
-#define X86_FEATURE_SSSE3      (4*32+ 9) /* Supplemental Streaming SIMD 
Extensions-3 */
-#define X86_FEATURE_CID                (4*32+10) /* Context ID */
-#define X86_FEATURE_CX16        (4*32+13) /* CMPXCHG16B */
-#define X86_FEATURE_XTPR       (4*32+14) /* Send Task Priority Messages */
-#define X86_FEATURE_PDCM       (4*32+15) /* Perf/Debug Capability MSR */
-#define X86_FEATURE_DCA                (4*32+18) /* Direct Cache Access */
-#define X86_FEATURE_SSE4_1     (4*32+19) /* Streaming SIMD Extensions 4.1 */
-#define X86_FEATURE_SSE4_2     (4*32+20) /* Streaming SIMD Extensions 4.2 */
-#define X86_FEATURE_X2APIC      (4*32+21) /* x2APIC */
-#define X86_FEATURE_POPCNT     (4*32+23) /* POPCNT instruction */
-#define X86_FEATURE_TSC_DEADLINE (4*32+24) /* "tdt" TSC Deadline Timer */
-#define X86_FEATURE_AES                (4*32+25) /* AES acceleration 
instructions */
-#define X86_FEATURE_XSAVE      (4*32+26) /* XSAVE/XRSTOR/XSETBV/XGETBV */
-#define X86_FEATURE_AVX                (4*32+28) /* Advanced Vector Extensions 
*/
-#define X86_FEATURE_F16C       (4*32+29) /* Half-precision convert instruction 
*/
-#define X86_FEATURE_HYPERVISOR (4*32+31) /* Running under some hypervisor */
+/* More extended AMD flags: CPUID level 0x80000001, ecx */
+#define X86_FEATURE_LAHF_LM      0 /* LAHF/SAHF in long mode */
+#define X86_FEATURE_CMP_LEGACY   1 /* If yes HyperThreading not valid */
+#define X86_FEATURE_SVM          2 /* Secure virtual machine */
+#define X86_FEATURE_EXTAPIC      3 /* Extended APIC space */
+#define X86_FEATURE_CR8_LEGACY   4 /* CR8 in 32-bit mode */
+#define X86_FEATURE_ABM          5 /* Advanced bit manipulation */
+#define X86_FEATURE_SSE4A        6 /* SSE-4A */
+#define X86_FEATURE_MISALIGNSSE  7 /* Misaligned SSE mode */
+#define X86_FEATURE_3DNOWPREFETCH 8 /* 3DNow prefetch instructions */
+#define X86_FEATURE_OSVW         9 /* OS Visible Workaround */
+#define X86_FEATURE_IBS         10 /* Instruction Based Sampling */
+#define X86_FEATURE_XOP         11 /* extended AVX instructions */
+#define X86_FEATURE_SKINIT      12 /* SKINIT/STGI instructions */
+#define X86_FEATURE_WDT         13 /* Watchdog timer */
+#define X86_FEATURE_LWP         15 /* Light Weight Profiling */
+#define X86_FEATURE_FMA4        16 /* 4 operands MAC instructions */
+#define X86_FEATURE_NODEID_MSR  19 /* NodeId MSR */
+#define X86_FEATURE_TBM         21 /* trailing bit manipulations */
+#define X86_FEATURE_TOPOEXT     22 /* topology extensions CPUID leafs */
 
-/* VIA/Cyrix/Centaur-defined CPU features, CPUID level 0xC0000001, word 5 */
-#define X86_FEATURE_XSTORE     (5*32+ 2) /* on-CPU RNG present (xstore insn) */
-#define X86_FEATURE_XSTORE_EN  (5*32+ 3) /* on-CPU RNG enabled */
-#define X86_FEATURE_XCRYPT     (5*32+ 6) /* on-CPU crypto (xcrypt insn) */
-#define X86_FEATURE_XCRYPT_EN  (5*32+ 7) /* on-CPU crypto enabled */
-#define X86_FEATURE_ACE2       (5*32+ 8) /* Advanced Cryptography Engine v2 */
-#define X86_FEATURE_ACE2_EN    (5*32+ 9) /* ACE v2 enabled */
-#define X86_FEATURE_PHE                (5*32+ 10) /* PadLock Hash Engine */
-#define X86_FEATURE_PHE_EN     (5*32+ 11) /* PHE enabled */
-#define X86_FEATURE_PMM                (5*32+ 12) /* PadLock Montgomery 
Multiplier */
-#define X86_FEATURE_PMM_EN     (5*32+ 13) /* PMM enabled */
-
-/* More extended AMD flags: CPUID level 0x80000001, ecx, word 6 */
-#define X86_FEATURE_LAHF_LM     (6*32+ 0) /* LAHF/SAHF in long mode */
-#define X86_FEATURE_CMP_LEGACY  (6*32+ 1) /* If yes HyperThreading not valid */
-#define X86_FEATURE_SVM         (6*32+ 2) /* Secure virtual machine */
-#define X86_FEATURE_EXTAPIC     (6*32+ 3) /* Extended APIC space */
-#define X86_FEATURE_CR8_LEGACY  (6*32+ 4) /* CR8 in 32-bit mode */
-#define X86_FEATURE_ABM         (6*32+ 5) /* Advanced bit manipulation */
-#define X86_FEATURE_SSE4A       (6*32+ 6) /* SSE-4A */
-#define X86_FEATURE_MISALIGNSSE (6*32+ 7) /* Misaligned SSE mode */
-#define X86_FEATURE_3DNOWPREFETCH (6*32+ 8) /* 3DNow prefetch instructions */
-#define X86_FEATURE_OSVW        (6*32+ 9) /* OS Visible Workaround */
-#define X86_FEATURE_IBS         (6*32+10) /* Instruction Based Sampling */
-#define X86_FEATURE_XOP         (6*32+11) /* extended AVX instructions */
-#define X86_FEATURE_SKINIT      (6*32+12) /* SKINIT/STGI instructions */
-#define X86_FEATURE_WDT         (6*32+13) /* Watchdog timer */
-#define X86_FEATURE_LWP         (6*32+15) /* Light Weight Profiling */
-#define X86_FEATURE_FMA4        (6*32+16) /* 4 operands MAC instructions */
-#define X86_FEATURE_NODEID_MSR  (6*32+19) /* NodeId MSR */
-#define X86_FEATURE_TBM         (6*32+21) /* trailing bit manipulations */
-#define X86_FEATURE_TOPOEXT     (6*32+22) /* topology extensions CPUID leafs */
+/* Intel-defined CPU features, CPUID level 0x00000007:0 (ebx) */
+#define X86_FEATURE_FSGSBASE     0 /* {RD,WR}{FS,GS}BASE instructions */
 
 #endif /* __LIBXC_CPUFEATURE_H */
diff -r 840e16142824 -r 68947fbeaa76 tools/libxc/xc_cpuid_x86.c
--- a/tools/libxc/xc_cpuid_x86.c        Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxc/xc_cpuid_x86.c        Mon Jun 06 09:49:57 2011 +0100
@@ -25,9 +25,9 @@
 #include "xc_cpufeature.h"
 #include <xen/hvm/params.h>
 
-#define bitmaskof(idx)      (1u << ((idx) & 31))
-#define clear_bit(idx, dst) ((dst) &= ~(1u << ((idx) & 31)))
-#define set_bit(idx, dst)   ((dst) |= (1u << ((idx) & 31)))
+#define bitmaskof(idx)      (1u << (idx))
+#define clear_bit(idx, dst) ((dst) &= ~(1u << (idx)))
+#define set_bit(idx, dst)   ((dst) |= (1u << (idx)))
 
 #define DEF_MAX_BASE 0x0000000du
 #define DEF_MAX_INTELEXT  0x80000008u
@@ -466,6 +466,14 @@
         set_bit(X86_FEATURE_HYPERVISOR, regs[2]);
         break;
 
+    case 7:
+        if ( input[1] == 0 )
+            regs[1] &= bitmaskof(X86_FEATURE_FSGSBASE);
+        else
+            regs[1] = 0;
+        regs[0] = regs[2] = regs[3] = 0;
+        break;
+
     case 0x0000000d:
         xc_cpuid_config_xsave(xch, domid, xfeature_mask, input, regs);
         break;
@@ -612,7 +620,7 @@
             input[0] = 0x80000000u;
 
         input[1] = XEN_CPUID_INPUT_UNUSED;
-        if ( (input[0] == 4) || (input[0] == 0xd) )
+        if ( (input[0] == 4) || (input[0] == 7) || (input[0] == 0xd) )
             input[1] = 0;
 
         if ( (input[0] & 0x80000000u) && (input[0] > ext_max) )
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/Makefile
--- a/tools/libxl/Makefile      Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/Makefile      Mon Jun 06 09:49:57 2011 +0100
@@ -35,7 +35,7 @@
 LIBXL_OBJS = flexarray.o libxl.o libxl_create.o libxl_dm.o libxl_pci.o \
                        libxl_dom.o libxl_exec.o libxl_xshelp.o libxl_device.o \
                        libxl_internal.o libxl_utils.o libxl_uuid.o 
$(LIBXL_OBJS-y)
-LIBXL_OBJS += _libxl_types.o
+LIBXL_OBJS += _libxl_types.o libxl_flask.o
 
 $(LIBXL_OBJS): CFLAGS += $(CFLAGS_libxenctrl) $(CFLAGS_libxenguest) 
$(CFLAGS_libxenstore) $(CFLAGS_libblktapctl)
 
@@ -69,7 +69,7 @@
 
 _libxl_paths.h: genpath
        sed -e "s/\([^=]*\)=\(.*\)/#define \1 \2/g" $@.tmp >$@.2.tmp
-       if ! cmp $@.2.tmp $@; then mv -f $@.2.tmp $@; fi
+       if ! cmp -s $@.2.tmp $@; then mv -f $@.2.tmp $@; fi
 
 libxl_paths.c: _libxl_paths.h
 
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/libxl.c
--- a/tools/libxl/libxl.c       Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/libxl.c       Mon Jun 06 09:49:57 2011 +0100
@@ -38,8 +38,6 @@
 
 #define PAGE_TO_MEMKB(pages) ((pages) * 4)
 #define BACKEND_STRING_SIZE 5
-#define STRINGIFY(x) #x
-#define TOSTRING(x) STRINGIFY(x)
 
 int libxl_ctx_alloc(libxl_ctx **pctx, int version, xentoollog_logger * lg)
 {
@@ -87,6 +85,7 @@
 
 int libxl_ctx_free(libxl_ctx *ctx)
 {
+    if (!ctx) return 0;
     if (ctx->xch) xc_interface_close(ctx->xch);
     libxl_version_info_destroy(&ctx->version_info);
     if (ctx->xsh) xs_daemon_close(ctx->xsh); 
@@ -342,6 +341,7 @@
 {
     memcpy(&(xlinfo->uuid), xcinfo->handle, sizeof(xen_domain_handle_t));
     xlinfo->domid = xcinfo->domain;
+    xlinfo->ssidref = xcinfo->ssidref;
 
     xlinfo->dying    = !!(xcinfo->flags&XEN_DOMINF_dying);
     xlinfo->shutdown = !!(xcinfo->flags&XEN_DOMINF_shutdown);
@@ -707,7 +707,7 @@
     disk->format = LIBXL_DISK_FORMAT_EMPTY;
     /* this value is returned to the user: do not free right away */
     disk->vdev = xs_read(ctx->xsh, XBT_NULL, libxl__sprintf(&gc, "%s/dev", 
backend), NULL);
-    disk->unpluggable = 1;
+    disk->removable = 1;
     disk->readwrite = 0;
     disk->is_cdrom = 1;
 
@@ -970,6 +970,13 @@
         goto out_free;
     }
 
+    if (disk->script) {
+        LIBXL__LOG(ctx, LIBXL__LOG_ERROR, "External block scripts"
+                   " not yet supported, sorry");
+        rc = ERROR_INVAL;
+        goto out_free;
+    }
+
     devid = libxl__device_disk_dev_number(disk->vdev, NULL, NULL);
     if (devid==-1) {
         LIBXL__LOG(ctx, LIBXL__LOG_ERROR, "Invalid or unsupported"
@@ -1040,7 +1047,7 @@
     flexarray_append(back, "online");
     flexarray_append(back, "1");
     flexarray_append(back, "removable");
-    flexarray_append(back, libxl__sprintf(&gc, "%d", (disk->unpluggable) ? 1 : 
0));
+    flexarray_append(back, libxl__sprintf(&gc, "%d", (disk->removable) ? 1 : 
0));
     flexarray_append(back, "bootable");
     flexarray_append(back, libxl__sprintf(&gc, "%d", 1));
     flexarray_append(back, "state");
@@ -1583,7 +1590,7 @@
                 libxl__sprintf(gc, "%s/%s/type", be_path, *dir)), 
                 &(pdisk->backend));
             pdisk->vdev = xs_read(ctx->xsh, XBT_NULL, libxl__sprintf(gc, 
"%s/%s/dev", be_path, *dir), &len);
-            pdisk->unpluggable = atoi(libxl__xs_read(gc, XBT_NULL, 
libxl__sprintf(gc, "%s/%s/removable", be_path, *dir)));
+            pdisk->removable = atoi(libxl__xs_read(gc, XBT_NULL, 
libxl__sprintf(gc, "%s/%s/removable", be_path, *dir)));
             if (!strcmp(libxl__xs_read(gc, XBT_NULL, libxl__sprintf(gc, 
"%s/%s/mode", be_path, *dir)), "w"))
                 pdisk->readwrite = 1;
             else
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/libxl.h
--- a/tools/libxl/libxl.h       Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/libxl.h       Mon Jun 06 09:49:57 2011 +0100
@@ -232,7 +232,7 @@
 
 /* context functions */
 int libxl_ctx_alloc(libxl_ctx **pctx, int version, xentoollog_logger *lg);
-int libxl_ctx_free(libxl_ctx *ctx);
+int libxl_ctx_free(libxl_ctx *ctx /* 0 is OK */);
 int libxl_ctx_postfork(libxl_ctx *ctx);
 
 /* domain related functions */
@@ -499,6 +499,14 @@
     return domid > 0 && domid < DOMID_FIRST_RESERVED;
 }
 
+int libxl_flask_context_to_sid(libxl_ctx *ctx, char *buf, size_t len,
+                               uint32_t *ssidref);
+int libxl_flask_sid_to_context(libxl_ctx *ctx, uint32_t ssidref, char **buf, 
+                               size_t *len);
+int libxl_flask_getenforce(libxl_ctx *ctx);
+int libxl_flask_setenforce(libxl_ctx *ctx, int mode);
+int libxl_flask_loadpolicy(libxl_ctx *ctx, void *policy, uint32_t size);
+
 /* common paths */
 const char *libxl_sbindir_path(void);
 const char *libxl_bindir_path(void);
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/libxl.idl
--- a/tools/libxl/libxl.idl     Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/libxl.idl     Mon Jun 06 09:49:57 2011 +0100
@@ -89,6 +89,7 @@
 libxl_dominfo = Struct("dominfo",[
     ("uuid",        libxl_uuid),
     ("domid",       libxl_domid),
+    ("ssidref",      uint32),
     ("running",     bool),
     ("blocked",     bool),
     ("paused",      bool),
@@ -138,7 +139,7 @@
     ("hvm",          bool),
     ("hap",          bool),
     ("oos",          bool),
-    ("ssidref",      integer),
+    ("ssidref",      uint32),
     ("name",         string),
     ("uuid",         libxl_uuid),
     ("xsdata",       libxl_key_value_list),
@@ -278,7 +279,8 @@
     ("vdev", string),
     ("backend", libxl_disk_backend),
     ("format", libxl_disk_format),
-    ("unpluggable", integer),
+    ("script", string),
+    ("removable", integer),
     ("readwrite", integer),
     ("is_cdrom", integer),
     ])
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/libxl_device.c
--- a/tools/libxl/libxl_device.c        Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/libxl_device.c        Mon Jun 06 09:49:57 2011 +0100
@@ -485,7 +485,9 @@
             }
             if (starting && FD_ISSET(starting->for_spawn->fd, &rfds)) {
                 unsigned char dummy;
-                read(starting->for_spawn->fd, &dummy, sizeof(dummy));
+                if (read(starting->for_spawn->fd, &dummy, sizeof(dummy)) != 1)
+                    LIBXL__LOG_ERRNO(ctx, LIBXL__LOG_DEBUG,
+                                     "failed to read spawn status pipe");
             }
         }
     }
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/libxl_exec.c
--- a/tools/libxl/libxl_exec.c  Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/libxl_exec.c  Mon Jun 06 09:49:57 2011 +0100
@@ -45,7 +45,7 @@
     env_debug = getenv("_LIBXL_DEBUG_EXEC_FDS");
     if (!env_debug) return;
 
-    debug = strtol(env_debug, (char **) NULL, 10);atoi(env_debug);
+    debug = strtol(env_debug, (char **) NULL, 10);
     if (debug <= 0) return;
 
     for (i = 4; i < 256; i++) {
@@ -220,8 +220,10 @@
     rc = (WIFEXITED(status) ? WEXITSTATUS(status) :
           WIFSIGNALED(status) && WTERMSIG(status) < 127
           ? WTERMSIG(status)+128 : -1);
-    if (for_spawn)
-        write(pipes[1], &dummy, sizeof(dummy));
+    if (for_spawn) {
+        if (write(pipes[1], &dummy, sizeof(dummy)) != 1)
+            perror("libxl__spawn_spawn: unable to signal child exit to 
parent");
+    }
     _exit(rc);
 
  err_parent_pipes:
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/libxl_flask.c
--- /dev/null   Thu Jan 01 00:00:00 1970 +0000
+++ b/tools/libxl/libxl_flask.c Mon Jun 06 09:49:57 2011 +0100
@@ -0,0 +1,71 @@
+/*
+ *
+ *  Author: Machon Gregory, <mbgrego@xxxxxxxxxxxxxx>
+ *
+ *  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 <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <errno.h>
+#include <xenctrl.h>
+
+#include "libxl.h"
+#include "libxl_internal.h"
+
+int libxl_flask_context_to_sid(libxl_ctx *ctx, char *buf, size_t len,
+                               uint32_t *ssidref)
+{
+    int rc;
+
+    rc = xc_flask_context_to_sid(ctx->xch, buf, len, ssidref);
+   
+    return rc;
+}
+
+int libxl_flask_sid_to_context(libxl_ctx *ctx, uint32_t ssidref, 
+                               char **buf, size_t *len)
+{
+    int rc;
+    char tmp[XC_PAGE_SIZE];
+
+    rc = xc_flask_sid_to_context(ctx->xch, ssidref, tmp, sizeof(tmp));
+                                    
+    if (!rc) {
+        *len = strlen(tmp);
+        *buf = strdup(tmp); 
+    }
+     
+    return rc;
+}
+
+int libxl_flask_getenforce(libxl_ctx *ctx)
+{
+    int rc;
+
+    rc = xc_flask_getenforce(ctx->xch);
+
+    return rc; 
+}
+
+int libxl_flask_setenforce(libxl_ctx *ctx, int mode)
+{
+    int rc;
+
+    rc = xc_flask_setenforce(ctx->xch, mode);
+
+    return rc;
+}
+
+int libxl_flask_loadpolicy(libxl_ctx *ctx, void *policy, uint32_t size)
+{
+
+    int rc;
+
+    rc = xc_flask_load(ctx->xch, policy, size);
+
+    return rc;
+}
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/libxl_internal.h
--- a/tools/libxl/libxl_internal.h      Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/libxl_internal.h      Mon Jun 06 09:49:57 2011 +0100
@@ -370,4 +370,8 @@
 _hidden int libxl__file_reference_unmap(libxl_file_reference *f);
 
 _hidden int libxl__e820_alloc(libxl_ctx *ctx, uint32_t domid, 
libxl_domain_config *d_config);
+
+#define STRINGIFY(x) #x
+#define TOSTRING(x) STRINGIFY(x)
+
 #endif
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/libxl_pci.c
--- a/tools/libxl/libxl_pci.c   Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/libxl_pci.c   Mon Jun 06 09:49:57 2011 +0100
@@ -48,7 +48,7 @@
     value = 0;
     value |= (pcidev->bus & 0xff) << 16;
     value |= (pcidev->dev & 0x1f) << (8+3);
-    value |= (pcidev->func & 0x3) << (8+0);
+    value |= (pcidev->func & 0x7) << (8+0);
 
     return value;
 }
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/libxl_utils.c
--- a/tools/libxl/libxl_utils.c Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/libxl_utils.c Mon Jun 06 09:49:57 2011 +0100
@@ -556,7 +556,7 @@
     libxl_string_to_backend(ctx, val, &(disk->backend));
     disk->vdev = libxl__xs_read(&gc, XBT_NULL, libxl__sprintf(&gc, "%s/dev", 
be_path));
     val = libxl__xs_read(&gc, XBT_NULL, libxl__sprintf(&gc, "%s/removable", 
be_path));
-    disk->unpluggable = !strcmp(val, "1");
+    disk->removable = !strcmp(val, "1");
     val = libxl__xs_read(&gc, XBT_NULL, libxl__sprintf(&gc, "%s/mode", 
be_path));
     disk->readwrite = !!strcmp(val, "w");
     val = libxl__xs_read(&gc, XBT_NULL, libxl__sprintf(&gc, "%s/device-type", 
diskpath));
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/libxlu_cfg.c
--- a/tools/libxl/libxlu_cfg.c  Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/libxlu_cfg.c  Mon Jun 06 09:49:57 2011 +0100
@@ -1,3 +1,21 @@
+/*
+ * libxlu_cfg.c - xl configuration file parsing: setup and helper functions
+ *
+ * Copyright (C) 2010      Citrix Ltd.
+ * Author Ian Jackson <ian.jackson@xxxxxxxxxxxxx>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License as published
+ * by the Free Software Foundation; version 2.1 only. with the special
+ * exception on linking described in file LICENSE.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU Lesser General Public License for more details.
+ */
+
+
 #include <limits.h>
 
 #include "libxlu_internal.h"
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/libxlu_cfg_i.h
--- a/tools/libxl/libxlu_cfg_i.h        Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/libxlu_cfg_i.h        Mon Jun 06 09:49:57 2011 +0100
@@ -1,3 +1,20 @@
+/*
+ * libxlu_cfg_i.h - xl configuration file parsing: parser-internal declarations
+ *
+ * Copyright (C) 2010      Citrix Ltd.
+ * Author Ian Jackson <ian.jackson@xxxxxxxxxxxxx>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License as published
+ * by the Free Software Foundation; version 2.1 only. with the special
+ * exception on linking described in file LICENSE.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU Lesser General Public License for more details.
+ */
+
 #ifndef LIBXLU_CFG_I_H
 #define LIBXLU_CFG_I_H
 
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/libxlu_cfg_l.c
--- a/tools/libxl/libxlu_cfg_l.c        Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/libxlu_cfg_l.c        Mon Jun 06 09:49:57 2011 +0100
@@ -479,7 +479,23 @@
 #define YY_RESTORE_YY_MORE_OFFSET
 #line 1 "libxlu_cfg_l.l"
 /* -*- fundamental -*- */
-#line 4 "libxlu_cfg_l.l"
+/*
+ * libxlu_cfg_l.l - xl configuration file parsing: lexer
+ *
+ * Copyright (C) 2010      Citrix Ltd.
+ * Author Ian Jackson <ian.jackson@xxxxxxxxxxxxx>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License as published
+ * by the Free Software Foundation; version 2.1 only. with the special
+ * exception on linking described in file LICENSE.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU Lesser General Public License for more details.
+ */
+#line 20 "libxlu_cfg_l.l"
 #include "libxlu_cfg_i.h"
 
 #define ctx ((CfgParseContext*)yyextra)
@@ -498,7 +514,7 @@
 void xlu__cfg_yyset_column(int  column_no, yyscan_t yyscanner);
 
 
-#line 502 "libxlu_cfg_l.c"
+#line 518 "libxlu_cfg_l.c"
 
 #define INITIAL 0
 #define lexerr 1
@@ -743,10 +759,10 @@
        register int yy_act;
     struct yyguts_t * yyg = (struct yyguts_t*)yyscanner;
 
-#line 37 "libxlu_cfg_l.l"
+#line 53 "libxlu_cfg_l.l"
 
 
-#line 750 "libxlu_cfg_l.c"
+#line 766 "libxlu_cfg_l.c"
 
     yylval = yylval_param;
 
@@ -849,7 +865,7 @@
 
 case 1:
 YY_RULE_SETUP
-#line 39 "libxlu_cfg_l.l"
+#line 55 "libxlu_cfg_l.l"
 {
                           yylval->string= xlu__cfgl_strdup(ctx,yytext);
                           GOT(IDENT);
@@ -857,7 +873,7 @@
        YY_BREAK
 case 2:
 YY_RULE_SETUP
-#line 43 "libxlu_cfg_l.l"
+#line 59 "libxlu_cfg_l.l"
 {
                           yylval->string= xlu__cfgl_strdup(ctx,yytext);
                           GOT(NUMBER);
@@ -865,43 +881,43 @@
        YY_BREAK
 case 3:
 YY_RULE_SETUP
-#line 48 "libxlu_cfg_l.l"
+#line 64 "libxlu_cfg_l.l"
 
        YY_BREAK
 case 4:
 YY_RULE_SETUP
-#line 50 "libxlu_cfg_l.l"
+#line 66 "libxlu_cfg_l.l"
 { GOT(','); }
        YY_BREAK
 case 5:
 YY_RULE_SETUP
-#line 51 "libxlu_cfg_l.l"
+#line 67 "libxlu_cfg_l.l"
 { GOT('['); }
        YY_BREAK
 case 6:
 YY_RULE_SETUP
-#line 52 "libxlu_cfg_l.l"
+#line 68 "libxlu_cfg_l.l"
 { GOT(']'); }
        YY_BREAK
 case 7:
 YY_RULE_SETUP
-#line 53 "libxlu_cfg_l.l"
+#line 69 "libxlu_cfg_l.l"
 { GOT('='); }
        YY_BREAK
 case 8:
 YY_RULE_SETUP
-#line 54 "libxlu_cfg_l.l"
+#line 70 "libxlu_cfg_l.l"
 { GOT(';'); }
        YY_BREAK
 case 9:
 /* rule 9 can match eol */
 YY_RULE_SETUP
-#line 56 "libxlu_cfg_l.l"
+#line 72 "libxlu_cfg_l.l"
 { yylloc->first_line= yylineno-1; return NEWLINE; }
        YY_BREAK
 case 10:
 YY_RULE_SETUP
-#line 58 "libxlu_cfg_l.l"
+#line 74 "libxlu_cfg_l.l"
 {
                           yylval->string= xlu__cfgl_dequote(ctx,yytext);
                           GOT(STRING);
@@ -909,7 +925,7 @@
        YY_BREAK
 case 11:
 YY_RULE_SETUP
-#line 62 "libxlu_cfg_l.l"
+#line 78 "libxlu_cfg_l.l"
 {
                           yylval->string= xlu__cfgl_dequote(ctx,yytext);
                           GOT(STRING);
@@ -917,7 +933,7 @@
        YY_BREAK
 case 12:
 YY_RULE_SETUP
-#line 67 "libxlu_cfg_l.l"
+#line 83 "libxlu_cfg_l.l"
 {
                           ctx->likely_python= 1;
                           BEGIN(lexerr);
@@ -926,7 +942,7 @@
        YY_BREAK
 case 13:
 YY_RULE_SETUP
-#line 73 "libxlu_cfg_l.l"
+#line 89 "libxlu_cfg_l.l"
 {
                           BEGIN(lexerr);
                           yymore();
@@ -934,7 +950,7 @@
        YY_BREAK
 case 14:
 YY_RULE_SETUP
-#line 78 "libxlu_cfg_l.l"
+#line 94 "libxlu_cfg_l.l"
 {
                           xlu__cfgl_lexicalerror(ctx,"lexical error");
                           BEGIN(0);
@@ -943,7 +959,7 @@
 case 15:
 /* rule 15 can match eol */
 YY_RULE_SETUP
-#line 83 "libxlu_cfg_l.l"
+#line 99 "libxlu_cfg_l.l"
 {
                           xlu__cfgl_lexicalerror(ctx,"lexical error");
                           BEGIN(0);
@@ -952,10 +968,10 @@
        YY_BREAK
 case 16:
 YY_RULE_SETUP
-#line 88 "libxlu_cfg_l.l"
+#line 104 "libxlu_cfg_l.l"
 YY_FATAL_ERROR( "flex scanner jammed" );
        YY_BREAK
-#line 959 "libxlu_cfg_l.c"
+#line 975 "libxlu_cfg_l.c"
 case YY_STATE_EOF(INITIAL):
 case YY_STATE_EOF(lexerr):
        yyterminate();
@@ -2105,4 +2121,4 @@
 
 #define YYTABLES_NAME "yytables"
 
-#line 88 "libxlu_cfg_l.l"
+#line 104 "libxlu_cfg_l.l"
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/libxlu_cfg_l.h
--- a/tools/libxl/libxlu_cfg_l.h        Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/libxlu_cfg_l.h        Mon Jun 06 09:49:57 2011 +0100
@@ -350,7 +350,7 @@
 #undef YY_DECL
 #endif
 
-#line 88 "libxlu_cfg_l.l"
+#line 104 "libxlu_cfg_l.l"
 
 #line 356 "libxlu_cfg_l.h"
 #undef xlu__cfg_yyIN_HEADER
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/libxlu_cfg_l.l
--- a/tools/libxl/libxlu_cfg_l.l        Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/libxlu_cfg_l.l        Mon Jun 06 09:49:57 2011 +0100
@@ -1,4 +1,20 @@
 /* -*- fundamental -*- */
+/*
+ * libxlu_cfg_l.l - xl configuration file parsing: lexer
+ *
+ * Copyright (C) 2010      Citrix Ltd.
+ * Author Ian Jackson <ian.jackson@xxxxxxxxxxxxx>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License as published
+ * by the Free Software Foundation; version 2.1 only. with the special
+ * exception on linking described in file LICENSE.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU Lesser General Public License for more details.
+ */
 
 %{
 #include "libxlu_cfg_i.h"
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/libxlu_cfg_y.c
--- a/tools/libxl/libxlu_cfg_y.c        Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/libxlu_cfg_y.c        Mon Jun 06 09:49:57 2011 +0100
@@ -90,7 +90,7 @@
 
 
 /* Copy the first part of user declarations.  */
-#line 3 "libxlu_cfg_y.y"
+#line 19 "libxlu_cfg_y.y"
 
 #define YYLEX_PARAM ctx->scanner
 #include "libxlu_cfg_i.h"
@@ -117,7 +117,7 @@
 
 #if ! defined YYSTYPE && ! defined YYSTYPE_IS_DECLARED
 typedef union YYSTYPE
-#line 9 "libxlu_cfg_y.y"
+#line 25 "libxlu_cfg_y.y"
 {
   char *string;
   XLU_ConfigSetting *setting;
@@ -439,9 +439,9 @@
 /* YYRLINE[YYN] -- source line where rule number YYN was defined.  */
 static const yytype_uint8 yyrline[] =
 {
-       0,    31,    31,    32,    34,    34,    36,    37,    39,    40,
-      42,    43,    45,    46,    48,    49,    50,    52,    53,    55,
-      57
+       0,    47,    47,    48,    50,    50,    52,    53,    55,    56,
+      58,    59,    61,    62,    64,    65,    66,    68,    69,    71,
+      73
 };
 #endif
 
@@ -1062,37 +1062,37 @@
   switch (yytype)
     {
       case 3: /* "IDENT" */
-#line 24 "libxlu_cfg_y.y"
+#line 40 "libxlu_cfg_y.y"
        { free((yyvaluep->string)); };
 #line 1068 "libxlu_cfg_y.c"
        break;
       case 4: /* "STRING" */
-#line 24 "libxlu_cfg_y.y"
+#line 40 "libxlu_cfg_y.y"
        { free((yyvaluep->string)); };
 #line 1073 "libxlu_cfg_y.c"
        break;
       case 5: /* "NUMBER" */
-#line 24 "libxlu_cfg_y.y"
+#line 40 "libxlu_cfg_y.y"
        { free((yyvaluep->string)); };
 #line 1078 "libxlu_cfg_y.c"
        break;
       case 17: /* "value" */
-#line 27 "libxlu_cfg_y.y"
+#line 43 "libxlu_cfg_y.y"
        { xlu__cfg_set_free((yyvaluep->setting)); };
 #line 1083 "libxlu_cfg_y.c"
        break;
       case 18: /* "atom" */
-#line 24 "libxlu_cfg_y.y"
+#line 40 "libxlu_cfg_y.y"
        { free((yyvaluep->string)); };
 #line 1088 "libxlu_cfg_y.c"
        break;
       case 19: /* "valuelist" */
-#line 27 "libxlu_cfg_y.y"
+#line 43 "libxlu_cfg_y.y"
        { xlu__cfg_set_free((yyvaluep->setting)); };
 #line 1093 "libxlu_cfg_y.c"
        break;
       case 20: /* "values" */
-#line 27 "libxlu_cfg_y.y"
+#line 43 "libxlu_cfg_y.y"
        { xlu__cfg_set_free((yyvaluep->setting)); };
 #line 1098 "libxlu_cfg_y.c"
        break;
@@ -1417,52 +1417,52 @@
   switch (yyn)
     {
         case 4:
-#line 34 "libxlu_cfg_y.y"
+#line 50 "libxlu_cfg_y.y"
     { xlu__cfg_set_store(ctx,(yyvsp[(1) - (3)].string),(yyvsp[(3) - 
(3)].setting),(yylsp[(3) - (3)]).first_line); ;}
     break;
 
   case 10:
-#line 42 "libxlu_cfg_y.y"
+#line 58 "libxlu_cfg_y.y"
     { (yyval.setting)= xlu__cfg_set_mk(ctx,1,(yyvsp[(1) - (1)].string)); ;}
     break;
 
   case 11:
-#line 43 "libxlu_cfg_y.y"
+#line 59 "libxlu_cfg_y.y"
     { (yyval.setting)= (yyvsp[(3) - (4)].setting); ;}
     break;
 
   case 12:
-#line 45 "libxlu_cfg_y.y"
+#line 61 "libxlu_cfg_y.y"
     { (yyval.string)= (yyvsp[(1) - (1)].string); ;}
     break;
 
   case 13:
-#line 46 "libxlu_cfg_y.y"
+#line 62 "libxlu_cfg_y.y"
     { (yyval.string)= (yyvsp[(1) - (1)].string); ;}
     break;
 
   case 14:
-#line 48 "libxlu_cfg_y.y"
+#line 64 "libxlu_cfg_y.y"
     { (yyval.setting)= xlu__cfg_set_mk(ctx,0,0); ;}
     break;
 
   case 15:
-#line 49 "libxlu_cfg_y.y"
+#line 65 "libxlu_cfg_y.y"
     { (yyval.setting)= (yyvsp[(1) - (1)].setting); ;}
     break;
 
   case 16:
-#line 50 "libxlu_cfg_y.y"
+#line 66 "libxlu_cfg_y.y"
     { (yyval.setting)= (yyvsp[(1) - (3)].setting); ;}
     break;
 
   case 17:
-#line 52 "libxlu_cfg_y.y"
+#line 68 "libxlu_cfg_y.y"
     { (yyval.setting)= xlu__cfg_set_mk(ctx,2,(yyvsp[(1) - (2)].string)); ;}
     break;
 
   case 18:
-#line 53 "libxlu_cfg_y.y"
+#line 69 "libxlu_cfg_y.y"
     { xlu__cfg_set_add(ctx,(yyvsp[(1) - (5)].setting),(yyvsp[(4) - 
(5)].string)); (yyval.setting)= (yyvsp[(1) - (5)].setting); ;}
     break;
 
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/libxlu_cfg_y.h
--- a/tools/libxl/libxlu_cfg_y.h        Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/libxlu_cfg_y.h        Mon Jun 06 09:49:57 2011 +0100
@@ -56,7 +56,7 @@
 
 #if ! defined YYSTYPE && ! defined YYSTYPE_IS_DECLARED
 typedef union YYSTYPE
-#line 9 "libxlu_cfg_y.y"
+#line 25 "libxlu_cfg_y.y"
 {
   char *string;
   XLU_ConfigSetting *setting;
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/libxlu_cfg_y.y
--- a/tools/libxl/libxlu_cfg_y.y        Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/libxlu_cfg_y.y        Mon Jun 06 09:49:57 2011 +0100
@@ -1,4 +1,20 @@
 /* -*- fundamental -*- */
+/*
+ * libxlu_cfg_l.y - xl configuration file parsing: parser
+ *
+ * Copyright (C) 2010      Citrix Ltd.
+ * Author Ian Jackson <ian.jackson@xxxxxxxxxxxxx>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License as published
+ * by the Free Software Foundation; version 2.1 only. with the special
+ * exception on linking described in file LICENSE.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU Lesser General Public License for more details.
+ */
 
 %{
 #define YYLEX_PARAM ctx->scanner
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/libxlu_internal.h
--- a/tools/libxl/libxlu_internal.h     Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/libxlu_internal.h     Mon Jun 06 09:49:57 2011 +0100
@@ -45,4 +45,8 @@
     void *scanner;
 } CfgParseContext;
 
+
+#define STRINGIFY(x) #x
+#define TOSTRING(x) STRINGIFY(x)
+
 #endif /*LIBXLU_INTERNAL_H*/
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/xl.h
--- a/tools/libxl/xl.h  Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/xl.h  Mon Jun 06 09:49:57 2011 +0100
@@ -87,6 +87,9 @@
 int main_cpupoolcpuremove(int argc, char **argv);
 int main_cpupoolmigrate(int argc, char **argv);
 int main_cpupoolnumasplit(int argc, char **argv);
+int main_getenforce(int argc, char **argv);
+int main_setenforce(int argc, char **argv);
+int main_loadpolicy(int argc, char **argv);
 
 void help(const char *command);
 
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/xl_cmdimpl.c
--- a/tools/libxl/xl_cmdimpl.c  Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/xl_cmdimpl.c  Mon Jun 06 09:49:57 2011 +0100
@@ -393,7 +393,7 @@
         printf("\t\t\t(physpath %s)\n", d_config->disks[i].pdev_path);
         printf("\t\t\t(phystype %d)\n", d_config->disks[i].backend);
         printf("\t\t\t(virtpath %s)\n", d_config->disks[i].vdev);
-        printf("\t\t\t(unpluggable %d)\n", d_config->disks[i].unpluggable);
+        printf("\t\t\t(unpluggable %d)\n", d_config->disks[i].removable);
         printf("\t\t\t(readwrite %d)\n", d_config->disks[i].readwrite);
         printf("\t\t\t(is_cdrom %d)\n", d_config->disks[i].is_cdrom);
         printf("\t\t)\n");
@@ -591,7 +591,7 @@
                 *p = '\0';
                 if ( !strcmp(tok, "cdrom") ) {
                     disk->is_cdrom = 1;
-                    disk->unpluggable = 1;
+                    disk->removable = 1;
                 }else{
                     fprintf(stderr, "Unknown virtual disk type: %s\n", tok);
                     return 0;
@@ -652,6 +652,19 @@
 
     libxl_init_create_info(c_info);
 
+    if (!xlu_cfg_get_string (config, "seclabel", &buf)) {
+        e = libxl_flask_context_to_sid(ctx, (char *)buf, strlen(buf),
+                                    &c_info->ssidref);
+        if (e) {
+            if (errno == ENOSYS) {
+                fprintf(stderr, "XSM Disabled: seclabel not supported\n");    
+            } else {
+                fprintf(stderr, "Invalid seclabel: %s\n", buf);
+                exit(1);
+            }
+        }
+    }
+
     c_info->hvm = 0;
     if (!xlu_cfg_get_string (config, "builder", &buf) &&
         !strncmp(buf, "hvm", strlen(buf)))
@@ -1503,10 +1516,6 @@
 
     parse_config_data(config_file, config_data, config_len, &d_config, 
&d_config.dm_info);
 
-    ret = 0;
-    if (dom_info->dryrun)
-        goto out;
-
     if (migrate_fd >= 0) {
         if (d_config.c_info.name) {
             /* when we receive a domain we get its name from the config
@@ -1525,9 +1534,13 @@
         }
     }
 
-    if (debug)
+    if (debug || dom_info->dryrun)
         printf_info(-1, &d_config, &d_config.dm_info);
 
+    ret = 0;
+    if (dom_info->dryrun)
+        goto out;
+
 start:
     domid = -1;
 
@@ -2264,13 +2277,14 @@
     }
 }
 
-static void list_domains(int verbose, const libxl_dominfo *info, int nb_domain)
+static void list_domains(int verbose, int context, const libxl_dominfo *info, 
int nb_domain)
 {
     int i;
     static const char shutdown_reason_letters[]= "-rscw";
 
     printf("Name                                        ID   Mem 
VCPUs\tState\tTime(s)");
-    if (verbose) printf("   UUID                            Reason-Code");
+    if (verbose) printf("   UUID                            
Reason-Code\tSecurity Label");
+    if (context && !verbose) printf("   Security Label");
     printf("\n");
     for (i = 0; i < nb_domain; i++) {
         char *domname;
@@ -2294,9 +2308,22 @@
         free(domname);
         if (verbose) {
             printf(" " LIBXL_UUID_FMT, LIBXL_UUID_BYTES(info[i].uuid));
-           if (info[i].shutdown) printf(" %8x", shutdown_reason);
-           else printf(" %8s", "-");
-       }
+            if (info[i].shutdown) printf(" %8x", shutdown_reason);
+            else printf(" %8s", "-");
+        }
+        if (verbose || context) {
+            int rc;
+            size_t size;
+            char *buf;
+            rc = libxl_flask_sid_to_context(ctx, info[i].ssidref, &buf, 
+                                            &size); 
+            if (rc < 0)
+                printf("  -");
+            else {
+                printf("  %s", buf);
+                free(buf);
+            }
+        }
         putchar('\n');
     }
 }
@@ -3032,12 +3059,14 @@
 int main_list(int argc, char **argv)
 {
     int opt, verbose = 0;
+    int context = 0;
     int details = 0;
     int option_index = 0;
     static struct option long_options[] = {
         {"long", 0, 0, 'l'},
         {"help", 0, 0, 'h'},
         {"verbose", 0, 0, 'v'},
+        {"context", 0, 0, 'Z'},
         {0, 0, 0, 0}
     };
 
@@ -3046,7 +3075,7 @@
     int nb_domain, rc;
 
     while (1) {
-        opt = getopt_long(argc, argv, "lvh", long_options, &option_index);
+        opt = getopt_long(argc, argv, "lvhZ", long_options, &option_index);
         if (opt == -1)
             break;
 
@@ -3060,6 +3089,9 @@
         case 'v':
             verbose = 1;
             break;
+        case 'Z':
+            context = 1;
+            break;
         default:
             fprintf(stderr, "option `%c' not supported.\n", optopt);
             break;
@@ -3095,7 +3127,7 @@
     if (details)
         list_domains_details(info, nb_domain);
     else
-        list_domains(verbose, info, nb_domain);
+        list_domains(verbose, context, info, nb_domain);
 
     free(info_free);
 
@@ -4149,7 +4181,7 @@
         return 1;
     }
     disk.vdev = argv[optind+2];
-    disk.unpluggable = 1;
+    disk.removable = 1;
     disk.readwrite = ((argc-optind <= 3) || (argv[optind+3][0] == 'w'));
 
     if (domain_qualifier_to_domid(argv[optind], &fe_domid, 0) < 0) {
@@ -5280,3 +5312,122 @@
 
     return ret;
 }
+
+int main_getenforce(int argc, char **argv)
+{
+    int ret;
+
+    ret = libxl_flask_getenforce(ctx);
+
+    if (ret < 0) {
+        if (errno == ENOSYS)
+            printf("Flask XSM Disabled\n");
+        else
+            fprintf(stderr, "Failed to get enforcing mode\n");
+    }
+    else if (ret == 1)
+        printf("Enforcing\n");
+    else if (ret == 0)
+        printf("Permissive\n");
+
+    return ret; 
+}
+
+int main_setenforce(int argc, char **argv)
+{
+    int ret, mode = -1;
+    const char *p = NULL;
+
+    if (optind >= argc) {
+        help("setenforce");
+        return 2;
+    }
+
+    p = argv[optind];
+
+    if (!strcmp(p, "0"))
+        mode = 0;
+    else if (!strcmp(p, "1"))
+        mode = 1;
+    else if (!strcasecmp(p, "permissive"))
+        mode = 0;
+    else if (!strcasecmp(p, "enforcing"))
+        mode = 1;
+    else {
+        help("setenforce");
+        return 2;
+    }
+   
+    ret = libxl_flask_setenforce(ctx, mode);
+
+    if (ret) {
+        if (errno == ENOSYS) {
+            fprintf(stderr, "Flask XSM disabled\n");
+        } 
+        else 
+            fprintf(stderr, "error occured while setting enforcing mode 
(%i)\n", ret);
+    }
+
+    return ret;
+}
+
+int main_loadpolicy(int argc, char **argv)
+{
+    const char *polFName;
+    int polFd = 0;
+    void *polMemCp = NULL;
+    struct stat info;
+    int ret;
+
+    if (optind >= argc) {
+        help("loadpolicy");
+        return 2;
+    }
+
+    polFName = argv[optind];
+    polFd = open(polFName, O_RDONLY);
+    if ( polFd < 0 ) {
+        fprintf(stderr, "Error occurred opening policy file '%s': %s\n",
+                polFName, strerror(errno));
+        ret = -1;
+        goto done;
+    }
+    
+    ret = stat(polFName, &info);
+    if ( ret < 0 ) {
+        fprintf(stderr, "Error occurred retrieving information about"
+                "policy file '%s': %s\n", polFName, strerror(errno));
+        goto done;
+    }
+
+    polMemCp = malloc(info.st_size);
+     
+    ret = read(polFd, polMemCp, info.st_size);
+    if ( ret < 0 ) {
+        fprintf(stderr, "Unable to read new Flask policy file: %s\n",
+                strerror(errno));
+        goto done;
+    }
+
+    ret = libxl_flask_loadpolicy(ctx, polMemCp, info.st_size);
+
+    if (ret < 0) {
+        if (errno == ENOSYS) {
+            fprintf(stderr, "Flask XSM disabled\n");
+        } else {
+            errno = -ret;
+            fprintf(stderr, "Unable to load new Flask policy: %s\n",
+                    strerror(errno));
+            ret = -1;
+        }
+    } else {
+        printf("Successfully loaded policy.\n");
+    }
+
+done:
+    free(polMemCp);
+    if ( polFd > 0 )
+        close(polFd);
+
+    return ret;
+}
diff -r 840e16142824 -r 68947fbeaa76 tools/libxl/xl_cmdtable.c
--- a/tools/libxl/xl_cmdtable.c Thu Jun 02 13:16:52 2011 +0100
+++ b/tools/libxl/xl_cmdtable.c Mon Jun 06 09:49:57 2011 +0100
@@ -36,7 +36,8 @@
       "List information about all/some domains",
       "[options] [Domain]\n",
       "-l, --long              Output all VM details\n"
-      "-v, --verbose           Prints out UUIDs",
+      "-v, --verbose           Prints out UUIDs and security context\n"
+      "-Z, --context           Prints out security context"
     },
     { "destroy",
       &main_destroy,
@@ -364,6 +365,21 @@
       "Splits up the machine into one CPU pool per NUMA node",
       "",
     },
+    { "getenforce",
+      &main_getenforce,
+      "Returns the current enforcing mode of the Flask Xen security module",
+      "",
+    },
+    { "setenforce",
+      &main_setenforce,
+      "Sets the current enforcing mode of the Flask Xen security module",
+      "<1|0|Enforcing|Permissive>",
+    },
+    { "loadpolicy",
+      &main_loadpolicy,
+      "Loads a new policy int the Flask Xen security module",
+      "<policy file>",
+    },
 };
 
 int cmdtable_len = sizeof(cmd_table)/sizeof(struct cmd_spec);
diff -r 840e16142824 -r 68947fbeaa76 xen/arch/x86/hvm/hvm.c
--- a/xen/arch/x86/hvm/hvm.c    Thu Jun 02 13:16:52 2011 +0100
+++ b/xen/arch/x86/hvm/hvm.c    Mon Jun 06 09:49:57 2011 +0100
@@ -2375,7 +2375,6 @@
     return rc ? len : 0; /* fake a copy_from_user() return code */
 }
 
-#define bitmaskof(idx)  (1U << ((idx) & 31))
 void hvm_cpuid(unsigned int input, unsigned int *eax, unsigned int *ebx,
                                    unsigned int *ecx, unsigned int *edx)
 {
@@ -2402,7 +2401,7 @@
         /* Fix up OSXSAVE. */
         if ( xsave_enabled(v) )
             *ecx |= (v->arch.hvm_vcpu.guest_cr[4] & X86_CR4_OSXSAVE) ?
-                     bitmaskof(X86_FEATURE_OSXSAVE) : 0;
+                     cpufeat_mask(X86_FEATURE_OSXSAVE) : 0;
         break;
     case 0xb:
         /* Fix the x2APIC identifier. */
@@ -2433,7 +2432,7 @@
            tsc_mode == TSC_MODE_DEFAULT and host_tsc_is_safe() returns 1 */
         if ( v->domain->arch.tsc_mode != TSC_MODE_DEFAULT ||
              !host_tsc_is_safe() )
-            *edx &= ~bitmaskof(X86_FEATURE_RDTSCP);
+            *edx &= ~cpufeat_mask(X86_FEATURE_RDTSCP);
         break;
     }
 }
@@ -2462,7 +2461,7 @@
     fixed_range_base = (uint64_t *)v->arch.hvm_vcpu.mtrr.fixed_ranges;
 
     hvm_cpuid(1, &cpuid[0], &cpuid[1], &cpuid[2], &cpuid[3]);
-    mtrr = !!(cpuid[3] & bitmaskof(X86_FEATURE_MTRR));
+    mtrr = !!(cpuid[3] & cpufeat_mask(X86_FEATURE_MTRR));
 
     switch ( msr )
     {
@@ -2574,7 +2573,7 @@
                (uint32_t)msr_content, (uint32_t)(msr_content >> 32));
 
     hvm_cpuid(1, &cpuid[0], &cpuid[1], &cpuid[2], &cpuid[3]);
-    mtrr = !!(cpuid[3] & bitmaskof(X86_FEATURE_MTRR));
+    mtrr = !!(cpuid[3] & cpufeat_mask(X86_FEATURE_MTRR));
 
     switch ( msr )
     {
diff -r 840e16142824 -r 68947fbeaa76 xen/arch/x86/hvm/svm/svm.c
--- a/xen/arch/x86/hvm/svm/svm.c        Thu Jun 02 13:16:52 2011 +0100
+++ b/xen/arch/x86/hvm/svm/svm.c        Mon Jun 06 09:49:57 2011 +0100
@@ -1191,7 +1191,6 @@
         vmcb_set_cr0(vmcb, vmcb_get_cr0(vmcb) & ~X86_CR0_TS);
 }
 
-#define bitmaskof(idx)  (1U << ((idx) & 31))
 static void svm_cpuid_intercept(
     unsigned int *eax, unsigned int *ebx,
     unsigned int *ecx, unsigned int *edx)
diff -r 840e16142824 -r 68947fbeaa76 xen/arch/x86/hvm/vmx/vmx.c
--- a/xen/arch/x86/hvm/vmx/vmx.c        Thu Jun 02 13:16:52 2011 +0100
+++ b/xen/arch/x86/hvm/vmx/vmx.c        Mon Jun 06 09:49:57 2011 +0100
@@ -1484,7 +1484,6 @@
     }
 }
 
-#define bitmaskof(idx)  (1U << ((idx) & 31))
 static void vmx_cpuid_intercept(
     unsigned int *eax, unsigned int *ebx,
     unsigned int *ecx, unsigned int *edx)
@@ -1501,9 +1500,9 @@
             /* SYSCALL is visible iff running in long mode. */
             hvm_get_segment_register(v, x86_seg_cs, &cs);
             if ( cs.attr.fields.l )
-                *edx |= bitmaskof(X86_FEATURE_SYSCALL);
+                *edx |= cpufeat_mask(X86_FEATURE_SYSCALL);
             else
-                *edx &= ~(bitmaskof(X86_FEATURE_SYSCALL));
+                *edx &= ~(cpufeat_mask(X86_FEATURE_SYSCALL));
 
             break;
     }
diff -r 840e16142824 -r 68947fbeaa76 xen/arch/x86/setup.c
--- a/xen/arch/x86/setup.c      Thu Jun 02 13:16:52 2011 +0100
+++ b/xen/arch/x86/setup.c      Mon Jun 06 09:49:57 2011 +0100
@@ -57,6 +57,10 @@
 static bool_t __initdata opt_watchdog;
 boolean_param("watchdog", opt_watchdog);
 
+/* smep: Enable/disable Supervisor Mode Execution Protection (default on). */
+static bool_t __initdata disable_smep;
+invbool_param("smep", disable_smep);
+
 /* **** Linux config option: propagated to domain0. */
 /* "acpi=off":    Sisables both ACPI table parsing and interpreter. */
 /* "acpi=force":  Override the disable blacklist.                   */
@@ -1200,11 +1204,17 @@
     arch_init_memory();
 
     identify_cpu(&boot_cpu_data);
+
     if ( cpu_has_fxsr )
         set_in_cr4(X86_CR4_OSFXSR);
     if ( cpu_has_xmm )
         set_in_cr4(X86_CR4_OSXMMEXCPT);
 
+    if ( disable_smep )
+        setup_clear_cpu_cap(X86_FEATURE_SMEP);
+    if ( cpu_has_smep )
+        set_in_cr4(X86_CR4_SMEP);
+
     local_irq_enable();
 
 #ifdef CONFIG_X86_64
diff -r 840e16142824 -r 68947fbeaa76 xen/arch/x86/traps.c
--- a/xen/arch/x86/traps.c      Thu Jun 02 13:16:52 2011 +0100
+++ b/xen/arch/x86/traps.c      Mon Jun 06 09:49:57 2011 +0100
@@ -813,6 +813,13 @@
            __clear_bit(X86_FEATURE_X2APIC % 32, &c);
         __set_bit(X86_FEATURE_HYPERVISOR % 32, &c);
         break;
+    case 7:
+        if ( regs->ecx == 0 )
+            b &= cpufeat_mask(X86_FEATURE_FSGSBASE);
+        else
+            b = 0;
+        a = c = d = 0;
+        break;
     case 0x80000001:
         /* Modify Feature Information. */
         if ( is_pv_32bit_vcpu(current) )
@@ -1132,7 +1139,13 @@
     (((va) >= HYPERVISOR_VIRT_START))
 #endif
 
-static int __spurious_page_fault(
+enum pf_type {
+    real_fault,
+    smep_fault,
+    spurious_fault
+};
+
+static enum pf_type __page_fault_type(
     unsigned long addr, unsigned int error_code)
 {
     unsigned long mfn, cr3 = read_cr3();
@@ -1144,7 +1157,7 @@
 #endif
     l2_pgentry_t l2e, *l2t;
     l1_pgentry_t l1e, *l1t;
-    unsigned int required_flags, disallowed_flags;
+    unsigned int required_flags, disallowed_flags, page_user;
 
     /*
      * We do not take spurious page faults in IRQ handlers as we do not
@@ -1152,11 +1165,11 @@
      * map_domain_page() is not IRQ-safe.
      */
     if ( in_irq() )
-        return 0;
+        return real_fault;
 
     /* Reserved bit violations are never spurious faults. */
     if ( error_code & PFEC_reserved_bit )
-        return 0;
+        return real_fault;
 
     required_flags  = _PAGE_PRESENT;
     if ( error_code & PFEC_write_access )
@@ -1168,6 +1181,8 @@
     if ( error_code & PFEC_insn_fetch )
         disallowed_flags |= _PAGE_NX_BIT;
 
+    page_user = _PAGE_USER;
+
     mfn = cr3 >> PAGE_SHIFT;
 
 #if CONFIG_PAGING_LEVELS >= 4
@@ -1177,7 +1192,8 @@
     unmap_domain_page(l4t);
     if ( ((l4e_get_flags(l4e) & required_flags) != required_flags) ||
          (l4e_get_flags(l4e) & disallowed_flags) )
-        return 0;
+        return real_fault;
+    page_user &= l4e_get_flags(l4e);
 #endif
 
 #if CONFIG_PAGING_LEVELS >= 3
@@ -1190,13 +1206,14 @@
     unmap_domain_page(l3t);
 #if CONFIG_PAGING_LEVELS == 3
     if ( !(l3e_get_flags(l3e) & _PAGE_PRESENT) )
-        return 0;
+        return real_fault;
 #else
     if ( ((l3e_get_flags(l3e) & required_flags) != required_flags) ||
          (l3e_get_flags(l3e) & disallowed_flags) )
-        return 0;
+        return real_fault;
+    page_user &= l3e_get_flags(l3e);
     if ( l3e_get_flags(l3e) & _PAGE_PSE )
-        return 1;
+        goto leaf;
 #endif
 #endif
 
@@ -1206,9 +1223,10 @@
     unmap_domain_page(l2t);
     if ( ((l2e_get_flags(l2e) & required_flags) != required_flags) ||
          (l2e_get_flags(l2e) & disallowed_flags) )
-        return 0;
+        return real_fault;
+    page_user &= l2e_get_flags(l2e);
     if ( l2e_get_flags(l2e) & _PAGE_PSE )
-        return 1;
+        goto leaf;
 
     l1t = map_domain_page(mfn);
     l1e = l1e_read_atomic(&l1t[l1_table_offset(addr)]);
@@ -1216,26 +1234,36 @@
     unmap_domain_page(l1t);
     if ( ((l1e_get_flags(l1e) & required_flags) != required_flags) ||
          (l1e_get_flags(l1e) & disallowed_flags) )
-        return 0;
-
-    return 1;
+        return real_fault;
+    page_user &= l1e_get_flags(l1e);
+
+leaf:
+    /*
+     * Supervisor Mode Execution Protection (SMEP):
+     * Disallow supervisor execution from user-accessible mappings
+     */
+    if ( (read_cr4() & X86_CR4_SMEP) && page_user &&
+         ((error_code & (PFEC_insn_fetch|PFEC_user_mode)) == PFEC_insn_fetch) )
+        return smep_fault;
+
+    return spurious_fault;
 }
 
-static int spurious_page_fault(
+static enum pf_type spurious_page_fault(
     unsigned long addr, unsigned int error_code)
 {
     unsigned long flags;
-    int           is_spurious;
+    enum pf_type pf_type;
 
     /*
      * Disabling interrupts prevents TLB flushing, and hence prevents
      * page tables from becoming invalid under our feet during the walk.
      */
     local_irq_save(flags);
-    is_spurious = __spurious_page_fault(addr, error_code);
+    pf_type = __page_fault_type(addr, error_code);
     local_irq_restore(flags);
 
-    return is_spurious;
+    return pf_type;
 }
 
 static int fixup_page_fault(unsigned long addr, struct cpu_user_regs *regs)
@@ -1310,6 +1338,7 @@
 {
     unsigned long addr, fixup;
     unsigned int error_code;
+    enum pf_type pf_type;
 
     addr = read_cr2();
 
@@ -1325,7 +1354,9 @@
 
     if ( unlikely(!guest_mode(regs)) )
     {
-        if ( spurious_page_fault(addr, error_code) )
+        pf_type = spurious_page_fault(addr, error_code);
+        BUG_ON(pf_type == smep_fault);
+        if ( pf_type != real_fault )
             return;
 
         if ( likely((fixup = search_exception_table(regs->eip)) != 0) )
@@ -1347,9 +1378,17 @@
               error_code, _p(addr));
     }
 
-    if ( unlikely(current->domain->arch.suppress_spurious_page_faults
-                  && spurious_page_fault(addr, error_code)) )
-        return;
+    if ( unlikely(current->domain->arch.suppress_spurious_page_faults) )
+    {
+        pf_type = spurious_page_fault(addr, error_code);
+        if ( pf_type == smep_fault )
+        {
+            gdprintk(XENLOG_ERR, "Fatal SMEP fault\n");
+            domain_crash(current->domain);
+        }
+        if ( pf_type != real_fault )
+            return;
+    }
 
     propagate_page_fault(addr, regs->error_code);
 }
diff -r 840e16142824 -r 68947fbeaa76 xen/include/asm-x86/cpufeature.h
--- a/xen/include/asm-x86/cpufeature.h  Thu Jun 02 13:16:52 2011 +0100
+++ b/xen/include/asm-x86/cpufeature.h  Mon Jun 06 09:49:57 2011 +0100
@@ -141,11 +141,13 @@
 #define X86_FEATURE_TBM         (6*32+21) /* trailing bit manipulations */
 #define X86_FEATURE_TOPOEXT     (6*32+22) /* topology extensions CPUID leafs */
 
-/* Intel-defined CPU features, CPUID level 0x00000007:0 (ebx), word 9 */
+/* Intel-defined CPU features, CPUID level 0x00000007:0 (ebx), word 7 */
 #define X86_FEATURE_FSGSBASE   (7*32+ 0) /* {RD,WR}{FS,GS}BASE instructions */
+#define X86_FEATURE_SMEP       (7*32+ 7) /* Supervisor Mode Execution 
Protection */
 
 #define cpu_has(c, bit)                test_bit(bit, (c)->x86_capability)
 #define boot_cpu_has(bit)      test_bit(bit, boot_cpu_data.x86_capability)
+#define cpufeat_mask(idx)       (1u << ((idx) & 31))
 
 #ifdef __i386__
 #define cpu_has_vme            boot_cpu_has(X86_FEATURE_VME)
@@ -201,6 +203,8 @@
 #define cpu_has_fsgsbase       boot_cpu_has(X86_FEATURE_FSGSBASE)
 #endif
 
+#define cpu_has_smep            boot_cpu_has(X86_FEATURE_SMEP)
+
 #define cpu_has_ffxsr           ((boot_cpu_data.x86_vendor == X86_VENDOR_AMD) \
                                  && boot_cpu_has(X86_FEATURE_FFXSR))
 
diff -r 840e16142824 -r 68947fbeaa76 xen/include/asm-x86/domain.h
--- a/xen/include/asm-x86/domain.h      Thu Jun 02 13:16:52 2011 +0100
+++ b/xen/include/asm-x86/domain.h      Mon Jun 06 09:49:57 2011 +0100
@@ -516,12 +516,14 @@
 /* Convert between guest-visible and real CR4 values. */
 #define pv_guest_cr4_to_real_cr4(v)                         \
     (((v)->arch.pv_vcpu.ctrlreg[4]                          \
-      | (mmu_cr4_features & (X86_CR4_PGE | X86_CR4_PSE))    \
-      | ((v)->domain->arch.vtsc ? X86_CR4_TSD : 0)         \
-      | ((xsave_enabled(v))? X86_CR4_OSXSAVE : 0))              \
-      & ~X86_CR4_DE)
-#define real_cr4_to_pv_guest_cr4(c) \
-    ((c) & ~(X86_CR4_PGE | X86_CR4_PSE | X86_CR4_TSD | X86_CR4_OSXSAVE))
+      | (mmu_cr4_features                                   \
+         & (X86_CR4_PGE | X86_CR4_PSE | X86_CR4_SMEP))      \
+      | ((v)->domain->arch.vtsc ? X86_CR4_TSD : 0)          \
+      | ((xsave_enabled(v))? X86_CR4_OSXSAVE : 0))          \
+     & ~X86_CR4_DE)
+#define real_cr4_to_pv_guest_cr4(c)                         \
+    ((c) & ~(X86_CR4_PGE | X86_CR4_PSE | X86_CR4_TSD        \
+             | X86_CR4_OSXSAVE | X86_CR4_SMEP))
 
 void domain_cpuid(struct domain *d,
                   unsigned int  input,
diff -r 840e16142824 -r 68947fbeaa76 xen/include/asm-x86/processor.h
--- a/xen/include/asm-x86/processor.h   Thu Jun 02 13:16:52 2011 +0100
+++ b/xen/include/asm-x86/processor.h   Mon Jun 06 09:49:57 2011 +0100
@@ -85,6 +85,7 @@
 #define X86_CR4_SMXE           0x4000  /* enable SMX */
 #define X86_CR4_FSGSBASE       0x10000 /* enable {rd,wr}{fs,gs}base */
 #define X86_CR4_OSXSAVE        0x40000 /* enable XSAVE/XRSTOR */
+#define X86_CR4_SMEP           0x100000/* enable SMEP */
 
 /*
  * Trap/fault mnemonics.

_______________________________________________
Xen-changelog mailing list
Xen-changelog@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-changelog


 


Rackspace

Lists.xenproject.org is hosted with RackSpace, monitoring our
servers 24x7x365 and backed by RackSpace's Fanatical Support®.