diff --git a/hw/core/qdev.c b/hw/core/qdev.c index b3d519645a..413b41376f 100644 --- a/hw/core/qdev.c +++ b/hw/core/qdev.c @@ -453,6 +453,17 @@ void qdev_connect_gpio_out_named(DeviceState *dev, const char *name, int n, g_free(propname); } +qemu_irq qdev_get_gpio_out_connector(DeviceState *dev, const char *name, int n) +{ + char *propname = g_strdup_printf("%s[%d]", + name ? name : "unnamed-gpio-out", n); + + qemu_irq ret = (qemu_irq)object_property_get_link(OBJECT(dev), propname, + NULL); + + return ret; +} + /* disconnect a GPIO ouput, returning the disconnected input (if any) */ static qemu_irq qdev_disconnect_gpio_out_named(DeviceState *dev, diff --git a/hw/core/sysbus.c b/hw/core/sysbus.c index 7bfe381cd8..945dec53d0 100644 --- a/hw/core/sysbus.c +++ b/hw/core/sysbus.c @@ -84,6 +84,27 @@ static const TypeInfo system_bus_info = { .class_init = system_bus_class_init, }; +/* Check whether an IRQ source exists */ +bool sysbus_has_irq(SysBusDevice *dev, int n) +{ + char *prop = g_strdup_printf("%s[%d]", SYSBUS_DEVICE_GPIO_IRQ, n); + ObjectProperty *r; + + r = object_property_find(OBJECT(dev), prop, NULL); + return (r != NULL); +} + +bool sysbus_is_irq_connected(SysBusDevice *dev, int n) +{ + return !!sysbus_get_connected_irq(dev, n); +} + +qemu_irq sysbus_get_connected_irq(SysBusDevice *dev, int n) +{ + DeviceState *d = DEVICE(dev); + return qdev_get_gpio_out_connector(d, SYSBUS_DEVICE_GPIO_IRQ, n); +} + void sysbus_connect_irq(SysBusDevice *dev, int n, qemu_irq irq) { qdev_connect_gpio_out_named(DEVICE(dev), SYSBUS_DEVICE_GPIO_IRQ, n, irq); diff --git a/include/hw/qdev-core.h b/include/hw/qdev-core.h index 00a15a3977..d3a29408d4 100644 --- a/include/hw/qdev-core.h +++ b/include/hw/qdev-core.h @@ -272,6 +272,7 @@ qemu_irq qdev_get_gpio_in_named(DeviceState *dev, const char *name, int n); void qdev_connect_gpio_out(DeviceState *dev, int n, qemu_irq pin); void qdev_connect_gpio_out_named(DeviceState *dev, const char *name, int n, qemu_irq pin); +qemu_irq qdev_get_gpio_out_connector(DeviceState *dev, const char *name, int n); qemu_irq qdev_intercept_gpio_out(DeviceState *dev, qemu_irq icpt, const char *name, int n); diff --git a/include/hw/sysbus.h b/include/hw/sysbus.h index 80529ffed8..2a3cfa785f 100644 --- a/include/hw/sysbus.h +++ b/include/hw/sysbus.h @@ -66,7 +66,10 @@ void sysbus_pass_irq(SysBusDevice *dev, SysBusDevice *target); void sysbus_init_ioports(SysBusDevice *dev, pio_addr_t ioport, pio_addr_t size); +bool sysbus_has_irq(SysBusDevice *dev, int n); void sysbus_connect_irq(SysBusDevice *dev, int n, qemu_irq irq); +bool sysbus_is_irq_connected(SysBusDevice *dev, int n); +qemu_irq sysbus_get_connected_irq(SysBusDevice *dev, int n); void sysbus_mmio_map(SysBusDevice *dev, int n, hwaddr addr); void sysbus_mmio_map_overlap(SysBusDevice *dev, int n, hwaddr addr, int priority);