qemu

FORK: QEMU emulator
git clone https://git.neptards.moe/neptards/qemu.git
Log | Files | Refs | Submodules | LICENSE

qom-qmp-cmds.c (6810B)


      1 /*
      2  * QMP commands related to QOM
      3  *
      4  * Copyright IBM, Corp. 2011
      5  *
      6  * Authors:
      7  *  Anthony Liguori   <aliguori@us.ibm.com>
      8  *
      9  * This work is licensed under the terms of the GNU GPL, version 2.  See
     10  * the COPYING file in the top-level directory.
     11  *
     12  * Contributions after 2012-01-13 are licensed under the terms of the
     13  * GNU GPL, version 2 or (at your option) any later version.
     14  */
     15 
     16 #include "qemu/osdep.h"
     17 #include "block/qdict.h"
     18 #include "hw/qdev-core.h"
     19 #include "qapi/error.h"
     20 #include "qapi/qapi-commands-qdev.h"
     21 #include "qapi/qapi-commands-qom.h"
     22 #include "qapi/qapi-visit-qom.h"
     23 #include "qapi/qmp/qdict.h"
     24 #include "qapi/qmp/qerror.h"
     25 #include "qapi/qobject-input-visitor.h"
     26 #include "qapi/qobject-output-visitor.h"
     27 #include "qemu/cutils.h"
     28 #include "qom/object_interfaces.h"
     29 #include "qom/qom-qobject.h"
     30 
     31 ObjectPropertyInfoList *qmp_qom_list(const char *path, Error **errp)
     32 {
     33     Object *obj;
     34     bool ambiguous = false;
     35     ObjectPropertyInfoList *props = NULL;
     36     ObjectProperty *prop;
     37     ObjectPropertyIterator iter;
     38 
     39     obj = object_resolve_path(path, &ambiguous);
     40     if (obj == NULL) {
     41         if (ambiguous) {
     42             error_setg(errp, "Path '%s' is ambiguous", path);
     43         } else {
     44             error_set(errp, ERROR_CLASS_DEVICE_NOT_FOUND,
     45                       "Device '%s' not found", path);
     46         }
     47         return NULL;
     48     }
     49 
     50     object_property_iter_init(&iter, obj);
     51     while ((prop = object_property_iter_next(&iter))) {
     52         ObjectPropertyInfo *value = g_new0(ObjectPropertyInfo, 1);
     53 
     54         QAPI_LIST_PREPEND(props, value);
     55 
     56         value->name = g_strdup(prop->name);
     57         value->type = g_strdup(prop->type);
     58     }
     59 
     60     return props;
     61 }
     62 
     63 void qmp_qom_set(const char *path, const char *property, QObject *value,
     64                  Error **errp)
     65 {
     66     Object *obj;
     67 
     68     obj = object_resolve_path(path, NULL);
     69     if (!obj) {
     70         error_set(errp, ERROR_CLASS_DEVICE_NOT_FOUND,
     71                   "Device '%s' not found", path);
     72         return;
     73     }
     74 
     75     object_property_set_qobject(obj, property, value, errp);
     76 }
     77 
     78 QObject *qmp_qom_get(const char *path, const char *property, Error **errp)
     79 {
     80     Object *obj;
     81 
     82     obj = object_resolve_path(path, NULL);
     83     if (!obj) {
     84         error_set(errp, ERROR_CLASS_DEVICE_NOT_FOUND,
     85                   "Device '%s' not found", path);
     86         return NULL;
     87     }
     88 
     89     return object_property_get_qobject(obj, property, errp);
     90 }
     91 
     92 static void qom_list_types_tramp(ObjectClass *klass, void *data)
     93 {
     94     ObjectTypeInfoList **pret = data;
     95     ObjectTypeInfo *info;
     96     ObjectClass *parent = object_class_get_parent(klass);
     97 
     98     info = g_malloc0(sizeof(*info));
     99     info->name = g_strdup(object_class_get_name(klass));
    100     info->has_abstract = info->abstract = object_class_is_abstract(klass);
    101     if (parent) {
    102         info->has_parent = true;
    103         info->parent = g_strdup(object_class_get_name(parent));
    104     }
    105 
    106     QAPI_LIST_PREPEND(*pret, info);
    107 }
    108 
    109 ObjectTypeInfoList *qmp_qom_list_types(bool has_implements,
    110                                        const char *implements,
    111                                        bool has_abstract,
    112                                        bool abstract,
    113                                        Error **errp)
    114 {
    115     ObjectTypeInfoList *ret = NULL;
    116 
    117     module_load_qom_all();
    118     object_class_foreach(qom_list_types_tramp, implements, abstract, &ret);
    119 
    120     return ret;
    121 }
    122 
    123 ObjectPropertyInfoList *qmp_device_list_properties(const char *typename,
    124                                                 Error **errp)
    125 {
    126     ObjectClass *klass;
    127     Object *obj;
    128     ObjectProperty *prop;
    129     ObjectPropertyIterator iter;
    130     ObjectPropertyInfoList *prop_list = NULL;
    131 
    132     klass = module_object_class_by_name(typename);
    133     if (klass == NULL) {
    134         error_set(errp, ERROR_CLASS_DEVICE_NOT_FOUND,
    135                   "Device '%s' not found", typename);
    136         return NULL;
    137     }
    138 
    139     if (!object_class_dynamic_cast(klass, TYPE_DEVICE)
    140         || object_class_is_abstract(klass)) {
    141         error_setg(errp, QERR_INVALID_PARAMETER_VALUE, "typename",
    142                    "a non-abstract device type");
    143         return NULL;
    144     }
    145 
    146     obj = object_new(typename);
    147 
    148     object_property_iter_init(&iter, obj);
    149     while ((prop = object_property_iter_next(&iter))) {
    150         ObjectPropertyInfo *info;
    151 
    152         /* Skip Object and DeviceState properties */
    153         if (strcmp(prop->name, "type") == 0 ||
    154             strcmp(prop->name, "realized") == 0 ||
    155             strcmp(prop->name, "hotpluggable") == 0 ||
    156             strcmp(prop->name, "hotplugged") == 0 ||
    157             strcmp(prop->name, "parent_bus") == 0) {
    158             continue;
    159         }
    160 
    161         /* Skip legacy properties since they are just string versions of
    162          * properties that we already list.
    163          */
    164         if (strstart(prop->name, "legacy-", NULL)) {
    165             continue;
    166         }
    167 
    168         info = g_new0(ObjectPropertyInfo, 1);
    169         info->name = g_strdup(prop->name);
    170         info->type = g_strdup(prop->type);
    171         info->has_description = !!prop->description;
    172         info->description = g_strdup(prop->description);
    173         info->default_value = qobject_ref(prop->defval);
    174         info->has_default_value = !!info->default_value;
    175 
    176         QAPI_LIST_PREPEND(prop_list, info);
    177     }
    178 
    179     object_unref(obj);
    180 
    181     return prop_list;
    182 }
    183 
    184 ObjectPropertyInfoList *qmp_qom_list_properties(const char *typename,
    185                                              Error **errp)
    186 {
    187     ObjectClass *klass;
    188     Object *obj = NULL;
    189     ObjectProperty *prop;
    190     ObjectPropertyIterator iter;
    191     ObjectPropertyInfoList *prop_list = NULL;
    192 
    193     klass = object_class_by_name(typename);
    194     if (klass == NULL) {
    195         error_set(errp, ERROR_CLASS_DEVICE_NOT_FOUND,
    196                   "Class '%s' not found", typename);
    197         return NULL;
    198     }
    199 
    200     if (!object_class_dynamic_cast(klass, TYPE_OBJECT)) {
    201         error_setg(errp, QERR_INVALID_PARAMETER_VALUE, "typename",
    202                    "a QOM type");
    203         return NULL;
    204     }
    205 
    206     if (object_class_is_abstract(klass)) {
    207         object_class_property_iter_init(&iter, klass);
    208     } else {
    209         obj = object_new(typename);
    210         object_property_iter_init(&iter, obj);
    211     }
    212     while ((prop = object_property_iter_next(&iter))) {
    213         ObjectPropertyInfo *info;
    214 
    215         info = g_malloc0(sizeof(*info));
    216         info->name = g_strdup(prop->name);
    217         info->type = g_strdup(prop->type);
    218         info->has_description = !!prop->description;
    219         info->description = g_strdup(prop->description);
    220 
    221         QAPI_LIST_PREPEND(prop_list, info);
    222     }
    223 
    224     object_unref(obj);
    225 
    226     return prop_list;
    227 }
    228 
    229 void qmp_object_add(ObjectOptions *options, Error **errp)
    230 {
    231     user_creatable_add_qapi(options, errp);
    232 }
    233 
    234 void qmp_object_del(const char *id, Error **errp)
    235 {
    236     user_creatable_del(id, errp);
    237 }