diff --git a/src/mainboard/emulation/qemu-x86/Kconfig b/src/mainboard/emulation/qemu-x86/Kconfig index bf21acd5c2..f8167941fd 100644 --- a/src/mainboard/emulation/qemu-x86/Kconfig +++ b/src/mainboard/emulation/qemu-x86/Kconfig @@ -3,6 +3,7 @@ if BOARD_EMULATION_QEMU_X86 config BOARD_SPECIFIC_OPTIONS # dummy def_bool y select ARCH_X86 + select CPU_QEMU_X86 select SOUTHBRIDGE_INTEL_I82371EB select CACHE_AS_RAM select HAVE_OPTION_TABLE diff --git a/src/mainboard/emulation/qemu-x86/devicetree.cb b/src/mainboard/emulation/qemu-x86/devicetree.cb index 11b2a41977..f37454be09 100644 --- a/src/mainboard/emulation/qemu-x86/devicetree.cb +++ b/src/mainboard/emulation/qemu-x86/devicetree.cb @@ -1,4 +1,9 @@ chip mainboard/emulation/qemu-x86 + device cpu_cluster 0 on + chip cpu/qemu-x86 + device lapic 0 on end + end + end device domain 0 on device pci 0.0 on end # northbridge (i440fx) chip southbridge/intel/i82371eb # southbridge diff --git a/src/mainboard/emulation/qemu-x86/northbridge.c b/src/mainboard/emulation/qemu-x86/northbridge.c index d785bebbc4..992a39e673 100644 --- a/src/mainboard/emulation/qemu-x86/northbridge.c +++ b/src/mainboard/emulation/qemu-x86/northbridge.c @@ -1,4 +1,5 @@ #include +#include #include #include #include @@ -11,6 +12,8 @@ #include #include +#include "fw_cfg.h" + #include "memory.c" static void cpu_pci_domain_set_resources(device_t dev) @@ -130,6 +133,46 @@ static struct device_operations pci_domain_ops = { #endif }; +static void cpu_bus_init(device_t dev) +{ + initialize_cpus(dev->link_list); +} + +static unsigned int cpu_bus_scan(device_t bus, unsigned int max) +{ + int max_cpus = fw_cfg_max_cpus(); + device_t cpu; + int i; + + if (max_cpus < 0) + return 0; + + /* + * TODO: This only handles the simple "qemu -smp $nr" case + * correctly. qemu also allows to specify the number of + * cores, threads & sockets. + */ + printk(BIOS_INFO, "QEMU: max_cpus is %d\n", max_cpus); + for (i = 0; i < max_cpus; i++) { + cpu = add_cpu_device(bus->link_list, i, 1); + if (cpu) + set_cpu_topology(cpu, 1, 0, i, 0); + } + return max_cpus; +} + +static void cpu_bus_noop(device_t dev) +{ +} + +static struct device_operations cpu_bus_ops = { + .read_resources = cpu_bus_noop, + .set_resources = cpu_bus_noop, + .enable_resources = cpu_bus_noop, + .init = cpu_bus_init, + .scan_bus = cpu_bus_scan, +}; + static void northbridge_enable(struct device *dev) { /* Set the operations if it is a special bus type */ @@ -137,6 +180,9 @@ static void northbridge_enable(struct device *dev) dev->ops = &pci_domain_ops; pci_set_method(dev); } + else if (dev->path.type == DEVICE_PATH_CPU_CLUSTER) { + dev->ops = &cpu_bus_ops; + } } struct chip_operations mainboard_emulation_qemu_x86_ops = {