qdev: add a interface to register subclasses
[qemu.git] / hw / qdev.c
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 static bool qdev_hot_added = false;
35 static bool qdev_hot_removed = false;
36
37 /* This is a nasty hack to allow passing a NULL bus to qdev_create. */
38 static BusState *main_system_bus;
39 static void main_system_bus_create(void);
40
41 DeviceInfo *device_info_list;
42
43 static BusState *qbus_find_recursive(BusState *bus, const char *name,
44 const BusInfo *info);
45 static BusState *qbus_find(const char *path);
46
47 /* Register a new device type. */
48 static void qdev_subclass_init(ObjectClass *klass, void *data)
49 {
50 DeviceClass *dc = DEVICE_CLASS(klass);
51
52 dc->info = data;
53 dc->reset = dc->info->reset;
54
55 /* Poison to try to detect future uses */
56 dc->info->reset = NULL;
57 }
58
59 DeviceInfo *qdev_get_info(DeviceState *dev)
60 {
61 return DEVICE_GET_CLASS(dev)->info;
62 }
63
64 void qdev_register_subclass(DeviceInfo *info, const char *parent)
65 {
66 TypeInfo type_info = {};
67
68 assert(info->size >= sizeof(DeviceState));
69 assert(!info->next);
70
71 type_info.name = info->name;
72 type_info.parent = parent;
73 type_info.instance_size = info->size;
74 type_info.class_init = qdev_subclass_init;
75 type_info.class_data = info;
76
77 type_register_static(&type_info);
78
79 info->next = device_info_list;
80 device_info_list = info;
81 }
82
83 void qdev_register(DeviceInfo *info)
84 {
85 qdev_register_subclass(info, TYPE_DEVICE);
86 }
87
88 static DeviceInfo *qdev_find_info(BusInfo *bus_info, const char *name)
89 {
90 DeviceInfo *info;
91
92 /* first check device names */
93 for (info = device_info_list; info != NULL; info = info->next) {
94 if (bus_info && info->bus_info != bus_info)
95 continue;
96 if (strcmp(info->name, name) != 0)
97 continue;
98 return info;
99 }
100
101 /* failing that check the aliases */
102 for (info = device_info_list; info != NULL; info = info->next) {
103 if (bus_info && info->bus_info != bus_info)
104 continue;
105 if (!info->alias)
106 continue;
107 if (strcmp(info->alias, name) != 0)
108 continue;
109 return info;
110 }
111 return NULL;
112 }
113
114 bool qdev_exists(const char *name)
115 {
116 return !!qdev_find_info(NULL, name);
117 }
118 static void qdev_property_add_legacy(DeviceState *dev, Property *prop,
119 Error **errp);
120
121 static DeviceState *qdev_create_from_info(BusState *bus, DeviceInfo *info)
122 {
123 DeviceState *dev;
124 Property *prop;
125
126 assert(bus->info == info->bus_info);
127 dev = DEVICE(object_new(info->name));
128 dev->parent_bus = bus;
129 qdev_prop_set_defaults(dev, qdev_get_info(dev)->props);
130 qdev_prop_set_defaults(dev, dev->parent_bus->info->props);
131 qdev_prop_set_globals(dev);
132 QTAILQ_INSERT_HEAD(&bus->children, dev, sibling);
133 if (qdev_hotplug) {
134 assert(bus->allow_hotplug);
135 dev->hotplugged = 1;
136 qdev_hot_added = true;
137 }
138 dev->instance_id_alias = -1;
139 QTAILQ_INIT(&dev->properties);
140 dev->state = DEV_STATE_CREATED;
141
142 for (prop = qdev_get_info(dev)->props; prop && prop->name; prop++) {
143 qdev_property_add_legacy(dev, prop, NULL);
144 qdev_property_add_static(dev, prop, NULL);
145 }
146
147 for (prop = qdev_get_info(dev)->bus_info->props; prop && prop->name; prop++) {
148 qdev_property_add_legacy(dev, prop, NULL);
149 qdev_property_add_static(dev, prop, NULL);
150 }
151
152 qdev_property_add_str(dev, "type", qdev_get_type, NULL, NULL);
153
154 return dev;
155 }
156
157 /* Create a new device. This only initializes the device state structure
158 and allows properties to be set. qdev_init should be called to
159 initialize the actual device emulation. */
160 DeviceState *qdev_create(BusState *bus, const char *name)
161 {
162 DeviceState *dev;
163
164 dev = qdev_try_create(bus, name);
165 if (!dev) {
166 if (bus) {
167 hw_error("Unknown device '%s' for bus '%s'\n", name,
168 bus->info->name);
169 } else {
170 hw_error("Unknown device '%s' for default sysbus\n", name);
171 }
172 }
173
174 return dev;
175 }
176
177 DeviceState *qdev_try_create(BusState *bus, const char *name)
178 {
179 DeviceInfo *info;
180
181 if (!bus) {
182 bus = sysbus_get_default();
183 }
184
185 info = qdev_find_info(bus->info, name);
186 if (!info) {
187 return NULL;
188 }
189
190 return qdev_create_from_info(bus, info);
191 }
192
193 static void qdev_print_devinfo(DeviceInfo *info)
194 {
195 error_printf("name \"%s\", bus %s",
196 info->name, info->bus_info->name);
197 if (info->alias) {
198 error_printf(", alias \"%s\"", info->alias);
199 }
200 if (info->desc) {
201 error_printf(", desc \"%s\"", info->desc);
202 }
203 if (info->no_user) {
204 error_printf(", no-user");
205 }
206 error_printf("\n");
207 }
208
209 static int set_property(const char *name, const char *value, void *opaque)
210 {
211 DeviceState *dev = opaque;
212
213 if (strcmp(name, "driver") == 0)
214 return 0;
215 if (strcmp(name, "bus") == 0)
216 return 0;
217
218 if (qdev_prop_parse(dev, name, value) == -1) {
219 return -1;
220 }
221 return 0;
222 }
223
224 int qdev_device_help(QemuOpts *opts)
225 {
226 const char *driver;
227 DeviceInfo *info;
228 Property *prop;
229
230 driver = qemu_opt_get(opts, "driver");
231 if (driver && !strcmp(driver, "?")) {
232 for (info = device_info_list; info != NULL; info = info->next) {
233 if (info->no_user) {
234 continue; /* not available, don't show */
235 }
236 qdev_print_devinfo(info);
237 }
238 return 1;
239 }
240
241 if (!driver || !qemu_opt_get(opts, "?")) {
242 return 0;
243 }
244
245 info = qdev_find_info(NULL, driver);
246 if (!info) {
247 return 0;
248 }
249
250 for (prop = info->props; prop && prop->name; prop++) {
251 /*
252 * TODO Properties without a parser are just for dirty hacks.
253 * qdev_prop_ptr is the only such PropertyInfo. It's marked
254 * for removal. This conditional should be removed along with
255 * it.
256 */
257 if (!prop->info->parse) {
258 continue; /* no way to set it, don't show */
259 }
260 error_printf("%s.%s=%s\n", info->name, prop->name,
261 prop->info->legacy_name ?: prop->info->name);
262 }
263 for (prop = info->bus_info->props; prop && prop->name; prop++) {
264 if (!prop->info->parse) {
265 continue; /* no way to set it, don't show */
266 }
267 error_printf("%s.%s=%s\n", info->name, prop->name,
268 prop->info->legacy_name ?: prop->info->name);
269 }
270 return 1;
271 }
272
273 static DeviceState *qdev_get_peripheral(void)
274 {
275 static DeviceState *dev;
276
277 if (dev == NULL) {
278 dev = qdev_create(NULL, "container");
279 qdev_property_add_child(qdev_get_root(), "peripheral", dev, NULL);
280 qdev_init_nofail(dev);
281 }
282
283 return dev;
284 }
285
286 static DeviceState *qdev_get_peripheral_anon(void)
287 {
288 static DeviceState *dev;
289
290 if (dev == NULL) {
291 dev = qdev_create(NULL, "container");
292 qdev_property_add_child(qdev_get_root(), "peripheral-anon", dev, NULL);
293 qdev_init_nofail(dev);
294 }
295
296 return dev;
297 }
298
299 DeviceState *qdev_device_add(QemuOpts *opts)
300 {
301 const char *driver, *path, *id;
302 DeviceInfo *info;
303 DeviceState *qdev;
304 BusState *bus;
305
306 driver = qemu_opt_get(opts, "driver");
307 if (!driver) {
308 qerror_report(QERR_MISSING_PARAMETER, "driver");
309 return NULL;
310 }
311
312 /* find driver */
313 info = qdev_find_info(NULL, driver);
314 if (!info || info->no_user) {
315 qerror_report(QERR_INVALID_PARAMETER_VALUE, "driver", "a driver name");
316 error_printf_unless_qmp("Try with argument '?' for a list.\n");
317 return NULL;
318 }
319
320 /* find bus */
321 path = qemu_opt_get(opts, "bus");
322 if (path != NULL) {
323 bus = qbus_find(path);
324 if (!bus) {
325 return NULL;
326 }
327 if (bus->info != info->bus_info) {
328 qerror_report(QERR_BAD_BUS_FOR_DEVICE,
329 driver, bus->info->name);
330 return NULL;
331 }
332 } else {
333 bus = qbus_find_recursive(main_system_bus, NULL, info->bus_info);
334 if (!bus) {
335 qerror_report(QERR_NO_BUS_FOR_DEVICE,
336 info->name, info->bus_info->name);
337 return NULL;
338 }
339 }
340 if (qdev_hotplug && !bus->allow_hotplug) {
341 qerror_report(QERR_BUS_NO_HOTPLUG, bus->name);
342 return NULL;
343 }
344
345 /* create device, set properties */
346 qdev = qdev_create_from_info(bus, info);
347 id = qemu_opts_id(opts);
348 if (id) {
349 qdev->id = id;
350 qdev_property_add_child(qdev_get_peripheral(), qdev->id, qdev, NULL);
351 } else {
352 static int anon_count;
353 gchar *name = g_strdup_printf("device[%d]", anon_count++);
354 qdev_property_add_child(qdev_get_peripheral_anon(), name,
355 qdev, NULL);
356 g_free(name);
357 }
358 if (qemu_opt_foreach(opts, set_property, qdev, 1) != 0) {
359 qdev_free(qdev);
360 return NULL;
361 }
362 if (qdev_init(qdev) < 0) {
363 qerror_report(QERR_DEVICE_INIT_FAILED, driver);
364 return NULL;
365 }
366 qdev->opts = opts;
367 return qdev;
368 }
369
370 /* Initialize a device. Device properties should be set before calling
371 this function. IRQs and MMIO regions should be connected/mapped after
372 calling this function.
373 On failure, destroy the device and return negative value.
374 Return 0 on success. */
375 int qdev_init(DeviceState *dev)
376 {
377 int rc;
378
379 assert(dev->state == DEV_STATE_CREATED);
380 rc = qdev_get_info(dev)->init(dev, qdev_get_info(dev));
381 if (rc < 0) {
382 qdev_free(dev);
383 return rc;
384 }
385 if (qdev_get_info(dev)->vmsd) {
386 vmstate_register_with_alias_id(dev, -1, qdev_get_info(dev)->vmsd, dev,
387 dev->instance_id_alias,
388 dev->alias_required_for_version);
389 }
390 dev->state = DEV_STATE_INITIALIZED;
391 if (dev->hotplugged) {
392 device_reset(dev);
393 }
394 return 0;
395 }
396
397 void qdev_set_legacy_instance_id(DeviceState *dev, int alias_id,
398 int required_for_version)
399 {
400 assert(dev->state == DEV_STATE_CREATED);
401 dev->instance_id_alias = alias_id;
402 dev->alias_required_for_version = required_for_version;
403 }
404
405 int qdev_unplug(DeviceState *dev)
406 {
407 if (!dev->parent_bus->allow_hotplug) {
408 qerror_report(QERR_BUS_NO_HOTPLUG, dev->parent_bus->name);
409 return -1;
410 }
411 assert(qdev_get_info(dev)->unplug != NULL);
412
413 qdev_hot_removed = true;
414
415 return qdev_get_info(dev)->unplug(dev);
416 }
417
418 static int qdev_reset_one(DeviceState *dev, void *opaque)
419 {
420 device_reset(dev);
421
422 return 0;
423 }
424
425 BusState *sysbus_get_default(void)
426 {
427 if (!main_system_bus) {
428 main_system_bus_create();
429 }
430 return main_system_bus;
431 }
432
433 static int qbus_reset_one(BusState *bus, void *opaque)
434 {
435 if (bus->info->reset) {
436 return bus->info->reset(bus);
437 }
438 return 0;
439 }
440
441 void qdev_reset_all(DeviceState *dev)
442 {
443 qdev_walk_children(dev, qdev_reset_one, qbus_reset_one, NULL);
444 }
445
446 void qbus_reset_all_fn(void *opaque)
447 {
448 BusState *bus = opaque;
449 qbus_walk_children(bus, qdev_reset_one, qbus_reset_one, NULL);
450 }
451
452 /* can be used as ->unplug() callback for the simple cases */
453 int qdev_simple_unplug_cb(DeviceState *dev)
454 {
455 /* just zap it */
456 qdev_free(dev);
457 return 0;
458 }
459
460
461 /* Like qdev_init(), but terminate program via error_report() instead of
462 returning an error value. This is okay during machine creation.
463 Don't use for hotplug, because there callers need to recover from
464 failure. Exception: if you know the device's init() callback can't
465 fail, then qdev_init_nofail() can't fail either, and is therefore
466 usable even then. But relying on the device implementation that
467 way is somewhat unclean, and best avoided. */
468 void qdev_init_nofail(DeviceState *dev)
469 {
470 DeviceInfo *info = qdev_get_info(dev);
471
472 if (qdev_init(dev) < 0) {
473 error_report("Initialization of device %s failed", info->name);
474 exit(1);
475 }
476 }
477
478 static void qdev_property_del_all(DeviceState *dev)
479 {
480 while (!QTAILQ_EMPTY(&dev->properties)) {
481 DeviceProperty *prop = QTAILQ_FIRST(&dev->properties);
482
483 QTAILQ_REMOVE(&dev->properties, prop, node);
484
485 if (prop->release) {
486 prop->release(dev, prop->name, prop->opaque);
487 }
488
489 g_free(prop->name);
490 g_free(prop->type);
491 g_free(prop);
492 }
493 }
494
495 static void qdev_property_del_child(DeviceState *dev, DeviceState *child, Error **errp)
496 {
497 DeviceProperty *prop;
498
499 QTAILQ_FOREACH(prop, &dev->properties, node) {
500 if (strstart(prop->type, "child<", NULL) && prop->opaque == child) {
501 break;
502 }
503 }
504
505 g_assert(prop != NULL);
506
507 QTAILQ_REMOVE(&dev->properties, prop, node);
508
509 if (prop->release) {
510 prop->release(dev, prop->name, prop->opaque);
511 }
512
513 g_free(prop->name);
514 g_free(prop->type);
515 g_free(prop);
516 }
517
518 /* Unlink device from bus and free the structure. */
519 void qdev_free(DeviceState *dev)
520 {
521 BusState *bus;
522 Property *prop;
523
524 qdev_property_del_all(dev);
525
526 if (dev->state == DEV_STATE_INITIALIZED) {
527 while (dev->num_child_bus) {
528 bus = QLIST_FIRST(&dev->child_bus);
529 qbus_free(bus);
530 }
531 if (qdev_get_info(dev)->vmsd)
532 vmstate_unregister(dev, qdev_get_info(dev)->vmsd, dev);
533 if (qdev_get_info(dev)->exit)
534 qdev_get_info(dev)->exit(dev);
535 if (dev->opts)
536 qemu_opts_del(dev->opts);
537 }
538 QTAILQ_REMOVE(&dev->parent_bus->children, dev, sibling);
539 for (prop = qdev_get_info(dev)->props; prop && prop->name; prop++) {
540 if (prop->info->free) {
541 prop->info->free(dev, prop);
542 }
543 }
544 if (dev->parent) {
545 qdev_property_del_child(dev->parent, dev, NULL);
546 }
547 if (dev->ref != 0) {
548 qerror_report(QERR_DEVICE_IN_USE, dev->id?:"");
549 }
550 object_delete(OBJECT(dev));
551 }
552
553 void qdev_machine_creation_done(void)
554 {
555 /*
556 * ok, initial machine setup is done, starting from now we can
557 * only create hotpluggable devices
558 */
559 qdev_hotplug = 1;
560 }
561
562 bool qdev_machine_modified(void)
563 {
564 return qdev_hot_added || qdev_hot_removed;
565 }
566
567 /* Get a character (serial) device interface. */
568 CharDriverState *qdev_init_chardev(DeviceState *dev)
569 {
570 static int next_serial;
571
572 /* FIXME: This function needs to go away: use chardev properties! */
573 return serial_hds[next_serial++];
574 }
575
576 BusState *qdev_get_parent_bus(DeviceState *dev)
577 {
578 return dev->parent_bus;
579 }
580
581 void qdev_init_gpio_in(DeviceState *dev, qemu_irq_handler handler, int n)
582 {
583 assert(dev->num_gpio_in == 0);
584 dev->num_gpio_in = n;
585 dev->gpio_in = qemu_allocate_irqs(handler, dev, n);
586 }
587
588 void qdev_init_gpio_out(DeviceState *dev, qemu_irq *pins, int n)
589 {
590 assert(dev->num_gpio_out == 0);
591 dev->num_gpio_out = n;
592 dev->gpio_out = pins;
593 }
594
595 qemu_irq qdev_get_gpio_in(DeviceState *dev, int n)
596 {
597 assert(n >= 0 && n < dev->num_gpio_in);
598 return dev->gpio_in[n];
599 }
600
601 void qdev_connect_gpio_out(DeviceState * dev, int n, qemu_irq pin)
602 {
603 assert(n >= 0 && n < dev->num_gpio_out);
604 dev->gpio_out[n] = pin;
605 }
606
607 void qdev_set_nic_properties(DeviceState *dev, NICInfo *nd)
608 {
609 qdev_prop_set_macaddr(dev, "mac", nd->macaddr.a);
610 if (nd->vlan)
611 qdev_prop_set_vlan(dev, "vlan", nd->vlan);
612 if (nd->netdev)
613 qdev_prop_set_netdev(dev, "netdev", nd->netdev);
614 if (nd->nvectors != DEV_NVECTORS_UNSPECIFIED &&
615 qdev_prop_exists(dev, "vectors")) {
616 qdev_prop_set_uint32(dev, "vectors", nd->nvectors);
617 }
618 nd->instantiated = 1;
619 }
620
621 BusState *qdev_get_child_bus(DeviceState *dev, const char *name)
622 {
623 BusState *bus;
624
625 QLIST_FOREACH(bus, &dev->child_bus, sibling) {
626 if (strcmp(name, bus->name) == 0) {
627 return bus;
628 }
629 }
630 return NULL;
631 }
632
633 int qbus_walk_children(BusState *bus, qdev_walkerfn *devfn,
634 qbus_walkerfn *busfn, void *opaque)
635 {
636 DeviceState *dev;
637 int err;
638
639 if (busfn) {
640 err = busfn(bus, opaque);
641 if (err) {
642 return err;
643 }
644 }
645
646 QTAILQ_FOREACH(dev, &bus->children, sibling) {
647 err = qdev_walk_children(dev, devfn, busfn, opaque);
648 if (err < 0) {
649 return err;
650 }
651 }
652
653 return 0;
654 }
655
656 int qdev_walk_children(DeviceState *dev, qdev_walkerfn *devfn,
657 qbus_walkerfn *busfn, void *opaque)
658 {
659 BusState *bus;
660 int err;
661
662 if (devfn) {
663 err = devfn(dev, opaque);
664 if (err) {
665 return err;
666 }
667 }
668
669 QLIST_FOREACH(bus, &dev->child_bus, sibling) {
670 err = qbus_walk_children(bus, devfn, busfn, opaque);
671 if (err < 0) {
672 return err;
673 }
674 }
675
676 return 0;
677 }
678
679 static BusState *qbus_find_recursive(BusState *bus, const char *name,
680 const BusInfo *info)
681 {
682 DeviceState *dev;
683 BusState *child, *ret;
684 int match = 1;
685
686 if (name && (strcmp(bus->name, name) != 0)) {
687 match = 0;
688 }
689 if (info && (bus->info != info)) {
690 match = 0;
691 }
692 if (match) {
693 return bus;
694 }
695
696 QTAILQ_FOREACH(dev, &bus->children, sibling) {
697 QLIST_FOREACH(child, &dev->child_bus, sibling) {
698 ret = qbus_find_recursive(child, name, info);
699 if (ret) {
700 return ret;
701 }
702 }
703 }
704 return NULL;
705 }
706
707 DeviceState *qdev_find_recursive(BusState *bus, const char *id)
708 {
709 DeviceState *dev, *ret;
710 BusState *child;
711
712 QTAILQ_FOREACH(dev, &bus->children, sibling) {
713 if (dev->id && strcmp(dev->id, id) == 0)
714 return dev;
715 QLIST_FOREACH(child, &dev->child_bus, sibling) {
716 ret = qdev_find_recursive(child, id);
717 if (ret) {
718 return ret;
719 }
720 }
721 }
722 return NULL;
723 }
724
725 static void qbus_list_bus(DeviceState *dev)
726 {
727 BusState *child;
728 const char *sep = " ";
729
730 error_printf("child busses at \"%s\":",
731 dev->id ? dev->id : object_get_typename(OBJECT(dev)));
732 QLIST_FOREACH(child, &dev->child_bus, sibling) {
733 error_printf("%s\"%s\"", sep, child->name);
734 sep = ", ";
735 }
736 error_printf("\n");
737 }
738
739 static void qbus_list_dev(BusState *bus)
740 {
741 DeviceState *dev;
742 const char *sep = " ";
743
744 error_printf("devices at \"%s\":", bus->name);
745 QTAILQ_FOREACH(dev, &bus->children, sibling) {
746 error_printf("%s\"%s\"", sep, object_get_typename(OBJECT(dev)));
747 if (dev->id)
748 error_printf("/\"%s\"", dev->id);
749 sep = ", ";
750 }
751 error_printf("\n");
752 }
753
754 static BusState *qbus_find_bus(DeviceState *dev, char *elem)
755 {
756 BusState *child;
757
758 QLIST_FOREACH(child, &dev->child_bus, sibling) {
759 if (strcmp(child->name, elem) == 0) {
760 return child;
761 }
762 }
763 return NULL;
764 }
765
766 static DeviceState *qbus_find_dev(BusState *bus, char *elem)
767 {
768 DeviceState *dev;
769
770 /*
771 * try to match in order:
772 * (1) instance id, if present
773 * (2) driver name
774 * (3) driver alias, if present
775 */
776 QTAILQ_FOREACH(dev, &bus->children, sibling) {
777 if (dev->id && strcmp(dev->id, elem) == 0) {
778 return dev;
779 }
780 }
781 QTAILQ_FOREACH(dev, &bus->children, sibling) {
782 if (strcmp(object_get_typename(OBJECT(dev)), elem) == 0) {
783 return dev;
784 }
785 }
786 QTAILQ_FOREACH(dev, &bus->children, sibling) {
787 if (qdev_get_info(dev)->alias && strcmp(qdev_get_info(dev)->alias, elem) == 0) {
788 return dev;
789 }
790 }
791 return NULL;
792 }
793
794 static BusState *qbus_find(const char *path)
795 {
796 DeviceState *dev;
797 BusState *bus;
798 char elem[128];
799 int pos, len;
800
801 /* find start element */
802 if (path[0] == '/') {
803 bus = main_system_bus;
804 pos = 0;
805 } else {
806 if (sscanf(path, "%127[^/]%n", elem, &len) != 1) {
807 assert(!path[0]);
808 elem[0] = len = 0;
809 }
810 bus = qbus_find_recursive(main_system_bus, elem, NULL);
811 if (!bus) {
812 qerror_report(QERR_BUS_NOT_FOUND, elem);
813 return NULL;
814 }
815 pos = len;
816 }
817
818 for (;;) {
819 assert(path[pos] == '/' || !path[pos]);
820 while (path[pos] == '/') {
821 pos++;
822 }
823 if (path[pos] == '\0') {
824 return bus;
825 }
826
827 /* find device */
828 if (sscanf(path+pos, "%127[^/]%n", elem, &len) != 1) {
829 assert(0);
830 elem[0] = len = 0;
831 }
832 pos += len;
833 dev = qbus_find_dev(bus, elem);
834 if (!dev) {
835 qerror_report(QERR_DEVICE_NOT_FOUND, elem);
836 if (!monitor_cur_is_qmp()) {
837 qbus_list_dev(bus);
838 }
839 return NULL;
840 }
841
842 assert(path[pos] == '/' || !path[pos]);
843 while (path[pos] == '/') {
844 pos++;
845 }
846 if (path[pos] == '\0') {
847 /* last specified element is a device. If it has exactly
848 * one child bus accept it nevertheless */
849 switch (dev->num_child_bus) {
850 case 0:
851 qerror_report(QERR_DEVICE_NO_BUS, elem);
852 return NULL;
853 case 1:
854 return QLIST_FIRST(&dev->child_bus);
855 default:
856 qerror_report(QERR_DEVICE_MULTIPLE_BUSSES, elem);
857 if (!monitor_cur_is_qmp()) {
858 qbus_list_bus(dev);
859 }
860 return NULL;
861 }
862 }
863
864 /* find bus */
865 if (sscanf(path+pos, "%127[^/]%n", elem, &len) != 1) {
866 assert(0);
867 elem[0] = len = 0;
868 }
869 pos += len;
870 bus = qbus_find_bus(dev, elem);
871 if (!bus) {
872 qerror_report(QERR_BUS_NOT_FOUND, elem);
873 if (!monitor_cur_is_qmp()) {
874 qbus_list_bus(dev);
875 }
876 return NULL;
877 }
878 }
879 }
880
881 void qbus_create_inplace(BusState *bus, BusInfo *info,
882 DeviceState *parent, const char *name)
883 {
884 char *buf;
885 int i,len;
886
887 bus->info = info;
888 bus->parent = parent;
889
890 if (name) {
891 /* use supplied name */
892 bus->name = g_strdup(name);
893 } else if (parent && parent->id) {
894 /* parent device has id -> use it for bus name */
895 len = strlen(parent->id) + 16;
896 buf = g_malloc(len);
897 snprintf(buf, len, "%s.%d", parent->id, parent->num_child_bus);
898 bus->name = buf;
899 } else {
900 /* no id -> use lowercase bus type for bus name */
901 len = strlen(info->name) + 16;
902 buf = g_malloc(len);
903 len = snprintf(buf, len, "%s.%d", info->name,
904 parent ? parent->num_child_bus : 0);
905 for (i = 0; i < len; i++)
906 buf[i] = qemu_tolower(buf[i]);
907 bus->name = buf;
908 }
909
910 QTAILQ_INIT(&bus->children);
911 if (parent) {
912 QLIST_INSERT_HEAD(&parent->child_bus, bus, sibling);
913 parent->num_child_bus++;
914 } else if (bus != main_system_bus) {
915 /* TODO: once all bus devices are qdevified,
916 only reset handler for main_system_bus should be registered here. */
917 qemu_register_reset(qbus_reset_all_fn, bus);
918 }
919 }
920
921 BusState *qbus_create(BusInfo *info, DeviceState *parent, const char *name)
922 {
923 BusState *bus;
924
925 bus = g_malloc0(info->size);
926 bus->qdev_allocated = 1;
927 qbus_create_inplace(bus, info, parent, name);
928 return bus;
929 }
930
931 static void main_system_bus_create(void)
932 {
933 /* assign main_system_bus before qbus_create_inplace()
934 * in order to make "if (bus != main_system_bus)" work */
935 main_system_bus = g_malloc0(system_bus_info.size);
936 main_system_bus->qdev_allocated = 1;
937 qbus_create_inplace(main_system_bus, &system_bus_info, NULL,
938 "main-system-bus");
939 }
940
941 void qbus_free(BusState *bus)
942 {
943 DeviceState *dev;
944
945 while ((dev = QTAILQ_FIRST(&bus->children)) != NULL) {
946 qdev_free(dev);
947 }
948 if (bus->parent) {
949 QLIST_REMOVE(bus, sibling);
950 bus->parent->num_child_bus--;
951 } else {
952 assert(bus != main_system_bus); /* main_system_bus is never freed */
953 qemu_unregister_reset(qbus_reset_all_fn, bus);
954 }
955 g_free((void*)bus->name);
956 if (bus->qdev_allocated) {
957 g_free(bus);
958 }
959 }
960
961 #define qdev_printf(fmt, ...) monitor_printf(mon, "%*s" fmt, indent, "", ## __VA_ARGS__)
962 static void qbus_print(Monitor *mon, BusState *bus, int indent);
963
964 static void qdev_print_props(Monitor *mon, DeviceState *dev, Property *props,
965 const char *prefix, int indent)
966 {
967 char buf[64];
968
969 if (!props)
970 return;
971 while (props->name) {
972 /*
973 * TODO Properties without a print method are just for dirty
974 * hacks. qdev_prop_ptr is the only such PropertyInfo. It's
975 * marked for removal. The test props->info->print should be
976 * removed along with it.
977 */
978 if (props->info->print) {
979 props->info->print(dev, props, buf, sizeof(buf));
980 qdev_printf("%s-prop: %s = %s\n", prefix, props->name, buf);
981 }
982 props++;
983 }
984 }
985
986 static void qdev_print(Monitor *mon, DeviceState *dev, int indent)
987 {
988 BusState *child;
989 qdev_printf("dev: %s, id \"%s\"\n", object_get_typename(OBJECT(dev)),
990 dev->id ? dev->id : "");
991 indent += 2;
992 if (dev->num_gpio_in) {
993 qdev_printf("gpio-in %d\n", dev->num_gpio_in);
994 }
995 if (dev->num_gpio_out) {
996 qdev_printf("gpio-out %d\n", dev->num_gpio_out);
997 }
998 qdev_print_props(mon, dev, qdev_get_info(dev)->props, "dev", indent);
999 qdev_print_props(mon, dev, dev->parent_bus->info->props, "bus", indent);
1000 if (dev->parent_bus->info->print_dev)
1001 dev->parent_bus->info->print_dev(mon, dev, indent);
1002 QLIST_FOREACH(child, &dev->child_bus, sibling) {
1003 qbus_print(mon, child, indent);
1004 }
1005 }
1006
1007 static void qbus_print(Monitor *mon, BusState *bus, int indent)
1008 {
1009 struct DeviceState *dev;
1010
1011 qdev_printf("bus: %s\n", bus->name);
1012 indent += 2;
1013 qdev_printf("type %s\n", bus->info->name);
1014 QTAILQ_FOREACH(dev, &bus->children, sibling) {
1015 qdev_print(mon, dev, indent);
1016 }
1017 }
1018 #undef qdev_printf
1019
1020 void do_info_qtree(Monitor *mon)
1021 {
1022 if (main_system_bus)
1023 qbus_print(mon, main_system_bus, 0);
1024 }
1025
1026 void do_info_qdm(Monitor *mon)
1027 {
1028 DeviceInfo *info;
1029
1030 for (info = device_info_list; info != NULL; info = info->next) {
1031 qdev_print_devinfo(info);
1032 }
1033 }
1034
1035 int do_device_add(Monitor *mon, const QDict *qdict, QObject **ret_data)
1036 {
1037 QemuOpts *opts;
1038
1039 opts = qemu_opts_from_qdict(qemu_find_opts("device"), qdict);
1040 if (!opts) {
1041 return -1;
1042 }
1043 if (!monitor_cur_is_qmp() && qdev_device_help(opts)) {
1044 qemu_opts_del(opts);
1045 return 0;
1046 }
1047 if (!qdev_device_add(opts)) {
1048 qemu_opts_del(opts);
1049 return -1;
1050 }
1051 return 0;
1052 }
1053
1054 int do_device_del(Monitor *mon, const QDict *qdict, QObject **ret_data)
1055 {
1056 const char *id = qdict_get_str(qdict, "id");
1057 DeviceState *dev;
1058
1059 dev = qdev_find_recursive(main_system_bus, id);
1060 if (NULL == dev) {
1061 qerror_report(QERR_DEVICE_NOT_FOUND, id);
1062 return -1;
1063 }
1064 return qdev_unplug(dev);
1065 }
1066
1067 static int qdev_get_fw_dev_path_helper(DeviceState *dev, char *p, int size)
1068 {
1069 int l = 0;
1070
1071 if (dev && dev->parent_bus) {
1072 char *d;
1073 l = qdev_get_fw_dev_path_helper(dev->parent_bus->parent, p, size);
1074 if (dev->parent_bus->info->get_fw_dev_path) {
1075 d = dev->parent_bus->info->get_fw_dev_path(dev);
1076 l += snprintf(p + l, size - l, "%s", d);
1077 g_free(d);
1078 } else {
1079 l += snprintf(p + l, size - l, "%s", object_get_typename(OBJECT(dev)));
1080 }
1081 }
1082 l += snprintf(p + l , size - l, "/");
1083
1084 return l;
1085 }
1086
1087 char* qdev_get_fw_dev_path(DeviceState *dev)
1088 {
1089 char path[128];
1090 int l;
1091
1092 l = qdev_get_fw_dev_path_helper(dev, path, 128);
1093
1094 path[l-1] = '\0';
1095
1096 return strdup(path);
1097 }
1098
1099 char *qdev_get_type(DeviceState *dev, Error **errp)
1100 {
1101 return g_strdup(object_get_typename(OBJECT(dev)));
1102 }
1103
1104 void qdev_ref(DeviceState *dev)
1105 {
1106 dev->ref++;
1107 }
1108
1109 void qdev_unref(DeviceState *dev)
1110 {
1111 g_assert(dev->ref > 0);
1112 dev->ref--;
1113 }
1114
1115 void qdev_property_add(DeviceState *dev, const char *name, const char *type,
1116 DevicePropertyAccessor *get, DevicePropertyAccessor *set,
1117 DevicePropertyRelease *release,
1118 void *opaque, Error **errp)
1119 {
1120 DeviceProperty *prop = g_malloc0(sizeof(*prop));
1121
1122 prop->name = g_strdup(name);
1123 prop->type = g_strdup(type);
1124
1125 prop->get = get;
1126 prop->set = set;
1127 prop->release = release;
1128 prop->opaque = opaque;
1129
1130 QTAILQ_INSERT_TAIL(&dev->properties, prop, node);
1131 }
1132
1133 static DeviceProperty *qdev_property_find(DeviceState *dev, const char *name)
1134 {
1135 DeviceProperty *prop;
1136
1137 QTAILQ_FOREACH(prop, &dev->properties, node) {
1138 if (strcmp(prop->name, name) == 0) {
1139 return prop;
1140 }
1141 }
1142
1143 return NULL;
1144 }
1145
1146 void qdev_property_get(DeviceState *dev, Visitor *v, const char *name,
1147 Error **errp)
1148 {
1149 DeviceProperty *prop = qdev_property_find(dev, name);
1150
1151 if (prop == NULL) {
1152 error_set(errp, QERR_PROPERTY_NOT_FOUND, dev->id?:"", name);
1153 return;
1154 }
1155
1156 if (!prop->get) {
1157 error_set(errp, QERR_PERMISSION_DENIED);
1158 } else {
1159 prop->get(dev, v, prop->opaque, name, errp);
1160 }
1161 }
1162
1163 void qdev_property_set(DeviceState *dev, Visitor *v, const char *name,
1164 Error **errp)
1165 {
1166 DeviceProperty *prop = qdev_property_find(dev, name);
1167
1168 if (prop == NULL) {
1169 error_set(errp, QERR_PROPERTY_NOT_FOUND, dev->id?:"", name);
1170 return;
1171 }
1172
1173 if (!prop->set) {
1174 error_set(errp, QERR_PERMISSION_DENIED);
1175 } else {
1176 prop->set(dev, v, prop->opaque, name, errp);
1177 }
1178 }
1179
1180 const char *qdev_property_get_type(DeviceState *dev, const char *name, Error **errp)
1181 {
1182 DeviceProperty *prop = qdev_property_find(dev, name);
1183
1184 if (prop == NULL) {
1185 error_set(errp, QERR_PROPERTY_NOT_FOUND, dev->id?:"", name);
1186 return NULL;
1187 }
1188
1189 return prop->type;
1190 }
1191
1192 /**
1193 * Legacy property handling
1194 */
1195
1196 static void qdev_get_legacy_property(DeviceState *dev, Visitor *v, void *opaque,
1197 const char *name, Error **errp)
1198 {
1199 Property *prop = opaque;
1200
1201 char buffer[1024];
1202 char *ptr = buffer;
1203
1204 prop->info->print(dev, prop, buffer, sizeof(buffer));
1205 visit_type_str(v, &ptr, name, errp);
1206 }
1207
1208 static void qdev_set_legacy_property(DeviceState *dev, Visitor *v, void *opaque,
1209 const char *name, Error **errp)
1210 {
1211 Property *prop = opaque;
1212 Error *local_err = NULL;
1213 char *ptr = NULL;
1214 int ret;
1215
1216 if (dev->state != DEV_STATE_CREATED) {
1217 error_set(errp, QERR_PERMISSION_DENIED);
1218 return;
1219 }
1220
1221 visit_type_str(v, &ptr, name, &local_err);
1222 if (local_err) {
1223 error_propagate(errp, local_err);
1224 return;
1225 }
1226
1227 ret = prop->info->parse(dev, prop, ptr);
1228 error_set_from_qdev_prop_error(errp, ret, dev, prop, ptr);
1229 g_free(ptr);
1230 }
1231
1232 /**
1233 * @qdev_add_legacy_property - adds a legacy property
1234 *
1235 * Do not use this is new code! Properties added through this interface will
1236 * be given names and types in the "legacy" namespace.
1237 *
1238 * Legacy properties are always processed as strings. The format of the string
1239 * depends on the property type.
1240 */
1241 void qdev_property_add_legacy(DeviceState *dev, Property *prop,
1242 Error **errp)
1243 {
1244 gchar *name, *type;
1245
1246 name = g_strdup_printf("legacy-%s", prop->name);
1247 type = g_strdup_printf("legacy<%s>",
1248 prop->info->legacy_name ?: prop->info->name);
1249
1250 qdev_property_add(dev, name, type,
1251 prop->info->print ? qdev_get_legacy_property : NULL,
1252 prop->info->parse ? qdev_set_legacy_property : NULL,
1253 NULL,
1254 prop, errp);
1255
1256 g_free(type);
1257 g_free(name);
1258 }
1259
1260 /**
1261 * @qdev_property_add_static - add a @Property to a device.
1262 *
1263 * Static properties access data in a struct. The actual type of the
1264 * property and the field depends on the property type.
1265 */
1266 void qdev_property_add_static(DeviceState *dev, Property *prop,
1267 Error **errp)
1268 {
1269 qdev_property_add(dev, prop->name, prop->info->name,
1270 prop->info->get, prop->info->set,
1271 NULL,
1272 prop, errp);
1273 }
1274
1275 DeviceState *qdev_get_root(void)
1276 {
1277 static DeviceState *qdev_root;
1278
1279 if (!qdev_root) {
1280 qdev_root = qdev_create(NULL, "container");
1281 qdev_init_nofail(qdev_root);
1282 }
1283
1284 return qdev_root;
1285 }
1286
1287 static void qdev_get_child_property(DeviceState *dev, Visitor *v, void *opaque,
1288 const char *name, Error **errp)
1289 {
1290 DeviceState *child = opaque;
1291 gchar *path;
1292
1293 path = qdev_get_canonical_path(child);
1294 visit_type_str(v, &path, name, errp);
1295 g_free(path);
1296 }
1297
1298 static void qdev_release_child_property(DeviceState *dev, const char *name,
1299 void *opaque)
1300 {
1301 DeviceState *child = opaque;
1302
1303 qdev_unref(child);
1304 }
1305
1306 void qdev_property_add_child(DeviceState *dev, const char *name,
1307 DeviceState *child, Error **errp)
1308 {
1309 gchar *type;
1310
1311 type = g_strdup_printf("child<%s>", object_get_typename(OBJECT(child)));
1312
1313 qdev_property_add(dev, name, type, qdev_get_child_property,
1314 NULL, qdev_release_child_property,
1315 child, errp);
1316
1317 qdev_ref(child);
1318 g_assert(child->parent == NULL);
1319 child->parent = dev;
1320
1321 g_free(type);
1322 }
1323
1324 static void qdev_get_link_property(DeviceState *dev, Visitor *v, void *opaque,
1325 const char *name, Error **errp)
1326 {
1327 DeviceState **child = opaque;
1328 gchar *path;
1329
1330 if (*child) {
1331 path = qdev_get_canonical_path(*child);
1332 visit_type_str(v, &path, name, errp);
1333 g_free(path);
1334 } else {
1335 path = (gchar *)"";
1336 visit_type_str(v, &path, name, errp);
1337 }
1338 }
1339
1340 static void qdev_set_link_property(DeviceState *dev, Visitor *v, void *opaque,
1341 const char *name, Error **errp)
1342 {
1343 DeviceState **child = opaque;
1344 bool ambiguous = false;
1345 const char *type;
1346 char *path;
1347
1348 type = qdev_property_get_type(dev, name, NULL);
1349
1350 visit_type_str(v, &path, name, errp);
1351
1352 if (*child) {
1353 qdev_unref(*child);
1354 }
1355
1356 if (strcmp(path, "") != 0) {
1357 DeviceState *target;
1358
1359 target = qdev_resolve_path(path, &ambiguous);
1360 if (target) {
1361 gchar *target_type;
1362
1363 target_type = g_strdup_printf("link<%s>", object_get_typename(OBJECT(target)));
1364 if (strcmp(target_type, type) == 0) {
1365 *child = target;
1366 qdev_ref(target);
1367 } else {
1368 error_set(errp, QERR_INVALID_PARAMETER_TYPE, name, type);
1369 }
1370
1371 g_free(target_type);
1372 } else {
1373 error_set(errp, QERR_DEVICE_NOT_FOUND, path);
1374 }
1375 } else {
1376 *child = NULL;
1377 }
1378
1379 g_free(path);
1380 }
1381
1382 void qdev_property_add_link(DeviceState *dev, const char *name,
1383 const char *type, DeviceState **child,
1384 Error **errp)
1385 {
1386 gchar *full_type;
1387
1388 full_type = g_strdup_printf("link<%s>", type);
1389
1390 qdev_property_add(dev, name, full_type,
1391 qdev_get_link_property,
1392 qdev_set_link_property,
1393 NULL, child, errp);
1394
1395 g_free(full_type);
1396 }
1397
1398 gchar *qdev_get_canonical_path(DeviceState *dev)
1399 {
1400 DeviceState *root = qdev_get_root();
1401 char *newpath = NULL, *path = NULL;
1402
1403 while (dev != root) {
1404 DeviceProperty *prop = NULL;
1405
1406 g_assert(dev->parent != NULL);
1407
1408 QTAILQ_FOREACH(prop, &dev->parent->properties, node) {
1409 if (!strstart(prop->type, "child<", NULL)) {
1410 continue;
1411 }
1412
1413 if (prop->opaque == dev) {
1414 if (path) {
1415 newpath = g_strdup_printf("%s/%s", prop->name, path);
1416 g_free(path);
1417 path = newpath;
1418 } else {
1419 path = g_strdup(prop->name);
1420 }
1421 break;
1422 }
1423 }
1424
1425 g_assert(prop != NULL);
1426
1427 dev = dev->parent;
1428 }
1429
1430 newpath = g_strdup_printf("/%s", path);
1431 g_free(path);
1432
1433 return newpath;
1434 }
1435
1436 static DeviceState *qdev_resolve_abs_path(DeviceState *parent,
1437 gchar **parts,
1438 int index)
1439 {
1440 DeviceProperty *prop;
1441 DeviceState *child;
1442
1443 if (parts[index] == NULL) {
1444 return parent;
1445 }
1446
1447 if (strcmp(parts[index], "") == 0) {
1448 return qdev_resolve_abs_path(parent, parts, index + 1);
1449 }
1450
1451 prop = qdev_property_find(parent, parts[index]);
1452 if (prop == NULL) {
1453 return NULL;
1454 }
1455
1456 child = NULL;
1457 if (strstart(prop->type, "link<", NULL)) {
1458 DeviceState **pchild = prop->opaque;
1459 if (*pchild) {
1460 child = *pchild;
1461 }
1462 } else if (strstart(prop->type, "child<", NULL)) {
1463 child = prop->opaque;
1464 }
1465
1466 if (!child) {
1467 return NULL;
1468 }
1469
1470 return qdev_resolve_abs_path(child, parts, index + 1);
1471 }
1472
1473 static DeviceState *qdev_resolve_partial_path(DeviceState *parent,
1474 gchar **parts,
1475 bool *ambiguous)
1476 {
1477 DeviceState *dev;
1478 DeviceProperty *prop;
1479
1480 dev = qdev_resolve_abs_path(parent, parts, 0);
1481
1482 QTAILQ_FOREACH(prop, &parent->properties, node) {
1483 DeviceState *found;
1484
1485 if (!strstart(prop->type, "child<", NULL)) {
1486 continue;
1487 }
1488
1489 found = qdev_resolve_partial_path(prop->opaque, parts, ambiguous);
1490 if (found) {
1491 if (dev) {
1492 if (ambiguous) {
1493 *ambiguous = true;
1494 }
1495 return NULL;
1496 }
1497 dev = found;
1498 }
1499
1500 if (ambiguous && *ambiguous) {
1501 return NULL;
1502 }
1503 }
1504
1505 return dev;
1506 }
1507
1508 DeviceState *qdev_resolve_path(const char *path, bool *ambiguous)
1509 {
1510 bool partial_path = true;
1511 DeviceState *dev;
1512 gchar **parts;
1513
1514 parts = g_strsplit(path, "/", 0);
1515 if (parts == NULL || parts[0] == NULL) {
1516 g_strfreev(parts);
1517 return qdev_get_root();
1518 }
1519
1520 if (strcmp(parts[0], "") == 0) {
1521 partial_path = false;
1522 }
1523
1524 if (partial_path) {
1525 if (ambiguous) {
1526 *ambiguous = false;
1527 }
1528 dev = qdev_resolve_partial_path(qdev_get_root(), parts, ambiguous);
1529 } else {
1530 dev = qdev_resolve_abs_path(qdev_get_root(), parts, 1);
1531 }
1532
1533 g_strfreev(parts);
1534
1535 return dev;
1536 }
1537
1538 typedef struct StringProperty
1539 {
1540 char *(*get)(DeviceState *, Error **);
1541 void (*set)(DeviceState *, const char *, Error **);
1542 } StringProperty;
1543
1544 static void qdev_property_get_str(DeviceState *dev, Visitor *v, void *opaque,
1545 const char *name, Error **errp)
1546 {
1547 StringProperty *prop = opaque;
1548 char *value;
1549
1550 value = prop->get(dev, errp);
1551 if (value) {
1552 visit_type_str(v, &value, name, errp);
1553 g_free(value);
1554 }
1555 }
1556
1557 static void qdev_property_set_str(DeviceState *dev, Visitor *v, void *opaque,
1558 const char *name, Error **errp)
1559 {
1560 StringProperty *prop = opaque;
1561 char *value;
1562 Error *local_err = NULL;
1563
1564 visit_type_str(v, &value, name, &local_err);
1565 if (local_err) {
1566 error_propagate(errp, local_err);
1567 return;
1568 }
1569
1570 prop->set(dev, value, errp);
1571 g_free(value);
1572 }
1573
1574 static void qdev_property_release_str(DeviceState *dev, const char *name,
1575 void *opaque)
1576 {
1577 StringProperty *prop = opaque;
1578 g_free(prop);
1579 }
1580
1581 void qdev_property_add_str(DeviceState *dev, const char *name,
1582 char *(*get)(DeviceState *, Error **),
1583 void (*set)(DeviceState *, const char *, Error **),
1584 Error **errp)
1585 {
1586 StringProperty *prop = g_malloc0(sizeof(*prop));
1587
1588 prop->get = get;
1589 prop->set = set;
1590
1591 qdev_property_add(dev, name, "string",
1592 get ? qdev_property_get_str : NULL,
1593 set ? qdev_property_set_str : NULL,
1594 qdev_property_release_str,
1595 prop, errp);
1596 }
1597
1598 void qdev_machine_init(void)
1599 {
1600 qdev_get_peripheral_anon();
1601 qdev_get_peripheral();
1602 }
1603
1604 void device_reset(DeviceState *dev)
1605 {
1606 DeviceClass *klass = DEVICE_GET_CLASS(dev);
1607
1608 if (klass->reset) {
1609 klass->reset(dev);
1610 }
1611 }
1612
1613 static TypeInfo device_type_info = {
1614 .name = TYPE_DEVICE,
1615 .parent = TYPE_OBJECT,
1616 .instance_size = sizeof(DeviceState),
1617 .abstract = true,
1618 .class_size = sizeof(DeviceClass),
1619 };
1620
1621 static void init_qdev(void)
1622 {
1623 type_register_static(&device_type_info);
1624 }
1625
1626 device_init(init_qdev);