#define MAX_BLK_DEVS 10
#define ZIPL_FILENAME "s390-zipl.rom"
+#define TYPE_S390_MACHINE "s390-machine"
static VirtIOS390Bus *s390_bus;
static S390CPU **ipi_states;
s390_virtio_hcall_set_status);
}
-/*
- * The number of running CPUs. On s390 a shutdown is the state of all CPUs
- * being either stopped or disabled (for interrupts) waiting. We have to
- * track this number to call the shutdown sequence accordingly. This
- * number is modified either on startup or while holding the big qemu lock.
- */
-static unsigned s390_running_cpus;
-
-void s390_add_running_cpu(S390CPU *cpu)
-{
- CPUState *cs = CPU(cpu);
- CPUS390XState *env = &cpu->env;
-
- if (cs->halted) {
- s390_running_cpus++;
- cs->halted = 0;
- env->exception_index = -1;
- }
-}
-
-unsigned s390_del_running_cpu(S390CPU *cpu)
-{
- CPUState *cs = CPU(cpu);
- CPUS390XState *env = &cpu->env;
-
- if (cs->halted == 0) {
- assert(s390_running_cpus >= 1);
- s390_running_cpus--;
- cs->halted = 1;
- env->exception_index = EXCP_HLT;
- }
- return s390_running_cpus;
-}
-
void s390_init_ipl_dev(const char *kernel_filename,
const char *kernel_cmdline,
const char *initrd_filename,
ipi_states[i] = cpu;
cs->halted = 1;
- cpu->env.exception_index = EXCP_HLT;
+ cs->exception_index = EXCP_HLT;
cpu->env.storage_keys = storage_keys;
}
}
}
/* PC hardware initialisation */
-static void s390_init(QEMUMachineInitArgs *args)
+static void s390_init(MachineState *machine)
{
- ram_addr_t my_ram_size = args->ram_size;
+ ram_addr_t my_ram_size = machine->ram_size;
MemoryRegion *sysmem = get_system_memory();
MemoryRegion *ram = g_new(MemoryRegion, 1);
- int shift = 0;
+ int increment_size = 20;
uint8_t *storage_keys;
void *virtio_region;
hwaddr virtio_region_len;
hwaddr virtio_region_start;
- /* s390x ram size detection needs a 16bit multiplier + an increment. So
- guests > 64GB can be specified in 2MB steps etc. */
- while ((my_ram_size >> (20 + shift)) > 65535) {
- shift++;
+ /*
+ * The storage increment size is a multiple of 1M and is a power of 2.
+ * The number of storage increments must be MAX_STORAGE_INCREMENTS or
+ * fewer.
+ */
+ while ((my_ram_size >> increment_size) > MAX_STORAGE_INCREMENTS) {
+ increment_size++;
}
- my_ram_size = my_ram_size >> (20 + shift) << (20 + shift);
+ my_ram_size = my_ram_size >> increment_size << increment_size;
/* let's propagate the changed ram size into the global variable. */
ram_size = my_ram_size;
/* get a BUS */
s390_bus = s390_virtio_bus_init(&my_ram_size);
s390_sclp_init();
- s390_init_ipl_dev(args->kernel_filename, args->kernel_cmdline,
- args->initrd_filename, ZIPL_FILENAME);
+ s390_init_ipl_dev(machine->kernel_filename, machine->kernel_cmdline,
+ machine->initrd_filename, ZIPL_FILENAME);
s390_flic_init();
/* register hypercalls */
s390_virtio_register_hcalls();
/* allocate RAM */
- memory_region_init_ram(ram, NULL, "s390.ram", my_ram_size);
+ memory_region_init_ram(ram, NULL, "s390.ram", my_ram_size, &error_abort);
vmstate_register_ram_global(ram);
memory_region_add_subregion(sysmem, 0, ram);
storage_keys = g_malloc0(my_ram_size / TARGET_PAGE_SIZE);
/* init CPUs */
- s390_init_cpus(args->cpu_model, storage_keys);
+ s390_init_cpus(machine->cpu_model, storage_keys);
/* Create VirtIO network adapters */
s390_create_virtio_net((BusState *)s390_bus, "virtio-net-s390");
}
-static QEMUMachine s390_machine = {
- .name = "s390-virtio",
- .alias = "s390",
- .desc = "VirtIO based S390 machine",
- .init = s390_init,
- .block_default_type = IF_VIRTIO,
- .no_cdrom = 1,
- .no_floppy = 1,
- .no_serial = 1,
- .no_parallel = 1,
- .no_sdcard = 1,
- .use_virtcon = 1,
- .max_cpus = 255,
- .is_default = 1,
+void s390_nmi(NMIState *n, int cpu_index, Error **errp)
+{
+ CPUState *cs = qemu_get_cpu(cpu_index);
+
+ if (s390_cpu_restart(S390_CPU(cs))) {
+ error_set(errp, QERR_UNSUPPORTED);
+ }
+}
+
+static void s390_machine_class_init(ObjectClass *oc, void *data)
+{
+ MachineClass *mc = MACHINE_CLASS(oc);
+ NMIClass *nc = NMI_CLASS(oc);
+
+ mc->name = "s390-virtio";
+ mc->alias = "s390";
+ mc->desc = "VirtIO based S390 machine";
+ mc->init = s390_init;
+ mc->block_default_type = IF_VIRTIO;
+ mc->max_cpus = 255;
+ mc->no_serial = 1;
+ mc->no_parallel = 1;
+ mc->use_virtcon = 1;
+ mc->no_floppy = 1;
+ mc->no_cdrom = 1;
+ mc->no_sdcard = 1;
+ mc->is_default = 1;
+ nc->nmi_monitor_handler = s390_nmi;
+}
+
+static const TypeInfo s390_machine_info = {
+ .name = TYPE_S390_MACHINE,
+ .parent = TYPE_MACHINE,
+ .class_init = s390_machine_class_init,
+ .interfaces = (InterfaceInfo[]) {
+ { TYPE_NMI },
+ { }
+ },
};
-static void s390_machine_init(void)
+static void s390_machine_register_types(void)
{
- qemu_register_machine(&s390_machine);
+ type_register_static(&s390_machine_info);
}
-machine_init(s390_machine_init);
+type_init(s390_machine_register_types)