Jan Kiszka <jan.kis...@web.de> writes: > From: Jan Kiszka <jan.kis...@siemens.com> > > Add qdev_iterate_recursive to walk the complete qtree invoking a > callback for each device. Use this service to implement > qdev_find_id_recursive. > > Signed-off-by: Jan Kiszka <jan.kis...@siemens.com> > --- > hw/qdev.c | 29 +++++++++++++++++++++++++---- > hw/qdev.h | 3 +++ > 2 files changed, 28 insertions(+), 4 deletions(-) > > diff --git a/hw/qdev.c b/hw/qdev.c > index 2d1d171..466d8d5 100644 > --- a/hw/qdev.c > +++ b/hw/qdev.c > @@ -475,16 +475,22 @@ static BusState *qbus_find_recursive(BusState *bus, > const char *name, > return NULL; > } > > -static DeviceState *qdev_find_id_recursive(BusState *bus, const char *id) > +void *qdev_iterate_recursive(BusState *bus, qdev_iteratefn callback, > + void *opaque) > { > DeviceState *dev, *ret; > BusState *child; > > + if (!bus) { > + bus = main_system_bus; > + } > QTAILQ_FOREACH(dev, &bus->children, sibling) { > - if (dev->id && strcmp(dev->id, id) == 0) > - return dev; > + ret = callback(dev, opaque); > + if (ret) { > + return ret; > + } > QTAILQ_FOREACH(child, &dev->child_bus, sibling) { > - ret = qdev_find_id_recursive(child, id); > + ret = qdev_iterate_recursive(child, callback, opaque); > if (ret) { > return ret; > }
I'd call "iterate recursive" simply "walk". It's common usage for trees. Except this isn't a walk or iteration, it's a search: the walk stops as soon as the callback returns non-null. Not obvious from the name, therefore needs a comment. [...]