Patchwork [RFC,v4,44/44] qom: Introduce CPU class

login
register
mail settings
Submitter Andreas Färber
Date March 10, 2012, 2:28 a.m.
Message ID <1331346496-10736-45-git-send-email-afaerber@suse.de>
Download mbox | patch
Permalink /patch/145800/
State New
Headers show

Comments

Andreas Färber - March 10, 2012, 2:28 a.m.
Reintroduce CPUState as QOM object: It's abstract and derived directly
from TYPE_OBJECT for compatibility with the user emulators.
The identifier CPUState avoids conflicts between CPU() and the struct.

Introduce $(qom-twice-y) to build it separately for system and for user
emulators.

Prepare a virtual reset method, (re)introduce cpu_reset() as wrapper.

Signed-off-by: Andreas Färber <afaerber@suse.de>
Cc: Anthony Liguori <anthony@codemonkey.ws>
---
 Makefile.objs      |    3 ++
 configure          |    1 +
 include/qemu/cpu.h |   75 ++++++++++++++++++++++++++++++++++++++++++++++++++++
 qom/Makefile       |    1 +
 qom/cpu.c          |   58 ++++++++++++++++++++++++++++++++++++++++
 5 files changed, 138 insertions(+), 0 deletions(-)
 create mode 100644 include/qemu/cpu.h
 create mode 100644 qom/cpu.c
Igor Mammedov - March 12, 2012, 9:38 a.m.
On 03/10/2012 03:28 AM, Andreas Färber wrote:
> Reintroduce CPUState as QOM object: It's abstract and derived directly
> from TYPE_OBJECT for compatibility with the user emulators.
> The identifier CPUState avoids conflicts between CPU() and the struct.
>
> Introduce $(qom-twice-y) to build it separately for system and for user
> emulators.
>
> Prepare a virtual reset method, (re)introduce cpu_reset() as wrapper.
>
> Signed-off-by: Andreas Färber<afaerber@suse.de>
> Cc: Anthony Liguori<anthony@codemonkey.ws>
> ---
>   Makefile.objs      |    3 ++
>   configure          |    1 +
>   include/qemu/cpu.h |   75 ++++++++++++++++++++++++++++++++++++++++++++++++++++
>   qom/Makefile       |    1 +
>   qom/cpu.c          |   58 ++++++++++++++++++++++++++++++++++++++++
>   5 files changed, 138 insertions(+), 0 deletions(-)
>   create mode 100644 include/qemu/cpu.h
>   create mode 100644 qom/cpu.c
>
> diff --git a/Makefile.objs b/Makefile.objs
> index 431b7a1..291baf5 100644
> --- a/Makefile.objs
> +++ b/Makefile.objs
> @@ -14,6 +14,7 @@ universal-obj-y += $(qobject-obj-y)
>   # QOM
>   include $(SRC_PATH)/qom/Makefile
>   qom-obj-y = $(addprefix qom/, $(qom-y))
> +qom-obj-twice-y = $(addprefix qom/, $(qom-twice-y))
>
>   universal-obj-y += $(qom-obj-y)
>
> @@ -89,6 +90,7 @@ fsdev-obj-$(CONFIG_VIRTFS) += $(addprefix fsdev/, $(fsdev-nested-y))
>
>   common-obj-y = $(block-obj-y) blockdev.o
>   common-obj-y += $(net-obj-y)
> +common-obj-y += $(qom-obj-twice-y)
>   common-obj-$(CONFIG_LINUX) += $(fsdev-obj-$(CONFIG_LINUX))
>   common-obj-y += readline.o console.o cursor.o
>   common-obj-y += $(oslib-obj-y)
> @@ -194,6 +196,7 @@ user-obj-y += cutils.o cache-utils.o
>   user-obj-y += module.o
>   user-obj-y += qemu-user.o
>   user-obj-y += $(trace-obj-y)
> +user-obj-y += $(qom-obj-twice-y)
>
>   ######################################################################
>   # libhw
> diff --git a/configure b/configure
> index 66a65d9..1826af5 100755
> --- a/configure
> +++ b/configure
> @@ -3888,6 +3888,7 @@ fi
>   d=libuser
>   mkdir -p $d
>   mkdir -p $d/trace
> +mkdir -p $d/qom
>   symlink $source_path/Makefile.user $d/Makefile
>
>   if test "$docs" = "yes" ; then
> diff --git a/include/qemu/cpu.h b/include/qemu/cpu.h
> new file mode 100644
> index 0000000..4291279
> --- /dev/null
> +++ b/include/qemu/cpu.h
> @@ -0,0 +1,75 @@
> +/*
> + * QEMU CPU model
> + *
> + * Copyright (c) 2012 SUSE LINUX Products GmbH
> + *
> + * This program is free software; you can redistribute it and/or
> + * modify it under the terms of the GNU General Public License
> + * as published by the Free Software Foundation; either version 2
> + * of the License, or (at your option) any later version.
> + *
> + * This program is distributed in the hope that it will be useful,
> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
> + * GNU General Public License for more details.
> + *
> + * You should have received a copy of the GNU General Public License
> + * along with this program; if not, see
> + *<http://www.gnu.org/licenses/gpl-2.0.html>
> + */
> +#ifndef QEMU_CPU_H
> +#define QEMU_CPU_H
> +
> +#include "qemu/object.h"
> +
> +/**
> + * SECTION:cpu
> + * @section_id: QEMU-cpu
> + * @title: CPU Class
> + * @short_description: Base class for all CPUs
> + */
> +
> +#define TYPE_CPU "cpu"
> +
> +#define CPU(obj) OBJECT_CHECK(CPUState, (obj), TYPE_CPU)
> +#define CPU_CLASS(class) OBJECT_CLASS_CHECK(CPUClass, (class), TYPE_CPU)
> +#define CPU_GET_CLASS(obj) OBJECT_GET_CLASS(CPUClass, (obj), TYPE_CPU)
> +
> +typedef struct CPUState CPUState;
> +
> +/**
> + * CPUClass:
> + * @reset: Callback to reset the #CPU to its initial state.
> + *
> + * Represents a CPU family or model.
> + */
> +typedef struct CPUClass {
> +    /*<  private>*/
> +    ObjectClass parent_class;
> +    /*<  public>*/
> +
> +    void (*reset)(CPUState *cpu);
Why not use Object* as argument here?
It will be easier to generalize later qdev code and not make special case when
adding cpus.

BTW how we are going to generalize qdev and make its infrastructure available
to other types except of DEVICE_TYPE.
Maybe we should introduce some (abstract) base class (or interface) for basic
device that will define methods like reset, realize, unrealize and use it in
qdev code instead of DEVICE_TYPE?

> +} CPUClass;
> +
> +/**
> + * CPUState:
> + *
> + * State of one CPU core or thread.
> + */
> +struct CPUState {
> +    /*<  private>*/
> +    Object parent_obj;
> +    /*<  public>*/
> +
> +    /* TODO Move common fields from CPUState here. */
> +};
> +
> +
> +/**
> + * cpu_reset:
> + * @cpu: The CPU whose state is to be reset.
> + */
> +void cpu_reset(CPUState *cpu);
> +
> +
> +#endif
> diff --git a/qom/Makefile b/qom/Makefile
> index 885a263..34c6de5 100644
> --- a/qom/Makefile
> +++ b/qom/Makefile
> @@ -1 +1,2 @@
>   qom-y = object.o container.o qom-qobject.o
> +qom-twice-y = cpu.o
> diff --git a/qom/cpu.c b/qom/cpu.c
> new file mode 100644
> index 0000000..5b36046
> --- /dev/null
> +++ b/qom/cpu.c
> @@ -0,0 +1,58 @@
> +/*
> + * QEMU CPU model
> + *
> + * Copyright (c) 2012 SUSE LINUX Products GmbH
> + *
> + * This program is free software; you can redistribute it and/or
> + * modify it under the terms of the GNU General Public License
> + * as published by the Free Software Foundation; either version 2
> + * of the License, or (at your option) any later version.
> + *
> + * This program is distributed in the hope that it will be useful,
> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
> + * GNU General Public License for more details.
> + *
> + * You should have received a copy of the GNU General Public License
> + * along with this program; if not, see
> + *<http://www.gnu.org/licenses/gpl-2.0.html>
> + */
> +
> +#include "qemu/cpu.h"
> +#include "qemu-common.h"
> +
> +void cpu_reset(CPUState *cpu)
> +{
> +    CPUClass *klass = CPU_GET_CLASS(cpu);
> +
> +    if (klass->reset != NULL) {
> +        (*klass->reset)(cpu);
> +    }
> +}
> +
> +static void cpu_common_reset(CPUState *cpu)
> +{
> +}
> +
> +static void cpu_class_init(ObjectClass *klass, void *data)
> +{
> +    CPUClass *k = CPU_CLASS(klass);
> +
> +    k->reset = cpu_common_reset;
> +}
> +
> +static TypeInfo cpu_type_info = {
> +    .name = TYPE_CPU,
> +    .parent = TYPE_OBJECT,
> +    .instance_size = sizeof(CPUState),
> +    .abstract = true,
> +    .class_size = sizeof(CPUClass),
> +    .class_init = cpu_class_init,
> +};
> +
> +static void cpu_register_types(void)
> +{
> +    type_register_static(&cpu_type_info);
> +}
> +
> +type_init(cpu_register_types)
Andreas Färber - March 13, 2012, 12:13 p.m.
Am 12.03.2012 10:38, schrieb Igor Mammedov:
> On 03/10/2012 03:28 AM, Andreas Färber wrote:
>> Reintroduce CPUState as QOM object: It's abstract and derived directly
>> from TYPE_OBJECT for compatibility with the user emulators.
>> The identifier CPUState avoids conflicts between CPU() and the struct.
>>
>> Introduce $(qom-twice-y) to build it separately for system and for user
>> emulators.
>>
>> Prepare a virtual reset method, (re)introduce cpu_reset() as wrapper.
>>
>> Signed-off-by: Andreas Färber<afaerber@suse.de>
>> Cc: Anthony Liguori<anthony@codemonkey.ws>
>> ---
>>   Makefile.objs      |    3 ++
>>   configure          |    1 +
>>   include/qemu/cpu.h |   75
>> ++++++++++++++++++++++++++++++++++++++++++++++++++++
>>   qom/Makefile       |    1 +
>>   qom/cpu.c          |   58 ++++++++++++++++++++++++++++++++++++++++
>>   5 files changed, 138 insertions(+), 0 deletions(-)
>>   create mode 100644 include/qemu/cpu.h
>>   create mode 100644 qom/cpu.c

>> diff --git a/include/qemu/cpu.h b/include/qemu/cpu.h
>> new file mode 100644
>> index 0000000..4291279
>> --- /dev/null
>> +++ b/include/qemu/cpu.h

>> +/**
>> + * CPUClass:
>> + * @reset: Callback to reset the #CPU to its initial state.
>> + *
>> + * Represents a CPU family or model.
>> + */
>> +typedef struct CPUClass {
>> +    /*<  private>*/
>> +    ObjectClass parent_class;
>> +    /*<  public>*/
>> +
>> +    void (*reset)(CPUState *cpu);
> Why not use Object* as argument here?

In SysBusDeviceClass etc. we use the specific object type, too.
Obviously my CPU is the first "new" QOM type, so we can go different
ways if we want to. As long as it's a CPU-specific mechanism, using the
specific type avoids some casts.

> It will be easier to generalize later qdev code and not make special
> case when
> adding cpus.

I never heard anyone wanting to generalize reset so far. I don't think
it belongs into Object at least. Maybe DeviceState. Anthony? Paolo?

> BTW how we are going to generalize qdev and make its infrastructure
> available
> to other types except of DEVICE_TYPE.
> Maybe we should introduce some (abstract) base class (or interface) for
> basic
> device that will define methods like reset, realize, unrealize and use
> it in
> qdev code instead of DEVICE_TYPE?

I thought Anthony wanted to do realize/unrealize and "realized" property
in Object.

For SH4 I worked around that with my own sh7750_realize() function. This
series is taking much too long to move forward (the QOM "steam" seems to
be gone?) and I'm worried that introducing much more basic
infrastructure will make review and applying even slower, cf.
object_class_foreach_ordered()/_get_list().

Thanks for reviewing so far,

Andreas
Paolo Bonzini - March 13, 2012, 12:20 p.m.
Il 13/03/2012 13:13, Andreas Färber ha scritto:
> > It will be easier to generalize later qdev code and not make special
> > case when adding cpus.
> 
> I never heard anyone wanting to generalize reset so far. I don't think
> it belongs into Object at least. Maybe DeviceState. Anthony? Paolo?

I believe long term we want CPUs to become a DeviceState.  For now, I
think Andreas's prototype is fine.  Methods should not take a superclass
argument in general.

> This series is taking much too long to move forward (the QOM "steam"
> seems to be gone?) and I'm worried that introducing much more basic 
> infrastructure will make review and applying even slower, cf. 
> object_class_foreach_ordered()/_get_list().

Agreed, this series looks more or less good (and mostly mechanical
anyway).  Is it an RFC or what? :)  I wonder if reviewers are put off by
the subject.

Paolo
Andreas Färber - March 13, 2012, 12:53 p.m.
Am 13.03.2012 13:20, schrieb Paolo Bonzini:
> Il 13/03/2012 13:13, Andreas Färber ha scritto:
>>> It will be easier to generalize later qdev code and not make special
>>> case when adding cpus.
>>
>> I never heard anyone wanting to generalize reset so far. I don't think
>> it belongs into Object at least. Maybe DeviceState. Anthony? Paolo?
> 
> I believe long term we want CPUs to become a DeviceState.  For now, I
> think Andreas's prototype is fine.

I have prepared $(qom-obj-twice-y) to allow for:

#ifdef CONFIG_SOFTMMU
    .parent = TYPE_DEVICE, // or TYPE_SYS_BUS_DEVICE
#else
    .parent = TYPE_OBJECT,
#endif

So far it was not needed. :)

>  Methods should not take a superclass
> argument in general.

So to clarify, this is pro CPUState?

>> This series is taking much too long to move forward (the QOM "steam"
>> seems to be gone?) and I'm worried that introducing much more basic 
>> infrastructure will make review and applying even slower, cf. 
>> object_class_foreach_ordered()/_get_list().
> 
> Agreed, this series looks more or less good (and mostly mechanical
> anyway).

Thanks.

>  Is it an RFC or what? :)  I wonder if reviewers are put off by
> the subject.

The implied RFC is, are we okay with reusing "CPUState" this way? Or
does someone - last call! - have a better identifier name?

Getting this series merged either means coordinating the PULL with a
maintainer so that no merge conflicts arise in-flight, or having the
maintainer re-run the commit-creating script himself.

Andreas
Paolo Bonzini - March 13, 2012, 1:03 p.m.
Il 13/03/2012 13:53, Andreas Färber ha scritto:
>> >  Methods should not take a superclass
>> > argument in general.
> So to clarify, this is pro CPUState?

Yes.

>>> >> This series is taking much too long to move forward (the QOM "steam"
>>> >> seems to be gone?) and I'm worried that introducing much more basic 
>>> >> infrastructure will make review and applying even slower, cf. 
>>> >> object_class_foreach_ordered()/_get_list().
>> > 
>> > Agreed, this series looks more or less good (and mostly mechanical
>> > anyway).
> Thanks.
> 
>> >  Is it an RFC or what? :)  I wonder if reviewers are put off by
>> > the subject.
> The implied RFC is, are we okay with reusing "CPUState" this way? Or
> does someone - last call! - have a better identifier name?
> 
> Getting this series merged either means coordinating the PULL with a
> maintainer so that no merge conflicts arise in-flight, or having the
> maintainer re-run the commit-creating script himself.

FWIW I like it. :)

Paolo
Anthony Liguori - March 13, 2012, 6:16 p.m.
On 03/13/2012 07:20 AM, Paolo Bonzini wrote:
> Il 13/03/2012 13:13, Andreas Färber ha scritto:
>>> It will be easier to generalize later qdev code and not make special
>>> case when adding cpus.
>>
>> I never heard anyone wanting to generalize reset so far. I don't think
>> it belongs into Object at least. Maybe DeviceState. Anthony? Paolo?
>
> I believe long term we want CPUs to become a DeviceState.  For now, I
> think Andreas's prototype is fine.  Methods should not take a superclass
> argument in general.

Agreed 100%.  Methods should take whatever there class is as the argument.

>
>> This series is taking much too long to move forward (the QOM "steam"
>> seems to be gone?) and I'm worried that introducing much more basic
>> infrastructure will make review and applying even slower, cf.
>> object_class_foreach_ordered()/_get_list().
>
> Agreed, this series looks more or less good (and mostly mechanical
> anyway).  Is it an RFC or what? :)  I wonder if reviewers are put off by
> the subject.

44 patches is a bit scary.  Had I realized it was so straight forward, I would 
have reviewed it faster.

Anyway, I'm really happy with the whole series.  If it weren't an RFC, I'd apply 
it right now.

Andreas, please send out a new series that's !rfc or a pull request.

Really great work here, btw!

Regards,

Anthony Liguori

>
> Paolo
>
Anthony Liguori - March 14, 2012, 7:48 p.m.
On 03/14/2012 03:37 PM, Igor Mitsyanko wrote:
> On 13.03.2012 3:13 PM, Andreas Färber wrote:
>
>> In SysBusDeviceClass etc. we use the specific object type, too.
>> Obviously my CPU is the first "new" QOM type, so we can go different
>> ways if we want to. As long as it's a CPU-specific mechanism, using the
>> specific type avoids some casts.
>>
>>> It will be easier to generalize later qdev code and not make special
>>> case when
>>> adding cpus.
>>
>> I never heard anyone wanting to generalize reset so far. I don't think
>> it belongs into Object at least. Maybe DeviceState. Anthony? Paolo?
>>
>
> We can have a special object for this, let's call it ResetLine for example, with
> methods ResetLine::connect, ResetLine::assert or something like that. Different
> ResetLine objects could trigger reset of different sets of subdevices, just like
> real hardware can have several reset types (for example, STM32 has 3 different
> reset types).

I've explored a bunch of different models for this.  My current thinking is a 
realized:bool property that when set, would call a realize() virtual method and 
when unset would call an unrealize() virtual method.  The default implementation 
of [un]realize() would propagate the change to all composition children.

At one point, I modeled this as a Vcc Pin with similar semantics except that 
instead of relying on a property accessor, the realize function would connect to 
the device's Vcc pin to the children's Vcc pins via a set of Wire objects (that 
just propagate Pin state).

This later model is too low level IMHO.  I think we should stick with the 
functional realize property which covers 99% of devices.  For the 1%, we can use 
pins or just have additional properties as appropriate.

Regards,

Anthony Liguori
Andreas Färber - March 14, 2012, 7:57 p.m.
Am 14.03.2012 20:48, schrieb Anthony Liguori:
> On 03/14/2012 03:37 PM, Igor Mitsyanko wrote:
>> On 13.03.2012 3:13 PM, Andreas Färber wrote:
>>
>>> In SysBusDeviceClass etc. we use the specific object type, too.
>>> Obviously my CPU is the first "new" QOM type, so we can go different
>>> ways if we want to. As long as it's a CPU-specific mechanism, using the
>>> specific type avoids some casts.
>>>
>>>> It will be easier to generalize later qdev code and not make special
>>>> case when
>>>> adding cpus.
>>>
>>> I never heard anyone wanting to generalize reset so far. I don't think
>>> it belongs into Object at least. Maybe DeviceState. Anthony? Paolo?
>>>
>>
>> We can have a special object for this, let's call it ResetLine for
>> example, with
>> methods ResetLine::connect, ResetLine::assert or something like that.
>> Different
>> ResetLine objects could trigger reset of different sets of subdevices,
>> just like
>> real hardware can have several reset types (for example, STM32 has 3
>> different
>> reset types).
> 
> I've explored a bunch of different models for this.  My current thinking
> is a realized:bool property that when set, would call a realize()
> virtual method and when unset would call an unrealize() virtual method. 
> The default implementation of [un]realize() would propagate the change
> to all composition children.

I've found that model not to work with today's qdev remainders: We often
have a dependency tree of initfn and init a.k.a. realize functions, so
that we can't clearly separate between the two to do recursive
processing. Unless we do a three-stage initialization of Object::initfn,
what-is-now-DeviceState::init, Object::realize.

Andreas
Anthony Liguori - March 14, 2012, 8:01 p.m.
On 03/14/2012 02:57 PM, Andreas Färber wrote:
> Am 14.03.2012 20:48, schrieb Anthony Liguori:
>> On 03/14/2012 03:37 PM, Igor Mitsyanko wrote:
>>> On 13.03.2012 3:13 PM, Andreas Färber wrote:
>>>
>>>> In SysBusDeviceClass etc. we use the specific object type, too.
>>>> Obviously my CPU is the first "new" QOM type, so we can go different
>>>> ways if we want to. As long as it's a CPU-specific mechanism, using the
>>>> specific type avoids some casts.
>>>>
>>>>> It will be easier to generalize later qdev code and not make special
>>>>> case when
>>>>> adding cpus.
>>>>
>>>> I never heard anyone wanting to generalize reset so far. I don't think
>>>> it belongs into Object at least. Maybe DeviceState. Anthony? Paolo?
>>>>
>>>
>>> We can have a special object for this, let's call it ResetLine for
>>> example, with
>>> methods ResetLine::connect, ResetLine::assert or something like that.
>>> Different
>>> ResetLine objects could trigger reset of different sets of subdevices,
>>> just like
>>> real hardware can have several reset types (for example, STM32 has 3
>>> different
>>> reset types).
>>
>> I've explored a bunch of different models for this.  My current thinking
>> is a realized:bool property that when set, would call a realize()
>> virtual method and when unset would call an unrealize() virtual method.
>> The default implementation of [un]realize() would propagate the change
>> to all composition children.
>
> I've found that model not to work with today's qdev remainders: We often
> have a dependency tree of initfn and init a.k.a. realize functions, so
> that we can't clearly separate between the two to do recursive
> processing. Unless we do a three-stage initialization of Object::initfn,
> what-is-now-DeviceState::init, Object::realize.

Yes, there's quite a lot of refactoring to get to a two stage recursive init. 
This is why realized isn't a part of QOM/qdev today.

Regards,

Anthony Liguori

>
> Andreas
>
Andreas Färber - March 14, 2012, 8:37 p.m.
Am 14.03.2012 21:37, schrieb Igor Mitsyanko:
> On 13.03.2012 3:13 PM, Andreas Färber wrote:
> 
>> I never heard anyone wanting to generalize reset so far. I don't think
>> it belongs into Object at least. Maybe DeviceState. Anthony? Paolo?
>>
> 
> We can have a special object for this, let's call it ResetLine for
> example, with methods ResetLine::connect, ResetLine::assert or something
> like that. Different ResetLine objects could trigger reset of different
> sets of subdevices, just like real hardware can have several reset types
> (for example, STM32 has 3 different reset types).

Anthony provided a Reviewed-by, and given that this is a direct
conversion of cpu_reset() -> cpu_state_reset() -> CPUState::reset(), I
am preparing a PULL for this series tonight. That does not mean that the
code must stay like this forever. :)

cpu_reset() only handles the full reset of one CPU, as I understand, and
is called both at startup and at machine-level reset.

Anthony's Pin object, as qemu_irq successor, was planned post-4th QOM
series, I believe. -- "Small steps, Allie."

Andreas
Igor Mitsyanko - March 14, 2012, 8:37 p.m.
On 13.03.2012 3:13 PM, Andreas Färber wrote:

> In SysBusDeviceClass etc. we use the specific object type, too.
> Obviously my CPU is the first "new" QOM type, so we can go different
> ways if we want to. As long as it's a CPU-specific mechanism, using the
> specific type avoids some casts.
>
>> It will be easier to generalize later qdev code and not make special
>> case when
>> adding cpus.
>
> I never heard anyone wanting to generalize reset so far. I don't think
> it belongs into Object at least. Maybe DeviceState. Anthony? Paolo?
>

We can have a special object for this, let's call it ResetLine for 
example, with methods ResetLine::connect, ResetLine::assert or something 
like that. Different ResetLine objects could trigger reset of different 
sets of subdevices, just like real hardware can have several reset types 
(for example, STM32 has 3 different reset types).
Anthony Liguori - March 14, 2012, 8:40 p.m.
On 03/14/2012 03:37 PM, Andreas Färber wrote:
> Am 14.03.2012 21:37, schrieb Igor Mitsyanko:
>> On 13.03.2012 3:13 PM, Andreas Färber wrote:
>>
>>> I never heard anyone wanting to generalize reset so far. I don't think
>>> it belongs into Object at least. Maybe DeviceState. Anthony? Paolo?
>>>
>>
>> We can have a special object for this, let's call it ResetLine for
>> example, with methods ResetLine::connect, ResetLine::assert or something
>> like that. Different ResetLine objects could trigger reset of different
>> sets of subdevices, just like real hardware can have several reset types
>> (for example, STM32 has 3 different reset types).
>
> Anthony provided a Reviewed-by, and given that this is a direct
> conversion of cpu_reset() ->  cpu_state_reset() ->  CPUState::reset(), I
> am preparing a PULL for this series tonight. That does not mean that the
> code must stay like this forever. :)
>
> cpu_reset() only handles the full reset of one CPU, as I understand, and
> is called both at startup and at machine-level reset.
>
> Anthony's Pin object, as qemu_irq successor, was planned post-4th QOM
> series, I believe. -- "Small steps, Allie."

Ack.

Regards,

Anthony Liguori

>
> Andreas
>

Patch

diff --git a/Makefile.objs b/Makefile.objs
index 431b7a1..291baf5 100644
--- a/Makefile.objs
+++ b/Makefile.objs
@@ -14,6 +14,7 @@  universal-obj-y += $(qobject-obj-y)
 # QOM
 include $(SRC_PATH)/qom/Makefile
 qom-obj-y = $(addprefix qom/, $(qom-y))
+qom-obj-twice-y = $(addprefix qom/, $(qom-twice-y))
 
 universal-obj-y += $(qom-obj-y)
 
@@ -89,6 +90,7 @@  fsdev-obj-$(CONFIG_VIRTFS) += $(addprefix fsdev/, $(fsdev-nested-y))
 
 common-obj-y = $(block-obj-y) blockdev.o
 common-obj-y += $(net-obj-y)
+common-obj-y += $(qom-obj-twice-y)
 common-obj-$(CONFIG_LINUX) += $(fsdev-obj-$(CONFIG_LINUX))
 common-obj-y += readline.o console.o cursor.o
 common-obj-y += $(oslib-obj-y)
@@ -194,6 +196,7 @@  user-obj-y += cutils.o cache-utils.o
 user-obj-y += module.o
 user-obj-y += qemu-user.o
 user-obj-y += $(trace-obj-y)
+user-obj-y += $(qom-obj-twice-y)
 
 ######################################################################
 # libhw
diff --git a/configure b/configure
index 66a65d9..1826af5 100755
--- a/configure
+++ b/configure
@@ -3888,6 +3888,7 @@  fi
 d=libuser
 mkdir -p $d
 mkdir -p $d/trace
+mkdir -p $d/qom
 symlink $source_path/Makefile.user $d/Makefile
 
 if test "$docs" = "yes" ; then
diff --git a/include/qemu/cpu.h b/include/qemu/cpu.h
new file mode 100644
index 0000000..4291279
--- /dev/null
+++ b/include/qemu/cpu.h
@@ -0,0 +1,75 @@ 
+/*
+ * QEMU CPU model
+ *
+ * Copyright (c) 2012 SUSE LINUX Products GmbH
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, see
+ * <http://www.gnu.org/licenses/gpl-2.0.html>
+ */
+#ifndef QEMU_CPU_H
+#define QEMU_CPU_H
+
+#include "qemu/object.h"
+
+/**
+ * SECTION:cpu
+ * @section_id: QEMU-cpu
+ * @title: CPU Class
+ * @short_description: Base class for all CPUs
+ */
+
+#define TYPE_CPU "cpu"
+
+#define CPU(obj) OBJECT_CHECK(CPUState, (obj), TYPE_CPU)
+#define CPU_CLASS(class) OBJECT_CLASS_CHECK(CPUClass, (class), TYPE_CPU)
+#define CPU_GET_CLASS(obj) OBJECT_GET_CLASS(CPUClass, (obj), TYPE_CPU)
+
+typedef struct CPUState CPUState;
+
+/**
+ * CPUClass:
+ * @reset: Callback to reset the #CPU to its initial state.
+ *
+ * Represents a CPU family or model.
+ */
+typedef struct CPUClass {
+    /*< private >*/
+    ObjectClass parent_class;
+    /*< public >*/
+
+    void (*reset)(CPUState *cpu);
+} CPUClass;
+
+/**
+ * CPUState:
+ *
+ * State of one CPU core or thread.
+ */
+struct CPUState {
+    /*< private >*/
+    Object parent_obj;
+    /*< public >*/
+
+    /* TODO Move common fields from CPUState here. */
+};
+
+
+/**
+ * cpu_reset:
+ * @cpu: The CPU whose state is to be reset.
+ */
+void cpu_reset(CPUState *cpu);
+
+
+#endif
diff --git a/qom/Makefile b/qom/Makefile
index 885a263..34c6de5 100644
--- a/qom/Makefile
+++ b/qom/Makefile
@@ -1 +1,2 @@ 
 qom-y = object.o container.o qom-qobject.o
+qom-twice-y = cpu.o
diff --git a/qom/cpu.c b/qom/cpu.c
new file mode 100644
index 0000000..5b36046
--- /dev/null
+++ b/qom/cpu.c
@@ -0,0 +1,58 @@ 
+/*
+ * QEMU CPU model
+ *
+ * Copyright (c) 2012 SUSE LINUX Products GmbH
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, see
+ * <http://www.gnu.org/licenses/gpl-2.0.html>
+ */
+
+#include "qemu/cpu.h"
+#include "qemu-common.h"
+
+void cpu_reset(CPUState *cpu)
+{
+    CPUClass *klass = CPU_GET_CLASS(cpu);
+
+    if (klass->reset != NULL) {
+        (*klass->reset)(cpu);
+    }
+}
+
+static void cpu_common_reset(CPUState *cpu)
+{
+}
+
+static void cpu_class_init(ObjectClass *klass, void *data)
+{
+    CPUClass *k = CPU_CLASS(klass);
+
+    k->reset = cpu_common_reset;
+}
+
+static TypeInfo cpu_type_info = {
+    .name = TYPE_CPU,
+    .parent = TYPE_OBJECT,
+    .instance_size = sizeof(CPUState),
+    .abstract = true,
+    .class_size = sizeof(CPUClass),
+    .class_init = cpu_class_init,
+};
+
+static void cpu_register_types(void)
+{
+    type_register_static(&cpu_type_info);
+}
+
+type_init(cpu_register_types)