mirror of https://github.com/xemu-project/xemu.git
acpi dsdt rework, misc fixes
This completes the dsdt rewrite, and includes misc fixes all over the place. Signed-off-by: Michael S. Tsirkin <mst@redhat.com> -----BEGIN PGP SIGNATURE----- Version: GnuPG v1 iQEcBAABAgAGBQJWkXmiAAoJECgfDbjSjVRpRtoIAKCtPLZPapStgd85Fyl0m0Qg sVGcABtWxej+rwwpnOONJX2O0+fFp2aXh6mucirWtn5qaduMKj5Ou0wB9LnCUxyW tziafuHec/BQQ1TZ7WMGNJclVmLY6JmYMuSkcxeXHcskPnVdefGtTJEL8/fRA4/E RuIhjPIWpHGCm/ExXb41gfhh1GoTwIWJFBS53FR/Oc0oqVg7zlUOhUsfz02zk1QB WjAIedgXWFzeeGOAR4yKKMGMAJaJ1nueSfqD5lgMsAglbnOEIUYuQhQWDOWHdNMb +Xc2XBeYmnCxGk4KDx+h9H7Yacu9GDX3R4VUHSBPS92+YQdkUk3C3rUiDC9KcRE= =MsMN -----END PGP SIGNATURE----- Merge remote-tracking branch 'remotes/mst/tags/for_upstream' into staging acpi dsdt rework, misc fixes This completes the dsdt rewrite, and includes misc fixes all over the place. Signed-off-by: Michael S. Tsirkin <mst@redhat.com> # gpg: Signature made Sat 09 Jan 2016 21:20:34 GMT using RSA key ID D28D5469 # gpg: Good signature from "Michael S. Tsirkin <mst@kernel.org>" # gpg: aka "Michael S. Tsirkin <mst@redhat.com>" * remotes/mst/tags/for_upstream: (59 commits) virtio: fix error message for number of queues ivshmem: Store file descriptor for vhost-user negotiation migration/virtio: Remove simple .get/.put use Add VMSTATE_STRUCT_VARRAY_KNOWN i386/pc: expose identifying the floppy controller pc: acpi: remove unused ASL templates and related blobs/utils pc: acpi: switch to AML API composed DSDT pc: acpi: q35: PCST, PCSB opregions and PCIB field into SSDT pc: acpi: q35: move PCI0 device definition into SSDT pc: acpi: q35: move PCI0._OSC() method into SSDT pc: acpi: q35: move _PIC() method into SSDT pc: acpi: q35: move PRTP routing table into SSDT pc: acpi: q35: move PRTA routing table into SSDT pc: acpi: q35: move _PRT() into SSDT pc: acpi: q35: move ISA bridge into SSDT pc: acpi: q35: move IQST() into SSDT pc: acpi: q35: move IQCR() into SSDT pc: acpi: q35: move link devices to SSDT pc: acpi: q35: move GSI links to SSDT pc: acpi: piix4: acpi move PCI0 device to SSDT ... Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
This commit is contained in:
commit
d21ccd7bb9
10
exec.c
10
exec.c
|
@ -1757,6 +1757,16 @@ int qemu_get_ram_fd(ram_addr_t addr)
|
|||
return fd;
|
||||
}
|
||||
|
||||
void qemu_set_ram_fd(ram_addr_t addr, int fd)
|
||||
{
|
||||
RAMBlock *block;
|
||||
|
||||
rcu_read_lock();
|
||||
block = qemu_get_ram_block(addr);
|
||||
block->fd = fd;
|
||||
rcu_read_unlock();
|
||||
}
|
||||
|
||||
void *qemu_get_ram_block_host_ptr(ram_addr_t addr)
|
||||
{
|
||||
RAMBlock *block;
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
common-obj-$(CONFIG_ACPI_X86) += core.o piix4.o pcihp.o
|
||||
common-obj-$(CONFIG_ACPI_X86_ICH) += ich9.o tco.o
|
||||
common-obj-$(CONFIG_ACPI_CPU_HOTPLUG) += cpu_hotplug.o
|
||||
common-obj-$(CONFIG_ACPI_MEMORY_HOTPLUG) += memory_hotplug.o
|
||||
common-obj-$(CONFIG_ACPI_CPU_HOTPLUG) += cpu_hotplug.o cpu_hotplug_acpi_table.o
|
||||
common-obj-$(CONFIG_ACPI_MEMORY_HOTPLUG) += memory_hotplug.o memory_hotplug_acpi_table.o
|
||||
common-obj-$(CONFIG_ACPI_NVDIMM) += nvdimm.o
|
||||
common-obj-$(CONFIG_ACPI) += acpi_interface.o
|
||||
common-obj-$(CONFIG_ACPI) += bios-linker-loader.o
|
||||
|
|
|
@ -0,0 +1,135 @@
|
|||
/*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
|
||||
* 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 General Public License for more details.
|
||||
|
||||
* You should have received a copy of the GNU General Public License along
|
||||
* with this program; if not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "hw/acpi/cpu_hotplug.h"
|
||||
|
||||
void build_cpu_hotplug_aml(Aml *ctx)
|
||||
{
|
||||
Aml *method;
|
||||
Aml *if_ctx;
|
||||
Aml *else_ctx;
|
||||
Aml *sb_scope = aml_scope("_SB");
|
||||
uint8_t madt_tmpl[8] = {0x00, 0x08, 0x00, 0x00, 0x00, 0, 0, 0};
|
||||
Aml *cpu_id = aml_arg(0);
|
||||
Aml *cpu_on = aml_local(0);
|
||||
Aml *madt = aml_local(1);
|
||||
Aml *cpus_map = aml_name(CPU_ON_BITMAP);
|
||||
Aml *zero = aml_int(0);
|
||||
Aml *one = aml_int(1);
|
||||
|
||||
/*
|
||||
* _MAT method - creates an madt apic buffer
|
||||
* cpu_id = Arg0 = Processor ID = Local APIC ID
|
||||
* cpu_on = Local0 = CPON flag for this cpu
|
||||
* madt = Local1 = Buffer (in madt apic form) to return
|
||||
*/
|
||||
method = aml_method(CPU_MAT_METHOD, 1, AML_NOTSERIALIZED);
|
||||
aml_append(method,
|
||||
aml_store(aml_derefof(aml_index(cpus_map, cpu_id)), cpu_on));
|
||||
aml_append(method,
|
||||
aml_store(aml_buffer(sizeof(madt_tmpl), madt_tmpl), madt));
|
||||
/* Update the processor id, lapic id, and enable/disable status */
|
||||
aml_append(method, aml_store(cpu_id, aml_index(madt, aml_int(2))));
|
||||
aml_append(method, aml_store(cpu_id, aml_index(madt, aml_int(3))));
|
||||
aml_append(method, aml_store(cpu_on, aml_index(madt, aml_int(4))));
|
||||
aml_append(method, aml_return(madt));
|
||||
aml_append(sb_scope, method);
|
||||
|
||||
/*
|
||||
* _STA method - return ON status of cpu
|
||||
* cpu_id = Arg0 = Processor ID = Local APIC ID
|
||||
* cpu_on = Local0 = CPON flag for this cpu
|
||||
*/
|
||||
method = aml_method(CPU_STATUS_METHOD, 1, AML_NOTSERIALIZED);
|
||||
aml_append(method,
|
||||
aml_store(aml_derefof(aml_index(cpus_map, cpu_id)), cpu_on));
|
||||
if_ctx = aml_if(cpu_on);
|
||||
{
|
||||
aml_append(if_ctx, aml_return(aml_int(0xF)));
|
||||
}
|
||||
aml_append(method, if_ctx);
|
||||
else_ctx = aml_else();
|
||||
{
|
||||
aml_append(else_ctx, aml_return(zero));
|
||||
}
|
||||
aml_append(method, else_ctx);
|
||||
aml_append(sb_scope, method);
|
||||
|
||||
method = aml_method(CPU_EJECT_METHOD, 2, AML_NOTSERIALIZED);
|
||||
aml_append(method, aml_sleep(200));
|
||||
aml_append(sb_scope, method);
|
||||
|
||||
method = aml_method(CPU_SCAN_METHOD, 0, AML_NOTSERIALIZED);
|
||||
{
|
||||
Aml *while_ctx, *if_ctx2, *else_ctx2;
|
||||
Aml *bus_check_evt = aml_int(1);
|
||||
Aml *remove_evt = aml_int(3);
|
||||
Aml *status_map = aml_local(5); /* Local5 = active cpu bitmap */
|
||||
Aml *byte = aml_local(2); /* Local2 = last read byte from bitmap */
|
||||
Aml *idx = aml_local(0); /* Processor ID / APIC ID iterator */
|
||||
Aml *is_cpu_on = aml_local(1); /* Local1 = CPON flag for cpu */
|
||||
Aml *status = aml_local(3); /* Local3 = active state for cpu */
|
||||
|
||||
aml_append(method, aml_store(aml_name(CPU_STATUS_MAP), status_map));
|
||||
aml_append(method, aml_store(zero, byte));
|
||||
aml_append(method, aml_store(zero, idx));
|
||||
|
||||
/* While (idx < SizeOf(CPON)) */
|
||||
while_ctx = aml_while(aml_lless(idx, aml_sizeof(cpus_map)));
|
||||
aml_append(while_ctx,
|
||||
aml_store(aml_derefof(aml_index(cpus_map, idx)), is_cpu_on));
|
||||
|
||||
if_ctx = aml_if(aml_and(idx, aml_int(0x07), NULL));
|
||||
{
|
||||
/* Shift down previously read bitmap byte */
|
||||
aml_append(if_ctx, aml_shiftright(byte, one, byte));
|
||||
}
|
||||
aml_append(while_ctx, if_ctx);
|
||||
|
||||
else_ctx = aml_else();
|
||||
{
|
||||
/* Read next byte from cpu bitmap */
|
||||
aml_append(else_ctx, aml_store(aml_derefof(aml_index(status_map,
|
||||
aml_shiftright(idx, aml_int(3), NULL))), byte));
|
||||
}
|
||||
aml_append(while_ctx, else_ctx);
|
||||
|
||||
aml_append(while_ctx, aml_store(aml_and(byte, one, NULL), status));
|
||||
if_ctx = aml_if(aml_lnot(aml_equal(is_cpu_on, status)));
|
||||
{
|
||||
/* State change - update CPON with new state */
|
||||
aml_append(if_ctx, aml_store(status, aml_index(cpus_map, idx)));
|
||||
if_ctx2 = aml_if(aml_equal(status, one));
|
||||
{
|
||||
aml_append(if_ctx2,
|
||||
aml_call2(AML_NOTIFY_METHOD, idx, bus_check_evt));
|
||||
}
|
||||
aml_append(if_ctx, if_ctx2);
|
||||
else_ctx2 = aml_else();
|
||||
{
|
||||
aml_append(else_ctx2,
|
||||
aml_call2(AML_NOTIFY_METHOD, idx, remove_evt));
|
||||
}
|
||||
}
|
||||
aml_append(if_ctx, else_ctx2);
|
||||
aml_append(while_ctx, if_ctx);
|
||||
|
||||
aml_append(while_ctx, aml_increment(idx)); /* go to next cpu */
|
||||
aml_append(method, while_ctx);
|
||||
}
|
||||
aml_append(sb_scope, method);
|
||||
|
||||
aml_append(ctx, sb_scope);
|
||||
}
|
|
@ -0,0 +1,262 @@
|
|||
/*
|
||||
* Memory hotplug AML code of DSDT ACPI table
|
||||
*
|
||||
* Copyright (C) 2015 Red Hat Inc
|
||||
*
|
||||
* Author: Igor Mammedov <imammedo@redhat.com>
|
||||
*
|
||||
* This work is licensed under the terms of the GNU GPL, version 2 or later.
|
||||
* See the COPYING file in the top-level directory.
|
||||
*/
|
||||
|
||||
#include <stdbool.h>
|
||||
#include "hw/acpi/memory_hotplug.h"
|
||||
#include "include/hw/acpi/pc-hotplug.h"
|
||||
#include "hw/boards.h"
|
||||
|
||||
void build_memory_hotplug_aml(Aml *ctx, uint32_t nr_mem,
|
||||
uint16_t io_base, uint16_t io_len)
|
||||
{
|
||||
Aml *ifctx;
|
||||
Aml *method;
|
||||
Aml *pci_scope;
|
||||
Aml *mem_ctrl_dev;
|
||||
|
||||
/* scope for memory hotplug controller device node */
|
||||
pci_scope = aml_scope("_SB.PCI0");
|
||||
mem_ctrl_dev = aml_device(MEMORY_HOTPLUG_DEVICE);
|
||||
{
|
||||
Aml *one = aml_int(1);
|
||||
Aml *zero = aml_int(0);
|
||||
Aml *ret_val = aml_local(0);
|
||||
Aml *slot_arg0 = aml_arg(0);
|
||||
Aml *slots_nr = aml_name(MEMORY_SLOTS_NUMBER);
|
||||
Aml *ctrl_lock = aml_name(MEMORY_SLOT_LOCK);
|
||||
Aml *slot_selector = aml_name(MEMORY_SLOT_SLECTOR);
|
||||
|
||||
aml_append(mem_ctrl_dev, aml_name_decl("_HID", aml_string("PNP0A06")));
|
||||
aml_append(mem_ctrl_dev,
|
||||
aml_name_decl("_UID", aml_string("Memory hotplug resources")));
|
||||
|
||||
method = aml_method("_STA", 0, AML_NOTSERIALIZED);
|
||||
ifctx = aml_if(aml_equal(slots_nr, zero));
|
||||
{
|
||||
aml_append(ifctx, aml_return(zero));
|
||||
}
|
||||
aml_append(method, ifctx);
|
||||
/* present, functioning, decoding, not shown in UI */
|
||||
aml_append(method, aml_return(aml_int(0xB)));
|
||||
aml_append(mem_ctrl_dev, method);
|
||||
|
||||
aml_append(mem_ctrl_dev, aml_mutex(MEMORY_SLOT_LOCK, 0));
|
||||
|
||||
method = aml_method(MEMORY_SLOT_SCAN_METHOD, 0, AML_NOTSERIALIZED);
|
||||
{
|
||||
Aml *else_ctx;
|
||||
Aml *while_ctx;
|
||||
Aml *idx = aml_local(0);
|
||||
Aml *eject_req = aml_int(3);
|
||||
Aml *dev_chk = aml_int(1);
|
||||
|
||||
ifctx = aml_if(aml_equal(slots_nr, zero));
|
||||
{
|
||||
aml_append(ifctx, aml_return(zero));
|
||||
}
|
||||
aml_append(method, ifctx);
|
||||
|
||||
aml_append(method, aml_store(zero, idx));
|
||||
aml_append(method, aml_acquire(ctrl_lock, 0xFFFF));
|
||||
/* build AML that:
|
||||
* loops over all slots and Notifies DIMMs with
|
||||
* Device Check or Eject Request notifications if
|
||||
* slot has corresponding status bit set and clears
|
||||
* slot status.
|
||||
*/
|
||||
while_ctx = aml_while(aml_lless(idx, slots_nr));
|
||||
{
|
||||
Aml *ins_evt = aml_name(MEMORY_SLOT_INSERT_EVENT);
|
||||
Aml *rm_evt = aml_name(MEMORY_SLOT_REMOVE_EVENT);
|
||||
|
||||
aml_append(while_ctx, aml_store(idx, slot_selector));
|
||||
ifctx = aml_if(aml_equal(ins_evt, one));
|
||||
{
|
||||
aml_append(ifctx,
|
||||
aml_call2(MEMORY_SLOT_NOTIFY_METHOD,
|
||||
idx, dev_chk));
|
||||
aml_append(ifctx, aml_store(one, ins_evt));
|
||||
}
|
||||
aml_append(while_ctx, ifctx);
|
||||
|
||||
else_ctx = aml_else();
|
||||
ifctx = aml_if(aml_equal(rm_evt, one));
|
||||
{
|
||||
aml_append(ifctx,
|
||||
aml_call2(MEMORY_SLOT_NOTIFY_METHOD,
|
||||
idx, eject_req));
|
||||
aml_append(ifctx, aml_store(one, rm_evt));
|
||||
}
|
||||
aml_append(else_ctx, ifctx);
|
||||
aml_append(while_ctx, else_ctx);
|
||||
|
||||
aml_append(while_ctx, aml_add(idx, one, idx));
|
||||
}
|
||||
aml_append(method, while_ctx);
|
||||
aml_append(method, aml_release(ctrl_lock));
|
||||
aml_append(method, aml_return(one));
|
||||
}
|
||||
aml_append(mem_ctrl_dev, method);
|
||||
|
||||
method = aml_method(MEMORY_SLOT_STATUS_METHOD, 1, AML_NOTSERIALIZED);
|
||||
{
|
||||
Aml *slot_enabled = aml_name(MEMORY_SLOT_ENABLED);
|
||||
|
||||
aml_append(method, aml_store(zero, ret_val));
|
||||
aml_append(method, aml_acquire(ctrl_lock, 0xFFFF));
|
||||
aml_append(method,
|
||||
aml_store(aml_to_integer(slot_arg0), slot_selector));
|
||||
|
||||
ifctx = aml_if(aml_equal(slot_enabled, one));
|
||||
{
|
||||
aml_append(ifctx, aml_store(aml_int(0xF), ret_val));
|
||||
}
|
||||
aml_append(method, ifctx);
|
||||
|
||||
aml_append(method, aml_release(ctrl_lock));
|
||||
aml_append(method, aml_return(ret_val));
|
||||
}
|
||||
aml_append(mem_ctrl_dev, method);
|
||||
|
||||
method = aml_method(MEMORY_SLOT_CRS_METHOD, 1, AML_SERIALIZED);
|
||||
{
|
||||
Aml *mr64 = aml_name("MR64");
|
||||
Aml *mr32 = aml_name("MR32");
|
||||
Aml *crs_tmpl = aml_resource_template();
|
||||
Aml *minl = aml_name("MINL");
|
||||
Aml *minh = aml_name("MINH");
|
||||
Aml *maxl = aml_name("MAXL");
|
||||
Aml *maxh = aml_name("MAXH");
|
||||
Aml *lenl = aml_name("LENL");
|
||||
Aml *lenh = aml_name("LENH");
|
||||
|
||||
aml_append(method, aml_acquire(ctrl_lock, 0xFFFF));
|
||||
aml_append(method, aml_store(aml_to_integer(slot_arg0),
|
||||
slot_selector));
|
||||
|
||||
aml_append(crs_tmpl,
|
||||
aml_qword_memory(AML_POS_DECODE, AML_MIN_FIXED, AML_MAX_FIXED,
|
||||
AML_CACHEABLE, AML_READ_WRITE,
|
||||
0, 0x0, 0xFFFFFFFFFFFFFFFEULL, 0,
|
||||
0xFFFFFFFFFFFFFFFFULL));
|
||||
aml_append(method, aml_name_decl("MR64", crs_tmpl));
|
||||
aml_append(method,
|
||||
aml_create_dword_field(mr64, aml_int(14), "MINL"));
|
||||
aml_append(method,
|
||||
aml_create_dword_field(mr64, aml_int(18), "MINH"));
|
||||
aml_append(method,
|
||||
aml_create_dword_field(mr64, aml_int(38), "LENL"));
|
||||
aml_append(method,
|
||||
aml_create_dword_field(mr64, aml_int(42), "LENH"));
|
||||
aml_append(method,
|
||||
aml_create_dword_field(mr64, aml_int(22), "MAXL"));
|
||||
aml_append(method,
|
||||
aml_create_dword_field(mr64, aml_int(26), "MAXH"));
|
||||
|
||||
aml_append(method,
|
||||
aml_store(aml_name(MEMORY_SLOT_ADDR_HIGH), minh));
|
||||
aml_append(method,
|
||||
aml_store(aml_name(MEMORY_SLOT_ADDR_LOW), minl));
|
||||
aml_append(method,
|
||||
aml_store(aml_name(MEMORY_SLOT_SIZE_HIGH), lenh));
|
||||
aml_append(method,
|
||||
aml_store(aml_name(MEMORY_SLOT_SIZE_LOW), lenl));
|
||||
|
||||
/* 64-bit math: MAX = MIN + LEN - 1 */
|
||||
aml_append(method, aml_add(minl, lenl, maxl));
|
||||
aml_append(method, aml_add(minh, lenh, maxh));
|
||||
ifctx = aml_if(aml_lless(maxl, minl));
|
||||
{
|
||||
aml_append(ifctx, aml_add(maxh, one, maxh));
|
||||
}
|
||||
aml_append(method, ifctx);
|
||||
ifctx = aml_if(aml_lless(maxl, one));
|
||||
{
|
||||
aml_append(ifctx, aml_subtract(maxh, one, maxh));
|
||||
}
|
||||
aml_append(method, ifctx);
|
||||
aml_append(method, aml_subtract(maxl, one, maxl));
|
||||
|
||||
/* return 32-bit _CRS if addr/size is in low mem */
|
||||
/* TODO: remove it since all hotplugged DIMMs are in high mem */
|
||||
ifctx = aml_if(aml_equal(maxh, zero));
|
||||
{
|
||||
crs_tmpl = aml_resource_template();
|
||||
aml_append(crs_tmpl,
|
||||
aml_dword_memory(AML_POS_DECODE, AML_MIN_FIXED,
|
||||
AML_MAX_FIXED, AML_CACHEABLE,
|
||||
AML_READ_WRITE,
|
||||
0, 0x0, 0xFFFFFFFE, 0,
|
||||
0xFFFFFFFF));
|
||||
aml_append(ifctx, aml_name_decl("MR32", crs_tmpl));
|
||||
aml_append(ifctx,
|
||||
aml_create_dword_field(mr32, aml_int(10), "MIN"));
|
||||
aml_append(ifctx,
|
||||
aml_create_dword_field(mr32, aml_int(14), "MAX"));
|
||||
aml_append(ifctx,
|
||||
aml_create_dword_field(mr32, aml_int(22), "LEN"));
|
||||
aml_append(ifctx, aml_store(minl, aml_name("MIN")));
|
||||
aml_append(ifctx, aml_store(maxl, aml_name("MAX")));
|
||||
aml_append(ifctx, aml_store(lenl, aml_name("LEN")));
|
||||
|
||||
aml_append(ifctx, aml_release(ctrl_lock));
|
||||
aml_append(ifctx, aml_return(mr32));
|
||||
}
|
||||
aml_append(method, ifctx);
|
||||
|
||||
aml_append(method, aml_release(ctrl_lock));
|
||||
aml_append(method, aml_return(mr64));
|
||||
}
|
||||
aml_append(mem_ctrl_dev, method);
|
||||
|
||||
method = aml_method(MEMORY_SLOT_PROXIMITY_METHOD, 1,
|
||||
AML_NOTSERIALIZED);
|
||||
{
|
||||
Aml *proximity = aml_name(MEMORY_SLOT_PROXIMITY);
|
||||
|
||||
aml_append(method, aml_acquire(ctrl_lock, 0xFFFF));
|
||||
aml_append(method, aml_store(aml_to_integer(slot_arg0),
|
||||
slot_selector));
|
||||
aml_append(method, aml_store(proximity, ret_val));
|
||||
aml_append(method, aml_release(ctrl_lock));
|
||||
aml_append(method, aml_return(ret_val));
|
||||
}
|
||||
aml_append(mem_ctrl_dev, method);
|
||||
|
||||
method = aml_method(MEMORY_SLOT_OST_METHOD, 4, AML_NOTSERIALIZED);
|
||||
{
|
||||
Aml *ost_evt = aml_name(MEMORY_SLOT_OST_EVENT);
|
||||
Aml *ost_status = aml_name(MEMORY_SLOT_OST_STATUS);
|
||||
|
||||
aml_append(method, aml_acquire(ctrl_lock, 0xFFFF));
|
||||
aml_append(method, aml_store(aml_to_integer(slot_arg0),
|
||||
slot_selector));
|
||||
aml_append(method, aml_store(aml_arg(1), ost_evt));
|
||||
aml_append(method, aml_store(aml_arg(2), ost_status));
|
||||
aml_append(method, aml_release(ctrl_lock));
|
||||
}
|
||||
aml_append(mem_ctrl_dev, method);
|
||||
|
||||
method = aml_method(MEMORY_SLOT_EJECT_METHOD, 2, AML_NOTSERIALIZED);
|
||||
{
|
||||
Aml *eject = aml_name(MEMORY_SLOT_EJECT);
|
||||
|
||||
aml_append(method, aml_acquire(ctrl_lock, 0xFFFF));
|
||||
aml_append(method, aml_store(aml_to_integer(slot_arg0),
|
||||
slot_selector));
|
||||
aml_append(method, aml_store(one, eject));
|
||||
aml_append(method, aml_release(ctrl_lock));
|
||||
}
|
||||
aml_append(mem_ctrl_dev, method);
|
||||
}
|
||||
aml_append(pci_scope, mem_ctrl_dev);
|
||||
aml_append(ctx, pci_scope);
|
||||
}
|
|
@ -353,16 +353,18 @@ static void nvdimm_build_nfit(GSList *device_list, GArray *table_offsets,
|
|||
GArray *table_data, GArray *linker)
|
||||
{
|
||||
GArray *structures = nvdimm_build_device_structure(device_list);
|
||||
void *header;
|
||||
unsigned int header;
|
||||
|
||||
acpi_add_table(table_offsets, table_data);
|
||||
|
||||
/* NFIT header. */
|
||||
header = acpi_data_push(table_data, sizeof(NvdimmNfitHeader));
|
||||
header = table_data->len;
|
||||
acpi_data_push(table_data, sizeof(NvdimmNfitHeader));
|
||||
/* NVDIMM device structures. */
|
||||
g_array_append_vals(table_data, structures->data, structures->len);
|
||||
|
||||
build_header(linker, table_data, header, "NFIT",
|
||||
build_header(linker, table_data,
|
||||
(void *)(table_data->data + header), "NFIT",
|
||||
sizeof(NvdimmNfitHeader) + structures->len, 1, NULL);
|
||||
g_array_free(structures, true);
|
||||
}
|
||||
|
|
|
@ -8,33 +8,3 @@ obj-$(CONFIG_XEN) += ../xenpv/ xen/
|
|||
obj-y += kvmvapic.o
|
||||
obj-y += acpi-build.o
|
||||
obj-y += pci-assign-load-rom.o
|
||||
|
||||
gen-hex-y += hw/i386/acpi-dsdt.hex
|
||||
gen-hex-y += hw/i386/q35-acpi-dsdt.hex
|
||||
|
||||
hw/i386/acpi-build.o: hw/i386/acpi-build.c \
|
||||
$(gen-hex-y)
|
||||
|
||||
-include $(gen-hex-y:.hex=.d)
|
||||
|
||||
iasl-option=$(shell if test -z "`$(1) $(2) 2>&1 > /dev/null`" \
|
||||
; then echo "$(2)"; else echo "$(3)"; fi ;)
|
||||
|
||||
ifdef IASL
|
||||
#IASL Present. Generate hex files from .dsl
|
||||
hw/i386/%.hex: $(SRC_PATH)/hw/i386/%.dsl $(SRC_PATH)/scripts/acpi_extract_preprocess.py $(SRC_PATH)/scripts/acpi_extract.py
|
||||
$(call quiet-command, $(CPP) -x c -P $(QEMU_DGFLAGS) $(QEMU_INCLUDES) $< -o $*.dsl.i.orig, " CPP $(TARGET_DIR)$*.dsl.i.orig")
|
||||
$(call quiet-command, $(PYTHON) $(SRC_PATH)/scripts/acpi_extract_preprocess.py $*.dsl.i.orig > $*.dsl.i, " ACPI_PREPROCESS $(TARGET_DIR)$*.dsl.i")
|
||||
$(call quiet-command, $(IASL) $(call iasl-option,$(IASL),-Pn,) -vs -l -tc -p $* $*.dsl.i $(if $(V), , > /dev/null) 2>&1 ," IASL $(TARGET_DIR)$*.dsl.i")
|
||||
$(call quiet-command, $(PYTHON) $(SRC_PATH)/scripts/acpi_extract.py $*.lst > $*.off, " ACPI_EXTRACT $(TARGET_DIR)$*.off")
|
||||
$(call quiet-command, cat $*.off > $@, " CAT $(TARGET_DIR)$@")
|
||||
else
|
||||
#IASL Not present. Restore pre-generated hex files.
|
||||
hw/i386/%.hex: $(SRC_PATH)/hw/i386/%.hex.generated
|
||||
$(call quiet-command, cp -f $< $@, " CP $(TARGET_DIR)$@")
|
||||
endif
|
||||
|
||||
.PHONY: cleanhex
|
||||
cleanhex:
|
||||
rm -f hw/i386/*hex
|
||||
clean: cleanhex
|
||||
|
|
1369
hw/i386/acpi-build.c
1369
hw/i386/acpi-build.c
File diff suppressed because it is too large
Load Diff
|
@ -1,90 +0,0 @@
|
|||
/*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
|
||||
* 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 General Public License for more details.
|
||||
|
||||
* You should have received a copy of the GNU General Public License along
|
||||
* with this program; if not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/****************************************************************
|
||||
* CPU hotplug
|
||||
****************************************************************/
|
||||
|
||||
Scope(\_SB) {
|
||||
/* Objects filled in by run-time generated SSDT */
|
||||
External(NTFY, MethodObj)
|
||||
External(CPON, PkgObj)
|
||||
External(PRS, FieldUnitObj)
|
||||
|
||||
/* Methods called by run-time generated SSDT Processor objects */
|
||||
Method(CPMA, 1, NotSerialized) {
|
||||
// _MAT method - create an madt apic buffer
|
||||
// Arg0 = Processor ID = Local APIC ID
|
||||
// Local0 = CPON flag for this cpu
|
||||
Store(DerefOf(Index(CPON, Arg0)), Local0)
|
||||
// Local1 = Buffer (in madt apic form) to return
|
||||
Store(Buffer(8) {0x00, 0x08, 0x00, 0x00, 0x00, 0, 0, 0}, Local1)
|
||||
// Update the processor id, lapic id, and enable/disable status
|
||||
Store(Arg0, Index(Local1, 2))
|
||||
Store(Arg0, Index(Local1, 3))
|
||||
Store(Local0, Index(Local1, 4))
|
||||
Return (Local1)
|
||||
}
|
||||
Method(CPST, 1, NotSerialized) {
|
||||
// _STA method - return ON status of cpu
|
||||
// Arg0 = Processor ID = Local APIC ID
|
||||
// Local0 = CPON flag for this cpu
|
||||
Store(DerefOf(Index(CPON, Arg0)), Local0)
|
||||
If (Local0) {
|
||||
Return (0xF)
|
||||
} Else {
|
||||
Return (0x0)
|
||||
}
|
||||
}
|
||||
Method(CPEJ, 2, NotSerialized) {
|
||||
// _EJ0 method - eject callback
|
||||
Sleep(200)
|
||||
}
|
||||
|
||||
#define CPU_STATUS_LEN ACPI_GPE_PROC_LEN
|
||||
Method(PRSC, 0) {
|
||||
// Local5 = active cpu bitmap
|
||||
Store(PRS, Local5)
|
||||
// Local2 = last read byte from bitmap
|
||||
Store(Zero, Local2)
|
||||
// Local0 = Processor ID / APIC ID iterator
|
||||
Store(Zero, Local0)
|
||||
While (LLess(Local0, SizeOf(CPON))) {
|
||||
// Local1 = CPON flag for this cpu
|
||||
Store(DerefOf(Index(CPON, Local0)), Local1)
|
||||
If (And(Local0, 0x07)) {
|
||||
// Shift down previously read bitmap byte
|
||||
ShiftRight(Local2, 1, Local2)
|
||||
} Else {
|
||||
// Read next byte from cpu bitmap
|
||||
Store(DerefOf(Index(Local5, ShiftRight(Local0, 3))), Local2)
|
||||
}
|
||||
// Local3 = active state for this cpu
|
||||
Store(And(Local2, 1), Local3)
|
||||
|
||||
If (LNotEqual(Local1, Local3)) {
|
||||
// State change - update CPON with new state
|
||||
Store(Local3, Index(CPON, Local0))
|
||||
// Do CPU notify
|
||||
If (LEqual(Local3, 1)) {
|
||||
NTFY(Local0, 1)
|
||||
} Else {
|
||||
NTFY(Local0, 3)
|
||||
}
|
||||
}
|
||||
Increment(Local0)
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,41 +0,0 @@
|
|||
/*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
|
||||
* 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 General Public License for more details.
|
||||
|
||||
* You should have received a copy of the GNU General Public License along
|
||||
* with this program; if not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/****************************************************************
|
||||
* Debugging
|
||||
****************************************************************/
|
||||
|
||||
Scope(\) {
|
||||
/* Debug Output */
|
||||
OperationRegion(DBG, SystemIO, 0x0402, 0x01)
|
||||
Field(DBG, ByteAcc, NoLock, Preserve) {
|
||||
DBGB, 8,
|
||||
}
|
||||
|
||||
/* Debug method - use this method to send output to the QEMU
|
||||
* BIOS debug port. This method handles strings, integers,
|
||||
* and buffers. For example: DBUG("abc") DBUG(0x123) */
|
||||
Method(DBUG, 1) {
|
||||
ToHexString(Arg0, Local0)
|
||||
ToBuffer(Local0, Local0)
|
||||
Subtract(SizeOf(Local0), 1, Local1)
|
||||
Store(Zero, Local2)
|
||||
While (LLess(Local2, Local1)) {
|
||||
Store(DerefOf(Index(Local0, Local2)), DBGB)
|
||||
Increment(Local2)
|
||||
}
|
||||
Store(0x0A, DBGB)
|
||||
}
|
||||
}
|
|
@ -1,48 +0,0 @@
|
|||
/*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
|
||||
* 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 General Public License for more details.
|
||||
|
||||
* You should have received a copy of the GNU General Public License along
|
||||
* with this program; if not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/****************************************************************
|
||||
* HPET
|
||||
****************************************************************/
|
||||
|
||||
Scope(\_SB) {
|
||||
Device(HPET) {
|
||||
Name(_HID, EISAID("PNP0103"))
|
||||
Name(_UID, 0)
|
||||
OperationRegion(HPTM, SystemMemory, 0xFED00000, 0x400)
|
||||
Field(HPTM, DWordAcc, Lock, Preserve) {
|
||||
VEND, 32,
|
||||
PRD, 32,
|
||||
}
|
||||
Method(_STA, 0, NotSerialized) {
|
||||
Store(VEND, Local0)
|
||||
Store(PRD, Local1)
|
||||
ShiftRight(Local0, 16, Local0)
|
||||
If (LOr(LEqual(Local0, 0), LEqual(Local0, 0xffff))) {
|
||||
Return (0x0)
|
||||
}
|
||||
If (LOr(LEqual(Local1, 0), LGreater(Local1, 100000000))) {
|
||||
Return (0x0)
|
||||
}
|
||||
Return (0x0F)
|
||||
}
|
||||
Name(_CRS, ResourceTemplate() {
|
||||
Memory32Fixed(ReadOnly,
|
||||
0xFED00000, // Address Base
|
||||
0x00000400, // Address Length
|
||||
)
|
||||
})
|
||||
}
|
||||
}
|
|
@ -1,117 +0,0 @@
|
|||
/*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
|
||||
* 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 General Public License for more details.
|
||||
|
||||
* You should have received a copy of the GNU General Public License along
|
||||
* with this program; if not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/* Common legacy ISA style devices. */
|
||||
Scope(\_SB.PCI0.ISA) {
|
||||
|
||||
Device(RTC) {
|
||||
Name(_HID, EisaId("PNP0B00"))
|
||||
Name(_CRS, ResourceTemplate() {
|
||||
IO(Decode16, 0x0070, 0x0070, 0x10, 0x02)
|
||||
IRQNoFlags() { 8 }
|
||||
IO(Decode16, 0x0072, 0x0072, 0x02, 0x06)
|
||||
})
|
||||
}
|
||||
|
||||
Device(KBD) {
|
||||
Name(_HID, EisaId("PNP0303"))
|
||||
Method(_STA, 0, NotSerialized) {
|
||||
Return (0x0f)
|
||||
}
|
||||
Name(_CRS, ResourceTemplate() {
|
||||
IO(Decode16, 0x0060, 0x0060, 0x01, 0x01)
|
||||
IO(Decode16, 0x0064, 0x0064, 0x01, 0x01)
|
||||
IRQNoFlags() { 1 }
|
||||
})
|
||||
}
|
||||
|
||||
Device(MOU) {
|
||||
Name(_HID, EisaId("PNP0F13"))
|
||||
Method(_STA, 0, NotSerialized) {
|
||||
Return (0x0f)
|
||||
}
|
||||
Name(_CRS, ResourceTemplate() {
|
||||
IRQNoFlags() { 12 }
|
||||
})
|
||||
}
|
||||
|
||||
Device(FDC0) {
|
||||
Name(_HID, EisaId("PNP0700"))
|
||||
Method(_STA, 0, NotSerialized) {
|
||||
Store(FDEN, Local0)
|
||||
If (LEqual(Local0, 0)) {
|
||||
Return (0x00)
|
||||
} Else {
|
||||
Return (0x0F)
|
||||
}
|
||||
}
|
||||
Name(_CRS, ResourceTemplate() {
|
||||
IO(Decode16, 0x03F2, 0x03F2, 0x00, 0x04)
|
||||
IO(Decode16, 0x03F7, 0x03F7, 0x00, 0x01)
|
||||
IRQNoFlags() { 6 }
|
||||
DMA(Compatibility, NotBusMaster, Transfer8) { 2 }
|
||||
})
|
||||
}
|
||||
|
||||
Device(LPT) {
|
||||
Name(_HID, EisaId("PNP0400"))
|
||||
Method(_STA, 0, NotSerialized) {
|
||||
Store(LPEN, Local0)
|
||||
If (LEqual(Local0, 0)) {
|
||||
Return (0x00)
|
||||
} Else {
|
||||
Return (0x0F)
|
||||
}
|
||||
}
|
||||
Name(_CRS, ResourceTemplate() {
|
||||
IO(Decode16, 0x0378, 0x0378, 0x08, 0x08)
|
||||
IRQNoFlags() { 7 }
|
||||
})
|
||||
}
|
||||
|
||||
Device(COM1) {
|
||||
Name(_HID, EisaId("PNP0501"))
|
||||
Name(_UID, 0x01)
|
||||
Method(_STA, 0, NotSerialized) {
|
||||
Store(CAEN, Local0)
|
||||
If (LEqual(Local0, 0)) {
|
||||
Return (0x00)
|
||||
} Else {
|
||||
Return (0x0F)
|
||||
}
|
||||
}
|
||||
Name(_CRS, ResourceTemplate() {
|
||||
IO(Decode16, 0x03F8, 0x03F8, 0x00, 0x08)
|
||||
IRQNoFlags() { 4 }
|
||||
})
|
||||
}
|
||||
|
||||
Device(COM2) {
|
||||
Name(_HID, EisaId("PNP0501"))
|
||||
Name(_UID, 0x02)
|
||||
Method(_STA, 0, NotSerialized) {
|
||||
Store(CBEN, Local0)
|
||||
If (LEqual(Local0, 0)) {
|
||||
Return (0x00)
|
||||
} Else {
|
||||
Return (0x0F)
|
||||
}
|
||||
}
|
||||
Name(_CRS, ResourceTemplate() {
|
||||
IO(Decode16, 0x02F8, 0x02F8, 0x00, 0x08)
|
||||
IRQNoFlags() { 3 }
|
||||
})
|
||||
}
|
||||
}
|
|
@ -1,171 +0,0 @@
|
|||
/*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
|
||||
* 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 General Public License for more details.
|
||||
|
||||
* You should have received a copy of the GNU General Public License along
|
||||
* with this program; if not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
External(MEMORY_SLOT_NOTIFY_METHOD, MethodObj)
|
||||
|
||||
Scope(\_SB.PCI0) {
|
||||
Device(MEMORY_HOTPLUG_DEVICE) {
|
||||
Name(_HID, "PNP0A06")
|
||||
Name(_UID, "Memory hotplug resources")
|
||||
External(MEMORY_SLOTS_NUMBER, IntObj)
|
||||
|
||||
/* Memory hotplug IO registers */
|
||||
External(MEMORY_SLOT_ADDR_LOW, FieldUnitObj) // read only
|
||||
External(MEMORY_SLOT_ADDR_HIGH, FieldUnitObj) // read only
|
||||
External(MEMORY_SLOT_SIZE_LOW, FieldUnitObj) // read only
|
||||
External(MEMORY_SLOT_SIZE_HIGH, FieldUnitObj) // read only
|
||||
External(MEMORY_SLOT_PROXIMITY, FieldUnitObj) // read only
|
||||
External(MEMORY_SLOT_ENABLED, FieldUnitObj) // 1 if enabled, read only
|
||||
External(MEMORY_SLOT_INSERT_EVENT, FieldUnitObj) // (read) 1 if has a insert event. (write) 1 to clear event
|
||||
External(MEMORY_SLOT_REMOVE_EVENT, FieldUnitObj) // (read) 1 if has a remove event. (write) 1 to clear event
|
||||
External(MEMORY_SLOT_EJECT, FieldUnitObj) // initiates device eject, write only
|
||||
External(MEMORY_SLOT_SLECTOR, FieldUnitObj) // DIMM selector, write only
|
||||
External(MEMORY_SLOT_OST_EVENT, FieldUnitObj) // _OST event code, write only
|
||||
External(MEMORY_SLOT_OST_STATUS, FieldUnitObj) // _OST status code, write only
|
||||
|
||||
Method(_STA, 0) {
|
||||
If (LEqual(MEMORY_SLOTS_NUMBER, Zero)) {
|
||||
Return(0x0)
|
||||
}
|
||||
/* present, functioning, decoding, not shown in UI */
|
||||
Return(0xB)
|
||||
}
|
||||
|
||||
Mutex (MEMORY_SLOT_LOCK, 0)
|
||||
|
||||
Method(MEMORY_SLOT_SCAN_METHOD, 0) {
|
||||
If (LEqual(MEMORY_SLOTS_NUMBER, Zero)) {
|
||||
Return(Zero)
|
||||
}
|
||||
|
||||
Store(Zero, Local0) // Mem devs iterrator
|
||||
Acquire(MEMORY_SLOT_LOCK, 0xFFFF)
|
||||
while (LLess(Local0, MEMORY_SLOTS_NUMBER)) {
|
||||
Store(Local0, MEMORY_SLOT_SLECTOR) // select Local0 DIMM
|
||||
If (LEqual(MEMORY_SLOT_INSERT_EVENT, One)) { // Memory device needs check
|
||||
MEMORY_SLOT_NOTIFY_METHOD(Local0, 1)
|
||||
Store(1, MEMORY_SLOT_INSERT_EVENT)
|
||||
} Elseif (LEqual(MEMORY_SLOT_REMOVE_EVENT, One)) { // Ejection request
|
||||
MEMORY_SLOT_NOTIFY_METHOD(Local0, 3)
|
||||
Store(1, MEMORY_SLOT_REMOVE_EVENT)
|
||||
}
|
||||
Add(Local0, One, Local0) // goto next DIMM
|
||||
}
|
||||
Release(MEMORY_SLOT_LOCK)
|
||||
Return(One)
|
||||
}
|
||||
|
||||
Method(MEMORY_SLOT_STATUS_METHOD, 1) {
|
||||
Store(Zero, Local0)
|
||||
|
||||
Acquire(MEMORY_SLOT_LOCK, 0xFFFF)
|
||||
Store(ToInteger(Arg0), MEMORY_SLOT_SLECTOR) // select DIMM
|
||||
|
||||
If (LEqual(MEMORY_SLOT_ENABLED, One)) {
|
||||
Store(0xF, Local0)
|
||||
}
|
||||
|
||||
Release(MEMORY_SLOT_LOCK)
|
||||
Return(Local0)
|
||||
}
|
||||
|
||||
Method(MEMORY_SLOT_CRS_METHOD, 1, Serialized) {
|
||||
Acquire(MEMORY_SLOT_LOCK, 0xFFFF)
|
||||
Store(ToInteger(Arg0), MEMORY_SLOT_SLECTOR) // select DIMM
|
||||
|
||||
Name(MR64, ResourceTemplate() {
|
||||
QWordMemory(ResourceProducer, PosDecode, MinFixed, MaxFixed,
|
||||
Cacheable, ReadWrite,
|
||||
0x0000000000000000, // Address Space Granularity
|
||||
0x0000000000000000, // Address Range Minimum
|
||||
0xFFFFFFFFFFFFFFFE, // Address Range Maximum
|
||||
0x0000000000000000, // Address Translation Offset
|
||||
0xFFFFFFFFFFFFFFFF, // Address Length
|
||||
,, MW64, AddressRangeMemory, TypeStatic)
|
||||
})
|
||||
|
||||
CreateDWordField(MR64, 14, MINL)
|
||||
CreateDWordField(MR64, 18, MINH)
|
||||
CreateDWordField(MR64, 38, LENL)
|
||||
CreateDWordField(MR64, 42, LENH)
|
||||
CreateDWordField(MR64, 22, MAXL)
|
||||
CreateDWordField(MR64, 26, MAXH)
|
||||
|
||||
Store(MEMORY_SLOT_ADDR_HIGH, MINH)
|
||||
Store(MEMORY_SLOT_ADDR_LOW, MINL)
|
||||
Store(MEMORY_SLOT_SIZE_HIGH, LENH)
|
||||
Store(MEMORY_SLOT_SIZE_LOW, LENL)
|
||||
|
||||
// 64-bit math: MAX = MIN + LEN - 1
|
||||
Add(MINL, LENL, MAXL)
|
||||
Add(MINH, LENH, MAXH)
|
||||
If (LLess(MAXL, MINL)) {
|
||||
Add(MAXH, One, MAXH)
|
||||
}
|
||||
If (LLess(MAXL, One)) {
|
||||
Subtract(MAXH, One, MAXH)
|
||||
}
|
||||
Subtract(MAXL, One, MAXL)
|
||||
|
||||
If (LEqual(MAXH, Zero)){
|
||||
Name(MR32, ResourceTemplate() {
|
||||
DWordMemory(ResourceProducer, PosDecode, MinFixed, MaxFixed,
|
||||
Cacheable, ReadWrite,
|
||||
0x00000000, // Address Space Granularity
|
||||
0x00000000, // Address Range Minimum
|
||||
0xFFFFFFFE, // Address Range Maximum
|
||||
0x00000000, // Address Translation Offset
|
||||
0xFFFFFFFF, // Address Length
|
||||
,, MW32, AddressRangeMemory, TypeStatic)
|
||||
})
|
||||
CreateDWordField(MR32, MW32._MIN, MIN)
|
||||
CreateDWordField(MR32, MW32._MAX, MAX)
|
||||
CreateDWordField(MR32, MW32._LEN, LEN)
|
||||
Store(MINL, MIN)
|
||||
Store(MAXL, MAX)
|
||||
Store(LENL, LEN)
|
||||
|
||||
Release(MEMORY_SLOT_LOCK)
|
||||
Return(MR32)
|
||||
}
|
||||
|
||||
Release(MEMORY_SLOT_LOCK)
|
||||
Return(MR64)
|
||||
}
|
||||
|
||||
Method(MEMORY_SLOT_PROXIMITY_METHOD, 1) {
|
||||
Acquire(MEMORY_SLOT_LOCK, 0xFFFF)
|
||||
Store(ToInteger(Arg0), MEMORY_SLOT_SLECTOR) // select DIMM
|
||||
Store(MEMORY_SLOT_PROXIMITY, Local0)
|
||||
Release(MEMORY_SLOT_LOCK)
|
||||
Return(Local0)
|
||||
}
|
||||
|
||||
Method(MEMORY_SLOT_OST_METHOD, 4) {
|
||||
Acquire(MEMORY_SLOT_LOCK, 0xFFFF)
|
||||
Store(ToInteger(Arg0), MEMORY_SLOT_SLECTOR) // select DIMM
|
||||
Store(Arg1, MEMORY_SLOT_OST_EVENT)
|
||||
Store(Arg2, MEMORY_SLOT_OST_STATUS)
|
||||
Release(MEMORY_SLOT_LOCK)
|
||||
}
|
||||
|
||||
Method(MEMORY_SLOT_EJECT_METHOD, 2) {
|
||||
Acquire(MEMORY_SLOT_LOCK, 0xFFFF)
|
||||
Store(ToInteger(Arg0), MEMORY_SLOT_SLECTOR) // select DIMM
|
||||
Store(1, MEMORY_SLOT_EJECT)
|
||||
Release(MEMORY_SLOT_LOCK)
|
||||
}
|
||||
} // Device()
|
||||
} // Scope()
|
|
@ -1,303 +0,0 @@
|
|||
/*
|
||||
* Bochs/QEMU ACPI DSDT ASL definition
|
||||
*
|
||||
* Copyright (c) 2006 Fabrice Bellard
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License version 2 as published by the Free Software Foundation.
|
||||
*
|
||||
* This library 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.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this library; if not, write to the Free Software
|
||||
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
ACPI_EXTRACT_ALL_CODE AcpiDsdtAmlCode
|
||||
|
||||
DefinitionBlock (
|
||||
"acpi-dsdt.aml", // Output Filename
|
||||
"DSDT", // Signature
|
||||
0x01, // DSDT Compliance Revision
|
||||
"BXPC", // OEMID
|
||||
"BXDSDT", // TABLE ID
|
||||
0x1 // OEM Revision
|
||||
)
|
||||
{
|
||||
|
||||
#include "acpi-dsdt-dbug.dsl"
|
||||
|
||||
Scope(\_SB) {
|
||||
Device(PCI0) {
|
||||
Name(_HID, EisaId("PNP0A03"))
|
||||
Name(_ADR, 0x00)
|
||||
Name(_UID, 1)
|
||||
//#define PX13 S0B_
|
||||
// External(PX13, DeviceObj)
|
||||
}
|
||||
}
|
||||
|
||||
#include "acpi-dsdt-hpet.dsl"
|
||||
|
||||
/****************************************************************
|
||||
* PIIX4 PM
|
||||
****************************************************************/
|
||||
|
||||
Scope(\_SB.PCI0) {
|
||||
Device(PX13) {
|
||||
Name(_ADR, 0x00010003)
|
||||
OperationRegion(P13C, PCI_Config, 0x00, 0xff)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************
|
||||
* PIIX3 ISA bridge
|
||||
****************************************************************/
|
||||
|
||||
Scope(\_SB.PCI0) {
|
||||
|
||||
External(ISA, DeviceObj)
|
||||
|
||||
Device(ISA) {
|
||||
Name(_ADR, 0x00010000)
|
||||
|
||||
/* PIIX PCI to ISA irq remapping */
|
||||
OperationRegion(P40C, PCI_Config, 0x60, 0x04)
|
||||
|
||||
/* enable bits */
|
||||
Field(\_SB.PCI0.PX13.P13C, AnyAcc, NoLock, Preserve) {
|
||||
Offset(0x5f),
|
||||
, 7,
|
||||
LPEN, 1, // LPT
|
||||
Offset(0x67),
|
||||
, 3,
|
||||
CAEN, 1, // COM1
|
||||
, 3,
|
||||
CBEN, 1, // COM2
|
||||
}
|
||||
Name(FDEN, 1)
|
||||
}
|
||||
}
|
||||
|
||||
#include "acpi-dsdt-isa.dsl"
|
||||
|
||||
|
||||
/****************************************************************
|
||||
* PCI hotplug
|
||||
****************************************************************/
|
||||
|
||||
Scope(\_SB.PCI0) {
|
||||
OperationRegion(PCST, SystemIO, 0xae00, 0x08)
|
||||
Field(PCST, DWordAcc, NoLock, WriteAsZeros) {
|
||||
PCIU, 32,
|
||||
PCID, 32,
|
||||
}
|
||||
|
||||
OperationRegion(SEJ, SystemIO, 0xae08, 0x04)
|
||||
Field(SEJ, DWordAcc, NoLock, WriteAsZeros) {
|
||||
B0EJ, 32,
|
||||
}
|
||||
|
||||
OperationRegion(BNMR, SystemIO, 0xae10, 0x04)
|
||||
Field(BNMR, DWordAcc, NoLock, WriteAsZeros) {
|
||||
BNUM, 32,
|
||||
}
|
||||
|
||||
/* Lock to protect access to fields above. */
|
||||
Mutex(BLCK, 0)
|
||||
|
||||
/* Methods called by bulk generated PCI devices below */
|
||||
|
||||
/* Methods called by hotplug devices */
|
||||
Method(PCEJ, 2, NotSerialized) {
|
||||
// _EJ0 method - eject callback
|
||||
Acquire(BLCK, 0xFFFF)
|
||||
Store(Arg0, BNUM)
|
||||
Store(ShiftLeft(1, Arg1), B0EJ)
|
||||
Release(BLCK)
|
||||
Return (0x0)
|
||||
}
|
||||
|
||||
/* Hotplug notification method supplied by SSDT */
|
||||
External(\_SB.PCI0.PCNT, MethodObj)
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************
|
||||
* PCI IRQs
|
||||
****************************************************************/
|
||||
|
||||
Scope(\_SB) {
|
||||
Scope(PCI0) {
|
||||
Method (_PRT, 0) {
|
||||
Store(Package(128) {}, Local0)
|
||||
Store(Zero, Local1)
|
||||
While(LLess(Local1, 128)) {
|
||||
// slot = pin >> 2
|
||||
Store(ShiftRight(Local1, 2), Local2)
|
||||
|
||||
// lnk = (slot + pin) & 3
|
||||
Store(And(Add(Local1, Local2), 3), Local3)
|
||||
If (LEqual(Local3, 0)) {
|
||||
Store(Package(4) { Zero, Zero, LNKD, Zero }, Local4)
|
||||
}
|
||||
If (LEqual(Local3, 1)) {
|
||||
// device 1 is the power-management device, needs SCI
|
||||
If (LEqual(Local1, 4)) {
|
||||
Store(Package(4) { Zero, Zero, LNKS, Zero }, Local4)
|
||||
} Else {
|
||||
Store(Package(4) { Zero, Zero, LNKA, Zero }, Local4)
|
||||
}
|
||||
}
|
||||
If (LEqual(Local3, 2)) {
|
||||
Store(Package(4) { Zero, Zero, LNKB, Zero }, Local4)
|
||||
}
|
||||
If (LEqual(Local3, 3)) {
|
||||
Store(Package(4) { Zero, Zero, LNKC, Zero }, Local4)
|
||||
}
|
||||
|
||||
// Complete the interrupt routing entry:
|
||||
// Package(4) { 0x[slot]FFFF, [pin], [link], 0) }
|
||||
|
||||
Store(Or(ShiftLeft(Local2, 16), 0xFFFF), Index(Local4, 0))
|
||||
Store(And(Local1, 3), Index(Local4, 1))
|
||||
Store(Local4, Index(Local0, Local1))
|
||||
|
||||
Increment(Local1)
|
||||
}
|
||||
|
||||
Return(Local0)
|
||||
}
|
||||
}
|
||||
|
||||
Field(PCI0.ISA.P40C, ByteAcc, NoLock, Preserve) {
|
||||
PRQ0, 8,
|
||||
PRQ1, 8,
|
||||
PRQ2, 8,
|
||||
PRQ3, 8
|
||||
}
|
||||
|
||||
Method(IQST, 1, NotSerialized) {
|
||||
// _STA method - get status
|
||||
If (And(0x80, Arg0)) {
|
||||
Return (0x09)
|
||||
}
|
||||
Return (0x0B)
|
||||
}
|
||||
Method(IQCR, 1, Serialized) {
|
||||
// _CRS method - get current settings
|
||||
Name(PRR0, ResourceTemplate() {
|
||||
Interrupt(, Level, ActiveHigh, Shared) { 0 }
|
||||
})
|
||||
CreateDWordField(PRR0, 0x05, PRRI)
|
||||
If (LLess(Arg0, 0x80)) {
|
||||
Store(Arg0, PRRI)
|
||||
}
|
||||
Return (PRR0)
|
||||
}
|
||||
|
||||
#define define_link(link, uid, reg) \
|
||||
Device(link) { \
|
||||
Name(_HID, EISAID("PNP0C0F")) \
|
||||
Name(_UID, uid) \
|
||||
Name(_PRS, ResourceTemplate() { \
|
||||
Interrupt(, Level, ActiveHigh, Shared) { \
|
||||
5, 10, 11 \
|
||||
} \
|
||||
}) \
|
||||
Method(_STA, 0, NotSerialized) { \
|
||||
Return (IQST(reg)) \
|
||||
} \
|
||||
Method(_DIS, 0, NotSerialized) { \
|
||||
Or(reg, 0x80, reg) \
|
||||
} \
|
||||
Method(_CRS, 0, NotSerialized) { \
|
||||
Return (IQCR(reg)) \
|
||||
} \
|
||||
Method(_SRS, 1, NotSerialized) { \
|
||||
CreateDWordField(Arg0, 0x05, PRRI) \
|
||||
Store(PRRI, reg) \
|
||||
} \
|
||||
}
|
||||
|
||||
define_link(LNKA, 0, PRQ0)
|
||||
define_link(LNKB, 1, PRQ1)
|
||||
define_link(LNKC, 2, PRQ2)
|
||||
define_link(LNKD, 3, PRQ3)
|
||||
|
||||
Device(LNKS) {
|
||||
Name(_HID, EISAID("PNP0C0F"))
|
||||
Name(_UID, 4)
|
||||
Name(_PRS, ResourceTemplate() {
|
||||
Interrupt(, Level, ActiveHigh, Shared) { 9 }
|
||||
})
|
||||
|
||||
// The SCI cannot be disabled and is always attached to GSI 9,
|
||||
// so these are no-ops. We only need this link to override the
|
||||
// polarity to active high and match the content of the MADT.
|
||||
Method(_STA, 0, NotSerialized) { Return (0x0b) }
|
||||
Method(_DIS, 0, NotSerialized) { }
|
||||
Method(_CRS, 0, NotSerialized) { Return (_PRS) }
|
||||
Method(_SRS, 1, NotSerialized) { }
|
||||
}
|
||||
}
|
||||
|
||||
#include "hw/acpi/pc-hotplug.h"
|
||||
#define CPU_STATUS_BASE PIIX4_CPU_HOTPLUG_IO_BASE
|
||||
#include "acpi-dsdt-cpu-hotplug.dsl"
|
||||
#include "acpi-dsdt-mem-hotplug.dsl"
|
||||
|
||||
|
||||
/****************************************************************
|
||||
* General purpose events
|
||||
****************************************************************/
|
||||
Scope(\_GPE) {
|
||||
Name(_HID, "ACPI0006")
|
||||
|
||||
Method(_L00) {
|
||||
}
|
||||
Method(_E01) {
|
||||
// PCI hotplug event
|
||||
Acquire(\_SB.PCI0.BLCK, 0xFFFF)
|
||||
\_SB.PCI0.PCNT()
|
||||
Release(\_SB.PCI0.BLCK)
|
||||
}
|
||||
Method(_E02) {
|
||||
// CPU hotplug event
|
||||
\_SB.PRSC()
|
||||
}
|
||||
Method(_E03) {
|
||||
// Memory hotplug event
|
||||
\_SB.PCI0.MEMORY_HOTPLUG_DEVICE.MEMORY_SLOT_SCAN_METHOD()
|
||||
}
|
||||
Method(_L04) {
|
||||
}
|
||||
Method(_L05) {
|
||||
}
|
||||
Method(_L06) {
|
||||
}
|
||||
Method(_L07) {
|
||||
}
|
||||
Method(_L08) {
|
||||
}
|
||||
Method(_L09) {
|
||||
}
|
||||
Method(_L0A) {
|
||||
}
|
||||
Method(_L0B) {
|
||||
}
|
||||
Method(_L0C) {
|
||||
}
|
||||
Method(_L0D) {
|
||||
}
|
||||
Method(_L0E) {
|
||||
}
|
||||
Method(_L0F) {
|
||||
}
|
||||
}
|
||||
}
|
File diff suppressed because it is too large
Load Diff
44
hw/i386/pc.c
44
hw/i386/pc.c
|
@ -360,6 +360,31 @@ static const char * const fdc_container_path[] = {
|
|||
"/unattached", "/peripheral", "/peripheral-anon"
|
||||
};
|
||||
|
||||
/*
|
||||
* Locate the FDC at IO address 0x3f0, in order to configure the CMOS registers
|
||||
* and ACPI objects.
|
||||
*/
|
||||
ISADevice *pc_find_fdc0(void)
|
||||
{
|
||||
int i;
|
||||
Object *container;
|
||||
CheckFdcState state = { 0 };
|
||||
|
||||
for (i = 0; i < ARRAY_SIZE(fdc_container_path); i++) {
|
||||
container = container_get(qdev_get_machine(), fdc_container_path[i]);
|
||||
object_child_foreach(container, check_fdc, &state);
|
||||
}
|
||||
|
||||
if (state.multiple) {
|
||||
error_report("warning: multiple floppy disk controllers with "
|
||||
"iobase=0x3f0 have been found;\n"
|
||||
"the one being picked for CMOS setup might not reflect "
|
||||
"your intent");
|
||||
}
|
||||
|
||||
return state.floppy;
|
||||
}
|
||||
|
||||
static void pc_cmos_init_late(void *opaque)
|
||||
{
|
||||
pc_cmos_init_late_arg *arg = opaque;
|
||||
|
@ -368,8 +393,6 @@ static void pc_cmos_init_late(void *opaque)
|
|||
int8_t heads, sectors;
|
||||
int val;
|
||||
int i, trans;
|
||||
Object *container;
|
||||
CheckFdcState state = { 0 };
|
||||
|
||||
val = 0;
|
||||
if (ide_get_geometry(arg->idebus[0], 0,
|
||||
|
@ -399,22 +422,7 @@ static void pc_cmos_init_late(void *opaque)
|
|||
}
|
||||
rtc_set_memory(s, 0x39, val);
|
||||
|
||||
/*
|
||||
* Locate the FDC at IO address 0x3f0, and configure the CMOS registers
|
||||
* accordingly.
|
||||
*/
|
||||
for (i = 0; i < ARRAY_SIZE(fdc_container_path); i++) {
|
||||
container = container_get(qdev_get_machine(), fdc_container_path[i]);
|
||||
object_child_foreach(container, check_fdc, &state);
|
||||
}
|
||||
|
||||
if (state.multiple) {
|
||||
error_report("warning: multiple floppy disk controllers with "
|
||||
"iobase=0x3f0 have been found;\n"
|
||||
"the one being picked for CMOS setup might not reflect "
|
||||
"your intent");
|
||||
}
|
||||
pc_cmos_init_floppy(s, state.floppy);
|
||||
pc_cmos_init_floppy(s, pc_find_fdc0());
|
||||
|
||||
qemu_unregister_reset(pc_cmos_init_late, opaque);
|
||||
}
|
||||
|
|
|
@ -1,436 +0,0 @@
|
|||
/*
|
||||
* Bochs/QEMU ACPI DSDT ASL definition
|
||||
*
|
||||
* Copyright (c) 2006 Fabrice Bellard
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License version 2 as published by the Free Software Foundation.
|
||||
*
|
||||
* This library 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.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this library; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
/*
|
||||
* Copyright (c) 2010 Isaku Yamahata
|
||||
* yamahata at valinux co jp
|
||||
* Based on acpi-dsdt.dsl, but heavily modified for q35 chipset.
|
||||
*/
|
||||
|
||||
|
||||
ACPI_EXTRACT_ALL_CODE Q35AcpiDsdtAmlCode
|
||||
|
||||
DefinitionBlock (
|
||||
"q35-acpi-dsdt.aml",// Output Filename
|
||||
"DSDT", // Signature
|
||||
0x01, // DSDT Compliance Revision
|
||||
"BXPC", // OEMID
|
||||
"BXDSDT", // TABLE ID
|
||||
0x2 // OEM Revision
|
||||
)
|
||||
{
|
||||
|
||||
#include "acpi-dsdt-dbug.dsl"
|
||||
|
||||
Scope(\_SB) {
|
||||
OperationRegion(PCST, SystemIO, 0xae00, 0x0c)
|
||||
OperationRegion(PCSB, SystemIO, 0xae0c, 0x01)
|
||||
Field(PCSB, AnyAcc, NoLock, WriteAsZeros) {
|
||||
PCIB, 8,
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************
|
||||
* PCI Bus definition
|
||||
****************************************************************/
|
||||
Scope(\_SB) {
|
||||
Device(PCI0) {
|
||||
Name(_HID, EisaId("PNP0A08"))
|
||||
Name(_CID, EisaId("PNP0A03"))
|
||||
Name(_ADR, 0x00)
|
||||
Name(_UID, 1)
|
||||
|
||||
External(ISA, DeviceObj)
|
||||
|
||||
// _OSC: based on sample of ACPI3.0b spec
|
||||
Name(SUPP, 0) // PCI _OSC Support Field value
|
||||
Name(CTRL, 0) // PCI _OSC Control Field value
|
||||
Method(_OSC, 4) {
|
||||
// Create DWORD-addressable fields from the Capabilities Buffer
|
||||
CreateDWordField(Arg3, 0, CDW1)
|
||||
|
||||
// Check for proper UUID
|
||||
If (LEqual(Arg0, ToUUID("33DB4D5B-1FF7-401C-9657-7441C03DD766"))) {
|
||||
// Create DWORD-addressable fields from the Capabilities Buffer
|
||||
CreateDWordField(Arg3, 4, CDW2)
|
||||
CreateDWordField(Arg3, 8, CDW3)
|
||||
|
||||
// Save Capabilities DWORD2 & 3
|
||||
Store(CDW2, SUPP)
|
||||
Store(CDW3, CTRL)
|
||||
|
||||
// Always allow native PME, AER (no dependencies)
|
||||
// Never allow SHPC (no SHPC controller in this system)
|
||||
And(CTRL, 0x1D, CTRL)
|
||||
|
||||
#if 0 // For now, nothing to do
|
||||
If (Not(And(CDW1, 1))) { // Query flag clear?
|
||||
// Disable GPEs for features granted native control.
|
||||
If (And(CTRL, 0x01)) { // Hot plug control granted?
|
||||
Store(0, HPCE) // clear the hot plug SCI enable bit
|
||||
Store(1, HPCS) // clear the hot plug SCI status bit
|
||||
}
|
||||
If (And(CTRL, 0x04)) { // PME control granted?
|
||||
Store(0, PMCE) // clear the PME SCI enable bit
|
||||
Store(1, PMCS) // clear the PME SCI status bit
|
||||
}
|
||||
If (And(CTRL, 0x10)) { // OS restoring PCI Express cap structure?
|
||||
// Set status to not restore PCI Express cap structure
|
||||
// upon resume from S3
|
||||
Store(1, S3CR)
|
||||
}
|
||||
}
|
||||
#endif
|
||||
If (LNotEqual(Arg1, One)) {
|
||||
// Unknown revision
|
||||
Or(CDW1, 0x08, CDW1)
|
||||
}
|
||||
If (LNotEqual(CDW3, CTRL)) {
|
||||
// Capabilities bits were masked
|
||||
Or(CDW1, 0x10, CDW1)
|
||||
}
|
||||
// Update DWORD3 in the buffer
|
||||
Store(CTRL, CDW3)
|
||||
} Else {
|
||||
Or(CDW1, 4, CDW1) // Unrecognized UUID
|
||||
}
|
||||
Return (Arg3)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#include "acpi-dsdt-hpet.dsl"
|
||||
|
||||
|
||||
/****************************************************************
|
||||
* LPC ISA bridge
|
||||
****************************************************************/
|
||||
|
||||
Scope(\_SB.PCI0) {
|
||||
/* PCI D31:f0 LPC ISA bridge */
|
||||
Device(ISA) {
|
||||
Name (_ADR, 0x001F0000) // _ADR: Address
|
||||
|
||||
/* ICH9 PCI to ISA irq remapping */
|
||||
OperationRegion(PIRQ, PCI_Config, 0x60, 0x0C)
|
||||
|
||||
OperationRegion(LPCD, PCI_Config, 0x80, 0x2)
|
||||
Field(LPCD, AnyAcc, NoLock, Preserve) {
|
||||
COMA, 3,
|
||||
, 1,
|
||||
COMB, 3,
|
||||
|
||||
Offset(0x01),
|
||||
LPTD, 2,
|
||||
, 2,
|
||||
FDCD, 2
|
||||
}
|
||||
OperationRegion(LPCE, PCI_Config, 0x82, 0x2)
|
||||
Field(LPCE, AnyAcc, NoLock, Preserve) {
|
||||
CAEN, 1,
|
||||
CBEN, 1,
|
||||
LPEN, 1,
|
||||
FDEN, 1
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#include "acpi-dsdt-isa.dsl"
|
||||
|
||||
|
||||
/****************************************************************
|
||||
* PCI IRQs
|
||||
****************************************************************/
|
||||
|
||||
/* Zero => PIC mode, One => APIC Mode */
|
||||
Name(\PICF, Zero)
|
||||
Method(\_PIC, 1, NotSerialized) {
|
||||
Store(Arg0, \PICF)
|
||||
}
|
||||
|
||||
Scope(\_SB) {
|
||||
Scope(PCI0) {
|
||||
#define prt_slot_lnk(nr, lnk0, lnk1, lnk2, lnk3) \
|
||||
Package() { nr##ffff, 0, lnk0, 0 }, \
|
||||
Package() { nr##ffff, 1, lnk1, 0 }, \
|
||||
Package() { nr##ffff, 2, lnk2, 0 }, \
|
||||
Package() { nr##ffff, 3, lnk3, 0 }
|
||||
|
||||
#define prt_slot_lnkA(nr) prt_slot_lnk(nr, LNKA, LNKB, LNKC, LNKD)
|
||||
#define prt_slot_lnkB(nr) prt_slot_lnk(nr, LNKB, LNKC, LNKD, LNKA)
|
||||
#define prt_slot_lnkC(nr) prt_slot_lnk(nr, LNKC, LNKD, LNKA, LNKB)
|
||||
#define prt_slot_lnkD(nr) prt_slot_lnk(nr, LNKD, LNKA, LNKB, LNKC)
|
||||
|
||||
#define prt_slot_lnkE(nr) prt_slot_lnk(nr, LNKE, LNKF, LNKG, LNKH)
|
||||
#define prt_slot_lnkF(nr) prt_slot_lnk(nr, LNKF, LNKG, LNKH, LNKE)
|
||||
#define prt_slot_lnkG(nr) prt_slot_lnk(nr, LNKG, LNKH, LNKE, LNKF)
|
||||
#define prt_slot_lnkH(nr) prt_slot_lnk(nr, LNKH, LNKE, LNKF, LNKG)
|
||||
|
||||
Name(PRTP, package() {
|
||||
prt_slot_lnkE(0x0000),
|
||||
prt_slot_lnkF(0x0001),
|
||||
prt_slot_lnkG(0x0002),
|
||||
prt_slot_lnkH(0x0003),
|
||||
prt_slot_lnkE(0x0004),
|
||||
prt_slot_lnkF(0x0005),
|
||||
prt_slot_lnkG(0x0006),
|
||||
prt_slot_lnkH(0x0007),
|
||||
prt_slot_lnkE(0x0008),
|
||||
prt_slot_lnkF(0x0009),
|
||||
prt_slot_lnkG(0x000a),
|
||||
prt_slot_lnkH(0x000b),
|
||||
prt_slot_lnkE(0x000c),
|
||||
prt_slot_lnkF(0x000d),
|
||||
prt_slot_lnkG(0x000e),
|
||||
prt_slot_lnkH(0x000f),
|
||||
prt_slot_lnkE(0x0010),
|
||||
prt_slot_lnkF(0x0011),
|
||||
prt_slot_lnkG(0x0012),
|
||||
prt_slot_lnkH(0x0013),
|
||||
prt_slot_lnkE(0x0014),
|
||||
prt_slot_lnkF(0x0015),
|
||||
prt_slot_lnkG(0x0016),
|
||||
prt_slot_lnkH(0x0017),
|
||||
prt_slot_lnkE(0x0018),
|
||||
|
||||
/* INTA -> PIRQA for slot 25 - 31
|
||||
see the default value of D<N>IR */
|
||||
prt_slot_lnkA(0x0019),
|
||||
prt_slot_lnkA(0x001a),
|
||||
prt_slot_lnkA(0x001b),
|
||||
prt_slot_lnkA(0x001c),
|
||||
prt_slot_lnkA(0x001d),
|
||||
|
||||
/* PCIe->PCI bridge. use PIRQ[E-H] */
|
||||
prt_slot_lnkE(0x001e),
|
||||
|
||||
prt_slot_lnkA(0x001f)
|
||||
})
|
||||
|
||||
#define prt_slot_gsi(nr, gsi0, gsi1, gsi2, gsi3) \
|
||||
Package() { nr##ffff, 0, gsi0, 0 }, \
|
||||
Package() { nr##ffff, 1, gsi1, 0 }, \
|
||||
Package() { nr##ffff, 2, gsi2, 0 }, \
|
||||
Package() { nr##ffff, 3, gsi3, 0 }
|
||||
|
||||
#define prt_slot_gsiA(nr) prt_slot_gsi(nr, GSIA, GSIB, GSIC, GSID)
|
||||
#define prt_slot_gsiB(nr) prt_slot_gsi(nr, GSIB, GSIC, GSID, GSIA)
|
||||
#define prt_slot_gsiC(nr) prt_slot_gsi(nr, GSIC, GSID, GSIA, GSIB)
|
||||
#define prt_slot_gsiD(nr) prt_slot_gsi(nr, GSID, GSIA, GSIB, GSIC)
|
||||
|
||||
#define prt_slot_gsiE(nr) prt_slot_gsi(nr, GSIE, GSIF, GSIG, GSIH)
|
||||
#define prt_slot_gsiF(nr) prt_slot_gsi(nr, GSIF, GSIG, GSIH, GSIE)
|
||||
#define prt_slot_gsiG(nr) prt_slot_gsi(nr, GSIG, GSIH, GSIE, GSIF)
|
||||
#define prt_slot_gsiH(nr) prt_slot_gsi(nr, GSIH, GSIE, GSIF, GSIG)
|
||||
|
||||
Name(PRTA, package() {
|
||||
prt_slot_gsiE(0x0000),
|
||||
prt_slot_gsiF(0x0001),
|
||||
prt_slot_gsiG(0x0002),
|
||||
prt_slot_gsiH(0x0003),
|
||||
prt_slot_gsiE(0x0004),
|
||||
prt_slot_gsiF(0x0005),
|
||||
prt_slot_gsiG(0x0006),
|
||||
prt_slot_gsiH(0x0007),
|
||||
prt_slot_gsiE(0x0008),
|
||||
prt_slot_gsiF(0x0009),
|
||||
prt_slot_gsiG(0x000a),
|
||||
prt_slot_gsiH(0x000b),
|
||||
prt_slot_gsiE(0x000c),
|
||||
prt_slot_gsiF(0x000d),
|
||||
prt_slot_gsiG(0x000e),
|
||||
prt_slot_gsiH(0x000f),
|
||||
prt_slot_gsiE(0x0010),
|
||||
prt_slot_gsiF(0x0011),
|
||||
prt_slot_gsiG(0x0012),
|
||||
prt_slot_gsiH(0x0013),
|
||||
prt_slot_gsiE(0x0014),
|
||||
prt_slot_gsiF(0x0015),
|
||||
prt_slot_gsiG(0x0016),
|
||||
prt_slot_gsiH(0x0017),
|
||||
prt_slot_gsiE(0x0018),
|
||||
|
||||
/* INTA -> PIRQA for slot 25 - 31, but 30
|
||||
see the default value of D<N>IR */
|
||||
prt_slot_gsiA(0x0019),
|
||||
prt_slot_gsiA(0x001a),
|
||||
prt_slot_gsiA(0x001b),
|
||||
prt_slot_gsiA(0x001c),
|
||||
prt_slot_gsiA(0x001d),
|
||||
|
||||
/* PCIe->PCI bridge. use PIRQ[E-H] */
|
||||
prt_slot_gsiE(0x001e),
|
||||
|
||||
prt_slot_gsiA(0x001f)
|
||||
})
|
||||
|
||||
Method(_PRT, 0, NotSerialized) {
|
||||
/* PCI IRQ routing table, example from ACPI 2.0a specification,
|
||||
section 6.2.8.1 */
|
||||
/* Note: we provide the same info as the PCI routing
|
||||
table of the Bochs BIOS */
|
||||
If (LEqual(\PICF, Zero)) {
|
||||
Return (PRTP)
|
||||
} Else {
|
||||
Return (PRTA)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Field(PCI0.ISA.PIRQ, ByteAcc, NoLock, Preserve) {
|
||||
PRQA, 8,
|
||||
PRQB, 8,
|
||||
PRQC, 8,
|
||||
PRQD, 8,
|
||||
|
||||
Offset(0x08),
|
||||
PRQE, 8,
|
||||
PRQF, 8,
|
||||
PRQG, 8,
|
||||
PRQH, 8
|
||||
}
|
||||
|
||||
Method(IQST, 1, NotSerialized) {
|
||||
// _STA method - get status
|
||||
If (And(0x80, Arg0)) {
|
||||
Return (0x09)
|
||||
}
|
||||
Return (0x0B)
|
||||
}
|
||||
Method(IQCR, 1, Serialized) {
|
||||
// _CRS method - get current settings
|
||||
Name(PRR0, ResourceTemplate() {
|
||||
Interrupt(, Level, ActiveHigh, Shared) { 0 }
|
||||
})
|
||||
CreateDWordField(PRR0, 0x05, PRRI)
|
||||
Store(And(Arg0, 0x0F), PRRI)
|
||||
Return (PRR0)
|
||||
}
|
||||
|
||||
#define define_link(link, uid, reg) \
|
||||
Device(link) { \
|
||||
Name(_HID, EISAID("PNP0C0F")) \
|
||||
Name(_UID, uid) \
|
||||
Name(_PRS, ResourceTemplate() { \
|
||||
Interrupt(, Level, ActiveHigh, Shared) { \
|
||||
5, 10, 11 \
|
||||
} \
|
||||
}) \
|
||||
Method(_STA, 0, NotSerialized) { \
|
||||
Return (IQST(reg)) \
|
||||
} \
|
||||
Method(_DIS, 0, NotSerialized) { \
|
||||
Or(reg, 0x80, reg) \
|
||||
} \
|
||||
Method(_CRS, 0, NotSerialized) { \
|
||||
Return (IQCR(reg)) \
|
||||
} \
|
||||
Method(_SRS, 1, NotSerialized) { \
|
||||
CreateDWordField(Arg0, 0x05, PRRI) \
|
||||
Store(PRRI, reg) \
|
||||
} \
|
||||
}
|
||||
|
||||
define_link(LNKA, 0, PRQA)
|
||||
define_link(LNKB, 1, PRQB)
|
||||
define_link(LNKC, 2, PRQC)
|
||||
define_link(LNKD, 3, PRQD)
|
||||
define_link(LNKE, 4, PRQE)
|
||||
define_link(LNKF, 5, PRQF)
|
||||
define_link(LNKG, 6, PRQG)
|
||||
define_link(LNKH, 7, PRQH)
|
||||
|
||||
#define define_gsi_link(link, uid, gsi) \
|
||||
Device(link) { \
|
||||
Name(_HID, EISAID("PNP0C0F")) \
|
||||
Name(_UID, uid) \
|
||||
Name(_PRS, ResourceTemplate() { \
|
||||
Interrupt(, Level, ActiveHigh, Shared) { \
|
||||
gsi \
|
||||
} \
|
||||
}) \
|
||||
Name(_CRS, ResourceTemplate() { \
|
||||
Interrupt(, Level, ActiveHigh, Shared) { \
|
||||
gsi \
|
||||
} \
|
||||
}) \
|
||||
Method(_SRS, 1, NotSerialized) { \
|
||||
} \
|
||||
}
|
||||
|
||||
define_gsi_link(GSIA, 0, 0x10)
|
||||
define_gsi_link(GSIB, 0, 0x11)
|
||||
define_gsi_link(GSIC, 0, 0x12)
|
||||
define_gsi_link(GSID, 0, 0x13)
|
||||
define_gsi_link(GSIE, 0, 0x14)
|
||||
define_gsi_link(GSIF, 0, 0x15)
|
||||
define_gsi_link(GSIG, 0, 0x16)
|
||||
define_gsi_link(GSIH, 0, 0x17)
|
||||
}
|
||||
|
||||
#include "hw/acpi/pc-hotplug.h"
|
||||
#define CPU_STATUS_BASE ICH9_CPU_HOTPLUG_IO_BASE
|
||||
#include "acpi-dsdt-cpu-hotplug.dsl"
|
||||
#include "acpi-dsdt-mem-hotplug.dsl"
|
||||
|
||||
|
||||
/****************************************************************
|
||||
* General purpose events
|
||||
****************************************************************/
|
||||
Scope(\_GPE) {
|
||||
Name(_HID, "ACPI0006")
|
||||
|
||||
Method(_L00) {
|
||||
}
|
||||
Method(_L01) {
|
||||
}
|
||||
Method(_E02) {
|
||||
// CPU hotplug event
|
||||
\_SB.PRSC()
|
||||
}
|
||||
Method(_E03) {
|
||||
// Memory hotplug event
|
||||
\_SB.PCI0.MEMORY_HOTPLUG_DEVICE.MEMORY_SLOT_SCAN_METHOD()
|
||||
}
|
||||
Method(_L04) {
|
||||
}
|
||||
Method(_L05) {
|
||||
}
|
||||
Method(_L06) {
|
||||
}
|
||||
Method(_L07) {
|
||||
}
|
||||
Method(_L08) {
|
||||
}
|
||||
Method(_L09) {
|
||||
}
|
||||
Method(_L0A) {
|
||||
}
|
||||
Method(_L0B) {
|
||||
}
|
||||
Method(_L0C) {
|
||||
}
|
||||
Method(_L0D) {
|
||||
}
|
||||
Method(_L0E) {
|
||||
}
|
||||
Method(_L0F) {
|
||||
}
|
||||
}
|
||||
}
|
File diff suppressed because it is too large
Load Diff
|
@ -29,6 +29,7 @@
|
|||
#include "sysemu/char.h"
|
||||
#include "sysemu/hostmem.h"
|
||||
#include "qapi/visitor.h"
|
||||
#include "exec/ram_addr.h"
|
||||
|
||||
#include "hw/misc/ivshmem.h"
|
||||
|
||||
|
@ -422,6 +423,7 @@ static int create_shared_memory_BAR(IVShmemState *s, int fd, uint8_t attr,
|
|||
|
||||
memory_region_init_ram_ptr(&s->ivshmem, OBJECT(s), "ivshmem.bar2",
|
||||
s->ivshmem_size, ptr);
|
||||
qemu_set_ram_fd(s->ivshmem.ram_addr, fd);
|
||||
vmstate_register_ram(&s->ivshmem, DEVICE(s));
|
||||
memory_region_add_subregion(&s->bar, 0, &s->ivshmem);
|
||||
|
||||
|
@ -682,6 +684,7 @@ static void ivshmem_read(void *opaque, const uint8_t *buf, int size)
|
|||
}
|
||||
memory_region_init_ram_ptr(&s->ivshmem, OBJECT(s),
|
||||
"ivshmem.bar2", s->ivshmem_size, map_ptr);
|
||||
qemu_set_ram_fd(s->ivshmem.ram_addr, incoming_fd);
|
||||
vmstate_register_ram(&s->ivshmem, DEVICE(s));
|
||||
|
||||
IVSHMEM_DPRINTF("guest h/w addr = %p, size = %" PRIu64 "\n",
|
||||
|
@ -689,7 +692,6 @@ static void ivshmem_read(void *opaque, const uint8_t *buf, int size)
|
|||
|
||||
memory_region_add_subregion(&s->bar, 0, &s->ivshmem);
|
||||
|
||||
close(incoming_fd);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -991,7 +993,6 @@ static void pci_ivshmem_realize(PCIDevice *dev, Error **errp)
|
|||
}
|
||||
|
||||
create_shared_memory_BAR(s, fd, attr, errp);
|
||||
close(fd);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1010,11 +1011,15 @@ static void pci_ivshmem_exit(PCIDevice *dev)
|
|||
if (memory_region_is_mapped(&s->ivshmem)) {
|
||||
if (!s->hostmem) {
|
||||
void *addr = memory_region_get_ram_ptr(&s->ivshmem);
|
||||
int fd;
|
||||
|
||||
if (munmap(addr, s->ivshmem_size) == -1) {
|
||||
error_report("Failed to munmap shared memory %s",
|
||||
strerror(errno));
|
||||
}
|
||||
|
||||
if ((fd = qemu_get_ram_fd(s->ivshmem.ram_addr)) != -1)
|
||||
close(fd);
|
||||
}
|
||||
|
||||
vmstate_unregister_ram(&s->ivshmem, DEVICE(dev));
|
||||
|
|
|
@ -761,7 +761,7 @@ static const IGDHostInfo igd_host_bridge_infos[] = {
|
|||
{0xa8, 4}, /* SNB: base of GTT stolen memory */
|
||||
};
|
||||
|
||||
static int host_pci_config_read(int pos, int len, uint32_t val)
|
||||
static int host_pci_config_read(int pos, int len, uint32_t *val)
|
||||
{
|
||||
char path[PATH_MAX];
|
||||
int config_fd;
|
||||
|
@ -784,12 +784,14 @@ static int host_pci_config_read(int pos, int len, uint32_t val)
|
|||
ret = -errno;
|
||||
goto out;
|
||||
}
|
||||
|
||||
do {
|
||||
rc = read(config_fd, (uint8_t *)&val, len);
|
||||
rc = read(config_fd, (uint8_t *)val, len);
|
||||
} while (rc < 0 && (errno == EINTR || errno == EAGAIN));
|
||||
if (rc != len) {
|
||||
ret = -errno;
|
||||
}
|
||||
|
||||
out:
|
||||
close(config_fd);
|
||||
return ret;
|
||||
|
@ -805,7 +807,7 @@ static int igd_pt_i440fx_initfn(struct PCIDevice *pci_dev)
|
|||
for (i = 0; i < num; i++) {
|
||||
pos = igd_host_bridge_infos[i].offset;
|
||||
len = igd_host_bridge_infos[i].len;
|
||||
rc = host_pci_config_read(pos, len, val);
|
||||
rc = host_pci_config_read(pos, len, &val);
|
||||
if (rc) {
|
||||
return -ENODEV;
|
||||
}
|
||||
|
|
|
@ -713,7 +713,7 @@ static void hpet_init(Object *obj)
|
|||
HPETState *s = HPET(obj);
|
||||
|
||||
/* HPET Area */
|
||||
memory_region_init_io(&s->iomem, obj, &hpet_ram_ops, s, "hpet", 0x400);
|
||||
memory_region_init_io(&s->iomem, obj, &hpet_ram_ops, s, "hpet", HPET_LEN);
|
||||
sysbus_init_mmio(sbd, &s->iomem);
|
||||
}
|
||||
|
||||
|
|
|
@ -1126,33 +1126,15 @@ static bool virtio_extra_state_needed(void *opaque)
|
|||
k->has_extra_state(qbus->parent);
|
||||
}
|
||||
|
||||
static void put_virtqueue_state(QEMUFile *f, void *pv, size_t size)
|
||||
{
|
||||
VirtIODevice *vdev = pv;
|
||||
int i;
|
||||
|
||||
for (i = 0; i < VIRTIO_QUEUE_MAX; i++) {
|
||||
qemu_put_be64(f, vdev->vq[i].vring.avail);
|
||||
qemu_put_be64(f, vdev->vq[i].vring.used);
|
||||
}
|
||||
}
|
||||
|
||||
static int get_virtqueue_state(QEMUFile *f, void *pv, size_t size)
|
||||
{
|
||||
VirtIODevice *vdev = pv;
|
||||
int i;
|
||||
|
||||
for (i = 0; i < VIRTIO_QUEUE_MAX; i++) {
|
||||
vdev->vq[i].vring.avail = qemu_get_be64(f);
|
||||
vdev->vq[i].vring.used = qemu_get_be64(f);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static VMStateInfo vmstate_info_virtqueue = {
|
||||
static const VMStateDescription vmstate_virtqueue = {
|
||||
.name = "virtqueue_state",
|
||||
.get = get_virtqueue_state,
|
||||
.put = put_virtqueue_state,
|
||||
.version_id = 1,
|
||||
.minimum_version_id = 1,
|
||||
.fields = (VMStateField[]) {
|
||||
VMSTATE_UINT64(vring.avail, struct VirtQueue),
|
||||
VMSTATE_UINT64(vring.used, struct VirtQueue),
|
||||
VMSTATE_END_OF_LIST()
|
||||
}
|
||||
};
|
||||
|
||||
static const VMStateDescription vmstate_virtio_virtqueues = {
|
||||
|
@ -1161,44 +1143,20 @@ static const VMStateDescription vmstate_virtio_virtqueues = {
|
|||
.minimum_version_id = 1,
|
||||
.needed = &virtio_virtqueue_needed,
|
||||
.fields = (VMStateField[]) {
|
||||
{
|
||||
.name = "virtqueues",
|
||||
.version_id = 0,
|
||||
.field_exists = NULL,
|
||||
.size = 0,
|
||||
.info = &vmstate_info_virtqueue,
|
||||
.flags = VMS_SINGLE,
|
||||
.offset = 0,
|
||||
},
|
||||
VMSTATE_STRUCT_VARRAY_KNOWN(vq, struct VirtIODevice, VIRTIO_QUEUE_MAX,
|
||||
0, vmstate_virtqueue, VirtQueue),
|
||||
VMSTATE_END_OF_LIST()
|
||||
}
|
||||
};
|
||||
|
||||
static void put_ringsize_state(QEMUFile *f, void *pv, size_t size)
|
||||
{
|
||||
VirtIODevice *vdev = pv;
|
||||
int i;
|
||||
|
||||
for (i = 0; i < VIRTIO_QUEUE_MAX; i++) {
|
||||
qemu_put_be32(f, vdev->vq[i].vring.num_default);
|
||||
}
|
||||
}
|
||||
|
||||
static int get_ringsize_state(QEMUFile *f, void *pv, size_t size)
|
||||
{
|
||||
VirtIODevice *vdev = pv;
|
||||
int i;
|
||||
|
||||
for (i = 0; i < VIRTIO_QUEUE_MAX; i++) {
|
||||
vdev->vq[i].vring.num_default = qemu_get_be32(f);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static VMStateInfo vmstate_info_ringsize = {
|
||||
static const VMStateDescription vmstate_ringsize = {
|
||||
.name = "ringsize_state",
|
||||
.get = get_ringsize_state,
|
||||
.put = put_ringsize_state,
|
||||
.version_id = 1,
|
||||
.minimum_version_id = 1,
|
||||
.fields = (VMStateField[]) {
|
||||
VMSTATE_UINT32(vring.num_default, struct VirtQueue),
|
||||
VMSTATE_END_OF_LIST()
|
||||
}
|
||||
};
|
||||
|
||||
static const VMStateDescription vmstate_virtio_ringsize = {
|
||||
|
@ -1207,15 +1165,8 @@ static const VMStateDescription vmstate_virtio_ringsize = {
|
|||
.minimum_version_id = 1,
|
||||
.needed = &virtio_ringsize_needed,
|
||||
.fields = (VMStateField[]) {
|
||||
{
|
||||
.name = "ringsize",
|
||||
.version_id = 0,
|
||||
.field_exists = NULL,
|
||||
.size = 0,
|
||||
.info = &vmstate_info_ringsize,
|
||||
.flags = VMS_SINGLE,
|
||||
.offset = 0,
|
||||
},
|
||||
VMSTATE_STRUCT_VARRAY_KNOWN(vq, struct VirtIODevice, VIRTIO_QUEUE_MAX,
|
||||
0, vmstate_ringsize, VirtQueue),
|
||||
VMSTATE_END_OF_LIST()
|
||||
}
|
||||
};
|
||||
|
@ -1429,7 +1380,7 @@ int virtio_load(VirtIODevice *vdev, QEMUFile *f, int version_id)
|
|||
num = qemu_get_be32(f);
|
||||
|
||||
if (num > VIRTIO_QUEUE_MAX) {
|
||||
error_report("Invalid number of PCI queues: 0x%x", num);
|
||||
error_report("Invalid number of virtqueues: 0x%x", num);
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
|
|
@ -72,6 +72,7 @@ ram_addr_t qemu_ram_alloc_resizeable(ram_addr_t size, ram_addr_t max_size,
|
|||
void *host),
|
||||
MemoryRegion *mr, Error **errp);
|
||||
int qemu_get_ram_fd(ram_addr_t addr);
|
||||
void qemu_set_ram_fd(ram_addr_t addr, int fd);
|
||||
void *qemu_get_ram_block_host_ptr(ram_addr_t addr);
|
||||
void qemu_ram_free(ram_addr_t addr);
|
||||
|
||||
|
|
|
@ -16,6 +16,8 @@
|
|||
#define ACPI_BUILD_RSDP_FILE "etc/acpi/rsdp"
|
||||
#define ACPI_BUILD_TPMLOG_FILE "etc/tpm/log"
|
||||
|
||||
#define AML_NOTIFY_METHOD "NTFY"
|
||||
|
||||
typedef enum {
|
||||
AML_NO_OPCODE = 0,/* has only data */
|
||||
AML_OPCODE, /* has opcode optionally followed by data */
|
||||
|
@ -80,6 +82,7 @@ typedef enum {
|
|||
typedef enum {
|
||||
AML_SYSTEM_MEMORY = 0X00,
|
||||
AML_SYSTEM_IO = 0X01,
|
||||
AML_PCI_CONFIG = 0X02,
|
||||
} AmlRegionSpace;
|
||||
|
||||
typedef enum {
|
||||
|
|
|
@ -14,6 +14,7 @@
|
|||
|
||||
#include "hw/acpi/acpi.h"
|
||||
#include "hw/acpi/pc-hotplug.h"
|
||||
#include "hw/acpi/aml-build.h"
|
||||
|
||||
typedef struct AcpiCpuHotplug {
|
||||
MemoryRegion io;
|
||||
|
@ -25,4 +26,13 @@ void acpi_cpu_plug_cb(ACPIREGS *ar, qemu_irq irq,
|
|||
|
||||
void acpi_cpu_hotplug_init(MemoryRegion *parent, Object *owner,
|
||||
AcpiCpuHotplug *gpe_cpu, uint16_t base);
|
||||
|
||||
#define CPU_EJECT_METHOD "CPEJ"
|
||||
#define CPU_MAT_METHOD "CPMA"
|
||||
#define CPU_ON_BITMAP "CPON"
|
||||
#define CPU_STATUS_METHOD "CPST"
|
||||
#define CPU_STATUS_MAP "PRS"
|
||||
#define CPU_SCAN_METHOD "PRSC"
|
||||
|
||||
void build_cpu_hotplug_aml(Aml *ctx);
|
||||
#endif
|
||||
|
|
|
@ -4,6 +4,7 @@
|
|||
#include "hw/qdev-core.h"
|
||||
#include "hw/acpi/acpi.h"
|
||||
#include "migration/vmstate.h"
|
||||
#include "hw/acpi/aml-build.h"
|
||||
|
||||
/**
|
||||
* MemStatus:
|
||||
|
@ -45,4 +46,12 @@ extern const VMStateDescription vmstate_memory_hotplug;
|
|||
vmstate_memory_hotplug, MemHotplugState)
|
||||
|
||||
void acpi_memory_ospm_status(MemHotplugState *mem_st, ACPIOSTInfoList ***list);
|
||||
|
||||
#define MEMORY_HOTPLUG_DEVICE "MHPD"
|
||||
#define MEMORY_SLOT_SCAN_METHOD "MSCN"
|
||||
#define MEMORY_HOTPLUG_HANDLER_PATH "\\_SB.PCI0." \
|
||||
MEMORY_HOTPLUG_DEVICE "." MEMORY_SLOT_SCAN_METHOD
|
||||
|
||||
void build_memory_hotplug_aml(Aml *ctx, uint32_t nr_mem,
|
||||
uint16_t io_base, uint16_t io_len);
|
||||
#endif
|
||||
|
|
|
@ -32,28 +32,26 @@
|
|||
#define ACPI_MEMORY_HOTPLUG_IO_LEN 24
|
||||
#define ACPI_MEMORY_HOTPLUG_BASE 0x0a00
|
||||
|
||||
#define MEMORY_HOTPLUG_DEVICE MHPD
|
||||
#define MEMORY_SLOTS_NUMBER MDNR
|
||||
#define MEMORY_HOTPLUG_IO_REGION HPMR
|
||||
#define MEMORY_SLOT_ADDR_LOW MRBL
|
||||
#define MEMORY_SLOT_ADDR_HIGH MRBH
|
||||
#define MEMORY_SLOT_SIZE_LOW MRLL
|
||||
#define MEMORY_SLOT_SIZE_HIGH MRLH
|
||||
#define MEMORY_SLOT_PROXIMITY MPX
|
||||
#define MEMORY_SLOT_ENABLED MES
|
||||
#define MEMORY_SLOT_INSERT_EVENT MINS
|
||||
#define MEMORY_SLOT_REMOVE_EVENT MRMV
|
||||
#define MEMORY_SLOT_EJECT MEJ
|
||||
#define MEMORY_SLOT_SLECTOR MSEL
|
||||
#define MEMORY_SLOT_OST_EVENT MOEV
|
||||
#define MEMORY_SLOT_OST_STATUS MOSC
|
||||
#define MEMORY_SLOT_LOCK MLCK
|
||||
#define MEMORY_SLOT_STATUS_METHOD MRST
|
||||
#define MEMORY_SLOT_CRS_METHOD MCRS
|
||||
#define MEMORY_SLOT_OST_METHOD MOST
|
||||
#define MEMORY_SLOT_PROXIMITY_METHOD MPXM
|
||||
#define MEMORY_SLOT_EJECT_METHOD MEJ0
|
||||
#define MEMORY_SLOT_NOTIFY_METHOD MTFY
|
||||
#define MEMORY_SLOT_SCAN_METHOD MSCN
|
||||
#define MEMORY_SLOTS_NUMBER "MDNR"
|
||||
#define MEMORY_HOTPLUG_IO_REGION "HPMR"
|
||||
#define MEMORY_SLOT_ADDR_LOW "MRBL"
|
||||
#define MEMORY_SLOT_ADDR_HIGH "MRBH"
|
||||
#define MEMORY_SLOT_SIZE_LOW "MRLL"
|
||||
#define MEMORY_SLOT_SIZE_HIGH "MRLH"
|
||||
#define MEMORY_SLOT_PROXIMITY "MPX"
|
||||
#define MEMORY_SLOT_ENABLED "MES"
|
||||
#define MEMORY_SLOT_INSERT_EVENT "MINS"
|
||||
#define MEMORY_SLOT_REMOVE_EVENT "MRMV"
|
||||
#define MEMORY_SLOT_EJECT "MEJ"
|
||||
#define MEMORY_SLOT_SLECTOR "MSEL"
|
||||
#define MEMORY_SLOT_OST_EVENT "MOEV"
|
||||
#define MEMORY_SLOT_OST_STATUS "MOSC"
|
||||
#define MEMORY_SLOT_LOCK "MLCK"
|
||||
#define MEMORY_SLOT_STATUS_METHOD "MRST"
|
||||
#define MEMORY_SLOT_CRS_METHOD "MCRS"
|
||||
#define MEMORY_SLOT_OST_METHOD "MOST"
|
||||
#define MEMORY_SLOT_PROXIMITY_METHOD "MPXM"
|
||||
#define MEMORY_SLOT_EJECT_METHOD "MEJ0"
|
||||
#define MEMORY_SLOT_NOTIFY_METHOD "MTFY"
|
||||
|
||||
#endif
|
||||
|
|
|
@ -267,6 +267,8 @@ typedef void (*cpu_set_smm_t)(int smm, void *arg);
|
|||
|
||||
void ioapic_init_gsi(GSIState *gsi_state, const char *parent_name);
|
||||
|
||||
ISADevice *pc_find_fdc0(void);
|
||||
|
||||
/* acpi_piix.c */
|
||||
|
||||
I2CBus *piix4_pm_init(PCIBus *bus, int devfn, uint32_t smb_io_base,
|
||||
|
|
|
@ -16,6 +16,7 @@
|
|||
#include "qom/object.h"
|
||||
|
||||
#define HPET_BASE 0xfed00000
|
||||
#define HPET_LEN 0x400
|
||||
#define HPET_CLK_PERIOD 10 /* 10 ns*/
|
||||
|
||||
#define FS_PER_NS 1000000 /* 1000000 femtoseconds == 1 ns */
|
||||
|
|
|
@ -374,6 +374,19 @@ extern const VMStateInfo vmstate_info_bitmap;
|
|||
.offset = vmstate_offset_array(_state, _field, _type, _num),\
|
||||
}
|
||||
|
||||
/* a variable length array (i.e. _type *_field) but we know the
|
||||
* length
|
||||
*/
|
||||
#define VMSTATE_STRUCT_VARRAY_KNOWN(_field, _state, _num, _version, _vmsd, _type) { \
|
||||
.name = (stringify(_field)), \
|
||||
.num = (_num), \
|
||||
.version_id = (_version), \
|
||||
.vmsd = &(_vmsd), \
|
||||
.size = sizeof(_type), \
|
||||
.flags = VMS_STRUCT|VMS_ARRAY, \
|
||||
.offset = offsetof(_state, _field), \
|
||||
}
|
||||
|
||||
#define VMSTATE_STRUCT_VARRAY_UINT8(_field, _state, _field_num, _version, _vmsd, _type) { \
|
||||
.name = (stringify(_field)), \
|
||||
.num_offset = vmstate_offset_value(_state, _field_num, uint8_t), \
|
||||
|
|
|
@ -1,367 +0,0 @@
|
|||
#!/usr/bin/python
|
||||
# Copyright (C) 2011 Red Hat, Inc., Michael S. Tsirkin <mst@redhat.com>
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; either version 2 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License along
|
||||
# with this program; if not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
# Process mixed ASL/AML listing (.lst file) produced by iasl -l
|
||||
# Locate and execute ACPI_EXTRACT directives, output offset info
|
||||
#
|
||||
# Documentation of ACPI_EXTRACT_* directive tags:
|
||||
#
|
||||
# These directive tags output offset information from AML for BIOS runtime
|
||||
# table generation.
|
||||
# Each directive is of the form:
|
||||
# ACPI_EXTRACT_<TYPE> <array_name> <Operator> (...)
|
||||
# and causes the extractor to create an array
|
||||
# named <array_name> with offset, in the generated AML,
|
||||
# of an object of a given type in the following <Operator>.
|
||||
#
|
||||
# A directive must fit on a single code line.
|
||||
#
|
||||
# Object type in AML is verified, a mismatch causes a build failure.
|
||||
#
|
||||
# Directives and operators currently supported are:
|
||||
# ACPI_EXTRACT_NAME_DWORD_CONST - extract a Dword Const object from Name()
|
||||
# ACPI_EXTRACT_NAME_WORD_CONST - extract a Word Const object from Name()
|
||||
# ACPI_EXTRACT_NAME_BYTE_CONST - extract a Byte Const object from Name()
|
||||
# ACPI_EXTRACT_METHOD_STRING - extract a NameString from Method()
|
||||
# ACPI_EXTRACT_NAME_STRING - extract a NameString from Name()
|
||||
# ACPI_EXTRACT_PROCESSOR_START - start of Processor() block
|
||||
# ACPI_EXTRACT_PROCESSOR_STRING - extract a NameString from Processor()
|
||||
# ACPI_EXTRACT_PROCESSOR_END - offset at last byte of Processor() + 1
|
||||
# ACPI_EXTRACT_PKG_START - start of Package block
|
||||
#
|
||||
# ACPI_EXTRACT_ALL_CODE - create an array storing the generated AML bytecode
|
||||
#
|
||||
# ACPI_EXTRACT is not allowed anywhere else in code, except in comments.
|
||||
|
||||
import re;
|
||||
import sys;
|
||||
import fileinput;
|
||||
|
||||
aml = []
|
||||
asl = []
|
||||
output = {}
|
||||
debug = ""
|
||||
|
||||
class asl_line:
|
||||
line = None
|
||||
lineno = None
|
||||
aml_offset = None
|
||||
|
||||
def die(diag):
|
||||
sys.stderr.write("Error: %s; %s\n" % (diag, debug))
|
||||
sys.exit(1)
|
||||
|
||||
#Store an ASL command, matching AML offset, and input line (for debugging)
|
||||
def add_asl(lineno, line):
|
||||
l = asl_line()
|
||||
l.line = line
|
||||
l.lineno = lineno
|
||||
l.aml_offset = len(aml)
|
||||
asl.append(l)
|
||||
|
||||
#Store an AML byte sequence
|
||||
#Verify that offset output by iasl matches # of bytes so far
|
||||
def add_aml(offset, line):
|
||||
o = int(offset, 16);
|
||||
# Sanity check: offset must match size of code so far
|
||||
if (o != len(aml)):
|
||||
die("Offset 0x%x != 0x%x" % (o, len(aml)))
|
||||
# Strip any trailing dots and ASCII dump after "
|
||||
line = re.sub(r'\s*\.*\s*".*$',"", line)
|
||||
# Strip traling whitespace
|
||||
line = re.sub(r'\s+$',"", line)
|
||||
# Strip leading whitespace
|
||||
line = re.sub(r'^\s+',"", line)
|
||||
# Split on whitespace
|
||||
code = re.split(r'\s+', line)
|
||||
for c in code:
|
||||
# Require a legal hex number, two digits
|
||||
if (not(re.search(r'^[0-9A-Fa-f][0-9A-Fa-f]$', c))):
|
||||
die("Unexpected octet %s" % c);
|
||||
aml.append(int(c, 16));
|
||||
|
||||
# Process aml bytecode array, decoding AML
|
||||
def aml_pkglen_bytes(offset):
|
||||
# PkgLength can be multibyte. Bits 8-7 give the # of extra bytes.
|
||||
pkglenbytes = aml[offset] >> 6;
|
||||
return pkglenbytes + 1
|
||||
|
||||
def aml_pkglen(offset):
|
||||
pkgstart = offset
|
||||
pkglenbytes = aml_pkglen_bytes(offset)
|
||||
pkglen = aml[offset] & 0x3F
|
||||
# If multibyte, first nibble only uses bits 0-3
|
||||
if ((pkglenbytes > 1) and (pkglen & 0x30)):
|
||||
die("PkgLen bytes 0x%x but first nibble 0x%x expected 0x0X" %
|
||||
(pkglen, pkglen))
|
||||
offset += 1
|
||||
pkglenbytes -= 1
|
||||
for i in range(pkglenbytes):
|
||||
pkglen |= aml[offset + i] << (i * 8 + 4)
|
||||
if (len(aml) < pkgstart + pkglen):
|
||||
die("PckgLen 0x%x at offset 0x%x exceeds AML size 0x%x" %
|
||||
(pkglen, offset, len(aml)))
|
||||
return pkglen
|
||||
|
||||
# Given method offset, find its NameString offset
|
||||
def aml_method_string(offset):
|
||||
#0x14 MethodOp PkgLength NameString MethodFlags TermList
|
||||
if (aml[offset] != 0x14):
|
||||
die( "Method offset 0x%x: expected 0x14 actual 0x%x" %
|
||||
(offset, aml[offset]));
|
||||
offset += 1;
|
||||
pkglenbytes = aml_pkglen_bytes(offset)
|
||||
offset += pkglenbytes;
|
||||
return offset;
|
||||
|
||||
# Given name offset, find its NameString offset
|
||||
def aml_name_string(offset):
|
||||
#0x08 NameOp NameString DataRef
|
||||
if (aml[offset] != 0x08):
|
||||
die( "Name offset 0x%x: expected 0x08 actual 0x%x" %
|
||||
(offset, aml[offset]));
|
||||
offset += 1
|
||||
# Block Name Modifier. Skip it.
|
||||
if (aml[offset] == 0x5c or aml[offset] == 0x5e):
|
||||
offset += 1
|
||||
return offset;
|
||||
|
||||
# Given data offset, find variable length byte buffer offset
|
||||
def aml_data_buffer(offset, length):
|
||||
#0x11 PkgLength BufferSize ByteList
|
||||
if (length > 63):
|
||||
die( "Name offset 0x%x: expected a one byte PkgLength (length<=63)" %
|
||||
(offset));
|
||||
expect = [0x11, length+3, 0x0A, length]
|
||||
if (aml[offset:offset+4] != expect):
|
||||
die( "Name offset 0x%x: expected %s actual %s" %
|
||||
(offset, expect, aml[offset:offset+4]))
|
||||
return offset + len(expect)
|
||||
|
||||
# Given data offset, find dword const offset
|
||||
def aml_data_dword_const(offset):
|
||||
#0x08 NameOp NameString DataRef
|
||||
if (aml[offset] != 0x0C):
|
||||
die( "Name offset 0x%x: expected 0x0C actual 0x%x" %
|
||||
(offset, aml[offset]));
|
||||
return offset + 1;
|
||||
|
||||
# Given data offset, find word const offset
|
||||
def aml_data_word_const(offset):
|
||||
#0x08 NameOp NameString DataRef
|
||||
if (aml[offset] != 0x0B):
|
||||
die( "Name offset 0x%x: expected 0x0B actual 0x%x" %
|
||||
(offset, aml[offset]));
|
||||
return offset + 1;
|
||||
|
||||
# Given data offset, find byte const offset
|
||||
def aml_data_byte_const(offset):
|
||||
#0x08 NameOp NameString DataRef
|
||||
if (aml[offset] != 0x0A):
|
||||
die( "Name offset 0x%x: expected 0x0A actual 0x%x" %
|
||||
(offset, aml[offset]));
|
||||
return offset + 1;
|
||||
|
||||
# Find name'd buffer
|
||||
def aml_name_buffer(offset, length):
|
||||
return aml_data_buffer(aml_name_string(offset) + 4, length)
|
||||
|
||||
# Given name offset, find dword const offset
|
||||
def aml_name_dword_const(offset):
|
||||
return aml_data_dword_const(aml_name_string(offset) + 4)
|
||||
|
||||
# Given name offset, find word const offset
|
||||
def aml_name_word_const(offset):
|
||||
return aml_data_word_const(aml_name_string(offset) + 4)
|
||||
|
||||
# Given name offset, find byte const offset
|
||||
def aml_name_byte_const(offset):
|
||||
return aml_data_byte_const(aml_name_string(offset) + 4)
|
||||
|
||||
def aml_device_start(offset):
|
||||
#0x5B 0x82 DeviceOp PkgLength NameString
|
||||
if ((aml[offset] != 0x5B) or (aml[offset + 1] != 0x82)):
|
||||
die( "Name offset 0x%x: expected 0x5B 0x82 actual 0x%x 0x%x" %
|
||||
(offset, aml[offset], aml[offset + 1]));
|
||||
return offset
|
||||
|
||||
def aml_device_string(offset):
|
||||
#0x5B 0x82 DeviceOp PkgLength NameString
|
||||
start = aml_device_start(offset)
|
||||
offset += 2
|
||||
pkglenbytes = aml_pkglen_bytes(offset)
|
||||
offset += pkglenbytes
|
||||
return offset
|
||||
|
||||
def aml_device_end(offset):
|
||||
start = aml_device_start(offset)
|
||||
offset += 2
|
||||
pkglenbytes = aml_pkglen_bytes(offset)
|
||||
pkglen = aml_pkglen(offset)
|
||||
return offset + pkglen
|
||||
|
||||
def aml_processor_start(offset):
|
||||
#0x5B 0x83 ProcessorOp PkgLength NameString ProcID
|
||||
if ((aml[offset] != 0x5B) or (aml[offset + 1] != 0x83)):
|
||||
die( "Name offset 0x%x: expected 0x5B 0x83 actual 0x%x 0x%x" %
|
||||
(offset, aml[offset], aml[offset + 1]));
|
||||
return offset
|
||||
|
||||
def aml_processor_string(offset):
|
||||
#0x5B 0x83 ProcessorOp PkgLength NameString ProcID
|
||||
start = aml_processor_start(offset)
|
||||
offset += 2
|
||||
pkglenbytes = aml_pkglen_bytes(offset)
|
||||
offset += pkglenbytes
|
||||
return offset
|
||||
|
||||
def aml_processor_end(offset):
|
||||
start = aml_processor_start(offset)
|
||||
offset += 2
|
||||
pkglenbytes = aml_pkglen_bytes(offset)
|
||||
pkglen = aml_pkglen(offset)
|
||||
return offset + pkglen
|
||||
|
||||
def aml_package_start(offset):
|
||||
offset = aml_name_string(offset) + 4
|
||||
# 0x12 PkgLength NumElements PackageElementList
|
||||
if (aml[offset] != 0x12):
|
||||
die( "Name offset 0x%x: expected 0x12 actual 0x%x" %
|
||||
(offset, aml[offset]));
|
||||
offset += 1
|
||||
return offset + aml_pkglen_bytes(offset) + 1
|
||||
|
||||
lineno = 0
|
||||
for line in fileinput.input():
|
||||
# Strip trailing newline
|
||||
line = line.rstrip();
|
||||
# line number and debug string to output in case of errors
|
||||
lineno = lineno + 1
|
||||
debug = "input line %d: %s" % (lineno, line)
|
||||
#ASL listing: space, then line#, then ...., then code
|
||||
pasl = re.compile('^\s+([0-9]+)(:\s\s|\.\.\.\.)\s*')
|
||||
m = pasl.search(line)
|
||||
if (m):
|
||||
add_asl(lineno, pasl.sub("", line));
|
||||
# AML listing: offset in hex, then ...., then code
|
||||
paml = re.compile('^([0-9A-Fa-f]+)(:\s\s|\.\.\.\.)\s*')
|
||||
m = paml.search(line)
|
||||
if (m):
|
||||
add_aml(m.group(1), paml.sub("", line))
|
||||
|
||||
# Now go over code
|
||||
# Track AML offset of a previous non-empty ASL command
|
||||
prev_aml_offset = -1
|
||||
for i in range(len(asl)):
|
||||
debug = "input line %d: %s" % (asl[i].lineno, asl[i].line)
|
||||
|
||||
l = asl[i].line
|
||||
|
||||
# skip if not an extract directive
|
||||
a = len(re.findall(r'ACPI_EXTRACT', l))
|
||||
if (not a):
|
||||
# If not empty, store AML offset. Will be used for sanity checks
|
||||
# IASL seems to put {}. at random places in the listing.
|
||||
# Ignore any non-words for the purpose of this test.
|
||||
m = re.search(r'\w+', l)
|
||||
if (m):
|
||||
prev_aml_offset = asl[i].aml_offset
|
||||
continue
|
||||
|
||||
if (a > 1):
|
||||
die("Expected at most one ACPI_EXTRACT per line, actual %d" % a)
|
||||
|
||||
mext = re.search(r'''
|
||||
^\s* # leading whitespace
|
||||
/\*\s* # start C comment
|
||||
(ACPI_EXTRACT_\w+) # directive: group(1)
|
||||
\s+ # whitspace separates directive from array name
|
||||
(\w+) # array name: group(2)
|
||||
\s*\*/ # end of C comment
|
||||
\s*$ # trailing whitespace
|
||||
''', l, re.VERBOSE)
|
||||
if (not mext):
|
||||
die("Stray ACPI_EXTRACT in input")
|
||||
|
||||
# previous command must have produced some AML,
|
||||
# otherwise we are in a middle of a block
|
||||
if (prev_aml_offset == asl[i].aml_offset):
|
||||
die("ACPI_EXTRACT directive in the middle of a block")
|
||||
|
||||
directive = mext.group(1)
|
||||
array = mext.group(2)
|
||||
offset = asl[i].aml_offset
|
||||
|
||||
if (directive == "ACPI_EXTRACT_ALL_CODE"):
|
||||
if array in output:
|
||||
die("%s directive used more than once" % directive)
|
||||
output[array] = aml
|
||||
continue
|
||||
if (directive == "ACPI_EXTRACT_NAME_BUFFER8"):
|
||||
offset = aml_name_buffer(offset, 8)
|
||||
elif (directive == "ACPI_EXTRACT_NAME_BUFFER16"):
|
||||
offset = aml_name_buffer(offset, 16)
|
||||
elif (directive == "ACPI_EXTRACT_NAME_DWORD_CONST"):
|
||||
offset = aml_name_dword_const(offset)
|
||||
elif (directive == "ACPI_EXTRACT_NAME_WORD_CONST"):
|
||||
offset = aml_name_word_const(offset)
|
||||
elif (directive == "ACPI_EXTRACT_NAME_BYTE_CONST"):
|
||||
offset = aml_name_byte_const(offset)
|
||||
elif (directive == "ACPI_EXTRACT_NAME_STRING"):
|
||||
offset = aml_name_string(offset)
|
||||
elif (directive == "ACPI_EXTRACT_METHOD_STRING"):
|
||||
offset = aml_method_string(offset)
|
||||
elif (directive == "ACPI_EXTRACT_DEVICE_START"):
|
||||
offset = aml_device_start(offset)
|
||||
elif (directive == "ACPI_EXTRACT_DEVICE_STRING"):
|
||||
offset = aml_device_string(offset)
|
||||
elif (directive == "ACPI_EXTRACT_DEVICE_END"):
|
||||
offset = aml_device_end(offset)
|
||||
elif (directive == "ACPI_EXTRACT_PROCESSOR_START"):
|
||||
offset = aml_processor_start(offset)
|
||||
elif (directive == "ACPI_EXTRACT_PROCESSOR_STRING"):
|
||||
offset = aml_processor_string(offset)
|
||||
elif (directive == "ACPI_EXTRACT_PROCESSOR_END"):
|
||||
offset = aml_processor_end(offset)
|
||||
elif (directive == "ACPI_EXTRACT_PKG_START"):
|
||||
offset = aml_package_start(offset)
|
||||
else:
|
||||
die("Unsupported directive %s" % directive)
|
||||
|
||||
if array not in output:
|
||||
output[array] = []
|
||||
output[array].append(offset)
|
||||
|
||||
debug = "at end of file"
|
||||
|
||||
def get_value_type(maxvalue):
|
||||
#Use type large enough to fit the table
|
||||
if (maxvalue >= 0x10000):
|
||||
return "int"
|
||||
elif (maxvalue >= 0x100):
|
||||
return "short"
|
||||
else:
|
||||
return "char"
|
||||
|
||||
# Pretty print output
|
||||
for array in output.keys():
|
||||
otype = get_value_type(max(output[array]))
|
||||
odata = []
|
||||
for value in output[array]:
|
||||
odata.append("0x%x" % value)
|
||||
sys.stdout.write("static unsigned %s %s[] = {\n" % (otype, array))
|
||||
sys.stdout.write(",\n".join(odata))
|
||||
sys.stdout.write('\n};\n');
|
|
@ -1,51 +0,0 @@
|
|||
#!/usr/bin/python
|
||||
# Copyright (C) 2011 Red Hat, Inc., Michael S. Tsirkin <mst@redhat.com>
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; either version 2 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License along
|
||||
# with this program; if not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
# Read a preprocessed ASL listing and put each ACPI_EXTRACT
|
||||
# directive in a comment, to make iasl skip it.
|
||||
# We also put each directive on a new line, the machinery
|
||||
# in tools/acpi_extract.py requires this.
|
||||
|
||||
import re;
|
||||
import sys;
|
||||
import fileinput;
|
||||
|
||||
def die(diag):
|
||||
sys.stderr.write("Error: %s\n" % (diag))
|
||||
sys.exit(1)
|
||||
|
||||
# Note: () around pattern make split return matched string as part of list
|
||||
psplit = re.compile(r''' (
|
||||
\b # At word boundary
|
||||
ACPI_EXTRACT_\w+ # directive
|
||||
\s+ # some whitespace
|
||||
\w+ # array name
|
||||
)''', re.VERBOSE);
|
||||
|
||||
lineno = 0
|
||||
for line in fileinput.input():
|
||||
# line number and debug string to output in case of errors
|
||||
lineno = lineno + 1
|
||||
debug = "input line %d: %s" % (lineno, line.rstrip())
|
||||
|
||||
s = psplit.split(line);
|
||||
# The way split works, each odd item is the matching ACPI_EXTRACT directive.
|
||||
# Put each in a comment, and on a line by itself.
|
||||
for i in range(len(s)):
|
||||
if (i % 2):
|
||||
sys.stdout.write("\n/* %s */\n" % s[i])
|
||||
else:
|
||||
sys.stdout.write(s[i])
|
|
@ -1,4 +0,0 @@
|
|||
cd x86_64-softmmu
|
||||
for file in hw/i386/*.hex; do
|
||||
cp -f $file ../$file.generated
|
||||
done
|
|
@ -580,6 +580,22 @@ static void test_acpi_asl(test_data *data)
|
|||
(gchar *)&signature,
|
||||
sdt->asl_file, sdt->aml_file,
|
||||
exp_sdt->asl_file, exp_sdt->aml_file);
|
||||
if (getenv("V")) {
|
||||
const char *diff_cmd = getenv("DIFF");
|
||||
if (diff_cmd) {
|
||||
int ret G_GNUC_UNUSED;
|
||||
char *diff = g_strdup_printf("%s %s %s", diff_cmd,
|
||||
exp_sdt->asl_file, sdt->asl_file);
|
||||
ret = system(diff) ;
|
||||
g_free(diff);
|
||||
} else {
|
||||
fprintf(stderr, "acpi-test: Warning. not showing "
|
||||
"difference since no diff utility is specified. "
|
||||
"Set 'DIFF' environment variable to a preferred "
|
||||
"diff utility and run 'make V=1 check' again to "
|
||||
"see ASL difference.");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
g_string_free(asl, true);
|
||||
|
|
Loading…
Reference in New Issue