Commit 769188d3 authored by Peter Maydell's avatar Peter Maydell
Browse files

Merge remote-tracking branch 'remotes/kraxel/tags/pull-usb-20140923-1' into staging



usb: enable hotplug, switch to realize, ohci tracing, misc fixes.

# gpg: Signature made Tue 23 Sep 2014 12:42:29 BST using RSA key ID D3E87138
# gpg: Good signature from "Gerd Hoffmann (work) <kraxel@redhat.com>"
# gpg:                 aka "Gerd Hoffmann <gerd@kraxel.org>"
# gpg:                 aka "Gerd Hoffmann (private) <kraxel@gmail.com>"

* remotes/kraxel/tags/pull-usb-20140923-1: (26 commits)
  usb: tag standalone ehci as hotpluggable
  usb: tag standalone uhci as hotpluggable
  usb: tag xhci as hotpluggable
  usb-serial: only check speed once at realize time
  usb-bus: introduce a wrapper function to check speed
  usb-bus: remove "init" from USBDeviceClass struct
  usb-mtp: convert init to realize
  usb-redir: convert init to realize
  usb-audio: convert init to realize
  dev-wacom: convert init to realize
  dev-hid: convert init to realize
  usb-ccid: convert init to realize
  dev-serial: convert init to realize
  dev-bluetooth: convert init to realize
  dev-uas: using error_report instead of fprintf
  dev-uas: convert init to realize
  dev-storage: usring error_report instead of fprintf/printf
  dev-storage: convert init to realize
  usb-hub: convert init to realize
  libusb: using error_report instead of fprintf
  ...

Signed-off-by: default avatarPeter Maydell <peter.maydell@linaro.org>
parents cad684c5 ec56214f
Loading
Loading
Loading
Loading
+52 −39
Original line number Diff line number Diff line
@@ -9,7 +9,7 @@ static void usb_bus_dev_print(Monitor *mon, DeviceState *qdev, int indent);

static char *usb_get_dev_path(DeviceState *dev);
static char *usb_get_fw_dev_path(DeviceState *qdev);
static int usb_qdev_exit(DeviceState *qdev);
static void usb_qdev_unrealize(DeviceState *qdev, Error **errp);

static Property usb_props[] = {
    DEFINE_PROP_STRING("port", USBDevice, port_path),
@@ -107,13 +107,13 @@ USBBus *usb_bus_find(int busnr)
    return NULL;
}

static int usb_device_init(USBDevice *dev)
static void usb_device_realize(USBDevice *dev, Error **errp)
{
    USBDeviceClass *klass = USB_DEVICE_GET_CLASS(dev);
    if (klass->init) {
        return klass->init(dev);

    if (klass->realize) {
        klass->realize(dev, errp);
    }
    return 0;
}

USBDevice *usb_device_find_device(USBDevice *dev, uint8_t addr)
@@ -232,36 +232,41 @@ void usb_device_free_streams(USBDevice *dev, USBEndpoint **eps, int nr_eps)
    }
}

static int usb_qdev_init(DeviceState *qdev)
static void usb_qdev_realize(DeviceState *qdev, Error **errp)
{
    USBDevice *dev = USB_DEVICE(qdev);
    int rc;
    Error *local_err = NULL;

    pstrcpy(dev->product_desc, sizeof(dev->product_desc),
            usb_device_get_product_desc(dev));
    dev->auto_attach = 1;
    QLIST_INIT(&dev->strings);
    usb_ep_init(dev);
    rc = usb_claim_port(dev);
    if (rc != 0) {
        return rc;

    usb_claim_port(dev, &local_err);
    if (local_err) {
        error_propagate(errp, local_err);
        return;
    }
    rc = usb_device_init(dev);
    if (rc != 0) {

    usb_device_realize(dev, &local_err);
    if (local_err) {
        usb_release_port(dev);
        return rc;
        error_propagate(errp, local_err);
        return;
    }

    if (dev->auto_attach) {
        rc = usb_device_attach(dev);
        if (rc != 0) {
            usb_qdev_exit(qdev);
            return rc;
        usb_device_attach(dev, &local_err);
        if (local_err) {
            usb_qdev_unrealize(qdev, NULL);
            error_propagate(errp, local_err);
            return;
        }
    }
    return 0;
}

static int usb_qdev_exit(DeviceState *qdev)
static void usb_qdev_unrealize(DeviceState *qdev, Error **errp)
{
    USBDevice *dev = USB_DEVICE(qdev);

@@ -272,7 +277,6 @@ static int usb_qdev_exit(DeviceState *qdev)
    if (dev->port) {
        usb_release_port(dev);
    }
    return 0;
}

typedef struct LegacyUSBFactory
@@ -392,7 +396,7 @@ void usb_unregister_port(USBBus *bus, USBPort *port)
    bus->nfree--;
}

int usb_claim_port(USBDevice *dev)
void usb_claim_port(USBDevice *dev, Error **errp)
{
    USBBus *bus = usb_bus_from_device(dev);
    USBPort *port;
@@ -406,9 +410,9 @@ int usb_claim_port(USBDevice *dev)
            }
        }
        if (port == NULL) {
            error_report("Error: usb port %s (bus %s) not found (in use?)",
            error_setg(errp, "Error: usb port %s (bus %s) not found (in use?)",
                       dev->port_path, bus->qbus.name);
            return -1;
            return;
        }
    } else {
        if (bus->nfree == 1 && strcmp(object_get_typename(OBJECT(dev)), "usb-hub") != 0) {
@@ -416,9 +420,9 @@ int usb_claim_port(USBDevice *dev)
            usb_create_simple(bus, "usb-hub");
        }
        if (bus->nfree == 0) {
            error_report("Error: tried to attach usb device %s to a bus "
            error_setg(errp, "Error: tried to attach usb device %s to a bus "
                       "with no free ports", dev->product_desc);
            return -1;
            return;
        }
        port = QTAILQ_FIRST(&bus->free);
    }
@@ -432,7 +436,6 @@ int usb_claim_port(USBDevice *dev)

    QTAILQ_INSERT_TAIL(&bus->used, port, next);
    bus->nused++;
    return 0;
}

void usb_release_port(USBDevice *dev)
@@ -475,7 +478,7 @@ static void usb_mask_to_str(char *dest, size_t size,
    }
}

int usb_device_attach(USBDevice *dev)
void usb_check_attach(USBDevice *dev, Error **errp)
{
    USBBus *bus = usb_bus_from_device(dev);
    USBPort *port = dev->port;
@@ -489,18 +492,28 @@ int usb_device_attach(USBDevice *dev)
                          devspeed, portspeed);

    if (!(port->speedmask & dev->speedmask)) {
        error_report("Warning: speed mismatch trying to attach"
        error_setg(errp, "Warning: speed mismatch trying to attach"
                   " usb device \"%s\" (%s speed)"
                   " to bus \"%s\", port \"%s\" (%s speed)",
                   dev->product_desc, devspeed,
                   bus->qbus.name, port->path, portspeed);
        return -1;
        return;
    }
}

void usb_device_attach(USBDevice *dev, Error **errp)
{
    USBPort *port = dev->port;
    Error *local_err = NULL;

    usb_check_attach(dev, &local_err);
    if (local_err) {
        error_propagate(errp, local_err);
        return;
    }

    dev->attached++;
    usb_attach(port);

    return 0;
}

int usb_device_detach(USBDevice *dev)
@@ -688,9 +701,9 @@ static void usb_device_class_init(ObjectClass *klass, void *data)
{
    DeviceClass *k = DEVICE_CLASS(klass);
    k->bus_type = TYPE_USB_BUS;
    k->init     = usb_qdev_init;
    k->unplug   = qdev_simple_unplug_cb;
    k->exit     = usb_qdev_exit;
    k->realize  = usb_qdev_realize;
    k->unrealize = usb_qdev_unrealize;
    k->props    = usb_props;
}

+2 −3
Original line number Diff line number Diff line
@@ -628,7 +628,7 @@ static void usb_audio_handle_destroy(USBDevice *dev)
    streambuf_fini(&s->out.buf);
}

static int usb_audio_initfn(USBDevice *dev)
static void usb_audio_realize(USBDevice *dev, Error **errp)
{
    USBAudioState *s = DO_UPCAST(USBAudioState, dev, dev);

@@ -651,7 +651,6 @@ static int usb_audio_initfn(USBDevice *dev)
                                s, output_callback, &s->out.as);
    AUD_set_volume_out(s->out.voice, s->out.mute, s->out.vol[0], s->out.vol[1]);
    AUD_set_active_out(s->out.voice, 0);
    return 0;
}

static const VMStateDescription vmstate_usb_audio = {
@@ -676,7 +675,7 @@ static void usb_audio_class_init(ObjectClass *klass, void *data)
    set_bit(DEVICE_CATEGORY_SOUND, dc->categories);
    k->product_desc   = "QEMU USB Audio Interface";
    k->usb_desc       = &desc_audio;
    k->init           = usb_audio_initfn;
    k->realize        = usb_audio_realize;
    k->handle_reset   = usb_audio_handle_reset;
    k->handle_control = usb_audio_handle_control;
    k->handle_data    = usb_audio_handle_data;
+2 −4
Original line number Diff line number Diff line
@@ -501,7 +501,7 @@ static void usb_bt_handle_destroy(USBDevice *dev)
    s->hci->acl_recv = NULL;
}

static int usb_bt_initfn(USBDevice *dev)
static void usb_bt_realize(USBDevice *dev, Error **errp)
{
    struct USBBtState *s = DO_UPCAST(struct USBBtState, dev, dev);

@@ -516,8 +516,6 @@ static int usb_bt_initfn(USBDevice *dev)
    s->hci->acl_recv = usb_bt_out_hci_packet_acl;
    usb_bt_handle_reset(&s->dev);
    s->intr = usb_ep_get(dev, USB_TOKEN_IN, USB_EVT_EP);

    return 0;
}

static USBDevice *usb_bt_init(USBBus *bus, const char *cmdline)
@@ -560,7 +558,7 @@ static void usb_bt_class_initfn(ObjectClass *klass, void *data)
    DeviceClass *dc = DEVICE_CLASS(klass);
    USBDeviceClass *uc = USB_DEVICE_CLASS(klass);

    uc->init           = usb_bt_initfn;
    uc->realize        = usb_bt_realize;
    uc->product_desc   = "QEMU BT dongle";
    uc->usb_desc       = &desc_bluetooth;
    uc->handle_reset   = usb_bt_handle_reset;
+13 −14
Original line number Diff line number Diff line
@@ -566,7 +566,7 @@ static void usb_hid_handle_destroy(USBDevice *dev)
    hid_free(&us->hid);
}

static int usb_hid_initfn(USBDevice *dev, int kind)
static void usb_hid_initfn(USBDevice *dev, int kind)
{
    USBHIDState *us = DO_UPCAST(USBHIDState, dev, dev);

@@ -579,10 +579,9 @@ static int usb_hid_initfn(USBDevice *dev, int kind)
    if (us->display && us->hid.s) {
        qemu_input_handler_bind(us->hid.s, us->display, us->head, NULL);
    }
    return 0;
}

static int usb_tablet_initfn(USBDevice *dev)
static void usb_tablet_realize(USBDevice *dev, Error **errp)
{
    USBHIDState *us = DO_UPCAST(USBHIDState, dev, dev);

@@ -594,22 +593,22 @@ static int usb_tablet_initfn(USBDevice *dev)
        dev->usb_desc = &desc_tablet2;
        break;
    default:
        error_report("Invalid usb version %d for usb-tabler (must be 1 or 2)",
                     us->usb_version);
        return -1;
        error_setg(errp, "Invalid usb version %d for usb-tablet "
                   "(must be 1 or 2)", us->usb_version);
        return;
    }

    return usb_hid_initfn(dev, HID_TABLET);
    usb_hid_initfn(dev, HID_TABLET);
}

static int usb_mouse_initfn(USBDevice *dev)
static void usb_mouse_realize(USBDevice *dev, Error **errp)
{
    return usb_hid_initfn(dev, HID_MOUSE);
    usb_hid_initfn(dev, HID_MOUSE);
}

static int usb_keyboard_initfn(USBDevice *dev)
static void usb_keyboard_realize(USBDevice *dev, Error **errp)
{
    return usb_hid_initfn(dev, HID_KEYBOARD);
    usb_hid_initfn(dev, HID_KEYBOARD);
}

static int usb_ptr_post_load(void *opaque, int version_id)
@@ -669,7 +668,7 @@ static void usb_tablet_class_initfn(ObjectClass *klass, void *data)
    USBDeviceClass *uc = USB_DEVICE_CLASS(klass);

    usb_hid_class_initfn(klass, data);
    uc->init           = usb_tablet_initfn;
    uc->realize        = usb_tablet_realize;
    uc->product_desc   = "QEMU USB Tablet";
    dc->vmsd = &vmstate_usb_ptr;
    dc->props = usb_tablet_properties;
@@ -689,7 +688,7 @@ static void usb_mouse_class_initfn(ObjectClass *klass, void *data)
    USBDeviceClass *uc = USB_DEVICE_CLASS(klass);

    usb_hid_class_initfn(klass, data);
    uc->init           = usb_mouse_initfn;
    uc->realize        = usb_mouse_realize;
    uc->product_desc   = "QEMU USB Mouse";
    uc->usb_desc       = &desc_mouse;
    dc->vmsd = &vmstate_usb_ptr;
@@ -714,7 +713,7 @@ static void usb_keyboard_class_initfn(ObjectClass *klass, void *data)
    USBDeviceClass *uc = USB_DEVICE_CLASS(klass);

    usb_hid_class_initfn(klass, data);
    uc->init           = usb_keyboard_initfn;
    uc->realize        = usb_keyboard_realize;
    uc->product_desc   = "QEMU USB Keyboard";
    uc->usb_desc       = &desc_keyboard;
    dc->vmsd = &vmstate_usb_kbd;
+4 −5
Original line number Diff line number Diff line
@@ -511,15 +511,15 @@ static USBPortOps usb_hub_port_ops = {
    .complete = usb_hub_complete,
};

static int usb_hub_initfn(USBDevice *dev)
static void usb_hub_realize(USBDevice *dev, Error **errp)
{
    USBHubState *s = DO_UPCAST(USBHubState, dev, dev);
    USBHubPort *port;
    int i;

    if (dev->port->hubcount == 5) {
        error_report("usb hub chain too deep");
        return -1;
        error_setg(errp, "usb hub chain too deep");
        return;
    }

    usb_desc_create_serial(dev);
@@ -533,7 +533,6 @@ static int usb_hub_initfn(USBDevice *dev)
        usb_port_location(&port->port, dev->port, i+1);
    }
    usb_hub_handle_reset(dev);
    return 0;
}

static const VMStateDescription vmstate_usb_hub_port = {
@@ -564,7 +563,7 @@ static void usb_hub_class_initfn(ObjectClass *klass, void *data)
    DeviceClass *dc = DEVICE_CLASS(klass);
    USBDeviceClass *uc = USB_DEVICE_CLASS(klass);

    uc->init           = usb_hub_initfn;
    uc->realize        = usb_hub_realize;
    uc->product_desc   = "QEMU USB Hub";
    uc->usb_desc       = &desc_hub;
    uc->find_device    = usb_hub_find_device;
Loading