aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--hw/acpi/aml-build.c28
-rw-r--r--hw/acpi/pci.c1
-rw-r--r--hw/acpi/pcihp.c104
-rw-r--r--hw/acpi/piix4.c3
-rw-r--r--hw/acpi/trace-events2
-rw-r--r--hw/acpi/utils.c17
-rw-r--r--hw/arm/virt-acpi-build.c12
-rw-r--r--hw/i386/acpi-build.c173
-rw-r--r--hw/i386/acpi-microvm.c32
-rw-r--r--hw/i386/microvm.c66
-rw-r--r--hw/i386/pc.c63
-rw-r--r--hw/i386/x86.c64
-rw-r--r--hw/pci/pci.c1
-rw-r--r--hw/sd/sd.c23
-rw-r--r--hw/sd/sdhci.c53
-rw-r--r--hw/virtio/vhost-user.c217
-rw-r--r--hw/virtio/virtio-mmio.c74
-rw-r--r--hw/virtio/virtio-pmem.c2
-rw-r--r--include/hw/acpi/aml-build.h6
-rw-r--r--include/hw/acpi/pci.h1
-rw-r--r--include/hw/acpi/pcihp.h9
-rw-r--r--include/hw/acpi/utils.h3
-rw-r--r--include/hw/i386/microvm.h4
-rw-r--r--include/hw/i386/pc.h4
-rw-r--r--include/hw/i386/x86.h4
-rw-r--r--include/hw/pci/pci.h1
-rw-r--r--tests/data/acpi/pc/DSDTbin5065 -> 6002 bytes
-rw-r--r--tests/data/acpi/pc/DSDT.acpihmatbin6390 -> 7327 bytes
-rw-r--r--tests/data/acpi/pc/DSDT.bridgebin6924 -> 8668 bytes
-rw-r--r--tests/data/acpi/pc/DSDT.cphpbin5529 -> 6466 bytes
-rw-r--r--tests/data/acpi/pc/DSDT.dimmpxmbin6719 -> 7656 bytes
-rw-r--r--tests/data/acpi/pc/DSDT.hpbridgebin5026 -> 5969 bytes
-rw-r--r--tests/data/acpi/pc/DSDT.ipmikcsbin5137 -> 6074 bytes
-rw-r--r--tests/data/acpi/pc/DSDT.memhpbin6424 -> 7361 bytes
-rw-r--r--tests/data/acpi/pc/DSDT.nohpetbin4923 -> 5860 bytes
-rw-r--r--tests/data/acpi/pc/DSDT.numamembin5071 -> 6008 bytes
-rw-r--r--tests/data/acpi/pc/DSDT.roothpbin5261 -> 6210 bytes
37 files changed, 633 insertions, 334 deletions
diff --git a/hw/acpi/aml-build.c b/hw/acpi/aml-build.c
index a2cd7a5..d33ce89 100644
--- a/hw/acpi/aml-build.c
+++ b/hw/acpi/aml-build.c
@@ -634,6 +634,19 @@ Aml *aml_to_buffer(Aml *src, Aml *dst)
return var;
}
+/* ACPI 2.0a: 17.2.4.4 Type 2 Opcodes Encoding: DefToDecimalString */
+Aml *aml_to_decimalstring(Aml *src, Aml *dst)
+{
+ Aml *var = aml_opcode(0x97 /* ToDecimalStringOp */);
+ aml_append(var, src);
+ if (dst) {
+ aml_append(var, dst);
+ } else {
+ build_append_byte(var->buf, 0x00 /* NullNameOp */);
+ }
+ return var;
+}
+
/* ACPI 1.0b: 16.2.5.4 Type 2 Opcodes Encoding: DefStore */
Aml *aml_store(Aml *val, Aml *target)
{
@@ -835,6 +848,21 @@ Aml *aml_call5(const char *method, Aml *arg1, Aml *arg2, Aml *arg3, Aml *arg4,
return var;
}
+/* helper to call method with 5 arguments */
+Aml *aml_call6(const char *method, Aml *arg1, Aml *arg2, Aml *arg3, Aml *arg4,
+ Aml *arg5, Aml *arg6)
+{
+ Aml *var = aml_alloc();
+ build_append_namestring(var->buf, "%s", method);
+ aml_append(var, arg1);
+ aml_append(var, arg2);
+ aml_append(var, arg3);
+ aml_append(var, arg4);
+ aml_append(var, arg5);
+ aml_append(var, arg6);
+ return var;
+}
+
/*
* ACPI 5.0: 6.4.3.8.1 GPIO Connection Descriptor
* Type 1, Large Item Name 0xC
diff --git a/hw/acpi/pci.c b/hw/acpi/pci.c
index ec455c3..75b1103 100644
--- a/hw/acpi/pci.c
+++ b/hw/acpi/pci.c
@@ -59,4 +59,3 @@ void build_mcfg(GArray *table_data, BIOSLinker *linker, AcpiMcfgInfo *info,
build_header(linker, table_data, (void *)(table_data->data + mcfg_start),
"MCFG", table_data->len - mcfg_start, 1, oem_id, oem_table_id);
}
-
diff --git a/hw/acpi/pcihp.c b/hw/acpi/pcihp.c
index 9dc4d3e..f4cb3c9 100644
--- a/hw/acpi/pcihp.c
+++ b/hw/acpi/pcihp.c
@@ -39,18 +39,34 @@
#include "trace.h"
#define ACPI_PCIHP_ADDR 0xae00
-#define ACPI_PCIHP_SIZE 0x0014
+#define ACPI_PCIHP_SIZE 0x0018
#define PCI_UP_BASE 0x0000
#define PCI_DOWN_BASE 0x0004
#define PCI_EJ_BASE 0x0008
#define PCI_RMV_BASE 0x000c
#define PCI_SEL_BASE 0x0010
+#define PCI_AIDX_BASE 0x0014
typedef struct AcpiPciHpFind {
int bsel;
PCIBus *bus;
} AcpiPciHpFind;
+static gint g_cmp_uint32(gconstpointer a, gconstpointer b, gpointer user_data)
+{
+ return a - b;
+}
+
+static GSequence *pci_acpi_index_list(void)
+{
+ static GSequence *used_acpi_index_list;
+
+ if (!used_acpi_index_list) {
+ used_acpi_index_list = g_sequence_new(NULL);
+ }
+ return used_acpi_index_list;
+}
+
static int acpi_pcihp_get_bsel(PCIBus *bus)
{
Error *local_err = NULL;
@@ -251,9 +267,13 @@ void acpi_pcihp_reset(AcpiPciHpState *s, bool acpihp_root_off)
acpi_pcihp_update(s);
}
+#define ONBOARD_INDEX_MAX (16 * 1024 - 1)
+
void acpi_pcihp_device_pre_plug_cb(HotplugHandler *hotplug_dev,
DeviceState *dev, Error **errp)
{
+ PCIDevice *pdev = PCI_DEVICE(dev);
+
/* Only hotplugged devices need the hotplug capability. */
if (dev->hotplugged &&
acpi_pcihp_get_bsel(pci_get_bus(PCI_DEVICE(dev))) < 0) {
@@ -261,6 +281,34 @@ void acpi_pcihp_device_pre_plug_cb(HotplugHandler *hotplug_dev,
ACPI_PCIHP_PROP_BSEL "' set");
return;
}
+
+ /*
+ * capped by systemd (see: udev-builtin-net_id.c)
+ * as it's the only known user honor it to avoid users
+ * misconfigure QEMU and then wonder why acpi-index doesn't work
+ */
+ if (pdev->acpi_index > ONBOARD_INDEX_MAX) {
+ error_setg(errp, "acpi-index should be less or equal to %u",
+ ONBOARD_INDEX_MAX);
+ return;
+ }
+
+ /*
+ * make sure that acpi-index is unique across all present PCI devices
+ */
+ if (pdev->acpi_index) {
+ GSequence *used_indexes = pci_acpi_index_list();
+
+ if (g_sequence_lookup(used_indexes, GINT_TO_POINTER(pdev->acpi_index),
+ g_cmp_uint32, NULL)) {
+ error_setg(errp, "a PCI device with acpi-index = %" PRIu32
+ " already exist", pdev->acpi_index);
+ return;
+ }
+ g_sequence_insert_sorted(used_indexes,
+ GINT_TO_POINTER(pdev->acpi_index),
+ g_cmp_uint32, NULL);
+ }
}
void acpi_pcihp_device_plug_cb(HotplugHandler *hotplug_dev, AcpiPciHpState *s,
@@ -299,8 +347,22 @@ void acpi_pcihp_device_plug_cb(HotplugHandler *hotplug_dev, AcpiPciHpState *s,
void acpi_pcihp_device_unplug_cb(HotplugHandler *hotplug_dev, AcpiPciHpState *s,
DeviceState *dev, Error **errp)
{
+ PCIDevice *pdev = PCI_DEVICE(dev);
+
trace_acpi_pci_unplug(PCI_SLOT(PCI_DEVICE(dev)->devfn),
acpi_pcihp_get_bsel(pci_get_bus(PCI_DEVICE(dev))));
+
+ /*
+ * clean up acpi-index so it could reused by another device
+ */
+ if (pdev->acpi_index) {
+ GSequence *used_indexes = pci_acpi_index_list();
+
+ g_sequence_remove(g_sequence_lookup(used_indexes,
+ GINT_TO_POINTER(pdev->acpi_index),
+ g_cmp_uint32, NULL));
+ }
+
qdev_unrealize(dev);
}
@@ -347,7 +409,6 @@ static uint64_t pci_read(void *opaque, hwaddr addr, unsigned int size)
trace_acpi_pci_down_read(val);
break;
case PCI_EJ_BASE:
- /* No feature defined yet */
trace_acpi_pci_features_read(val);
break;
case PCI_RMV_BASE:
@@ -357,6 +418,12 @@ static uint64_t pci_read(void *opaque, hwaddr addr, unsigned int size)
case PCI_SEL_BASE:
val = s->hotplug_select;
trace_acpi_pci_sel_read(val);
+ break;
+ case PCI_AIDX_BASE:
+ val = s->acpi_index;
+ s->acpi_index = 0;
+ trace_acpi_pci_acpi_index_read(val);
+ break;
default:
break;
}
@@ -367,8 +434,35 @@ static uint64_t pci_read(void *opaque, hwaddr addr, unsigned int size)
static void pci_write(void *opaque, hwaddr addr, uint64_t data,
unsigned int size)
{
+ int slot;
+ PCIBus *bus;
+ BusChild *kid, *next;
AcpiPciHpState *s = opaque;
+
+ s->acpi_index = 0;
switch (addr) {
+ case PCI_AIDX_BASE:
+ /*
+ * fetch acpi-index for specified slot so that follow up read from
+ * PCI_AIDX_BASE can return it to guest
+ */
+ slot = ctz32(data);
+
+ if (s->hotplug_select >= ACPI_PCIHP_MAX_HOTPLUG_BUS) {
+ break;
+ }
+
+ bus = acpi_pcihp_find_hotplug_bus(s, s->hotplug_select);
+ QTAILQ_FOREACH_SAFE(kid, &bus->qbus.children, sibling, next) {
+ Object *o = OBJECT(kid->child);
+ PCIDevice *dev = PCI_DEVICE(o);
+ if (PCI_SLOT(dev->devfn) == slot) {
+ s->acpi_index = object_property_get_uint(o, "acpi-index", NULL);
+ break;
+ }
+ }
+ trace_acpi_pci_acpi_index_write(s->hotplug_select, slot, s->acpi_index);
+ break;
case PCI_EJ_BASE:
if (s->hotplug_select >= ACPI_PCIHP_MAX_HOTPLUG_BUS) {
break;
@@ -413,6 +507,12 @@ void acpi_pcihp_init(Object *owner, AcpiPciHpState *s, PCIBus *root_bus,
OBJ_PROP_FLAG_READ);
}
+bool vmstate_acpi_pcihp_use_acpi_index(void *opaque, int version_id)
+{
+ AcpiPciHpState *s = opaque;
+ return s->acpi_index;
+}
+
const VMStateDescription vmstate_acpi_pcihp_pci_status = {
.name = "acpi_pcihp_pci_status",
.version_id = 1,
diff --git a/hw/acpi/piix4.c b/hw/acpi/piix4.c
index 1efc0de..6056d51 100644
--- a/hw/acpi/piix4.c
+++ b/hw/acpi/piix4.c
@@ -297,7 +297,8 @@ static const VMStateDescription vmstate_acpi = {
2, vmstate_pci_status,
struct AcpiPciHpPciStatus),
VMSTATE_PCI_HOTPLUG(acpi_pci_hotplug, PIIX4PMState,
- vmstate_test_use_acpi_hotplug_bridge),
+ vmstate_test_use_acpi_hotplug_bridge,
+ vmstate_acpi_pcihp_use_acpi_index),
VMSTATE_END_OF_LIST()
},
.subsections = (const VMStateDescription*[]) {
diff --git a/hw/acpi/trace-events b/hw/acpi/trace-events
index f91ced4..dcc1438 100644
--- a/hw/acpi/trace-events
+++ b/hw/acpi/trace-events
@@ -41,6 +41,8 @@ acpi_pci_unplug_request(int bsel, int slot) "bsel: %d slot: %d"
acpi_pci_up_read(uint32_t val) "%" PRIu32
acpi_pci_down_read(uint32_t val) "%" PRIu32
acpi_pci_features_read(uint32_t val) "%" PRIu32
+acpi_pci_acpi_index_read(uint32_t val) "%" PRIu32
+acpi_pci_acpi_index_write(unsigned bsel, unsigned slot, uint32_t aidx) "bsel: %u slot: %u aidx: %" PRIu32
acpi_pci_rmv_read(uint32_t val) "%" PRIu32
acpi_pci_sel_read(uint32_t val) "%" PRIu32
acpi_pci_ej_write(uint64_t addr, uint64_t data) "0x%" PRIx64 " <== %" PRIu64
diff --git a/hw/acpi/utils.c b/hw/acpi/utils.c
index a134a4d..0c486ea 100644
--- a/hw/acpi/utils.c
+++ b/hw/acpi/utils.c
@@ -27,9 +27,22 @@
#include "hw/loader.h"
MemoryRegion *acpi_add_rom_blob(FWCfgCallback update, void *opaque,
- GArray *blob, const char *name,
- uint64_t max_size)
+ GArray *blob, const char *name)
{
+ uint64_t max_size;
+
+ /* Reserve RAM space for tables: add another order of magnitude. */
+ if (!strcmp(name, ACPI_BUILD_TABLE_FILE)) {
+ max_size = 0x200000;
+ } else if (!strcmp(name, ACPI_BUILD_LOADER_FILE)) {
+ max_size = 0x10000;
+ } else if (!strcmp(name, ACPI_BUILD_RSDP_FILE)) {
+ max_size = 0x1000;
+ } else {
+ g_assert_not_reached();
+ }
+ g_assert(acpi_data_len(blob) <= max_size);
+
return rom_add_blob(name, blob->data, acpi_data_len(blob), max_size, -1,
name, update, opaque, NULL, true);
}
diff --git a/hw/arm/virt-acpi-build.c b/hw/arm/virt-acpi-build.c
index f9c9df9..f5a2b2d 100644
--- a/hw/arm/virt-acpi-build.c
+++ b/hw/arm/virt-acpi-build.c
@@ -859,13 +859,13 @@ void virt_acpi_setup(VirtMachineState *vms)
/* Now expose it all to Guest */
build_state->table_mr = acpi_add_rom_blob(virt_acpi_build_update,
build_state, tables.table_data,
- ACPI_BUILD_TABLE_FILE,
- ACPI_BUILD_TABLE_MAX_SIZE);
+ ACPI_BUILD_TABLE_FILE);
assert(build_state->table_mr != NULL);
- build_state->linker_mr =
- acpi_add_rom_blob(virt_acpi_build_update, build_state,
- tables.linker->cmd_blob, ACPI_BUILD_LOADER_FILE, 0);
+ build_state->linker_mr = acpi_add_rom_blob(virt_acpi_build_update,
+ build_state,
+ tables.linker->cmd_blob,
+ ACPI_BUILD_LOADER_FILE);
fw_cfg_add_file(vms->fw_cfg, ACPI_BUILD_TPMLOG_FILE, tables.tcpalog->data,
acpi_data_len(tables.tcpalog));
@@ -879,7 +879,7 @@ void virt_acpi_setup(VirtMachineState *vms)
build_state->rsdp_mr = acpi_add_rom_blob(virt_acpi_build_update,
build_state, tables.rsdp,
- ACPI_BUILD_RSDP_FILE, 0);
+ ACPI_BUILD_RSDP_FILE);
qemu_register_reset(virt_acpi_build_reset, build_state);
virt_acpi_build_reset(build_state);
diff --git a/hw/i386/acpi-build.c b/hw/i386/acpi-build.c
index 442b462..de98750 100644
--- a/hw/i386/acpi-build.c
+++ b/hw/i386/acpi-build.c
@@ -397,6 +397,13 @@ static void build_append_pci_bus_devices(Aml *parent_scope, PCIBus *bus,
aml_call2("PCEJ", aml_name("BSEL"), aml_name("_SUN"))
);
aml_append(dev, method);
+ method = aml_method("_DSM", 4, AML_SERIALIZED);
+ aml_append(method,
+ aml_return(aml_call6("PDSM", aml_arg(0), aml_arg(1),
+ aml_arg(2), aml_arg(3),
+ aml_name("BSEL"), aml_name("_SUN")))
+ );
+ aml_append(dev, method);
aml_append(parent_scope, dev);
build_append_pcihp_notify_entry(notify_method, slot);
@@ -424,6 +431,16 @@ static void build_append_pci_bus_devices(Aml *parent_scope, PCIBus *bus,
dev = aml_device("S%.02X", PCI_DEVFN(slot, 0));
aml_append(dev, aml_name_decl("_ADR", aml_int(slot << 16)));
+ if (bsel) {
+ aml_append(dev, aml_name_decl("_SUN", aml_int(slot)));
+ method = aml_method("_DSM", 4, AML_SERIALIZED);
+ aml_append(method, aml_return(
+ aml_call6("PDSM", aml_arg(0), aml_arg(1), aml_arg(2),
+ aml_arg(3), aml_name("BSEL"), aml_name("_SUN"))
+ ));
+ aml_append(dev, method);
+ }
+
if (pc->class_id == PCI_CLASS_DISPLAY_VGA) {
/* add VGA specific AML methods */
int s3d;
@@ -446,9 +463,7 @@ static void build_append_pci_bus_devices(Aml *parent_scope, PCIBus *bus,
aml_append(method, aml_return(aml_int(s3d)));
aml_append(dev, method);
} else if (hotplug_enabled_dev) {
- /* add _SUN/_EJ0 to make slot hotpluggable */
- aml_append(dev, aml_name_decl("_SUN", aml_int(slot)));
-
+ /* add _EJ0 to make slot hotpluggable */
method = aml_method("_EJ0", 1, AML_NOTSERIALIZED);
aml_append(method,
aml_call2("PCEJ", aml_name("BSEL"), aml_name("_SUN"))
@@ -511,6 +526,88 @@ static void build_append_pci_bus_devices(Aml *parent_scope, PCIBus *bus,
qobject_unref(bsel);
}
+Aml *aml_pci_device_dsm(void)
+{
+ Aml *method, *UUID, *ifctx, *ifctx1, *ifctx2, *ifctx3, *elsectx;
+ Aml *acpi_index = aml_local(0);
+ Aml *zero = aml_int(0);
+ Aml *bnum = aml_arg(4);
+ Aml *func = aml_arg(2);
+ Aml *rev = aml_arg(1);
+ Aml *sun = aml_arg(5);
+
+ method = aml_method("PDSM", 6, AML_SERIALIZED);
+
+ /*
+ * PCI Firmware Specification 3.1
+ * 4.6. _DSM Definitions for PCI
+ */
+ UUID = aml_touuid("E5C937D0-3553-4D7A-9117-EA4D19C3434D");
+ ifctx = aml_if(aml_equal(aml_arg(0), UUID));
+ {
+ aml_append(ifctx, aml_store(aml_call2("AIDX", bnum, sun), acpi_index));
+ ifctx1 = aml_if(aml_equal(func, zero));
+ {
+ uint8_t byte_list[1];
+
+ ifctx2 = aml_if(aml_equal(rev, aml_int(2)));
+ {
+ /*
+ * advertise function 7 if device has acpi-index
+ * acpi_index values:
+ * 0: not present (default value)
+ * FFFFFFFF: not supported (old QEMU without PIDX reg)
+ * other: device's acpi-index
+ */
+ ifctx3 = aml_if(aml_lnot(
+ aml_or(aml_equal(acpi_index, zero),
+ aml_equal(acpi_index, aml_int(0xFFFFFFFF)), NULL)
+ ));
+ {
+ byte_list[0] =
+ 1 /* have supported functions */ |
+ 1 << 7 /* support for function 7 */
+ ;
+ aml_append(ifctx3, aml_return(aml_buffer(1, byte_list)));
+ }
+ aml_append(ifctx2, ifctx3);
+ }
+ aml_append(ifctx1, ifctx2);
+
+ byte_list[0] = 0; /* nothing supported */
+ aml_append(ifctx1, aml_return(aml_buffer(1, byte_list)));
+ }
+ aml_append(ifctx, ifctx1);
+ elsectx = aml_else();
+ /*
+ * PCI Firmware Specification 3.1
+ * 4.6.7. _DSM for Naming a PCI or PCI Express Device Under
+ * Operating Systems
+ */
+ ifctx1 = aml_if(aml_equal(func, aml_int(7)));
+ {
+ Aml *pkg = aml_package(2);
+ Aml *ret = aml_local(1);
+
+ aml_append(pkg, zero);
+ /*
+ * optional, if not impl. should return null string
+ */
+ aml_append(pkg, aml_string("%s", ""));
+ aml_append(ifctx1, aml_store(pkg, ret));
+ /*
+ * update acpi-index to actual value
+ */
+ aml_append(ifctx1, aml_store(acpi_index, aml_index(ret, zero)));
+ aml_append(ifctx1, aml_return(ret));
+ }
+ aml_append(elsectx, ifctx1);
+ aml_append(ifctx, elsectx);
+ }
+ aml_append(method, ifctx);
+ return method;
+}
+
/**
* build_prt_entry:
* @link_name: link name for PCI route entry
@@ -1168,9 +1265,10 @@ static void build_piix4_pci_hotplug(Aml *table)
aml_append(scope, field);
aml_append(scope,
- aml_operation_region("BNMR", AML_SYSTEM_IO, aml_int(0xae10), 0x04));
+ aml_operation_region("BNMR", AML_SYSTEM_IO, aml_int(0xae10), 0x08));
field = aml_field("BNMR", AML_DWORD_ACC, AML_NOLOCK, AML_WRITE_AS_ZEROS);
aml_append(field, aml_named_field("BNUM", 32));
+ aml_append(field, aml_named_field("PIDX", 32));
aml_append(scope, field);
aml_append(scope, aml_mutex("BLCK", 0));
@@ -1184,6 +1282,18 @@ static void build_piix4_pci_hotplug(Aml *table)
aml_append(method, aml_return(aml_int(0)));
aml_append(scope, method);
+ method = aml_method("AIDX", 2, AML_NOTSERIALIZED);
+ aml_append(method, aml_acquire(aml_name("BLCK"), 0xFFFF));
+ aml_append(method, aml_store(aml_arg(0), aml_name("BNUM")));
+ aml_append(method,
+ aml_store(aml_shiftleft(aml_int(1), aml_arg(1)), aml_name("PIDX")));
+ aml_append(method, aml_store(aml_name("PIDX"), aml_local(0)));
+ aml_append(method, aml_release(aml_name("BLCK")));
+ aml_append(method, aml_return(aml_local(0)));
+ aml_append(scope, method);
+
+ aml_append(scope, aml_pci_device_dsm());
+
aml_append(table, scope);
}
@@ -1697,7 +1807,7 @@ build_dsdt(GArray *table_data, BIOSLinker *linker,
g_array_append_vals(table_data, dsdt->buf->data, dsdt->buf->len);
build_header(linker, table_data,
(void *)(table_data->data + table_data->len - dsdt->buf->len),
- "DSDT", dsdt->buf->len, 1, pcms->oem_id, pcms->oem_table_id);
+ "DSDT", dsdt->buf->len, 1, x86ms->oem_id, x86ms->oem_table_id);
free_aml_allocator();
}
@@ -1874,8 +1984,8 @@ build_srat(GArray *table_data, BIOSLinker *linker, MachineState *machine)
build_header(linker, table_data,
(void *)(table_data->data + srat_start),
"SRAT",
- table_data->len - srat_start, 1, pcms->oem_id,
- pcms->oem_table_id);
+ table_data->len - srat_start, 1, x86ms->oem_id,
+ x86ms->oem_table_id);
}
/*
@@ -2228,13 +2338,13 @@ void acpi_build(AcpiBuildTables *tables, MachineState *machine)
if (slic_oem.id) {
oem_id = slic_oem.id;
} else {
- oem_id = pcms->oem_id;
+ oem_id = x86ms->oem_id;
}
if (slic_oem.table_id) {
oem_table_id = slic_oem.table_id;
} else {
- oem_table_id = pcms->oem_table_id;
+ oem_table_id = x86ms->oem_table_id;
}
table_offsets = g_array_new(false, true /* clear */,
@@ -2275,30 +2385,30 @@ void acpi_build(AcpiBuildTables *tables, MachineState *machine)
acpi_add_table(table_offsets, tables_blob);
acpi_build_madt(tables_blob, tables->linker, x86ms,
- ACPI_DEVICE_IF(x86ms->acpi_dev), pcms->oem_id,
- pcms->oem_table_id);
+ ACPI_DEVICE_IF(x86ms->acpi_dev), x86ms->oem_id,
+ x86ms->oem_table_id);
vmgenid_dev = find_vmgenid_dev();
if (vmgenid_dev) {
acpi_add_table(table_offsets, tables_blob);
vmgenid_build_acpi(VMGENID(vmgenid_dev), tables_blob,
- tables->vmgenid, tables->linker, pcms->oem_id);
+ tables->vmgenid, tables->linker, x86ms->oem_id);
}
if (misc.has_hpet) {
acpi_add_table(table_offsets, tables_blob);
- build_hpet(tables_blob, tables->linker, pcms->oem_id,
- pcms->oem_table_id);
+ build_hpet(tables_blob, tables->linker, x86ms->oem_id,
+ x86ms->oem_table_id);
}
if (misc.tpm_version != TPM_VERSION_UNSPEC) {
if (misc.tpm_version == TPM_VERSION_1_2) {
acpi_add_table(table_offsets, tables_blob);
build_tpm_tcpa(tables_blob, tables->linker, tables->tcpalog,
- pcms->oem_id, pcms->oem_table_id);
+ x86ms->oem_id, x86ms->oem_table_id);
} else { /* TPM_VERSION_2_0 */
acpi_add_table(table_offsets, tables_blob);
build_tpm2(tables_blob, tables->linker, tables->tcpalog,
- pcms->oem_id, pcms->oem_table_id);
+ x86ms->oem_id, x86ms->oem_table_id);
}
}
if (pcms->numa_nodes) {
@@ -2306,40 +2416,40 @@ void acpi_build(AcpiBuildTables *tables, MachineState *machine)
build_srat(tables_blob, tables->linker, machine);
if (machine->numa_state->have_numa_distance) {
acpi_add_table(table_offsets, tables_blob);
- build_slit(tables_blob, tables->linker, machine, pcms->oem_id,
- pcms->oem_table_id);
+ build_slit(tables_blob, tables->linker, machine, x86ms->oem_id,
+ x86ms->oem_table_id);
}
if (machine->numa_state->hmat_enabled) {
acpi_add_table(table_offsets, tables_blob);
build_hmat(tables_blob, tables->linker, machine->numa_state,
- pcms->oem_id, pcms->oem_table_id);
+ x86ms->oem_id, x86ms->oem_table_id);
}
}
if (acpi_get_mcfg(&mcfg)) {
acpi_add_table(table_offsets, tables_blob);
- build_mcfg(tables_blob, tables->linker, &mcfg, pcms->oem_id,
- pcms->oem_table_id);
+ build_mcfg(tables_blob, tables->linker, &mcfg, x86ms->oem_id,
+ x86ms->oem_table_id);
}
if (x86_iommu_get_default()) {
IommuType IOMMUType = x86_iommu_get_type();
if (IOMMUType == TYPE_AMD) {
acpi_add_table(table_offsets, tables_blob);
- build_amd_iommu(tables_blob, tables->linker, pcms->oem_id,
- pcms->oem_table_id);
+ build_amd_iommu(tables_blob, tables->linker, x86ms->oem_id,
+ x86ms->oem_table_id);
} else if (IOMMUType == TYPE_INTEL) {
acpi_add_table(table_offsets, tables_blob);
- build_dmar_q35(tables_blob, tables->linker, pcms->oem_id,
- pcms->oem_table_id);
+ build_dmar_q35(tables_blob, tables->linker, x86ms->oem_id,
+ x86ms->oem_table_id);
}
}
if (machine->nvdimms_state->is_enabled) {
nvdimm_build_acpi(table_offsets, tables_blob, tables->linker,
machine->nvdimms_state, machine->ram_slots,
- pcms->oem_id, pcms->oem_table_id);
+ x86ms->oem_id, x86ms->oem_table_id);
}
acpi_add_table(table_offsets, tables_blob);
- build_waet(tables_blob, tables->linker, pcms->oem_id, pcms->oem_table_id);
+ build_waet(tables_blob, tables->linker, x86ms->oem_id, x86ms->oem_table_id);
/* Add tables supplied by user (if any) */
for (u = acpi_table_first(); u; u = acpi_table_next(u)) {
@@ -2358,7 +2468,7 @@ void acpi_build(AcpiBuildTables *tables, MachineState *machine)
{
AcpiRsdpData rsdp_data = {
.revision = 0,
- .oem_id = pcms->oem_id,
+ .oem_id = x86ms->oem_id,
.xsdt_tbl_offset = NULL,
.rsdt_tbl_offset = &rsdt,
};
@@ -2518,13 +2628,12 @@ void acpi_setup(void)
/* Now expose it all to Guest */
build_state->table_mr = acpi_add_rom_blob(acpi_build_update,
build_state, tables.table_data,
- ACPI_BUILD_TABLE_FILE,
- ACPI_BUILD_TABLE_MAX_SIZE);
+ ACPI_BUILD_TABLE_FILE);
assert(build_state->table_mr != NULL);
build_state->linker_mr =
acpi_add_rom_blob(acpi_build_update, build_state,
- tables.linker->cmd_blob, ACPI_BUILD_LOADER_FILE, 0);
+ tables.linker->cmd_blob, ACPI_BUILD_LOADER_FILE);
fw_cfg_add_file(x86ms->fw_cfg, ACPI_BUILD_TPMLOG_FILE,
tables.tcpalog->data, acpi_data_len(tables.tcpalog));
@@ -2563,7 +2672,7 @@ void acpi_setup(void)
build_state->rsdp = NULL;
build_state->rsdp_mr = acpi_add_rom_blob(acpi_build_update,
build_state, tables.rsdp,
- ACPI_BUILD_RSDP_FILE, 0);
+ ACPI_BUILD_RSDP_FILE);
}
qemu_register_reset(acpi_build_reset, build_state);
diff --git a/hw/i386/acpi-microvm.c b/hw/i386/acpi-microvm.c
index 54b3af4..ccd3303 100644
--- a/hw/i386/acpi-microvm.c
+++ b/hw/i386/acpi-microvm.c
@@ -149,7 +149,7 @@ build_dsdt_microvm(GArray *table_data, BIOSLinker *linker,
g_array_append_vals(table_data, dsdt->buf->data, dsdt->buf->len);
build_header(linker, table_data,
(void *)(table_data->data + table_data->len - dsdt->buf->len),
- "DSDT", dsdt->buf->len, 2, mms->oem_id, mms->oem_table_id);
+ "DSDT", dsdt->buf->len, 2, x86ms->oem_id, x86ms->oem_table_id);
free_aml_allocator();
}
@@ -201,24 +201,24 @@ static void acpi_build_microvm(AcpiBuildTables *tables,
pmfadt.dsdt_tbl_offset = &dsdt;
pmfadt.xdsdt_tbl_offset = &dsdt;
acpi_add_table(table_offsets, tables_blob);
- build_fadt(tables_blob, tables->linker, &pmfadt, mms->oem_id,
- mms->oem_table_id);
+ build_fadt(tables_blob, tables->linker, &pmfadt, x86ms->oem_id,
+ x86ms->oem_table_id);
acpi_add_table(table_offsets, tables_blob);
acpi_build_madt(tables_blob, tables->linker, X86_MACHINE(machine),
- ACPI_DEVICE_IF(x86ms->acpi_dev), mms->oem_id,
- mms->oem_table_id);
+ ACPI_DEVICE_IF(x86ms->acpi_dev), x86ms->oem_id,
+ x86ms->oem_table_id);
xsdt = tables_blob->len;
- build_xsdt(tables_blob, tables->linker, table_offsets, mms->oem_id,
- mms->oem_table_id);
+ build_xsdt(tables_blob, tables->linker, table_offsets, x86ms->oem_id,
+ x86ms->oem_table_id);
/* RSDP is in FSEG memory, so allocate it separately */
{
AcpiRsdpData rsdp_data = {
/* ACPI 2.0: 5.2.4.3 RSDP Structure */
.revision = 2, /* xsdt needs v2 */
- .oem_id = mms->oem_id,
+ .oem_id = x86ms->oem_id,
.xsdt_tbl_offset = &xsdt,
.rsdt_tbl_offset = NULL,
};
@@ -249,16 +249,12 @@ void acpi_setup_microvm(MicrovmMachineState *mms)
acpi_build_microvm(&tables, mms);
/* Now expose it all to Guest */
- acpi_add_rom_blob(acpi_build_no_update, NULL,
- tables.table_data,
- ACPI_BUILD_TABLE_FILE,
- ACPI_BUILD_TABLE_MAX_SIZE);
- acpi_add_rom_blob(acpi_build_no_update, NULL,
- tables.linker->cmd_blob,
- "etc/table-loader", 0);
- acpi_add_rom_blob(acpi_build_no_update, NULL,
- tables.rsdp,
- ACPI_BUILD_RSDP_FILE, 0);
+ acpi_add_rom_blob(acpi_build_no_update, NULL, tables.table_data,
+ ACPI_BUILD_TABLE_FILE);
+ acpi_add_rom_blob(acpi_build_no_update, NULL, tables.linker->cmd_blob,
+ ACPI_BUILD_LOADER_FILE);
+ acpi_add_rom_blob(acpi_build_no_update, NULL, tables.rsdp,
+ ACPI_BUILD_RSDP_FILE);
acpi_build_tables_cleanup(&tables, false);
}
diff --git a/hw/i386/microvm.c b/hw/i386/microvm.c
index 4e0cf4c..edf2b0f 100644
--- a/hw/i386/microvm.c
+++ b/hw/i386/microvm.c
@@ -648,51 +648,6 @@ static void microvm_powerdown_req(Notifier *notifier, void *data)
}
}
-static char *microvm_machine_get_oem_id(Object *obj, Error **errp)
-{
- MicrovmMachineState *mms = MICROVM_MACHINE(obj);
-
- return g_strdup(mms->oem_id);
-}
-
-static void microvm_machine_set_oem_id(Object *obj, const char *value,
- Error **errp)
-{
- MicrovmMachineState *mms = MICROVM_MACHINE(obj);
- size_t len = strlen(value);
-
- if (len > 6) {
- error_setg(errp,
- "User specified "MICROVM_MACHINE_OEM_ID" value is bigger than "
- "6 bytes in size");
- return;
- }
-
- strncpy(mms->oem_id, value, 6);
-}
-
-static char *microvm_machine_get_oem_table_id(Object *obj, Error **errp)
-{
- MicrovmMachineState *mms = MICROVM_MACHINE(obj);
-
- return g_strdup(mms->oem_table_id);
-}
-
-static void microvm_machine_set_oem_table_id(Object *obj, const char *value,
- Error **errp)
-{
- MicrovmMachineState *mms = MICROVM_MACHINE(obj);
- size_t len = strlen(value);
-
- if (len > 8) {
- error_setg(errp,
- "User specified "MICROVM_MACHINE_OEM_TABLE_ID" value is bigger than "
- "8 bytes in size");
- return;
- }
- strncpy(mms->oem_table_id, value, 8);
-}
-
static void microvm_machine_initfn(Object *obj)
{
MicrovmMachineState *mms = MICROVM_MACHINE(obj);
@@ -714,9 +669,6 @@ static void microvm_machine_initfn(Object *obj)
qemu_add_machine_init_done_notifier(&mms->machine_done);
mms->powerdown_req.notify = microvm_powerdown_req;
qemu_register_powerdown_notifier(&mms->powerdown_req);
-
- mms->oem_id = g_strndup(ACPI_BUILD_APPNAME6, 6);
- mms->oem_table_id = g_strndup(ACPI_BUILD_APPNAME8, 8);
}
static void microvm_class_init(ObjectClass *oc, void *data)
@@ -805,24 +757,6 @@ static void microvm_class_init(ObjectClass *oc, void *data)
MICROVM_MACHINE_AUTO_KERNEL_CMDLINE,
"Set off to disable adding virtio-mmio devices to the kernel cmdline");
- object_class_property_add_str(oc, MICROVM_MACHINE_OEM_ID,
- microvm_machine_get_oem_id,
- microvm_machine_set_oem_id);
- object_class_property_set_description(oc, MICROVM_MACHINE_OEM_ID,
- "Override the default value of field OEMID "
- "in ACPI table header."
- "The string may be up to 6 bytes in size");
-
-
- object_class_property_add_str(oc, MICROVM_MACHINE_OEM_TABLE_ID,
- microvm_machine_get_oem_table_id,
- microvm_machine_set_oem_table_id);
- object_class_property_set_description(oc, MICROVM_MACHINE_OEM_TABLE_ID,
- "Override the default value of field OEM Table ID "
- "in ACPI table header."
- "The string may be up to 8 bytes in size");
-
-
machine_class_allow_dynamic_sysbus_dev(mc, TYPE_RAMFB_DEVICE);
}
diff --git a/hw/i386/pc.c b/hw/i386/pc.c
index 35e1770..8a84b25 100644
--- a/hw/i386/pc.c
+++ b/hw/i386/pc.c
@@ -1608,49 +1608,6 @@ static void pc_machine_set_max_fw_size(Object *obj, Visitor *v,
pcms->max_fw_size = value;
}
-static char *pc_machine_get_oem_id(Object *obj, Error **errp)
-{
- PCMachineState *pcms = PC_MACHINE(obj);
-
- return g_strdup(pcms->oem_id);
-}
-
-static void pc_machine_set_oem_id(Object *obj, const char *value, Error **errp)
-{
- PCMachineState *pcms = PC_MACHINE(obj);
- size_t len = strlen(value);
-
- if (len > 6) {
- error_setg(errp,
- "User specified "PC_MACHINE_OEM_ID" value is bigger than "
- "6 bytes in size");
- return;
- }
-
- strncpy(pcms->oem_id, value, 6);
-}
-
-static char *pc_machine_get_oem_table_id(Object *obj, Error **errp)
-{
- PCMachineState *pcms = PC_MACHINE(obj);
-
- return g_strdup(pcms->oem_table_id);
-}
-
-static void pc_machine_set_oem_table_id(Object *obj, const char *value,
- Error **errp)
-{
- PCMachineState *pcms = PC_MACHINE(obj);
- size_t len = strlen(value);
-
- if (len > 8) {
- error_setg(errp,
- "User specified "PC_MACHINE_OEM_TABLE_ID" value is bigger than "
- "8 bytes in size");
- return;
- }
- strncpy(pcms->oem_table_id, value, 8);
-}
static void pc_machine_initfn(Object *obj)
{
@@ -1664,8 +1621,6 @@ static void pc_machine_initfn(Object *obj)
pcms->max_ram_below_4g = 0; /* use default */
/* acpi build is enabled by default if machine supports it */
pcms->acpi_build_enabled = PC_MACHINE_GET_CLASS(pcms)->has_acpi_build;
- pcms->oem_id = g_strndup(ACPI_BUILD_APPNAME6, 6);
- pcms->oem_table_id = g_strndup(ACPI_BUILD_APPNAME8, 8);
pcms->smbus_enabled = true;
pcms->sata_enabled = true;
pcms->pit_enabled = true;
@@ -1802,24 +1757,6 @@ static void pc_machine_class_init(ObjectClass *oc, void *data)
NULL, NULL);
object_class_property_set_description(oc, PC_MACHINE_MAX_FW_SIZE,
"Maximum combined firmware size");
-
- object_class_property_add_str(oc, PC_MACHINE_OEM_ID,
- pc_machine_get_oem_id,
- pc_machine_set_oem_id);
- object_class_property_set_description(oc, PC_MACHINE_OEM_ID,
- "Override the default value of field OEMID "
- "in ACPI table header."
- "The string may be up to 6 bytes in size");
-
-
- object_class_property_add_str(oc, PC_MACHINE_OEM_TABLE_ID,
- pc_machine_get_oem_table_id,
- pc_machine_set_oem_table_id);
- object_class_property_set_description(oc, PC_MACHINE_OEM_TABLE_ID,
- "Override the default value of field OEM Table ID "
- "in ACPI table header."
- "The string may be up to 8 bytes in size");
-
}
static const TypeInfo pc_machine_info = {
diff --git a/hw/i386/x86.c b/hw/i386/x86.c
index 7865660..ed796fe 100644
--- a/hw/i386/x86.c
+++ b/hw/i386/x86.c
@@ -1201,6 +1201,51 @@ static void x86_machine_set_acpi(Object *obj, Visitor *v, const char *name,
visit_type_OnOffAuto(v, name, &x86ms->acpi, errp);
}
+static char *x86_machine_get_oem_id(Object *obj, Error **errp)
+{
+ X86MachineState *x86ms = X86_MACHINE(obj);
+
+ return g_strdup(x86ms->oem_id);
+}
+
+static void x86_machine_set_oem_id(Object *obj, const char *value, Error **errp)
+{
+ X86MachineState *x86ms = X86_MACHINE(obj);
+ size_t len = strlen(value);
+
+ if (len > 6) {
+ error_setg(errp,
+ "User specified "X86_MACHINE_OEM_ID" value is bigger than "
+ "6 bytes in size");
+ return;
+ }
+
+ strncpy(x86ms->oem_id, value, 6);
+}
+
+static char *x86_machine_get_oem_table_id(Object *obj, Error **errp)
+{
+ X86MachineState *x86ms = X86_MACHINE(obj);
+
+ return g_strdup(x86ms->oem_table_id);
+}
+
+static void x86_machine_set_oem_table_id(Object *obj, const char *value,
+ Error **errp)
+{
+ X86MachineState *x86ms = X86_MACHINE(obj);
+ size_t len = strlen(value);
+
+ if (len > 8) {
+ error_setg(errp,
+ "User specified "X86_MACHINE_OEM_TABLE_ID
+ " value is bigger than "
+ "8 bytes in size");
+ return;
+ }
+ strncpy(x86ms->oem_table_id, value, 8);
+}
+
static void x86_machine_initfn(Object *obj)
{
X86MachineState *x86ms = X86_MACHINE(obj);
@@ -1209,6 +1254,8 @@ static void x86_machine_initfn(Object *obj)
x86ms->acpi = ON_OFF_AUTO_AUTO;
x86ms->smp_dies = 1;
x86ms->pci_irq_mask = ACPI_BUILD_PCI_IRQS;
+ x86ms->oem_id = g_strndup(ACPI_BUILD_APPNAME6, 6);
+ x86ms->oem_table_id = g_strndup(ACPI_BUILD_APPNAME8, 8);
}
static void x86_machine_class_init(ObjectClass *oc, void *data)
@@ -1235,6 +1282,23 @@ static void x86_machine_class_init(ObjectClass *oc, void *data)
NULL, NULL);
object_class_property_set_description(oc, X86_MACHINE_ACPI,
"Enable ACPI");
+
+ object_class_property_add_str(oc, X86_MACHINE_OEM_ID,
+ x86_machine_get_oem_id,
+ x86_machine_set_oem_id);
+ object_class_property_set_description(oc, X86_MACHINE_OEM_ID,
+ "Override the default value of field OEMID "
+ "in ACPI table header."
+ "The string may be up to 6 bytes in size");
+
+
+ object_class_property_add_str(oc, X86_MACHINE_OEM_TABLE_ID,
+ x86_machine_get_oem_table_id,
+ x86_machine_set_oem_table_id);
+ object_class_property_set_description(oc, X86_MACHINE_OEM_TABLE_ID,
+ "Override the default value of field OEM Table ID "
+ "in ACPI table header."
+ "The string may be up to 8 bytes in size");
}
static const TypeInfo x86_machine_info = {
diff --git a/hw/pci/pci.c b/hw/pci/pci.c
index 0eadcdb..ac9a248 100644
--- a/hw/pci/pci.c
+++ b/hw/pci/pci.c
@@ -79,6 +79,7 @@ static Property pci_props[] = {
QEMU_PCIE_EXTCAP_INIT_BITNR, true),
DEFINE_PROP_STRING("failover_pair_id", PCIDevice,
failover_pair_id),
+ DEFINE_PROP_UINT32("acpi-index", PCIDevice, acpi_index, 0),
DEFINE_PROP_END_OF_LIST()
};
diff --git a/hw/sd/sd.c b/hw/sd/sd.c
index 8b397ef..282d39a 100644
--- a/hw/sd/sd.c
+++ b/hw/sd/sd.c
@@ -47,6 +47,7 @@
#include "qemu/timer.h"
#include "qemu/log.h"
#include "qemu/module.h"
+#include "qemu-common.h"
#include "sdmmc-internal.h"
#include "trace.h"
@@ -762,10 +763,12 @@ static void sd_blk_write(SDState *sd, uint64_t addr, uint32_t len)
static void sd_erase(SDState *sd)
{
- int i;
uint64_t erase_start = sd->erase_start;
uint64_t erase_end = sd->erase_end;
bool sdsc = true;
+ uint64_t wpnum;
+ uint64_t erase_addr;
+ int erase_len = 1 << HWBLOCK_SHIFT;
trace_sdcard_erase(sd->erase_start, sd->erase_end);
if (sd->erase_start == INVALID_ADDRESS
@@ -794,17 +797,19 @@ static void sd_erase(SDState *sd)
sd->erase_end = INVALID_ADDRESS;
sd->csd[14] |= 0x40;
- /* Only SDSC cards support write protect groups */
- if (sdsc) {
- erase_start = sd_addr_to_wpnum(erase_start);
- erase_end = sd_addr_to_wpnum(erase_end);
-
- for (i = erase_start; i <= erase_end; i++) {
- assert(i < sd->wpgrps_size);
- if (test_bit(i, sd->wp_groups)) {
+ memset(sd->data, 0xff, erase_len);
+ for (erase_addr = erase_start; erase_addr <= erase_end;
+ erase_addr += erase_len) {
+ if (sdsc) {
+ /* Only SDSC cards support write protect groups */
+ wpnum = sd_addr_to_wpnum(erase_addr);
+ assert(wpnum < sd->wpgrps_size);
+ if (test_bit(wpnum, sd->wp_groups)) {
sd->card_status |= WP_ERASE_SKIP;
+ continue;
}
}
+ BLK_WRITE_BLOCK(erase_addr, erase_len);
}
}
diff --git a/hw/sd/sdhci.c b/hw/sd/sdhci.c
index 9acf446..5b86781 100644
--- a/hw/sd/sdhci.c
+++ b/hw/sd/sdhci.c
@@ -326,6 +326,7 @@ static void sdhci_send_command(SDHCIState *s)
SDRequest request;
uint8_t response[16];
int rlen;
+ bool timeout = false;
s->errintsts = 0;
s->acmd12errsts = 0;
@@ -349,6 +350,7 @@ static void sdhci_send_command(SDHCIState *s)
trace_sdhci_response16(s->rspreg[3], s->rspreg[2],
s->rspreg[1], s->rspreg[0]);
} else {
+ timeout = true;
trace_sdhci_error("timeout waiting for command response");
if (s->errintstsen & SDHC_EISEN_CMDTIMEOUT) {
s->errintsts |= SDHC_EIS_CMDTIMEOUT;
@@ -369,7 +371,7 @@ static void sdhci_send_command(SDHCIState *s)
sdhci_update_irq(s);
- if (s->blksize && (s->cmdreg & SDHC_CMD_DATA_PRESENT)) {
+ if (!timeout && s->blksize && (s->cmdreg & SDHC_CMD_DATA_PRESENT)) {
s->data_count = 0;
sdhci_data_transfer(s);
}
@@ -766,7 +768,9 @@ static void sdhci_do_adma(SDHCIState *s)
switch (dscr.attr & SDHC_ADMA_ATTR_ACT_MASK) {
case SDHC_ADMA_ATTR_ACT_TRAN: /* data transfer */
+ s->prnsts |= SDHC_DATA_INHIBIT | SDHC_DAT_LINE_ACTIVE;
if (s->trnmod & SDHC_TRNS_READ) {
+ s->prnsts |= SDHC_DOING_READ;
while (length) {
if (s->data_count == 0) {
sdbus_read_data(&s->sdbus, s->fifo_buffer, block_size);
@@ -794,6 +798,7 @@ static void sdhci_do_adma(SDHCIState *s)
}
}
} else {
+ s->prnsts |= SDHC_DOING_WRITE;
while (length) {
begin = s->data_count;
if ((length + begin) < block_size) {
@@ -1119,31 +1124,45 @@ sdhci_write(void *opaque, hwaddr offset, uint64_t val, unsigned size)
switch (offset & ~0x3) {
case SDHC_SYSAD:
- s->sdmasysad = (s->sdmasysad & mask) | value;
- MASKED_WRITE(s->sdmasysad, mask, value);
- /* Writing to last byte of sdmasysad might trigger transfer */
- if (!(mask & 0xFF000000) && TRANSFERRING_DATA(s->prnsts) && s->blkcnt &&
- s->blksize && SDHC_DMA_TYPE(s->hostctl1) == SDHC_CTRL_SDMA) {
- if (s->trnmod & SDHC_TRNS_MULTI) {
- sdhci_sdma_transfer_multi_blocks(s);
- } else {
- sdhci_sdma_transfer_single_block(s);
+ if (!TRANSFERRING_DATA(s->prnsts)) {
+ s->sdmasysad = (s->sdmasysad & mask) | value;
+ MASKED_WRITE(s->sdmasysad, mask, value);
+ /* Writing to last byte of sdmasysad might trigger transfer */
+ if (!(mask & 0xFF000000) && s->blkcnt && s->blksize &&
+ SDHC_DMA_TYPE(s->hostctl1) == SDHC_CTRL_SDMA) {
+ if (s->trnmod & SDHC_TRNS_MULTI) {
+ sdhci_sdma_transfer_multi_blocks(s);
+ } else {
+ sdhci_sdma_transfer_single_block(s);
+ }
}
}
break;
case SDHC_BLKSIZE:
if (!TRANSFERRING_DATA(s->prnsts)) {
+ uint16_t blksize = s->blksize;
+
MASKED_WRITE(s->blksize, mask, extract32(value, 0, 12));
MASKED_WRITE(s->blkcnt, mask >> 16, value >> 16);
- }
- /* Limit block size to the maximum buffer size */
- if (extract32(s->blksize, 0, 12) > s->buf_maxsz) {
- qemu_log_mask(LOG_GUEST_ERROR, "%s: Size 0x%x is larger than "
- "the maximum buffer 0x%x\n", __func__, s->blksize,
- s->buf_maxsz);
+ /* Limit block size to the maximum buffer size */
+ if (extract32(s->blksize, 0, 12) > s->buf_maxsz) {
+ qemu_log_mask(LOG_GUEST_ERROR, "%s: Size 0x%x is larger than "
+ "the maximum buffer 0x%x\n", __func__, s->blksize,
+ s->buf_maxsz);
+
+ s->blksize = deposit32(s->blksize, 0, 12, s->buf_maxsz);
+ }
- s->blksize = deposit32(s->blksize, 0, 12, s->buf_maxsz);
+ /*
+ * If the block size is programmed to a different value from
+ * the previous one, reset the data pointer of s->fifo_buffer[]
+ * so that s->fifo_buffer[] can be filled in using the new block
+ * size in the next transfer.
+ */
+ if (blksize != s->blksize) {
+ s->data_count = 0;
+ }
}
break;
diff --git a/hw/virtio/vhost-user.c b/hw/virtio/vhost-user.c
index 2fdd5da..ded0c10 100644
--- a/hw/virtio/vhost-user.c
+++ b/hw/virtio/vhost-user.c
@@ -16,6 +16,7 @@
#include "hw/virtio/virtio.h"
#include "hw/virtio/virtio-net.h"
#include "chardev/char-fe.h"
+#include "io/channel-socket.h"
#include "sysemu/kvm.h"
#include "qemu/error-report.h"
#include "qemu/main-loop.h"
@@ -237,7 +238,8 @@ struct vhost_user {
struct vhost_dev *dev;
/* Shared between vhost devs of the same virtio device */
VhostUserState *user;
- int slave_fd;
+ QIOChannel *slave_ioc;
+ GSource *slave_src;
NotifierWithReturn postcopy_notifier;
struct PostCopyFD postcopy_fd;
uint64_t postcopy_client_bases[VHOST_USER_MAX_RAM_SLOTS];
@@ -294,15 +296,27 @@ static int vhost_user_read_header(struct vhost_dev *dev, VhostUserMsg *msg)
return 0;
}
-static int vhost_user_read(struct vhost_dev *dev, VhostUserMsg *msg)
+struct vhost_user_read_cb_data {
+ struct vhost_dev *dev;
+ VhostUserMsg *msg;
+ GMainLoop *loop;
+ int ret;
+};
+
+static gboolean vhost_user_read_cb(GIOChannel *source, GIOCondition condition,
+ gpointer opaque)
{
+ struct vhost_user_read_cb_data *data = opaque;
+ struct vhost_dev *dev = data->dev;
+ VhostUserMsg *msg = data->msg;
struct vhost_user *u = dev->opaque;
CharBackend *chr = u->user->chr;
uint8_t *p = (uint8_t *) msg;
int r, size;
if (vhost_user_read_header(dev, msg) < 0) {
- return -1;
+ data->ret = -1;
+ goto end;
}
/* validate message size is sane */
@@ -310,7 +324,8 @@ static int vhost_user_read(struct vhost_dev *dev, VhostUserMsg *msg)
error_report("Failed to read msg header."
" Size %d exceeds the maximum %zu.", msg->hdr.size,
VHOST_USER_PAYLOAD_SIZE);
- return -1;
+ data->ret = -1;
+ goto end;
}
if (msg->hdr.size) {
@@ -320,11 +335,84 @@ static int vhost_user_read(struct vhost_dev *dev, VhostUserMsg *msg)
if (r != size) {
error_report("Failed to read msg payload."
" Read %d instead of %d.", r, msg->hdr.size);
- return -1;
+ data->ret = -1;
+ goto end;
}
}
- return 0;
+end:
+ g_main_loop_quit(data->loop);
+ return G_SOURCE_REMOVE;
+}
+
+static gboolean slave_read(QIOChannel *ioc, GIOCondition condition,
+ gpointer opaque);
+
+/*
+ * This updates the read handler to use a new event loop context.
+ * Event sources are removed from the previous context : this ensures
+ * that events detected in the previous context are purged. They will
+ * be re-detected and processed in the new context.
+ */
+static void slave_update_read_handler(struct vhost_dev *dev,
+ GMainContext *ctxt)
+{
+ struct vhost_user *u = dev->opaque;
+
+ if (!u->slave_ioc) {
+ return;
+ }
+
+ if (u->slave_src) {
+ g_source_destroy(u->slave_src);
+ g_source_unref(u->slave_src);
+ }
+
+ u->slave_src = qio_channel_add_watch_source(u->slave_ioc,
+ G_IO_IN | G_IO_HUP,
+ slave_read, dev, NULL,
+ ctxt);
+}
+
+static int vhost_user_read(struct vhost_dev *dev, VhostUserMsg *msg)
+{
+ struct vhost_user *u = dev->opaque;
+ CharBackend *chr = u->user->chr;
+ GMainContext *prev_ctxt = chr->chr->gcontext;
+ GMainContext *ctxt = g_main_context_new();
+ GMainLoop *loop = g_main_loop_new(ctxt, FALSE);
+ struct vhost_user_read_cb_data data = {
+ .dev = dev,
+ .loop = loop,
+ .msg = msg,
+ .ret = 0
+ };
+
+ /*
+ * We want to be able to monitor the slave channel fd while waiting
+ * for chr I/O. This requires an event loop, but we can't nest the
+ * one to which chr is currently attached : its fd handlers might not
+ * be prepared for re-entrancy. So we create a new one and switch chr
+ * to use it.
+ */
+ slave_update_read_handler(dev, ctxt);
+ qemu_chr_be_update_read_handlers(chr->chr, ctxt);
+ qemu_chr_fe_add_watch(chr, G_IO_IN | G_IO_HUP, vhost_user_read_cb, &data);
+
+ g_main_loop_run(loop);
+
+ /*
+ * Restore the previous event loop context. This also destroys/recreates
+ * event sources : this guarantees that all pending events in the original
+ * context that have been processed by the nested loop are purged.
+ */
+ qemu_chr_be_update_read_handlers(chr->chr, prev_ctxt);
+ slave_update_read_handler(dev, NULL);
+
+ g_main_loop_unref(loop);
+ g_main_context_unref(ctxt);
+
+ return data.ret;
}
static int process_message_reply(struct vhost_dev *dev,
@@ -1392,56 +1480,39 @@ static int vhost_user_slave_handle_vring_host_notifier(struct vhost_dev *dev,
return 0;
}
-static void slave_read(void *opaque)
+static void close_slave_channel(struct vhost_user *u)
+{
+ g_source_destroy(u->slave_src);
+ g_source_unref(u->slave_src);
+ u->slave_src = NULL;
+ object_unref(OBJECT(u->slave_ioc));
+ u->slave_ioc = NULL;
+}
+
+static gboolean slave_read(QIOChannel *ioc, GIOCondition condition,
+ gpointer opaque)
{
struct vhost_dev *dev = opaque;
struct vhost_user *u = dev->opaque;
VhostUserHeader hdr = { 0, };
VhostUserPayload payload = { 0, };
- int size, ret = 0;
+ Error *local_err = NULL;
+ gboolean rc = G_SOURCE_CONTINUE;
+ int ret = 0;
struct iovec iov;
- struct msghdr msgh;
- int fd[VHOST_USER_SLAVE_MAX_FDS];
- char control[CMSG_SPACE(sizeof(fd))];
- struct cmsghdr *cmsg;
- int i, fdsize = 0;
-
- memset(&msgh, 0, sizeof(msgh));
- msgh.msg_iov = &iov;
- msgh.msg_iovlen = 1;
- msgh.msg_control = control;
- msgh.msg_controllen = sizeof(control);
-
- memset(fd, -1, sizeof(fd));
+ g_autofree int *fd = NULL;
+ size_t fdsize = 0;
+ int i;
/* Read header */
iov.iov_base = &hdr;
iov.iov_len = VHOST_USER_HDR_SIZE;
- do {
- size = recvmsg(u->slave_fd, &msgh, 0);
- } while (size < 0 && (errno == EINTR || errno == EAGAIN));
-
- if (size != VHOST_USER_HDR_SIZE) {
- error_report("Failed to read from slave.");
+ if (qio_channel_readv_full_all(ioc, &iov, 1, &fd, &fdsize, &local_err)) {
+ error_report_err(local_err);
goto err;
}
- if (msgh.msg_flags & MSG_CTRUNC) {
- error_report("Truncated message.");
- goto err;
- }
-
- for (cmsg = CMSG_FIRSTHDR(&msgh); cmsg != NULL;
- cmsg = CMSG_NXTHDR(&msgh, cmsg)) {
- if (cmsg->cmsg_level == SOL_SOCKET &&
- cmsg->cmsg_type == SCM_RIGHTS) {
- fdsize = cmsg->cmsg_len - CMSG_LEN(0);
- memcpy(fd, CMSG_DATA(cmsg), fdsize);
- break;
- }
- }
-
if (hdr.size > VHOST_USER_PAYLOAD_SIZE) {
error_report("Failed to read msg header."
" Size %d exceeds the maximum %zu.", hdr.size,
@@ -1450,12 +1521,8 @@ static void slave_read(void *opaque)
}
/* Read payload */
- do {
- size = read(u->slave_fd, &payload, hdr.size);
- } while (size < 0 && (errno == EINTR || errno == EAGAIN));
-
- if (size != hdr.size) {
- error_report("Failed to read payload from slave.");
+ if (qio_channel_read_all(ioc, (char *) &payload, hdr.size, &local_err)) {
+ error_report_err(local_err);
goto err;
}
@@ -1468,20 +1535,13 @@ static void slave_read(void *opaque)
break;
case VHOST_USER_SLAVE_VRING_HOST_NOTIFIER_MSG:
ret = vhost_user_slave_handle_vring_host_notifier(dev, &payload.area,
- fd[0]);
+ fd ? fd[0] : -1);
break;
default:
error_report("Received unexpected msg type: %d.", hdr.request);
ret = -EINVAL;
}
- /* Close the remaining file descriptors. */
- for (i = 0; i < fdsize; i++) {
- if (fd[i] != -1) {
- close(fd[i]);
- }
- }
-
/*
* REPLY_ACK feature handling. Other reply types has to be managed
* directly in their request handlers.
@@ -1501,28 +1561,25 @@ static void slave_read(void *opaque)
iovec[1].iov_base = &payload;
iovec[1].iov_len = hdr.size;
- do {
- size = writev(u->slave_fd, iovec, ARRAY_SIZE(iovec));
- } while (size < 0 && (errno == EINTR || errno == EAGAIN));
-
- if (size != VHOST_USER_HDR_SIZE + hdr.size) {
- error_report("Failed to send msg reply to slave.");
+ if (qio_channel_writev_all(ioc, iovec, ARRAY_SIZE(iovec), &local_err)) {
+ error_report_err(local_err);
goto err;
}
}
- return;
+ goto fdcleanup;
err:
- qemu_set_fd_handler(u->slave_fd, NULL, NULL, NULL);
- close(u->slave_fd);
- u->slave_fd = -1;
- for (i = 0; i < fdsize; i++) {
- if (fd[i] != -1) {
+ close_slave_channel(u);
+ rc = G_SOURCE_REMOVE;
+
+fdcleanup:
+ if (fd) {
+ for (i = 0; i < fdsize; i++) {
close(fd[i]);
}
}
- return;
+ return rc;
}
static int vhost_setup_slave_channel(struct vhost_dev *dev)
@@ -1535,6 +1592,8 @@ static int vhost_setup_slave_channel(struct vhost_dev *dev)
int sv[2], ret = 0;
bool reply_supported = virtio_has_feature(dev->protocol_features,
VHOST_USER_PROTOCOL_F_REPLY_ACK);
+ Error *local_err = NULL;
+ QIOChannel *ioc;
if (!virtio_has_feature(dev->protocol_features,
VHOST_USER_PROTOCOL_F_SLAVE_REQ)) {
@@ -1546,8 +1605,13 @@ static int vhost_setup_slave_channel(struct vhost_dev *dev)
return -1;
}
- u->slave_fd = sv[0];
- qemu_set_fd_handler(u->slave_fd, slave_read, NULL, dev);
+ ioc = QIO_CHANNEL(qio_channel_socket_new_fd(sv[0], &local_err));
+ if (!ioc) {
+ error_report_err(local_err);
+ return -1;
+ }
+ u->slave_ioc = ioc;
+ slave_update_read_handler(dev, NULL);
if (reply_supported) {
msg.hdr.flags |= VHOST_USER_NEED_REPLY_MASK;
@@ -1565,9 +1629,7 @@ static int vhost_setup_slave_channel(struct vhost_dev *dev)
out:
close(sv[1]);
if (ret) {
- qemu_set_fd_handler(u->slave_fd, NULL, NULL, NULL);
- close(u->slave_fd);
- u->slave_fd = -1;
+ close_slave_channel(u);
}
return ret;
@@ -1804,7 +1866,6 @@ static int vhost_user_backend_init(struct vhost_dev *dev, void *opaque)
u = g_new0(struct vhost_user, 1);
u->user = opaque;
- u->slave_fd = -1;
u->dev = dev;
dev->opaque = u;
@@ -1919,10 +1980,8 @@ static int vhost_user_backend_cleanup(struct vhost_dev *dev)
close(u->postcopy_fd.fd);
u->postcopy_fd.handler = NULL;
}
- if (u->slave_fd >= 0) {
- qemu_set_fd_handler(u->slave_fd, NULL, NULL, NULL);
- close(u->slave_fd);
- u->slave_fd = -1;
+ if (u->slave_ioc) {
+ close_slave_channel(u);
}
g_free(u->region_rb);
u->region_rb = NULL;
diff --git a/hw/virtio/virtio-mmio.c b/hw/virtio/virtio-mmio.c
index 6990b98..342c918 100644
--- a/hw/virtio/virtio-mmio.c
+++ b/hw/virtio/virtio-mmio.c
@@ -112,15 +112,28 @@ static uint64_t virtio_mmio_read(void *opaque, hwaddr offset, unsigned size)
if (offset >= VIRTIO_MMIO_CONFIG) {
offset -= VIRTIO_MMIO_CONFIG;
- switch (size) {
- case 1:
- return virtio_config_readb(vdev, offset);
- case 2:
- return virtio_config_readw(vdev, offset);
- case 4:
- return virtio_config_readl(vdev, offset);
- default:
- abort();
+ if (proxy->legacy) {
+ switch (size) {
+ case 1:
+ return virtio_config_readb(vdev, offset);
+ case 2:
+ return virtio_config_readw(vdev, offset);
+ case 4:
+ return virtio_config_readl(vdev, offset);
+ default:
+ abort();
+ }
+ } else {
+ switch (size) {
+ case 1:
+ return virtio_config_modern_readb(vdev, offset);
+ case 2:
+ return virtio_config_modern_readw(vdev, offset);
+ case 4:
+ return virtio_config_modern_readl(vdev, offset);
+ default:
+ abort();
+ }
}
}
if (size != 4) {
@@ -245,20 +258,37 @@ static void virtio_mmio_write(void *opaque, hwaddr offset, uint64_t value,
if (offset >= VIRTIO_MMIO_CONFIG) {
offset -= VIRTIO_MMIO_CONFIG;
- switch (size) {
- case 1:
- virtio_config_writeb(vdev, offset, value);
- break;
- case 2:
- virtio_config_writew(vdev, offset, value);
- break;
- case 4:
- virtio_config_writel(vdev, offset, value);
- break;
- default:
- abort();
+ if (proxy->legacy) {
+ switch (size) {
+ case 1:
+ virtio_config_writeb(vdev, offset, value);
+ break;
+ case 2:
+ virtio_config_writew(vdev, offset, value);
+ break;
+ case 4:
+ virtio_config_writel(vdev, offset, value);
+ break;
+ default:
+ abort();
+ }
+ return;
+ } else {
+ switch (size) {
+ case 1:
+ virtio_config_modern_writeb(vdev, offset, value);
+ break;
+ case 2:
+ virtio_config_modern_writew(vdev, offset, value);
+ break;
+ case 4:
+ virtio_config_modern_writel(vdev, offset, value);
+ break;
+ default:
+ abort();
+ }
+ return;
}
- return;
}
if (size != 4) {
qemu_log_mask(LOG_GUEST_ERROR,
diff --git a/hw/virtio/virtio-pmem.c b/hw/virtio/virtio-pmem.c
index a3e0688..d1aeb90 100644
--- a/hw/virtio/virtio-pmem.c
+++ b/hw/virtio/virtio-pmem.c
@@ -47,7 +47,7 @@ static int worker_cb(void *opaque)
err = 1;
}
- virtio_stw_p(req_data->vdev, &req_data->resp.ret, err);
+ virtio_stl_p(req_data->vdev, &req_data->resp.ret, err);
return 0;
}
diff --git a/include/hw/acpi/aml-build.h b/include/hw/acpi/aml-build.h
index 380d3e3..471266d 100644
--- a/include/hw/acpi/aml-build.h
+++ b/include/hw/acpi/aml-build.h
@@ -4,9 +4,6 @@
#include "hw/acpi/acpi-defs.h"
#include "hw/acpi/bios-linker-loader.h"
-/* Reserve RAM space for tables: add another order of magnitude. */
-#define ACPI_BUILD_TABLE_MAX_SIZE 0x200000
-
#define ACPI_BUILD_APPNAME6 "BOCHS "
#define ACPI_BUILD_APPNAME8 "BXPC "
@@ -301,6 +298,7 @@ Aml *aml_arg(int pos);
Aml *aml_to_integer(Aml *arg);
Aml *aml_to_hexstring(Aml *src, Aml *dst);
Aml *aml_to_buffer(Aml *src, Aml *dst);
+Aml *aml_to_decimalstring(Aml *src, Aml *dst);
Aml *aml_store(Aml *val, Aml *target);
Aml *aml_and(Aml *arg1, Aml *arg2, Aml *dst);
Aml *aml_or(Aml *arg1, Aml *arg2, Aml *dst);
@@ -323,6 +321,8 @@ Aml *aml_call3(const char *method, Aml *arg1, Aml *arg2, Aml *arg3);
Aml *aml_call4(const char *method, Aml *arg1, Aml *arg2, Aml *arg3, Aml *arg4);
Aml *aml_call5(const char *method, Aml *arg1, Aml *arg2, Aml *arg3, Aml *arg4,
Aml *arg5);
+Aml *aml_call6(const char *method, Aml *arg1, Aml *arg2, Aml *arg3, Aml *arg4,
+ Aml *arg5, Aml *arg6);
Aml *aml_gpio_int(AmlConsumerAndProducer con_and_pro,
AmlLevelAndEdge edge_level,
AmlActiveHighAndLow active_level, AmlShared shared,
diff --git a/include/hw/acpi/pci.h b/include/hw/acpi/pci.h
index e514f17..b5deee0 100644
--- a/include/hw/acpi/pci.h
+++ b/include/hw/acpi/pci.h
@@ -35,4 +35,5 @@ typedef struct AcpiMcfgInfo {
void build_mcfg(GArray *table_data, BIOSLinker *linker, AcpiMcfgInfo *info,
const char *oem_id, const char *oem_table_id);
+Aml *aml_pci_device_dsm(void);
#endif
diff --git a/include/hw/acpi/pcihp.h b/include/hw/acpi/pcihp.h
index dfd3758..2dd90ae 100644
--- a/include/hw/acpi/pcihp.h
+++ b/include/hw/acpi/pcihp.h
@@ -46,6 +46,7 @@ typedef struct AcpiPciHpPciStatus {
typedef struct AcpiPciHpState {
AcpiPciHpPciStatus acpi_pcihp_pci_status[ACPI_PCIHP_MAX_HOTPLUG_BUS];
uint32_t hotplug_select;
+ uint32_t acpi_index;
PCIBus *root;
MemoryRegion io;
bool legacy_piix;
@@ -71,13 +72,17 @@ void acpi_pcihp_reset(AcpiPciHpState *s, bool acpihp_root_off);
extern const VMStateDescription vmstate_acpi_pcihp_pci_status;
-#define VMSTATE_PCI_HOTPLUG(pcihp, state, test_pcihp) \
+bool vmstate_acpi_pcihp_use_acpi_index(void *opaque, int version_id);
+
+#define VMSTATE_PCI_HOTPLUG(pcihp, state, test_pcihp, test_acpi_index) \
VMSTATE_UINT32_TEST(pcihp.hotplug_select, state, \
test_pcihp), \
VMSTATE_STRUCT_ARRAY_TEST(pcihp.acpi_pcihp_pci_status, state, \
ACPI_PCIHP_MAX_HOTPLUG_BUS, \
test_pcihp, 1, \
vmstate_acpi_pcihp_pci_status, \
- AcpiPciHpPciStatus)
+ AcpiPciHpPciStatus), \
+ VMSTATE_UINT32_TEST(pcihp.acpi_index, state, \
+ test_acpi_index)
#endif
diff --git a/include/hw/acpi/utils.h b/include/hw/acpi/utils.h
index 140b4de..0022df0 100644
--- a/include/hw/acpi/utils.h
+++ b/include/hw/acpi/utils.h
@@ -4,6 +4,5 @@
#include "hw/nvram/fw_cfg.h"
MemoryRegion *acpi_add_rom_blob(FWCfgCallback update, void *opaque,
- GArray *blob, const char *name,
- uint64_t max_size);
+ GArray *blob, const char *name);
#endif
diff --git a/include/hw/i386/microvm.h b/include/hw/i386/microvm.h
index 372b057..f25f837 100644
--- a/include/hw/i386/microvm.h
+++ b/include/hw/i386/microvm.h
@@ -76,8 +76,6 @@
#define MICROVM_MACHINE_ISA_SERIAL "isa-serial"
#define MICROVM_MACHINE_OPTION_ROMS "x-option-roms"
#define MICROVM_MACHINE_AUTO_KERNEL_CMDLINE "auto-kernel-cmdline"
-#define MICROVM_MACHINE_OEM_ID "oem-id"
-#define MICROVM_MACHINE_OEM_TABLE_ID "oem-table-id"
struct MicrovmMachineClass {
X86MachineClass parent;
@@ -106,8 +104,6 @@ struct MicrovmMachineState {
Notifier machine_done;
Notifier powerdown_req;
struct GPEXConfig gpex;
- char *oem_id;
- char *oem_table_id;
};
#define TYPE_MICROVM_MACHINE MACHINE_TYPE_NAME("microvm")
diff --git a/include/hw/i386/pc.h b/include/hw/i386/pc.h
index d4c3d73..dcf060b 100644
--- a/include/hw/i386/pc.h
+++ b/include/hw/i386/pc.h
@@ -46,8 +46,6 @@ typedef struct PCMachineState {
bool pit_enabled;
bool hpet_enabled;
uint64_t max_fw_size;
- char *oem_id;
- char *oem_table_id;
/* NUMA information: */
uint64_t numa_nodes;
@@ -65,8 +63,6 @@ typedef struct PCMachineState {
#define PC_MACHINE_SATA "sata"
#define PC_MACHINE_PIT "pit"
#define PC_MACHINE_MAX_FW_SIZE "max-fw-size"
-#define PC_MACHINE_OEM_ID "oem-id"
-#define PC_MACHINE_OEM_TABLE_ID "oem-table-id"
/**
* PCMachineClass:
*
diff --git a/include/hw/i386/x86.h b/include/hw/i386/x86.h
index 56080bd..26c9cc4 100644
--- a/include/hw/i386/x86.h
+++ b/include/hw/i386/x86.h
@@ -67,6 +67,8 @@ struct X86MachineState {
OnOffAuto smm;
OnOffAuto acpi;
+ char *oem_id;
+ char *oem_table_id;
/*
* Address space used by IOAPIC device. All IOAPIC interrupts
* will be translated to MSI messages in the address space.
@@ -76,6 +78,8 @@ struct X86MachineState {
#define X86_MACHINE_SMM "smm"
#define X86_MACHINE_ACPI "acpi"
+#define X86_MACHINE_OEM_ID "oem-id"
+#define X86_MACHINE_OEM_TABLE_ID "oem-table-id"
#define TYPE_X86_MACHINE MACHINE_TYPE_NAME("x86")
OBJECT_DECLARE_TYPE(X86MachineState, X86MachineClass, X86_MACHINE)
diff --git a/include/hw/pci/pci.h b/include/hw/pci/pci.h
index 1bc2314..6be4e0c 100644
--- a/include/hw/pci/pci.h
+++ b/include/hw/pci/pci.h
@@ -359,6 +359,7 @@ struct PCIDevice {
/* ID of standby device in net_failover pair */
char *failover_pair_id;
+ uint32_t acpi_index;
};
void pci_register_bar(PCIDevice *pci_dev, int region_num,
diff --git a/tests/data/acpi/pc/DSDT b/tests/data/acpi/pc/DSDT
index 11ef89b..b9dd9b3 100644
--- a/tests/data/acpi/pc/DSDT
+++ b/tests/data/acpi/pc/DSDT
Binary files differ
diff --git a/tests/data/acpi/pc/DSDT.acpihmat b/tests/data/acpi/pc/DSDT.acpihmat
index c561e91..cba5a1d 100644
--- a/tests/data/acpi/pc/DSDT.acpihmat
+++ b/tests/data/acpi/pc/DSDT.acpihmat
Binary files differ
diff --git a/tests/data/acpi/pc/DSDT.bridge b/tests/data/acpi/pc/DSDT.bridge
index a234075..a9b4d56 100644
--- a/tests/data/acpi/pc/DSDT.bridge
+++ b/tests/data/acpi/pc/DSDT.bridge
Binary files differ
diff --git a/tests/data/acpi/pc/DSDT.cphp b/tests/data/acpi/pc/DSDT.cphp
index 6ac47a7..8d86155 100644
--- a/tests/data/acpi/pc/DSDT.cphp
+++ b/tests/data/acpi/pc/DSDT.cphp
Binary files differ
diff --git a/tests/data/acpi/pc/DSDT.dimmpxm b/tests/data/acpi/pc/DSDT.dimmpxm
index d243772..e00a447 100644
--- a/tests/data/acpi/pc/DSDT.dimmpxm
+++ b/tests/data/acpi/pc/DSDT.dimmpxm
Binary files differ
diff --git a/tests/data/acpi/pc/DSDT.hpbridge b/tests/data/acpi/pc/DSDT.hpbridge
index 9dfac45..5d8ba19 100644
--- a/tests/data/acpi/pc/DSDT.hpbridge
+++ b/tests/data/acpi/pc/DSDT.hpbridge
Binary files differ
diff --git a/tests/data/acpi/pc/DSDT.ipmikcs b/tests/data/acpi/pc/DSDT.ipmikcs
index 1814f29..01e53bd 100644
--- a/tests/data/acpi/pc/DSDT.ipmikcs
+++ b/tests/data/acpi/pc/DSDT.ipmikcs
Binary files differ
diff --git a/tests/data/acpi/pc/DSDT.memhp b/tests/data/acpi/pc/DSDT.memhp
index 3c81339..b810379 100644
--- a/tests/data/acpi/pc/DSDT.memhp
+++ b/tests/data/acpi/pc/DSDT.memhp
Binary files differ
diff --git a/tests/data/acpi/pc/DSDT.nohpet b/tests/data/acpi/pc/DSDT.nohpet
index d7d21be..d4f0050 100644
--- a/tests/data/acpi/pc/DSDT.nohpet
+++ b/tests/data/acpi/pc/DSDT.nohpet
Binary files differ
diff --git a/tests/data/acpi/pc/DSDT.numamem b/tests/data/acpi/pc/DSDT.numamem
index 195f8da..8632dfe 100644
--- a/tests/data/acpi/pc/DSDT.numamem
+++ b/tests/data/acpi/pc/DSDT.numamem
Binary files differ
diff --git a/tests/data/acpi/pc/DSDT.roothp b/tests/data/acpi/pc/DSDT.roothp
index 1d0a2c2..cee3b4d 100644
--- a/tests/data/acpi/pc/DSDT.roothp
+++ b/tests/data/acpi/pc/DSDT.roothp
Binary files differ