static int usb_hid_handle_control(USBDevice *dev, USBPacket *p,

               int request, int value, int index, int length, uint8_t *data)

{

    USBHIDState *us = DO_UPCAST(USBHIDState, dev, dev);

    HIDState *hs = &us->hid;

    int ret;



    ret = usb_desc_handle_control(dev, p, request, value, index, length, data);

    if (ret >= 0) {

        return ret;

    }



    ret = 0;

    switch (request) {

    case DeviceRequest | USB_REQ_GET_INTERFACE:

        data[0] = 0;

        ret = 1;

        break;

    case DeviceOutRequest | USB_REQ_SET_INTERFACE:

        ret = 0;

        break;

        /* hid specific requests */

    case InterfaceRequest | USB_REQ_GET_DESCRIPTOR:

        switch (value >> 8) {

        case 0x22:

            if (hs->kind == HID_MOUSE) {

		memcpy(data, qemu_mouse_hid_report_descriptor,

		       sizeof(qemu_mouse_hid_report_descriptor));

		ret = sizeof(qemu_mouse_hid_report_descriptor);

            } else if (hs->kind == HID_TABLET) {

                memcpy(data, qemu_tablet_hid_report_descriptor,

		       sizeof(qemu_tablet_hid_report_descriptor));

		ret = sizeof(qemu_tablet_hid_report_descriptor);

            } else if (hs->kind == HID_KEYBOARD) {

                memcpy(data, qemu_keyboard_hid_report_descriptor,

                       sizeof(qemu_keyboard_hid_report_descriptor));

                ret = sizeof(qemu_keyboard_hid_report_descriptor);

            }

            break;

        default:

            goto fail;

        }

        break;

    case GET_REPORT:

        if (hs->kind == HID_MOUSE || hs->kind == HID_TABLET) {

            ret = hid_pointer_poll(hs, data, length);

        } else if (hs->kind == HID_KEYBOARD) {

            ret = hid_keyboard_poll(hs, data, length);

        }

        us->changed = hs->n > 0;

        break;

    case SET_REPORT:

        if (hs->kind == HID_KEYBOARD) {

            ret = hid_keyboard_write(hs, data, length);

        } else {

            goto fail;

        }

        break;

    case GET_PROTOCOL:

        if (hs->kind != HID_KEYBOARD && hs->kind != HID_MOUSE) {

            goto fail;

        }

        ret = 1;

        data[0] = us->protocol;

        break;

    case SET_PROTOCOL:

        if (hs->kind != HID_KEYBOARD && hs->kind != HID_MOUSE) {

            goto fail;

        }

        ret = 0;

        us->protocol = value;

        break;

    case GET_IDLE:

        ret = 1;

        data[0] = us->idle;

        break;

    case SET_IDLE:

        us->idle = (uint8_t) (value >> 8);

        usb_hid_set_next_idle(us, qemu_get_clock_ns(vm_clock));

        ret = 0;

        break;

    default:

    fail:

        ret = USB_RET_STALL;

        break;

    }

    return ret;

}

static int usb_hid_handle_control(USBDevice *dev, USBPacket *p,

               int request, int value, int index, int length, uint8_t *data)

{

    USBHIDState *us = DO_UPCAST(USBHIDState, dev, dev);

    HIDState *hs = &us->hid;

    int ret;



    ret = usb_desc_handle_control(dev, p, request, value, index, length, data);

    if (ret >= 0) {

        return ret;

    }



    ret = 0;

    switch (request) {

    case DeviceRequest | USB_REQ_GET_INTERFACE:

        data[0] = 0;

        ret = 1;

        break;

    case DeviceOutRequest | USB_REQ_SET_INTERFACE:

        ret = 0;

        break;

        

    case InterfaceRequest | USB_REQ_GET_DESCRIPTOR:

        switch (value >> 8) {

        case 0x22:

            if (hs->kind == HID_MOUSE) {

		memcpy(data, qemu_mouse_hid_report_descriptor,

		       sizeof(qemu_mouse_hid_report_descriptor));

		ret = sizeof(qemu_mouse_hid_report_descriptor);

            } else if (hs->kind == HID_TABLET) {

                memcpy(data, qemu_tablet_hid_report_descriptor,

		       sizeof(qemu_tablet_hid_report_descriptor));

		ret = sizeof(qemu_tablet_hid_report_descriptor);

            } else if (hs->kind == HID_KEYBOARD) {

                memcpy(data, qemu_keyboard_hid_report_descriptor,

                       sizeof(qemu_keyboard_hid_report_descriptor));

                ret = sizeof(qemu_keyboard_hid_report_descriptor);

            }

            break;

        default:

            goto fail;

        }

        break;

    case GET_REPORT:

        if (hs->kind == HID_MOUSE || hs->kind == HID_TABLET) {

            ret = hid_pointer_poll(hs, data, length);

        } else if (hs->kind == HID_KEYBOARD) {

            ret = hid_keyboard_poll(hs, data, length);

        }

        us->changed = hs->n > 0;

        break;

    case SET_REPORT:

        if (hs->kind == HID_KEYBOARD) {

            ret = hid_keyboard_write(hs, data, length);

        } else {

            goto fail;

        }

        break;

    case GET_PROTOCOL:

        if (hs->kind != HID_KEYBOARD && hs->kind != HID_MOUSE) {

            goto fail;

        }

        ret = 1;

        data[0] = us->protocol;

        break;

    case SET_PROTOCOL:

        if (hs->kind != HID_KEYBOARD && hs->kind != HID_MOUSE) {

            goto fail;

        }

        ret = 0;

        us->protocol = value;

        break;

    case GET_IDLE:

        ret = 1;

        data[0] = us->idle;

        break;

    case SET_IDLE:

        us->idle = (uint8_t) (value >> 8);

        usb_hid_set_next_idle(us, qemu_get_clock_ns(vm_clock));

        ret = 0;

        break;

    default:

    fail:

        ret = USB_RET_STALL;

        break;

    }

    return ret;

}

static int FUNC_0(USBDevice *VAR_0, USBPacket *VAR_1,

               int VAR_2, int VAR_3, int VAR_4, int VAR_5, uint8_t *VAR_6)

{

    USBHIDState *us = DO_UPCAST(USBHIDState, VAR_0, VAR_0);

    HIDState *hs = &us->hid;

    int VAR_7;



    VAR_7 = usb_desc_handle_control(VAR_0, VAR_1, VAR_2, VAR_3, VAR_4, VAR_5, VAR_6);

    if (VAR_7 >= 0) {

        return VAR_7;

    }



    VAR_7 = 0;

    switch (VAR_2) {

    case DeviceRequest | USB_REQ_GET_INTERFACE:

        VAR_6[0] = 0;

        VAR_7 = 1;

        break;

    case DeviceOutRequest | USB_REQ_SET_INTERFACE:

        VAR_7 = 0;

        break;

        

    case InterfaceRequest | USB_REQ_GET_DESCRIPTOR:

        switch (VAR_3 >> 8) {

        case 0x22:

            if (hs->kind == HID_MOUSE) {

		memcpy(VAR_6, qemu_mouse_hid_report_descriptor,

		       sizeof(qemu_mouse_hid_report_descriptor));

		VAR_7 = sizeof(qemu_mouse_hid_report_descriptor);

            } else if (hs->kind == HID_TABLET) {

                memcpy(VAR_6, qemu_tablet_hid_report_descriptor,

		       sizeof(qemu_tablet_hid_report_descriptor));

		VAR_7 = sizeof(qemu_tablet_hid_report_descriptor);

            } else if (hs->kind == HID_KEYBOARD) {

                memcpy(VAR_6, qemu_keyboard_hid_report_descriptor,

                       sizeof(qemu_keyboard_hid_report_descriptor));

                VAR_7 = sizeof(qemu_keyboard_hid_report_descriptor);

            }

            break;

        default:

            goto fail;

        }

        break;

    case GET_REPORT:

        if (hs->kind == HID_MOUSE || hs->kind == HID_TABLET) {

            VAR_7 = hid_pointer_poll(hs, VAR_6, VAR_5);

        } else if (hs->kind == HID_KEYBOARD) {

            VAR_7 = hid_keyboard_poll(hs, VAR_6, VAR_5);

        }

        us->changed = hs->n > 0;

        break;

    case SET_REPORT:

        if (hs->kind == HID_KEYBOARD) {

            VAR_7 = hid_keyboard_write(hs, VAR_6, VAR_5);

        } else {

            goto fail;

        }

        break;

    case GET_PROTOCOL:

        if (hs->kind != HID_KEYBOARD && hs->kind != HID_MOUSE) {

            goto fail;

        }

        VAR_7 = 1;

        VAR_6[0] = us->protocol;

        break;

    case SET_PROTOCOL:

        if (hs->kind != HID_KEYBOARD && hs->kind != HID_MOUSE) {

            goto fail;

        }

        VAR_7 = 0;

        us->protocol = VAR_3;

        break;

    case GET_IDLE:

        VAR_7 = 1;

        VAR_6[0] = us->idle;

        break;

    case SET_IDLE:

        us->idle = (uint8_t) (VAR_3 >> 8);

        usb_hid_set_next_idle(us, qemu_get_clock_ns(vm_clock));

        VAR_7 = 0;

        break;

    default:

    fail:

        VAR_7 = USB_RET_STALL;

        break;

    }

    return VAR_7;

}

static int FUNC_0(USBDevice *VAR_0, USBPacket *VAR_1,
int VAR_2, int VAR_3, int VAR_4, int VAR_5, uint8_t *VAR_6)
{ USBHIDState *us = DO_UPCAST(USBHIDState, VAR_0, VAR_0); HIDState *hs = &us->hid; int VAR_7; VAR_7 = usb_desc_handle_control(VAR_0, VAR_1, VAR_2, VAR_3, VAR_4, VAR_5, VAR_6); if (VAR_7 >= 0) { return VAR_7; } VAR_7 = 0; switch (VAR_2) { case DeviceRequest | USB_REQ_GET_INTERFACE:
VAR_6[0] = 0; VAR_7 = 1; break; case DeviceOutRequest | USB_REQ_SET_INTERFACE:
VAR_7 = 0; break; case InterfaceRequest | USB_REQ_GET_DESCRIPTOR:
switch (VAR_3 >> 8) { case 0x22:
if (hs->kind == HID_MOUSE) { memcpy(VAR_6, qemu_mouse_hid_report_descriptor,
sizeof(qemu_mouse_hid_report_descriptor)); VAR_7 = sizeof(qemu_mouse_hid_report_descriptor); } else if (hs->kind == HID_TABLET) { memcpy(VAR_6, qemu_tablet_hid_report_descriptor,
sizeof(qemu_tablet_hid_report_descriptor)); VAR_7 = sizeof(qemu_tablet_hid_report_descriptor); } else if (hs->kind == HID_KEYBOARD) { memcpy(VAR_6, qemu_keyboard_hid_report_descriptor,
sizeof(qemu_keyboard_hid_report_descriptor)); VAR_7 = sizeof(qemu_keyboard_hid_report_descriptor); } break; default:
goto fail; } break; case GET_REPORT:
if (hs->kind == HID_MOUSE || hs->kind == HID_TABLET) { VAR_7 = hid_pointer_poll(hs, VAR_6, VAR_5); } else if (hs->kind == HID_KEYBOARD) { VAR_7 = hid_keyboard_poll(hs, VAR_6, VAR_5); } us->changed = hs->n > 0; break; case SET_REPORT:
if (hs->kind == HID_KEYBOARD) { VAR_7 = hid_keyboard_write(hs, VAR_6, VAR_5); } else { goto fail; } break; case GET_PROTOCOL:
if (hs->kind != HID_KEYBOARD && hs->kind != HID_MOUSE) { goto fail; } VAR_7 = 1; VAR_6[0] = us->protocol; break; case SET_PROTOCOL:
if (hs->kind != HID_KEYBOARD && hs->kind != HID_MOUSE) { goto fail; } VAR_7 = 0; us->protocol = VAR_3; break; case GET_IDLE:
VAR_7 = 1; VAR_6[0] = us->idle; break; case SET_IDLE:
us->idle = (uint8_t) (VAR_3 >> 8); usb_hid_set_next_idle(us, qemu_get_clock_ns(vm_clock)); VAR_7 = 0; break; default:
fail:
VAR_7 = USB_RET_STALL; break; } return VAR_7; }