debuggers.hg
changeset 6990:739154e26fb7
Dynamically generate the local apic entries in ACPI MADT table.
The number of local apic entries is decided by the #vcpus passed
from the config file (eg./etc/xen/xmexample.vmx).
This feature is required by the SMP VMX domain.
Signed-off-by: Ke Yu <ke.yu@intel.com>
Signed-off-by: Xin Li <xin.b.li@intel.com>
Signed-off-by: Asit Mallick <asit.k.mallick@intel.com>
The number of local apic entries is decided by the #vcpus passed
from the config file (eg./etc/xen/xmexample.vmx).
This feature is required by the SMP VMX domain.
Signed-off-by: Ke Yu <ke.yu@intel.com>
Signed-off-by: Xin Li <xin.b.li@intel.com>
Signed-off-by: Asit Mallick <asit.k.mallick@intel.com>
author | kaf24@firebug.cl.cam.ac.uk |
---|---|
date | Tue Sep 20 09:02:43 2005 +0000 (2005-09-20) |
parents | d1cbfaf804d9 |
children | 3ef86b208f9b |
files | tools/firmware/acpi/acpi_madt.c tools/firmware/acpi/acpi_madt.h tools/firmware/vmxassist/Makefile tools/firmware/vmxassist/acpi_madt.c tools/firmware/vmxassist/vmxloader.c tools/libxc/xc_vmx_build.c |
line diff
1.1 --- a/tools/firmware/acpi/acpi_madt.c Mon Sep 19 17:10:20 2005 +0000 1.2 +++ b/tools/firmware/acpi/acpi_madt.c Tue Sep 20 09:02:43 2005 +0000 1.3 @@ -37,44 +37,7 @@ ACPI_MULTIPLE_APIC_DESCRIPTION_TABLE Mad 1.4 ACPI_LOCAL_APIC_ADDRESS, 1.5 ACPI_MULTIPLE_APIC_FLAGS, 1.6 }, 1.7 - // 1.8 - // LOCAL APIC Entries for 4 processors. 1.9 - // 1.10 - { 1.11 - { 1.12 - ACPI_PROCESSOR_LOCAL_APIC, 1.13 - sizeof (ACPI_LOCAL_APIC_STRUCTURE), 1.14 - 0x00, 1.15 - 0x00, 1.16 - 0x00000001, 1.17 - }, 1.18 - 1.19 - { 1.20 - ACPI_PROCESSOR_LOCAL_APIC, 1.21 - sizeof (ACPI_LOCAL_APIC_STRUCTURE), 1.22 - 0x01, 1.23 - 0x00, 1.24 - 0x00000000 1.25 - }, 1.26 - 1.27 - { 1.28 - ACPI_PROCESSOR_LOCAL_APIC, 1.29 - sizeof (ACPI_LOCAL_APIC_STRUCTURE), 1.30 - 0x02, 1.31 - 0x00, 1.32 - 0x00000000 1.33 - }, 1.34 - 1.35 - { 1.36 - ACPI_PROCESSOR_LOCAL_APIC, 1.37 - sizeof (ACPI_LOCAL_APIC_STRUCTURE), 1.38 - 0x03, 1.39 - 0x00, 1.40 - 0x00000000 1.41 - } 1.42 - } 1.43 - , 1.44 - 1.45 + 1.46 // 1.47 // IO APIC 1.48 // 1.49 @@ -87,5 +50,19 @@ ACPI_MULTIPLE_APIC_DESCRIPTION_TABLE Mad 1.50 ACPI_IO_APIC_ADDRESS_1, 1.51 0x0000 1.52 } 1.53 + }, 1.54 + 1.55 + // 1.56 + // LOCAL APIC Entries for up to 32 processors. 1.57 + // 1.58 + { 1.59 + { 1.60 + ACPI_PROCESSOR_LOCAL_APIC, 1.61 + sizeof (ACPI_LOCAL_APIC_STRUCTURE), 1.62 + 0x00, 1.63 + 0x00, 1.64 + 0x00000001, 1.65 + } 1.66 + 1.67 } 1.68 };
2.1 --- a/tools/firmware/acpi/acpi_madt.h Mon Sep 19 17:10:20 2005 +0000 2.2 +++ b/tools/firmware/acpi/acpi_madt.h Tue Sep 20 09:02:43 2005 +0000 2.3 @@ -35,9 +35,9 @@ 2.4 // 2.5 #pragma pack (1) 2.6 typedef struct { 2.7 - ACPI_2_0_MADT Header; 2.8 - ACPI_LOCAL_APIC_STRUCTURE LocalApic[4]; 2.9 - ACPI_IO_APIC_STRUCTURE IoApic[1]; 2.10 + ACPI_2_0_MADT Header; 2.11 + ACPI_IO_APIC_STRUCTURE IoApic[1]; 2.12 + ACPI_LOCAL_APIC_STRUCTURE LocalApic[32]; 2.13 } ACPI_MULTIPLE_APIC_DESCRIPTION_TABLE; 2.14 #pragma pack () 2.15
3.1 --- a/tools/firmware/vmxassist/Makefile Mon Sep 19 17:10:20 2005 +0000 3.2 +++ b/tools/firmware/vmxassist/Makefile Tue Sep 20 09:02:43 2005 +0000 3.3 @@ -41,9 +41,9 @@ OBJECTS = head.o trap.o vm86.o setup.o u 3.4 3.5 all: vmxloader 3.6 3.7 -vmxloader: roms.h vmxloader.c acpi.h 3.8 - ${CC} ${CFLAGS} ${DEFINES} -c vmxloader.c 3.9 - $(CC) -o vmxloader.tmp -m32 -nostdlib -Wl,-N -Wl,-Ttext -Wl,0x100000 vmxloader.o 3.10 +vmxloader: roms.h vmxloader.c acpi.h acpi_madt.c 3.11 + ${CC} ${CFLAGS} ${DEFINES} -c vmxloader.c -c acpi_madt.c 3.12 + $(CC) -o vmxloader.tmp -m32 -nostdlib -Wl,-N -Wl,-Ttext -Wl,0x100000 vmxloader.o acpi_madt.o 3.13 objcopy --change-addresses=0xC0000000 vmxloader.tmp vmxloader 3.14 rm -f vmxloader.tmp 3.15
4.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 4.2 +++ b/tools/firmware/vmxassist/acpi_madt.c Tue Sep 20 09:02:43 2005 +0000 4.3 @@ -0,0 +1,145 @@ 4.4 +/* 4.5 + * acpi_madt.c: Update ACPI MADT table for multiple processor guest. 4.6 + * 4.7 + * Yu Ke, ke.yu@intel.com 4.8 + * Copyright (c) 2005, Intel Corporation. 4.9 + * 4.10 + * This program is free software; you can redistribute it and/or modify it 4.11 + * under the terms and conditions of the GNU General Public License, 4.12 + * version 2, as published by the Free Software Foundation. 4.13 + * 4.14 + * This program is distributed in the hope it will be useful, but WITHOUT 4.15 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 4.16 + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for 4.17 + * more details. 4.18 + * 4.19 + * You should have received a copy of the GNU General Public License along with 4.20 + * this program; if not, write to the Free Software Foundation, Inc., 59 Temple 4.21 + * Place - Suite 330, Boston, MA 02111-1307 USA. 4.22 + */ 4.23 +#include "../acpi/acpi2_0.h" 4.24 +#include "../acpi/acpi_madt.h" 4.25 + 4.26 +#define NULL ((void*)0) 4.27 + 4.28 +extern int puts(const char *s); 4.29 + 4.30 +#define VCPU_MAGIC 0x76637075 /* "vcpu" */ 4.31 + 4.32 +/* xc_vmx_builder wrote vcpu block at 0x9F800. Return it. */ 4.33 +static int 4.34 +get_vcpus(void) 4.35 +{ 4.36 + unsigned long *vcpus; 4.37 + 4.38 + vcpus = (unsigned long *)0x9F800; 4.39 + if (vcpus[0] != VCPU_MAGIC) { 4.40 + puts("Bad vcpus magic, set vcpu number=1\n"); 4.41 + return 1; 4.42 + } 4.43 + 4.44 + return vcpus[1]; 4.45 +} 4.46 + 4.47 +static void * 4.48 +acpi_madt_get_madt(unsigned char *acpi_start) 4.49 +{ 4.50 + ACPI_2_0_RSDP *rsdp=NULL; 4.51 + ACPI_2_0_RSDT *rsdt=NULL; 4.52 + ACPI_MULTIPLE_APIC_DESCRIPTION_TABLE *madt; 4.53 + 4.54 + rsdp = (ACPI_2_0_RSDP *)(acpi_start + sizeof(ACPI_2_0_FACS)); 4.55 + if (rsdp->Signature != ACPI_2_0_RSDP_SIGNATURE) { 4.56 + puts("Bad RSDP signature\n"); 4.57 + return NULL; 4.58 + } 4.59 + 4.60 + rsdt= (ACPI_2_0_RSDT *) 4.61 + (acpi_start + rsdp->RsdtAddress - ACPI_PHYSICAL_ADDRESS); 4.62 + if (rsdt->Header.Signature != ACPI_2_0_RSDT_SIGNATURE) { 4.63 + puts("Bad RSDT signature\n"); 4.64 + return NULL; 4.65 + } 4.66 + 4.67 + madt = (ACPI_MULTIPLE_APIC_DESCRIPTION_TABLE *) 4.68 + ( acpi_start+ rsdt->Entry[1] - ACPI_PHYSICAL_ADDRESS); 4.69 + if (madt->Header.Header.Signature != 4.70 + ACPI_MULTIPLE_APIC_DESCRIPTION_TABLE_SIGNATURE) { 4.71 + puts("Bad MADT signature \n"); 4.72 + return NULL; 4.73 + } 4.74 + 4.75 + return madt; 4.76 +} 4.77 + 4.78 +static void 4.79 +set_checksum(void *start, int checksum_offset, int len) 4.80 +{ 4.81 + unsigned char sum = 0; 4.82 + unsigned char *ptr; 4.83 + 4.84 + ptr = start; 4.85 + ptr[checksum_offset] = 0; 4.86 + while (len--) 4.87 + sum += *ptr++; 4.88 + 4.89 + ptr = start; 4.90 + ptr[checksum_offset] = -sum; 4.91 +} 4.92 + 4.93 +static int 4.94 +acpi_madt_set_local_apics( 4.95 + int nr_vcpu, 4.96 + ACPI_MULTIPLE_APIC_DESCRIPTION_TABLE *madt) 4.97 +{ 4.98 + int i; 4.99 + 4.100 + if ((nr_vcpu > MAX_VIRT_CPUS) || (nr_vcpu < 0) || !madt) 4.101 + return -1; 4.102 + 4.103 + for (i = 0; i < nr_vcpu; i++) { 4.104 + madt->LocalApic[i].Type = ACPI_PROCESSOR_LOCAL_APIC; 4.105 + madt->LocalApic[i].Length = sizeof (ACPI_LOCAL_APIC_STRUCTURE); 4.106 + madt->LocalApic[i].AcpiProcessorId = i; 4.107 + madt->LocalApic[i].ApicId = i; 4.108 + madt->LocalApic[i].Flags = 1; 4.109 + } 4.110 + 4.111 + madt->Header.Header.Length = 4.112 + sizeof(ACPI_MULTIPLE_APIC_DESCRIPTION_TABLE) - 4.113 + (MAX_VIRT_CPUS - nr_vcpu)* sizeof(ACPI_LOCAL_APIC_STRUCTURE); 4.114 + 4.115 + return 0; 4.116 +} 4.117 + 4.118 +#define FIELD_OFFSET(TYPE,Field) ((unsigned int)(&(((TYPE *) 0)->Field))) 4.119 + 4.120 +int acpi_madt_update(unsigned char *acpi_start) 4.121 +{ 4.122 + int rc; 4.123 + ACPI_MULTIPLE_APIC_DESCRIPTION_TABLE *madt; 4.124 + 4.125 + madt = acpi_madt_get_madt(acpi_start); 4.126 + if (!madt) 4.127 + return -1; 4.128 + 4.129 + rc = acpi_madt_set_local_apics(get_vcpus(), madt); 4.130 + if (rc != 0) 4.131 + return rc; 4.132 + 4.133 + set_checksum( 4.134 + madt, FIELD_OFFSET(ACPI_TABLE_HEADER, Checksum), 4.135 + madt->Header.Header.Length); 4.136 + 4.137 + return 0; 4.138 +} 4.139 + 4.140 +/* 4.141 + * Local variables: 4.142 + * c-file-style: "linux" 4.143 + * indent-tabs-mode: t 4.144 + * c-indent-level: 8 4.145 + * c-basic-offset: 8 4.146 + * tab-width: 8 4.147 + * End: 4.148 + */
5.1 --- a/tools/firmware/vmxassist/vmxloader.c Mon Sep 19 17:10:20 2005 +0000 5.2 +++ b/tools/firmware/vmxassist/vmxloader.c Tue Sep 20 09:02:43 2005 +0000 5.3 @@ -27,6 +27,7 @@ 5.4 #ifdef _ACPI_ 5.5 #include "acpi.h" 5.6 #include "../acpi/acpi2_0.h" // for ACPI_PHYSICAL_ADDRESS 5.7 +int acpi_madt_update(unsigned char* acpi_start); 5.8 #endif 5.9 5.10 5.11 @@ -110,7 +111,10 @@ main() 5.12 } 5.13 #ifdef _ACPI_ 5.14 puts("Loading ACPI ...\n"); 5.15 - if (ACPI_PHYSICAL_ADDRESS+sizeof(acpi) <= 0xF0000 ){ 5.16 + 5.17 + acpi_madt_update(acpi); 5.18 + 5.19 + if (ACPI_PHYSICAL_ADDRESS+sizeof(acpi) <= 0xF0000) { 5.20 /* make sure acpi table does not overlap rombios 5.21 * currently acpi less than 8K will be OK. 5.22 */
6.1 --- a/tools/libxc/xc_vmx_build.c Mon Sep 19 17:10:20 2005 +0000 6.2 +++ b/tools/libxc/xc_vmx_build.c Tue Sep 20 09:02:43 2005 +0000 6.3 @@ -107,6 +107,33 @@ static void build_e820map(struct mem_map 6.4 mem_mapp->nr_map = nr_map; 6.5 } 6.6 6.7 +/* 6.8 + * Use E820 reserved memory 0x9F800 to pass number of vcpus to vmxloader 6.9 + * vmxloader will use it to config ACPI MADT table 6.10 + */ 6.11 +#define VCPU_MAGIC 0x76637075 /* "vcpu" */ 6.12 +static int 6.13 +set_nr_vcpus(int xc_handle, u32 dom, unsigned long *pfn_list, 6.14 + struct domain_setup_info *dsi, unsigned long vcpus) 6.15 +{ 6.16 + char *va_map; 6.17 + unsigned long *va_vcpus; 6.18 + 6.19 + va_map = xc_map_foreign_range( 6.20 + xc_handle, dom, PAGE_SIZE, PROT_READ|PROT_WRITE, 6.21 + pfn_list[(0x9F000 - dsi->v_start) >> PAGE_SHIFT]); 6.22 + if ( va_map == NULL ) 6.23 + return -1; 6.24 + 6.25 + va_vcpus = (unsigned long *)(va_map + 0x800); 6.26 + *va_vcpus++ = VCPU_MAGIC; 6.27 + *va_vcpus++ = vcpus; 6.28 + 6.29 + munmap(va_map, PAGE_SIZE); 6.30 + 6.31 + return 0; 6.32 +} 6.33 + 6.34 #ifdef __i386__ 6.35 static int zap_mmio_range(int xc_handle, u32 dom, 6.36 l2_pgentry_32_t *vl2tab, 6.37 @@ -496,7 +523,8 @@ static int setup_guest(int xc_handle, 6.38 MMU_MACHPHYS_UPDATE, count) ) 6.39 goto error_out; 6.40 } 6.41 - 6.42 + 6.43 + set_nr_vcpus(xc_handle, dom, page_array, &dsi, vcpus); 6.44 6.45 if ((boot_paramsp = xc_map_foreign_range( 6.46 xc_handle, dom, PAGE_SIZE, PROT_READ|PROT_WRITE,