From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from mailman by lists.gnu.org with tmda-scanned (Exim 4.43) id 1M25JC-0002lN-8j for qemu-devel@nongnu.org; Thu, 07 May 2009 11:14:50 -0400 Received: from exim by lists.gnu.org with spam-scanned (Exim 4.43) id 1M25J7-0002k6-KH for qemu-devel@nongnu.org; Thu, 07 May 2009 11:14:49 -0400 Received: from [199.232.76.173] (port=33752 helo=monty-python.gnu.org) by lists.gnu.org with esmtp (Exim 4.43) id 1M25J7-0002k3-H0 for qemu-devel@nongnu.org; Thu, 07 May 2009 11:14:45 -0400 Received: from e1.ny.us.ibm.com ([32.97.182.141]:32830) by monty-python.gnu.org with esmtps (TLS-1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.60) (envelope-from ) id 1M25J7-0000fA-7P for qemu-devel@nongnu.org; Thu, 07 May 2009 11:14:45 -0400 Received: from d01relay02.pok.ibm.com (d01relay02.pok.ibm.com [9.56.227.234]) by e1.ny.us.ibm.com (8.13.1/8.13.1) with ESMTP id n47FB05f024534 for ; Thu, 7 May 2009 11:11:00 -0400 Received: from d01av01.pok.ibm.com (d01av01.pok.ibm.com [9.56.224.215]) by d01relay02.pok.ibm.com (8.13.8/8.13.8/NCO v9.2) with ESMTP id n47FEeow140742 for ; Thu, 7 May 2009 11:14:40 -0400 Received: from d01av01.pok.ibm.com (loopback [127.0.0.1]) by d01av01.pok.ibm.com (8.12.11.20060308/8.13.3) with ESMTP id n47FEdWC026517 for ; Thu, 7 May 2009 11:14:40 -0400 From: Beth Kon Date: Thu, 7 May 2009 11:14:58 -0400 Message-Id: <1241709298-12958-1-git-send-email-eak@us.ibm.com> Subject: [Qemu-devel] [PATCH] Fix ACPI Table Collision List-Id: qemu-devel.nongnu.org List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , To: qemu-devel@nongnu.org Cc: Beth Kon , gleb@redhat.com Signed-off-by: Beth Kon A potential collision exists in the current rombios32.c between 2 ACPI table entries: rsdt->table_offset_entry[i+4] = cpu_to_le32(addr); (when i == 0) and rsdt->table_offset_entry[4] = cpu_to_le32(srat_addr); This patch corrects the problem. I have built this and very primitively tested that -numa doesn't make anything explode, but have not tested additional acpi tables. I'm hope others who have been playing with this stuff would be more readily able to confirm that nothing breaks. One thing I don't understand is why the line acpi_additional_tables(); /* resets cfg to required entry */ is needed. So maybe I'm missing some subtlety here. If someone could explain I'd appreciate it. diff --git a/bios/rombios32.c b/bios/rombios32.c index d8f6d4e..72f5e4c 100644 --- a/bios/rombios32.c +++ b/bios/rombios32.c @@ -47,6 +47,12 @@ typedef unsigned long long uint64_t; #define wbinvd() asm volatile("wbinvd") +#ifdef BX_QEMU +#define BASE_ACPI_TABLES 4 +#else +#define BASE_ACPI_TABLES 3 +#endif + #define CPUID_MSR (1 << 5) #define CPUID_APIC (1 << 9) #define CPUID_MTRR (1 << 12) @@ -1294,12 +1300,9 @@ struct rsdp_descriptor /* Root System Descriptor Pointer */ struct rsdt_descriptor_rev1 { ACPI_TABLE_HEADER_DEF /* ACPI common table header */ -#ifdef BX_QEMU - uint32_t table_offset_entry [5]; /* Array of pointers to other */ -#else - uint32_t table_offset_entry [3]; /* Array of pointers to other */ -#endif - /* ACPI tables */ + uint32_t table_offset_entry [BASE_ACPI_TABLES]; /* Array of pointers + * to other ACPI + * tables*/ } __attribute__((__packed__)); /* @@ -1666,8 +1669,14 @@ void acpi_bios_init(void) #ifdef BX_QEMU external_tables = acpi_additional_tables(); + qemu_cfg_select(QEMU_CFG_NUMA); + nb_numa_nodes = qemu_cfg_get64(); + if (nb_numa_nodes > 0) { + external_tables++; + } #else external_tables = 0; + nb_numa_nodes = 0; #endif addr = base_addr = ram_size - ACPI_DATA_SIZE; @@ -1693,12 +1702,6 @@ void acpi_bios_init(void) ssdt_addr = addr; ssdt = (void *)(addr); addr += acpi_build_processor_ssdt(ssdt); -#ifdef BX_QEMU - qemu_cfg_select(QEMU_CFG_NUMA); - nb_numa_nodes = qemu_cfg_get64(); -#else - nb_numa_nodes = 0; -#endif if (nb_numa_nodes > 0) { addr = (addr + 7) & ~7; srat_addr = addr; @@ -1897,9 +1900,13 @@ void acpi_bios_init(void) acpi_additional_tables(); /* resets cfg to required entry */ for(i = 0; i < external_tables; i++) { uint16_t len; + if (i == 0 && nb_numa_nodes > 0) { + rsdt->table_offset_entry[BASE_ACPI_TABLES] = cpu_to_le32(srat_addr); + continue; + } if(acpi_load_table(i, addr, &len) < 0) BX_PANIC("Failed to load ACPI table from QEMU\n"); - rsdt->table_offset_entry[i+4] = cpu_to_le32(addr); + rsdt->table_offset_entry[i + BASE_ACPI_TABLES] = cpu_to_le32(addr); addr += len; if(addr >= ram_size) BX_PANIC("ACPI table overflow\n"); @@ -1912,11 +1919,9 @@ void acpi_bios_init(void) rsdt->table_offset_entry[2] = cpu_to_le32(ssdt_addr); #ifdef BX_QEMU rsdt->table_offset_entry[3] = cpu_to_le32(hpet_addr); - if (nb_numa_nodes > 0) - rsdt->table_offset_entry[4] = cpu_to_le32(srat_addr); #endif acpi_build_table_header((struct acpi_table_header *)rsdt, "RSDT", - rsdt_size - (nb_numa_nodes > 0? 0: sizeof(uint32_t)), 1); + rsdt_size, 1); acpi_tables_size = addr - base_addr;