diff --git a/hw/arm/virt.c b/hw/arm/virt.c index 5d38c47444..77d9267599 100644 --- a/hw/arm/virt.c +++ b/hw/arm/virt.c @@ -923,7 +923,7 @@ static void machvirt_init(MachineState *machine) qemu_irq pic[NUM_IRQS]; MemoryRegion *sysmem = get_system_memory(); int gic_version = vms->gic_version; - int n; + int n, max_cpus; MemoryRegion *ram = g_new(MemoryRegion, 1); const char *cpu_model = machine->cpu_model; VirtBoardInfo *vbi; @@ -957,6 +957,22 @@ static void machvirt_init(MachineState *machine) exit(1); } + /* The maximum number of CPUs depends on the GIC version, or on how + * many redistributors we can fit into the memory map. + */ + if (gic_version == 3) { + max_cpus = vbi->memmap[VIRT_GIC_REDIST].size / 0x20000; + } else { + max_cpus = GIC_NCPU; + } + + if (smp_cpus > max_cpus) { + error_report("Number of SMP CPUs requested (%d) exceeds max CPUs " + "supported by machine 'mach-virt' (%d)", + smp_cpus, max_cpus); + exit(1); + } + vbi->smp_cpus = smp_cpus; if (machine->ram_size > vbi->memmap[VIRT_MEM].size) { @@ -1155,10 +1171,11 @@ static void virt_class_init(ObjectClass *oc, void *data) mc->desc = "ARM Virtual Machine", mc->init = machvirt_init; - /* Our maximum number of CPUs depends on how many redistributors - * we can fit into memory map + /* Start max_cpus at the maximum QEMU supports. We'll further restrict + * it later in machvirt_init, where we have more information about the + * configuration of the particular instance. */ - mc->max_cpus = a15memmap[VIRT_GIC_REDIST].size / 0x20000; + mc->max_cpus = MAX_CPUMASK_BITS; mc->has_dynamic_sysbus = true; mc->block_default_type = IF_VIRTIO; mc->no_cdrom = 1;