Statistics
| Branch: | Revision:

root / hw / qdev.c @ e23a1b33

History | View | Annotate | Download (20.5 kB)

1
/*
2
 *  Dynamic device configuration and creation.
3
 *
4
 *  Copyright (c) 2009 CodeSourcery
5
 *
6
 * This library is free software; you can redistribute it and/or
7
 * modify it under the terms of the GNU Lesser General Public
8
 * License as published by the Free Software Foundation; either
9
 * version 2 of the License, or (at your option) any later version.
10
 *
11
 * This library is distributed in the hope that it will be useful,
12
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14
 * Lesser General Public License for more details.
15
 *
16
 * You should have received a copy of the GNU Lesser General Public
17
 * License along with this library; if not, see <http://www.gnu.org/licenses/>.
18
 */
19

    
20
/* The theory here is that it should be possible to create a machine without
21
   knowledge of specific devices.  Historically board init routines have
22
   passed a bunch of arguments to each device, requiring the board know
23
   exactly which device it is dealing with.  This file provides an abstract
24
   API for device configuration and initialization.  Devices will generally
25
   inherit from a particular bus (e.g. PCI or I2C) rather than
26
   this API directly.  */
27

    
28
#include "net.h"
29
#include "qdev.h"
30
#include "sysemu.h"
31
#include "monitor.h"
32

    
33
static int qdev_hotplug = 0;
34

    
35
/* This is a nasty hack to allow passing a NULL bus to qdev_create.  */
36
static BusState *main_system_bus;
37

    
38
static DeviceInfo *device_info_list;
39

    
40
static BusState *qbus_find_recursive(BusState *bus, const char *name,
41
                                     const BusInfo *info);
42
static BusState *qbus_find(const char *path);
43

    
44
/* Register a new device type.  */
45
void qdev_register(DeviceInfo *info)
46
{
47
    assert(info->size >= sizeof(DeviceState));
48
    assert(!info->next);
49

    
50
    info->next = device_info_list;
51
    device_info_list = info;
52
}
53

    
54
static DeviceInfo *qdev_find_info(BusInfo *bus_info, const char *name)
55
{
56
    DeviceInfo *info;
57

    
58
    /* first check device names */
59
    for (info = device_info_list; info != NULL; info = info->next) {
60
        if (bus_info && info->bus_info != bus_info)
61
            continue;
62
        if (strcmp(info->name, name) != 0)
63
            continue;
64
        return info;
65
    }
66

    
67
    /* failing that check the aliases */
68
    for (info = device_info_list; info != NULL; info = info->next) {
69
        if (bus_info && info->bus_info != bus_info)
70
            continue;
71
        if (!info->alias)
72
            continue;
73
        if (strcmp(info->alias, name) != 0)
74
            continue;
75
        return info;
76
    }
77
    return NULL;
78
}
79

    
80
/* Create a new device.  This only initializes the device state structure
81
   and allows properties to be set.  qdev_init should be called to
82
   initialize the actual device emulation.  */
83
DeviceState *qdev_create(BusState *bus, const char *name)
84
{
85
    DeviceInfo *info;
86
    DeviceState *dev;
87

    
88
    if (!bus) {
89
        if (!main_system_bus) {
90
            main_system_bus = qbus_create(&system_bus_info, NULL, "main-system-bus");
91
        }
92
        bus = main_system_bus;
93
    }
94

    
95
    info = qdev_find_info(bus->info, name);
96
    if (!info) {
97
        hw_error("Unknown device '%s' for bus '%s'\n", name, bus->info->name);
98
    }
99

    
100
    dev = qemu_mallocz(info->size);
101
    dev->info = info;
102
    dev->parent_bus = bus;
103
    qdev_prop_set_defaults(dev, dev->info->props);
104
    qdev_prop_set_defaults(dev, dev->parent_bus->info->props);
105
    qdev_prop_set_compat(dev);
106
    QLIST_INSERT_HEAD(&bus->children, dev, sibling);
107
    if (qdev_hotplug) {
108
        assert(bus->allow_hotplug);
109
        dev->hotplugged = 1;
110
    }
111
    dev->state = DEV_STATE_CREATED;
112
    return dev;
113
}
114

    
115
static int qdev_print_devinfo(DeviceInfo *info, char *dest, int len)
116
{
117
    int pos = 0;
118
    int ret;
119

    
120
    ret = snprintf(dest+pos, len-pos, "name \"%s\", bus %s",
121
                   info->name, info->bus_info->name);
122
    pos += MIN(len-pos,ret);
123
    if (info->alias) {
124
        ret = snprintf(dest+pos, len-pos, ", alias \"%s\"", info->alias);
125
        pos += MIN(len-pos,ret);
126
    }
127
    if (info->desc) {
128
        ret = snprintf(dest+pos, len-pos, ", desc \"%s\"", info->desc);
129
        pos += MIN(len-pos,ret);
130
    }
131
    if (info->no_user) {
132
        ret = snprintf(dest+pos, len-pos, ", no-user");
133
        pos += MIN(len-pos,ret);
134
    }
135
    return pos;
136
}
137

    
138
static int set_property(const char *name, const char *value, void *opaque)
139
{
140
    DeviceState *dev = opaque;
141

    
142
    if (strcmp(name, "driver") == 0)
143
        return 0;
144
    if (strcmp(name, "bus") == 0)
145
        return 0;
146

    
147
    if (qdev_prop_parse(dev, name, value) == -1) {
148
        qemu_error("can't set property \"%s\" to \"%s\" for \"%s\"\n",
149
                   name, value, dev->info->name);
150
        return -1;
151
    }
152
    return 0;
153
}
154

    
155
DeviceState *qdev_device_add(QemuOpts *opts)
156
{
157
    const char *driver, *path, *id;
158
    DeviceInfo *info;
159
    DeviceState *qdev;
160
    BusState *bus;
161

    
162
    driver = qemu_opt_get(opts, "driver");
163
    if (!driver) {
164
        qemu_error("-device: no driver specified\n");
165
        return NULL;
166
    }
167
    if (strcmp(driver, "?") == 0) {
168
        char msg[256];
169
        for (info = device_info_list; info != NULL; info = info->next) {
170
            qdev_print_devinfo(info, msg, sizeof(msg));
171
            qemu_error("%s\n", msg);
172
        }
173
        return NULL;
174
    }
175

    
176
    /* find driver */
177
    info = qdev_find_info(NULL, driver);
178
    if (!info) {
179
        qemu_error("Device \"%s\" not found.  Try -device '?' for a list.\n",
180
                   driver);
181
        return NULL;
182
    }
183
    if (info->no_user) {
184
        qemu_error("device \"%s\" can't be added via command line\n",
185
                   info->name);
186
        return NULL;
187
    }
188

    
189
    /* find bus */
190
    path = qemu_opt_get(opts, "bus");
191
    if (path != NULL) {
192
        bus = qbus_find(path);
193
    } else {
194
        bus = qbus_find_recursive(main_system_bus, NULL, info->bus_info);
195
    }
196
    if (!bus) {
197
        qemu_error("Did not find %s bus for %s\n",
198
                   path ? path : info->bus_info->name, info->name);
199
        return NULL;
200
    }
201
    if (qdev_hotplug && !bus->allow_hotplug) {
202
        qemu_error("Bus %s does not support hotplugging\n",
203
                   bus->name);
204
        return NULL;
205
    }
206

    
207
    /* create device, set properties */
208
    qdev = qdev_create(bus, driver);
209
    id = qemu_opts_id(opts);
210
    if (id) {
211
        qdev->id = id;
212
    }
213
    if (qemu_opt_foreach(opts, set_property, qdev, 1) != 0) {
214
        qdev_free(qdev);
215
        return NULL;
216
    }
217
    if (qdev_init(qdev) != 0) {
218
        qemu_error("Error initializing device %s\n", driver);
219
        return NULL;
220
    }
221
    qdev->opts = opts;
222
    return qdev;
223
}
224

    
225
static void qdev_reset(void *opaque)
226
{
227
    DeviceState *dev = opaque;
228
    if (dev->info->reset)
229
        dev->info->reset(dev);
230
}
231

    
232
/* Initialize a device.  Device properties should be set before calling
233
   this function.  IRQs and MMIO regions should be connected/mapped after
234
   calling this function.
235
   On failure, destroy the device and return negative value.
236
   Return 0 on success.  */
237
int qdev_init(DeviceState *dev)
238
{
239
    int rc;
240

    
241
    assert(dev->state == DEV_STATE_CREATED);
242
    rc = dev->info->init(dev, dev->info);
243
    if (rc < 0) {
244
        qdev_free(dev);
245
        return rc;
246
    }
247
    qemu_register_reset(qdev_reset, dev);
248
    if (dev->info->vmsd)
249
        vmstate_register(-1, dev->info->vmsd, dev);
250
    dev->state = DEV_STATE_INITIALIZED;
251
    return 0;
252
}
253

    
254
int qdev_unplug(DeviceState *dev)
255
{
256
    if (!dev->parent_bus->allow_hotplug) {
257
        qemu_error("Bus %s does not support hotplugging\n",
258
                   dev->parent_bus->name);
259
        return -1;
260
    }
261
    return dev->info->unplug(dev);
262
}
263

    
264
/* can be used as ->unplug() callback for the simple cases */
265
int qdev_simple_unplug_cb(DeviceState *dev)
266
{
267
    /* just zap it */
268
    qdev_free(dev);
269
    return 0;
270
}
271

    
272
/* Like qdev_init(), but terminate program via hw_error() instead of
273
   returning an error value.  This is okay during machine creation.
274
   Don't use for hotplug, because there callers need to recover from
275
   failure.  Exception: if you know the device's init() callback can't
276
   fail, then qdev_init_nofail() can't fail either, and is therefore
277
   usable even then.  But relying on the device implementation that
278
   way is somewhat unclean, and best avoided.  */
279
void qdev_init_nofail(DeviceState *dev)
280
{
281
    DeviceInfo *info = dev->info;
282

    
283
    if (qdev_init(dev) < 0)
284
        hw_error("Initialization of device %s failed\n", info->name);
285
}
286

    
287
/* Unlink device from bus and free the structure.  */
288
void qdev_free(DeviceState *dev)
289
{
290
    BusState *bus;
291

    
292
    if (dev->state == DEV_STATE_INITIALIZED) {
293
        while (dev->num_child_bus) {
294
            bus = QLIST_FIRST(&dev->child_bus);
295
            qbus_free(bus);
296
        }
297
#if 0 /* FIXME: need sane vmstate_unregister function */
298
        if (dev->info->vmsd)
299
            vmstate_unregister(dev->info->vmsd, dev);
300
#endif
301
        if (dev->info->exit)
302
            dev->info->exit(dev);
303
        if (dev->opts)
304
            qemu_opts_del(dev->opts);
305
    }
306
    qemu_unregister_reset(qdev_reset, dev);
307
    QLIST_REMOVE(dev, sibling);
308
    qemu_free(dev);
309
}
310

    
311
void qdev_machine_creation_done(void)
312
{
313
    /*
314
     * ok, initial machine setup is done, starting from now we can
315
     * only create hotpluggable devices
316
     */
317
    qdev_hotplug = 1;
318
}
319

    
320
/* Get a character (serial) device interface.  */
321
CharDriverState *qdev_init_chardev(DeviceState *dev)
322
{
323
    static int next_serial;
324
    static int next_virtconsole;
325
    /* FIXME: This is a nasty hack that needs to go away.  */
326
    if (strncmp(dev->info->name, "virtio", 6) == 0) {
327
        return virtcon_hds[next_virtconsole++];
328
    } else {
329
        return serial_hds[next_serial++];
330
    }
331
}
332

    
333
BusState *qdev_get_parent_bus(DeviceState *dev)
334
{
335
    return dev->parent_bus;
336
}
337

    
338
void qdev_init_gpio_in(DeviceState *dev, qemu_irq_handler handler, int n)
339
{
340
    assert(dev->num_gpio_in == 0);
341
    dev->num_gpio_in = n;
342
    dev->gpio_in = qemu_allocate_irqs(handler, dev, n);
343
}
344

    
345
void qdev_init_gpio_out(DeviceState *dev, qemu_irq *pins, int n)
346
{
347
    assert(dev->num_gpio_out == 0);
348
    dev->num_gpio_out = n;
349
    dev->gpio_out = pins;
350
}
351

    
352
qemu_irq qdev_get_gpio_in(DeviceState *dev, int n)
353
{
354
    assert(n >= 0 && n < dev->num_gpio_in);
355
    return dev->gpio_in[n];
356
}
357

    
358
void qdev_connect_gpio_out(DeviceState * dev, int n, qemu_irq pin)
359
{
360
    assert(n >= 0 && n < dev->num_gpio_out);
361
    dev->gpio_out[n] = pin;
362
}
363

    
364
VLANClientState *qdev_get_vlan_client(DeviceState *dev,
365
                                      NetCanReceive *can_receive,
366
                                      NetReceive *receive,
367
                                      NetReceiveIOV *receive_iov,
368
                                      NetCleanup *cleanup,
369
                                      void *opaque)
370
{
371
    NICInfo *nd = dev->nd;
372
    assert(nd);
373
    nd->vc = qemu_new_vlan_client(nd->vlan, nd->model, nd->name, can_receive,
374
                                  receive, receive_iov, cleanup, opaque);
375
    return nd->vc;
376
}
377

    
378

    
379
void qdev_get_macaddr(DeviceState *dev, uint8_t *macaddr)
380
{
381
    memcpy(macaddr, dev->nd->macaddr, 6);
382
}
383

    
384
static int next_block_unit[IF_COUNT];
385

    
386
/* Get a block device.  This should only be used for single-drive devices
387
   (e.g. SD/Floppy/MTD).  Multi-disk devices (scsi/ide) should use the
388
   appropriate bus.  */
389
BlockDriverState *qdev_init_bdrv(DeviceState *dev, BlockInterfaceType type)
390
{
391
    int unit = next_block_unit[type]++;
392
    DriveInfo *dinfo;
393

    
394
    dinfo = drive_get(type, 0, unit);
395
    return dinfo ? dinfo->bdrv : NULL;
396
}
397

    
398
BusState *qdev_get_child_bus(DeviceState *dev, const char *name)
399
{
400
    BusState *bus;
401

    
402
    QLIST_FOREACH(bus, &dev->child_bus, sibling) {
403
        if (strcmp(name, bus->name) == 0) {
404
            return bus;
405
        }
406
    }
407
    return NULL;
408
}
409

    
410
static BusState *qbus_find_recursive(BusState *bus, const char *name,
411
                                     const BusInfo *info)
412
{
413
    DeviceState *dev;
414
    BusState *child, *ret;
415
    int match = 1;
416

    
417
    if (name && (strcmp(bus->name, name) != 0)) {
418
        match = 0;
419
    }
420
    if (info && (bus->info != info)) {
421
        match = 0;
422
    }
423
    if (match) {
424
        return bus;
425
    }
426

    
427
    QLIST_FOREACH(dev, &bus->children, sibling) {
428
        QLIST_FOREACH(child, &dev->child_bus, sibling) {
429
            ret = qbus_find_recursive(child, name, info);
430
            if (ret) {
431
                return ret;
432
            }
433
        }
434
    }
435
    return NULL;
436
}
437

    
438
static DeviceState *qdev_find_recursive(BusState *bus, const char *id)
439
{
440
    DeviceState *dev, *ret;
441
    BusState *child;
442

    
443
    QLIST_FOREACH(dev, &bus->children, sibling) {
444
        if (dev->id && strcmp(dev->id, id) == 0)
445
            return dev;
446
        QLIST_FOREACH(child, &dev->child_bus, sibling) {
447
            ret = qdev_find_recursive(child, id);
448
            if (ret) {
449
                return ret;
450
            }
451
        }
452
    }
453
    return NULL;
454
}
455

    
456
static void qbus_list_bus(DeviceState *dev, char *dest, int len)
457
{
458
    BusState *child;
459
    const char *sep = " ";
460
    int pos = 0;
461

    
462
    pos += snprintf(dest+pos, len-pos,"child busses at \"%s\":",
463
                    dev->id ? dev->id : dev->info->name);
464
    QLIST_FOREACH(child, &dev->child_bus, sibling) {
465
        pos += snprintf(dest+pos, len-pos, "%s\"%s\"", sep, child->name);
466
        sep = ", ";
467
    }
468
}
469

    
470
static void qbus_list_dev(BusState *bus, char *dest, int len)
471
{
472
    DeviceState *dev;
473
    const char *sep = " ";
474
    int pos = 0;
475

    
476
    pos += snprintf(dest+pos, len-pos, "devices at \"%s\":",
477
                    bus->name);
478
    QLIST_FOREACH(dev, &bus->children, sibling) {
479
        pos += snprintf(dest+pos, len-pos, "%s\"%s\"",
480
                        sep, dev->info->name);
481
        if (dev->id)
482
            pos += snprintf(dest+pos, len-pos, "/\"%s\"", dev->id);
483
        sep = ", ";
484
    }
485
}
486

    
487
static BusState *qbus_find_bus(DeviceState *dev, char *elem)
488
{
489
    BusState *child;
490

    
491
    QLIST_FOREACH(child, &dev->child_bus, sibling) {
492
        if (strcmp(child->name, elem) == 0) {
493
            return child;
494
        }
495
    }
496
    return NULL;
497
}
498

    
499
static DeviceState *qbus_find_dev(BusState *bus, char *elem)
500
{
501
    DeviceState *dev;
502

    
503
    /*
504
     * try to match in order:
505
     *   (1) instance id, if present
506
     *   (2) driver name
507
     *   (3) driver alias, if present
508
     */
509
    QLIST_FOREACH(dev, &bus->children, sibling) {
510
        if (dev->id  &&  strcmp(dev->id, elem) == 0) {
511
            return dev;
512
        }
513
    }
514
    QLIST_FOREACH(dev, &bus->children, sibling) {
515
        if (strcmp(dev->info->name, elem) == 0) {
516
            return dev;
517
        }
518
    }
519
    QLIST_FOREACH(dev, &bus->children, sibling) {
520
        if (dev->info->alias && strcmp(dev->info->alias, elem) == 0) {
521
            return dev;
522
        }
523
    }
524
    return NULL;
525
}
526

    
527
static BusState *qbus_find(const char *path)
528
{
529
    DeviceState *dev;
530
    BusState *bus;
531
    char elem[128], msg[256];
532
    int pos, len;
533

    
534
    /* find start element */
535
    if (path[0] == '/') {
536
        bus = main_system_bus;
537
        pos = 0;
538
    } else {
539
        if (sscanf(path, "%127[^/]%n", elem, &len) != 1) {
540
            qemu_error("path parse error (\"%s\")\n", path);
541
            return NULL;
542
        }
543
        bus = qbus_find_recursive(main_system_bus, elem, NULL);
544
        if (!bus) {
545
            qemu_error("bus \"%s\" not found\n", elem);
546
            return NULL;
547
        }
548
        pos = len;
549
    }
550

    
551
    for (;;) {
552
        if (path[pos] == '\0') {
553
            /* we are done */
554
            return bus;
555
        }
556

    
557
        /* find device */
558
        if (sscanf(path+pos, "/%127[^/]%n", elem, &len) != 1) {
559
            qemu_error("path parse error (\"%s\" pos %d)\n", path, pos);
560
            return NULL;
561
        }
562
        pos += len;
563
        dev = qbus_find_dev(bus, elem);
564
        if (!dev) {
565
            qbus_list_dev(bus, msg, sizeof(msg));
566
            qemu_error("device \"%s\" not found\n%s\n", elem, msg);
567
            return NULL;
568
        }
569
        if (path[pos] == '\0') {
570
            /* last specified element is a device.  If it has exactly
571
             * one child bus accept it nevertheless */
572
            switch (dev->num_child_bus) {
573
            case 0:
574
                qemu_error("device has no child bus (%s)\n", path);
575
                return NULL;
576
            case 1:
577
                return QLIST_FIRST(&dev->child_bus);
578
            default:
579
                qbus_list_bus(dev, msg, sizeof(msg));
580
                qemu_error("device has multiple child busses (%s)\n%s\n",
581
                           path, msg);
582
                return NULL;
583
            }
584
        }
585

    
586
        /* find bus */
587
        if (sscanf(path+pos, "/%127[^/]%n", elem, &len) != 1) {
588
            qemu_error("path parse error (\"%s\" pos %d)\n", path, pos);
589
            return NULL;
590
        }
591
        pos += len;
592
        bus = qbus_find_bus(dev, elem);
593
        if (!bus) {
594
            qbus_list_bus(dev, msg, sizeof(msg));
595
            qemu_error("child bus \"%s\" not found\n%s\n", elem, msg);
596
            return NULL;
597
        }
598
    }
599
}
600

    
601
void qbus_create_inplace(BusState *bus, BusInfo *info,
602
                         DeviceState *parent, const char *name)
603
{
604
    char *buf;
605
    int i,len;
606

    
607
    bus->info = info;
608
    bus->parent = parent;
609

    
610
    if (name) {
611
        /* use supplied name */
612
        bus->name = qemu_strdup(name);
613
    } else if (parent && parent->id) {
614
        /* parent device has id -> use it for bus name */
615
        len = strlen(parent->id) + 16;
616
        buf = qemu_malloc(len);
617
        snprintf(buf, len, "%s.%d", parent->id, parent->num_child_bus);
618
        bus->name = buf;
619
    } else {
620
        /* no id -> use lowercase bus type for bus name */
621
        len = strlen(info->name) + 16;
622
        buf = qemu_malloc(len);
623
        len = snprintf(buf, len, "%s.%d", info->name,
624
                       parent ? parent->num_child_bus : 0);
625
        for (i = 0; i < len; i++)
626
            buf[i] = qemu_tolower(buf[i]);
627
        bus->name = buf;
628
    }
629

    
630
    QLIST_INIT(&bus->children);
631
    if (parent) {
632
        QLIST_INSERT_HEAD(&parent->child_bus, bus, sibling);
633
        parent->num_child_bus++;
634
    }
635

    
636
}
637

    
638
BusState *qbus_create(BusInfo *info, DeviceState *parent, const char *name)
639
{
640
    BusState *bus;
641

    
642
    bus = qemu_mallocz(info->size);
643
    bus->qdev_allocated = 1;
644
    qbus_create_inplace(bus, info, parent, name);
645
    return bus;
646
}
647

    
648
void qbus_free(BusState *bus)
649
{
650
    DeviceState *dev;
651

    
652
    while ((dev = QLIST_FIRST(&bus->children)) != NULL) {
653
        qdev_free(dev);
654
    }
655
    if (bus->parent) {
656
        QLIST_REMOVE(bus, sibling);
657
        bus->parent->num_child_bus--;
658
    }
659
    if (bus->qdev_allocated) {
660
        qemu_free(bus);
661
    }
662
}
663

    
664
#define qdev_printf(fmt, ...) monitor_printf(mon, "%*s" fmt, indent, "", ## __VA_ARGS__)
665
static void qbus_print(Monitor *mon, BusState *bus, int indent);
666

    
667
static void qdev_print_props(Monitor *mon, DeviceState *dev, Property *props,
668
                             const char *prefix, int indent)
669
{
670
    char buf[64];
671

    
672
    if (!props)
673
        return;
674
    while (props->name) {
675
        if (props->info->print) {
676
            props->info->print(dev, props, buf, sizeof(buf));
677
            qdev_printf("%s-prop: %s = %s\n", prefix, props->name, buf);
678
        }
679
        props++;
680
    }
681
}
682

    
683
static void qdev_print(Monitor *mon, DeviceState *dev, int indent)
684
{
685
    BusState *child;
686
    qdev_printf("dev: %s, id \"%s\"\n", dev->info->name,
687
                dev->id ? dev->id : "");
688
    indent += 2;
689
    if (dev->num_gpio_in) {
690
        qdev_printf("gpio-in %d\n", dev->num_gpio_in);
691
    }
692
    if (dev->num_gpio_out) {
693
        qdev_printf("gpio-out %d\n", dev->num_gpio_out);
694
    }
695
    qdev_print_props(mon, dev, dev->info->props, "dev", indent);
696
    qdev_print_props(mon, dev, dev->parent_bus->info->props, "bus", indent);
697
    if (dev->parent_bus->info->print_dev)
698
        dev->parent_bus->info->print_dev(mon, dev, indent);
699
    QLIST_FOREACH(child, &dev->child_bus, sibling) {
700
        qbus_print(mon, child, indent);
701
    }
702
}
703

    
704
static void qbus_print(Monitor *mon, BusState *bus, int indent)
705
{
706
    struct DeviceState *dev;
707

    
708
    qdev_printf("bus: %s\n", bus->name);
709
    indent += 2;
710
    qdev_printf("type %s\n", bus->info->name);
711
    QLIST_FOREACH(dev, &bus->children, sibling) {
712
        qdev_print(mon, dev, indent);
713
    }
714
}
715
#undef qdev_printf
716

    
717
void do_info_qtree(Monitor *mon)
718
{
719
    if (main_system_bus)
720
        qbus_print(mon, main_system_bus, 0);
721
}
722

    
723
void do_info_qdm(Monitor *mon)
724
{
725
    DeviceInfo *info;
726
    char msg[256];
727

    
728
    for (info = device_info_list; info != NULL; info = info->next) {
729
        qdev_print_devinfo(info, msg, sizeof(msg));
730
        monitor_printf(mon, "%s\n", msg);
731
    }
732
}
733

    
734
void do_device_add(Monitor *mon, const QDict *qdict)
735
{
736
    QemuOpts *opts;
737

    
738
    opts = qemu_opts_parse(&qemu_device_opts,
739
                           qdict_get_str(qdict, "config"), "driver");
740
    if (opts)
741
        qdev_device_add(opts);
742
}
743

    
744
void do_device_del(Monitor *mon, const QDict *qdict)
745
{
746
    const char *id = qdict_get_str(qdict, "id");
747
    DeviceState *dev;
748

    
749
    dev = qdev_find_recursive(main_system_bus, id);
750
    if (NULL == dev) {
751
        qemu_error("Device '%s' not found\n", id);
752
        return;
753
    }
754
    qdev_unplug(dev);
755
}