aboutsummaryrefslogtreecommitdiff
path: root/hw/core/qdev-properties.c
diff options
context:
space:
mode:
Diffstat (limited to 'hw/core/qdev-properties.c')
-rw-r--r--hw/core/qdev-properties.c120
1 files changed, 120 insertions, 0 deletions
diff --git a/hw/core/qdev-properties.c b/hw/core/qdev-properties.c
index 509cbf155d..12a053e732 100644
--- a/hw/core/qdev-properties.c
+++ b/hw/core/qdev-properties.c
@@ -929,3 +929,123 @@ const PropertyInfo qdev_prop_link = {
.name = "link",
.create = create_link_property,
};
+
+void qdev_property_add_static(DeviceState *dev, Property *prop)
+{
+ Object *obj = OBJECT(dev);
+ ObjectProperty *op;
+
+ assert(!prop->info->create);
+
+ op = object_property_add(obj, prop->name, prop->info->name,
+ prop->info->get, prop->info->set,
+ prop->info->release,
+ prop);
+
+ object_property_set_description(obj, prop->name,
+ prop->info->description);
+
+ if (prop->set_default) {
+ prop->info->set_default_value(op, prop);
+ if (op->init) {
+ op->init(obj, op);
+ }
+ }
+}
+
+static void qdev_class_add_property(DeviceClass *klass, Property *prop)
+{
+ ObjectClass *oc = OBJECT_CLASS(klass);
+
+ if (prop->info->create) {
+ prop->info->create(oc, prop);
+ } else {
+ ObjectProperty *op;
+
+ op = object_class_property_add(oc,
+ prop->name, prop->info->name,
+ prop->info->get, prop->info->set,
+ prop->info->release,
+ prop);
+ if (prop->set_default) {
+ prop->info->set_default_value(op, prop);
+ }
+ }
+ object_class_property_set_description(oc, prop->name,
+ prop->info->description);
+}
+
+/**
+ * Legacy property handling
+ */
+
+static void qdev_get_legacy_property(Object *obj, Visitor *v,
+ const char *name, void *opaque,
+ Error **errp)
+{
+ DeviceState *dev = DEVICE(obj);
+ Property *prop = opaque;
+
+ char buffer[1024];
+ char *ptr = buffer;
+
+ prop->info->print(dev, prop, buffer, sizeof(buffer));
+ visit_type_str(v, name, &ptr, errp);
+}
+
+/**
+ * qdev_class_add_legacy_property:
+ * @dev: Device to add the property to.
+ * @prop: The qdev property definition.
+ *
+ * Add a legacy QOM property to @dev for qdev property @prop.
+ *
+ * Legacy properties are string versions of QOM properties. The format of
+ * the string depends on the property type. Legacy properties are only
+ * needed for "info qtree".
+ *
+ * Do not use this in new code! QOM Properties added through this interface
+ * will be given names in the "legacy" namespace.
+ */
+static void qdev_class_add_legacy_property(DeviceClass *dc, Property *prop)
+{
+ g_autofree char *name = NULL;
+
+ /* Register pointer properties as legacy properties */
+ if (!prop->info->print && prop->info->get) {
+ return;
+ }
+
+ name = g_strdup_printf("legacy-%s", prop->name);
+ object_class_property_add(OBJECT_CLASS(dc), name, "str",
+ prop->info->print ? qdev_get_legacy_property : prop->info->get,
+ NULL, NULL, prop);
+}
+
+void device_class_set_props(DeviceClass *dc, Property *props)
+{
+ Property *prop;
+
+ dc->props_ = props;
+ for (prop = props; prop && prop->name; prop++) {
+ qdev_class_add_legacy_property(dc, prop);
+ qdev_class_add_property(dc, prop);
+ }
+}
+
+void qdev_alias_all_properties(DeviceState *target, Object *source)
+{
+ ObjectClass *class;
+ Property *prop;
+
+ class = object_get_class(OBJECT(target));
+ do {
+ DeviceClass *dc = DEVICE_CLASS(class);
+
+ for (prop = dc->props_; prop && prop->name; prop++) {
+ object_property_add_alias(source, prop->name,
+ OBJECT(target), prop->name);
+ }
+ class = object_class_get_parent(class);
+ } while (class != object_class_by_name(TYPE_DEVICE));
+}