Message ID | 1456866806-31466-5-git-send-email-mjrosato@linux.vnet.ibm.com (mailing list archive) |
---|---|
State | New, archived |
Headers | show |
On Tue, 1 Mar 2016 16:13:24 -0500 Matthew Rosato <mjrosato@linux.vnet.ibm.com> wrote: > Link each CPUState as property machine/cpu[n] during initialization. > Add a hotplug handler to s390-virtio-ccw machine and set the > state during plug. > Additionally, maintain an array of state pointers indexed by CPU > id for fast lookup during interrupt handling. > > Signed-off-by: Matthew Rosato <mjrosato@linux.vnet.ibm.com> > --- > hw/s390x/s390-virtio-ccw.c | 33 +++++++++++++++++++++++++++++++++ > hw/s390x/s390-virtio.c | 26 +++++++++++++++++--------- > 2 files changed, 50 insertions(+), 9 deletions(-) > > diff --git a/hw/s390x/s390-virtio-ccw.c b/hw/s390x/s390-virtio-ccw.c > index b05ed8b..3090e76 100644 > --- a/hw/s390x/s390-virtio-ccw.c > +++ b/hw/s390x/s390-virtio-ccw.c > @@ -156,10 +156,40 @@ static void ccw_init(MachineState *machine) > gtod_save, gtod_load, kvm_state); > } > > +static void s390_cpu_plug(HotplugHandler *hotplug_dev, > + DeviceState *dev, Error **errp) > +{ > + gchar *name; > + S390CPU *cpu = S390_CPU(dev); > + CPUState *cs = CPU(dev); > + > + name = g_strdup_printf("cpu[%i]", cpu->env.cpu_num); > + object_property_set_link(OBJECT(qdev_get_machine()), OBJECT(cs), name, hotplug_dev is machine, just do cast here instead of qdev_get_machine() > + errp); looks like 'name' is being leaked > +} > + > +static void s390_machine_device_plug(HotplugHandler *hotplug_dev, > + DeviceState *dev, Error **errp) > +{ > + if (object_dynamic_cast(OBJECT(dev), TYPE_CPU)) { > + s390_cpu_plug(hotplug_dev, dev, errp); > + } > +} > + > +static HotplugHandler *s390_get_hotplug_handler(MachineState *machine, > + DeviceState *dev) > +{ > + if (object_dynamic_cast(OBJECT(dev), TYPE_CPU)) { > + return HOTPLUG_HANDLER(machine); > + } > + return NULL; > +} > + > static void ccw_machine_class_init(ObjectClass *oc, void *data) > { > MachineClass *mc = MACHINE_CLASS(oc); > NMIClass *nc = NMI_CLASS(oc); > + HotplugHandlerClass *hc = HOTPLUG_HANDLER_CLASS(oc); > > mc->init = ccw_init; > mc->reset = s390_machine_reset; > @@ -171,6 +201,8 @@ static void ccw_machine_class_init(ObjectClass *oc, void *data) > mc->no_sdcard = 1; > mc->use_sclp = 1; > mc->max_cpus = 255; > + mc->get_hotplug_handler = s390_get_hotplug_handler; > + hc->plug = s390_machine_device_plug; > nc->nmi_monitor_handler = s390_nmi; > } > > @@ -232,6 +264,7 @@ static const TypeInfo ccw_machine_info = { > .class_init = ccw_machine_class_init, > .interfaces = (InterfaceInfo[]) { > { TYPE_NMI }, > + { TYPE_HOTPLUG_HANDLER}, > { } > }, > }; > diff --git a/hw/s390x/s390-virtio.c b/hw/s390x/s390-virtio.c > index b3707f4..6bd9803 100644 > --- a/hw/s390x/s390-virtio.c > +++ b/hw/s390x/s390-virtio.c > @@ -60,15 +60,16 @@ > #define S390_TOD_CLOCK_VALUE_MISSING 0x00 > #define S390_TOD_CLOCK_VALUE_PRESENT 0x01 > > -static S390CPU **ipi_states; > +static S390CPU **cpu_states; > > S390CPU *s390_cpu_addr2state(uint16_t cpu_addr) > { > - if (cpu_addr >= smp_cpus) { > + if (cpu_addr >= max_cpus) { > return NULL; > } > > - return ipi_states[cpu_addr]; > + /* Fast lookup via CPU ID */ > + return cpu_states[cpu_addr]; > } this hunk seems to be unrelated to this patch, it probably belongs somewhere else > void s390_init_ipl_dev(const char *kernel_filename, > @@ -98,19 +99,26 @@ void s390_init_ipl_dev(const char *kernel_filename, > void s390_init_cpus(MachineState *machine) > { > int i; > + gchar *name; > > if (machine->cpu_model == NULL) { > machine->cpu_model = "host"; > } > > - ipi_states = g_malloc(sizeof(S390CPU *) * smp_cpus); > + cpu_states = g_malloc0(sizeof(S390CPU *) * max_cpus); > > - for (i = 0; i < smp_cpus; i++) { > - S390CPU *cpu; > - > - cpu = cpu_s390x_init(machine->cpu_model); > + for (i = 0; i < max_cpus; i++) { > + name = g_strdup_printf("cpu[%i]", i); > + object_property_add_link(OBJECT(machine), name, TYPE_S390_CPU, > + (Object **) &cpu_states[i], > + object_property_allow_set_link, > + OBJ_PROP_LINK_UNREF_ON_RELEASE, > + &error_abort); > + g_free(name); > + } > > - ipi_states[i] = cpu; > + for (i = 0; i < smp_cpus; i++) { > + cpu_s390x_init(machine->cpu_model); > } > } >
diff --git a/hw/s390x/s390-virtio-ccw.c b/hw/s390x/s390-virtio-ccw.c index b05ed8b..3090e76 100644 --- a/hw/s390x/s390-virtio-ccw.c +++ b/hw/s390x/s390-virtio-ccw.c @@ -156,10 +156,40 @@ static void ccw_init(MachineState *machine) gtod_save, gtod_load, kvm_state); } +static void s390_cpu_plug(HotplugHandler *hotplug_dev, + DeviceState *dev, Error **errp) +{ + gchar *name; + S390CPU *cpu = S390_CPU(dev); + CPUState *cs = CPU(dev); + + name = g_strdup_printf("cpu[%i]", cpu->env.cpu_num); + object_property_set_link(OBJECT(qdev_get_machine()), OBJECT(cs), name, + errp); +} + +static void s390_machine_device_plug(HotplugHandler *hotplug_dev, + DeviceState *dev, Error **errp) +{ + if (object_dynamic_cast(OBJECT(dev), TYPE_CPU)) { + s390_cpu_plug(hotplug_dev, dev, errp); + } +} + +static HotplugHandler *s390_get_hotplug_handler(MachineState *machine, + DeviceState *dev) +{ + if (object_dynamic_cast(OBJECT(dev), TYPE_CPU)) { + return HOTPLUG_HANDLER(machine); + } + return NULL; +} + static void ccw_machine_class_init(ObjectClass *oc, void *data) { MachineClass *mc = MACHINE_CLASS(oc); NMIClass *nc = NMI_CLASS(oc); + HotplugHandlerClass *hc = HOTPLUG_HANDLER_CLASS(oc); mc->init = ccw_init; mc->reset = s390_machine_reset; @@ -171,6 +201,8 @@ static void ccw_machine_class_init(ObjectClass *oc, void *data) mc->no_sdcard = 1; mc->use_sclp = 1; mc->max_cpus = 255; + mc->get_hotplug_handler = s390_get_hotplug_handler; + hc->plug = s390_machine_device_plug; nc->nmi_monitor_handler = s390_nmi; } @@ -232,6 +264,7 @@ static const TypeInfo ccw_machine_info = { .class_init = ccw_machine_class_init, .interfaces = (InterfaceInfo[]) { { TYPE_NMI }, + { TYPE_HOTPLUG_HANDLER}, { } }, }; diff --git a/hw/s390x/s390-virtio.c b/hw/s390x/s390-virtio.c index b3707f4..6bd9803 100644 --- a/hw/s390x/s390-virtio.c +++ b/hw/s390x/s390-virtio.c @@ -60,15 +60,16 @@ #define S390_TOD_CLOCK_VALUE_MISSING 0x00 #define S390_TOD_CLOCK_VALUE_PRESENT 0x01 -static S390CPU **ipi_states; +static S390CPU **cpu_states; S390CPU *s390_cpu_addr2state(uint16_t cpu_addr) { - if (cpu_addr >= smp_cpus) { + if (cpu_addr >= max_cpus) { return NULL; } - return ipi_states[cpu_addr]; + /* Fast lookup via CPU ID */ + return cpu_states[cpu_addr]; } void s390_init_ipl_dev(const char *kernel_filename, @@ -98,19 +99,26 @@ void s390_init_ipl_dev(const char *kernel_filename, void s390_init_cpus(MachineState *machine) { int i; + gchar *name; if (machine->cpu_model == NULL) { machine->cpu_model = "host"; } - ipi_states = g_malloc(sizeof(S390CPU *) * smp_cpus); + cpu_states = g_malloc0(sizeof(S390CPU *) * max_cpus); - for (i = 0; i < smp_cpus; i++) { - S390CPU *cpu; - - cpu = cpu_s390x_init(machine->cpu_model); + for (i = 0; i < max_cpus; i++) { + name = g_strdup_printf("cpu[%i]", i); + object_property_add_link(OBJECT(machine), name, TYPE_S390_CPU, + (Object **) &cpu_states[i], + object_property_allow_set_link, + OBJ_PROP_LINK_UNREF_ON_RELEASE, + &error_abort); + g_free(name); + } - ipi_states[i] = cpu; + for (i = 0; i < smp_cpus; i++) { + cpu_s390x_init(machine->cpu_model); } }
Link each CPUState as property machine/cpu[n] during initialization. Add a hotplug handler to s390-virtio-ccw machine and set the state during plug. Additionally, maintain an array of state pointers indexed by CPU id for fast lookup during interrupt handling. Signed-off-by: Matthew Rosato <mjrosato@linux.vnet.ibm.com> --- hw/s390x/s390-virtio-ccw.c | 33 +++++++++++++++++++++++++++++++++ hw/s390x/s390-virtio.c | 26 +++++++++++++++++--------- 2 files changed, 50 insertions(+), 9 deletions(-)