summary refs log tree commit diff stats
path: root/qom
diff options
context:
space:
mode:
Diffstat (limited to 'qom')
-rw-r--r--qom/Makefile1
-rw-r--r--qom/cpu.c58
-rw-r--r--qom/object.c51
3 files changed, 99 insertions, 11 deletions
diff --git a/qom/Makefile b/qom/Makefile
index 885a2631bb..34c6de558a 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 0000000000..5b360469c5
--- /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)
diff --git a/qom/object.c b/qom/object.c
index aa037d299f..9cd9506eb5 100644
--- a/qom/object.c
+++ b/qom/object.c
@@ -177,6 +177,19 @@ static size_t type_class_get_size(TypeImpl *ti)
     return sizeof(ObjectClass);
 }
 
+static size_t type_object_get_size(TypeImpl *ti)
+{
+    if (ti->instance_size) {
+        return ti->instance_size;
+    }
+
+    if (type_has_parent(ti)) {
+        return type_object_get_size(type_get_parent(ti));
+    }
+
+    return 0;
+}
+
 static void type_class_interface_init(TypeImpl *ti, InterfaceImpl *iface)
 {
     TypeInfo info = {
@@ -193,7 +206,7 @@ static void type_class_interface_init(TypeImpl *ti, InterfaceImpl *iface)
     g_free(name);
 }
 
-static void type_class_init(TypeImpl *ti)
+static void type_initialize(TypeImpl *ti)
 {
     size_t class_size = sizeof(ObjectClass);
     int i;
@@ -203,6 +216,7 @@ static void type_class_init(TypeImpl *ti)
     }
 
     ti->class_size = type_class_get_size(ti);
+    ti->instance_size = type_object_get_size(ti);
 
     ti->class = g_malloc0(ti->class_size);
     ti->class->type = ti;
@@ -210,7 +224,7 @@ static void type_class_init(TypeImpl *ti)
     if (type_has_parent(ti)) {
         TypeImpl *parent = type_get_parent(ti);
 
-        type_class_init(parent);
+        type_initialize(parent);
 
         class_size = parent->class_size;
         g_assert(parent->class_size <= ti->class_size);
@@ -264,9 +278,9 @@ void object_initialize_with_type(void *data, TypeImpl *type)
     Object *obj = data;
 
     g_assert(type != NULL);
-    g_assert(type->instance_size >= sizeof(Object));
+    type_initialize(type);
 
-    type_class_init(type);
+    g_assert(type->instance_size >= sizeof(Object));
     g_assert(type->abstract == false);
 
     memset(obj, 0, type->instance_size);
@@ -304,12 +318,9 @@ static void object_property_del_child(Object *obj, Object *child, Error **errp)
     ObjectProperty *prop;
 
     QTAILQ_FOREACH(prop, &obj->properties, node) {
-        if (!strstart(prop->type, "child<", NULL)) {
-            continue;
-        }
-
-        if (prop->opaque == child) {
+        if (strstart(prop->type, "child<", NULL) && prop->opaque == child) {
             object_property_del(obj, prop->name, errp);
+            break;
         }
     }
 }
@@ -356,6 +367,7 @@ Object *object_new_with_type(Type type)
     Object *obj;
 
     g_assert(type != NULL);
+    type_initialize(type);
 
     obj = g_malloc(type->instance_size);
     object_initialize_with_type(obj, type);
@@ -528,7 +540,7 @@ ObjectClass *object_class_by_name(const char *typename)
         return NULL;
     }
 
-    type_class_init(type);
+    type_initialize(type);
 
     return type->class;
 }
@@ -548,7 +560,7 @@ static void object_class_foreach_tramp(gpointer key, gpointer value,
     TypeImpl *type = value;
     ObjectClass *k;
 
-    type_class_init(type);
+    type_initialize(type);
     k = type->class;
 
     if (!data->include_abstract && type->abstract) {
@@ -572,6 +584,23 @@ void object_class_foreach(void (*fn)(ObjectClass *klass, void *opaque),
     g_hash_table_foreach(type_table_get(), object_class_foreach_tramp, &data);
 }
 
+static void object_class_get_list_tramp(ObjectClass *klass, void *opaque)
+{
+    GSList **list = opaque;
+
+    *list = g_slist_prepend(*list, klass);
+}
+
+GSList *object_class_get_list(const char *implements_type,
+                              bool include_abstract)
+{
+    GSList *list = NULL;
+
+    object_class_foreach(object_class_get_list_tramp,
+                         implements_type, include_abstract, &list);
+    return list;
+}
+
 void object_ref(Object *obj)
 {
     obj->ref++;