/*
 * BSD host USB redirector
 *
 * Copyright (c) 2006 Lonnie Mendez
 * Portions of code and concepts borrowed from
 * usb-linux.c and libusb's bsd.c and are copyright their respective owners.
 *
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 * of this software and associated documentation files (the "Software"), to deal
 * in the Software without restriction, including without limitation the rights
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 * copies of the Software, and to permit persons to whom the Software is
 * furnished to do so, subject to the following conditions:
 *
 * The above copyright notice and this permission notice shall be included in
 * all copies or substantial portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 * THE SOFTWARE.
 */

#include "qemu-common.h"
#include "monitor.h"
#include "hw/usb.h"

/* usb.h declares these */
#undef USB_SPEED_HIGH
#undef USB_SPEED_FULL
#undef USB_SPEED_LOW

#include <sys/ioctl.h>
#ifndef __DragonFly__
#include <dev/usb/usb.h>
#else
#include <bus/usb/usb.h>
#endif

/* This value has maximum potential at 16.
 * You should also set hw.usb.debug to gain
 * more detailed view.
 */
//#define DEBUG
#define UGEN_DEBUG_LEVEL 0


typedef int USBScanFunc(void *opaque, int bus_num, int addr, int class_id,
                        int vendor_id, int product_id,
                        const char *product_name, int speed);
static int usb_host_find_device(int *pbus_num, int *paddr,
                                const char *devname);

typedef struct USBHostDevice {
    USBDevice dev;
    int ep_fd[USB_MAX_ENDPOINTS];
    int devfd;
    char devpath[32];
} USBHostDevice;


static int ensure_ep_open(USBHostDevice *dev, int ep, int mode)
{
    char buf[32];
    int fd;

    /* Get the address for this endpoint */
    ep = UE_GET_ADDR(ep);

    if (dev->ep_fd[ep] < 0) {
#if defined(__FreeBSD__) || defined(__DragonFly__)
        snprintf(buf, sizeof(buf) - 1, "%s.%d", dev->devpath, ep);
#else
        snprintf(buf, sizeof(buf) - 1, "%s.%02d", dev->devpath, ep);
#endif
        /* Try to open it O_RDWR first for those devices which have in and out
         * endpoints with the same address (eg 0x02 and 0x82)
         */
        fd = open(buf, O_RDWR);
        if (fd < 0 && errno == ENXIO)
            fd = open(buf, mode);
        if (fd < 0) {
#ifdef DEBUG
            printf("ensure_ep_open: failed to open device endpoint %s: %s\n",
                   buf, strerror(errno));
#endif
        }
        dev->ep_fd[ep] = fd;
    }

    return dev->ep_fd[ep];
}

static void ensure_eps_closed(USBHostDevice *dev)
{
    int epnum = 1;

    if (!dev)
        return;

    while (epnum < USB_MAX_ENDPOINTS) {
        if (dev->ep_fd[epnum] >= 0) {
            close(dev->ep_fd[epnum]);
            dev->ep_fd[epnum] = -1;
        }
        epnum++;
    }
}

static void usb_host_handle_reset(USBDevice *dev)
{
#if 0
    USBHostDevice *s = (USBHostDevice *)dev;
#endif
}

/* XXX:
 * -check device states against transfer requests
 *  and return appropriate response
 */
static int usb_host_handle_control(USBDevice *dev,
                                   USBPacket *p,
                                   int request,
                                   int value,
                                   int index,
                                   int length,
                                   uint8_t *data)
{
    USBHostDevice *s = (USBHostDevice *)dev;
    struct usb_ctl_request req;
    struct usb_alt_interface aiface;
    int ret, timeout = 50;

    if ((request >> 8) == UT_WRITE_DEVICE &&
        (request & 0xff) == UR_SET_ADDRESS) {

        /* specific SET_ADDRESS support */
        dev->addr = value;
        return 0;
    } else if ((request >> 8) == UT_WRITE_DEVICE &&
               (request & 0xff) == UR_SET_CONFIG) {

        ensure_eps_closed(s); /* can't do this without all eps closed */

        ret = ioctl(s->devfd, USB_SET_CONFIG, &value);
        if (ret < 0) {
#ifdef DEBUG
            printf("handle_control: failed to set configuration - %s\n",
                   strerror(errno));
#endif
            return USB_RET_STALL;
        }

        return 0;
    } else if ((request >> 8) == UT_WRITE_INTERFACE &&
               (request & 0xff) == UR_SET_INTERFACE) {

        aiface.uai_interface_index = index;
        aiface.uai_alt_no = value;

        ensure_eps_closed(s); /* can't do this without all eps closed */
        ret = ioctl(s->devfd, USB_SET_ALTINTERFACE, &aiface);
        if (ret < 0) {
#ifdef DEBUG
            printf("handle_control: failed to set alternate interface - %s\n",
                   strerror(errno));
#endif
            return USB_RET_STALL;
        }

        return 0;
    } else {
        req.ucr_request.bmRequestType = request >> 8;
        req.ucr_request.bRequest = request & 0xff;
        USETW(req.ucr_request.wValue, value);
        USETW(req.ucr_request.wIndex, index);
        USETW(req.ucr_request.wLength, length);
        req.ucr_data = data;
        req.ucr_flags = USBD_SHORT_XFER_OK;

        ret = ioctl(s->devfd, USB_SET_TIMEOUT, &timeout);
#if defined(__NetBSD__) || defined(__OpenBSD__)
        if (ret < 0 && errno != EINVAL) {
#else
        if (ret < 0) {
#endif
#ifdef DEBUG
            printf("handle_control: setting timeout failed - %s\n",
                   strerror(errno));
#endif
        }

        ret = ioctl(s->devfd, USB_DO_REQUEST, &req);
        /* ugen returns EIO for usbd_do_request_ no matter what
         * happens with the transfer */
        if (ret < 0) {
#ifdef DEBUG
            printf("handle_control: error after request - %s\n",
                   strerror(errno));
#endif
            return USB_RET_NAK; // STALL
        } else {
            return req.ucr_actlen;
        }
    }
}

static int usb_host_handle_data(USBDevice *dev, USBPacket *p)
{
    USBHostDevice *s = (USBHostDevice *)dev;
    int ret, fd, mode;
    int one = 1, shortpacket = 0, timeout = 50;
    sigset_t new_mask, old_mask;
    uint8_t devep = p->devep;

    /* protect data transfers from SIGALRM signal */
    sigemptyset(&new_mask);
    sigaddset(&new_mask, SIGALRM);
    sigprocmask(SIG_BLOCK, &new_mask, &old_mask);

    if (p->pid == USB_TOKEN_IN) {
        devep |= 0x80;
        mode = O_RDONLY;
        shortpacket = 1;
    } else {
        mode = O_WRONLY;
    }

    fd = ensure_ep_open(s, devep, mode);
    if (fd < 0) {
        sigprocmask(SIG_SETMASK, &old_mask, NULL);
        return USB_RET_NODEV;
    }

    if (ioctl(fd, USB_SET_TIMEOUT, &timeout) < 0) {
#ifdef DEBUG
        printf("handle_data: failed to set timeout - %s\n",
               strerror(errno));
#endif
    }

    if (shortpacket) {
        if (ioctl(fd, USB_SET_SHORT_XFER, &one) < 0) {
#ifdef DEBUG
            printf("handle_data: failed to set short xfer mode - %s\n",
                   strerror(errno));
#endif
            sigprocmask(SIG_SETMASK, &old_mask, NULL);
        }
    }

    if (p->pid == USB_TOKEN_IN)
        ret = readv(fd, p->iov.iov, p->iov.niov);
    else
        ret = writev(fd, p->iov.iov, p->iov.niov);

    sigprocmask(SIG_SETMASK, &old_mask, NULL);

    if (ret < 0) {
#ifdef DEBUG
        printf("handle_data: error after %s data - %s\n",
               pid == USB_TOKEN_IN ? "reading" : "writing", strerror(errno));
#endif
        switch(errno) {
        case ETIMEDOUT:
        case EINTR:
            return USB_RET_NAK;
        default:
            return USB_RET_STALL;
        }
    } else {
        return ret;
    }
}

static void usb_host_handle_destroy(USBDevice *opaque)
{
    USBHostDevice *s = (USBHostDevice *)opaque;
    int i;

    for (i = 0; i < USB_MAX_ENDPOINTS; i++)
        if (s->ep_fd[i] >= 0)
            close(s->ep_fd[i]);

    if (s->devfd < 0)
        return;

    close(s->devfd);

    g_free(s);
}

static int usb_host_initfn(USBDevice *dev)
{
    return 0;
}

USBDevice *usb_host_device_open(const char *devname)
{
    struct usb_device_info bus_info, dev_info;
    USBDevice *d = NULL, *ret = NULL;
    USBHostDevice *dev;
    char ctlpath[PATH_MAX + 1];
    char buspath[PATH_MAX + 1];
    int bfd, dfd, bus, address, i;
    int ugendebug = UGEN_DEBUG_LEVEL;

    if (usb_host_find_device(&bus, &address, devname) < 0) {
        goto fail;
    }

    snprintf(buspath, PATH_MAX, "/dev/usb%d", bus);

    bfd = open(buspath, O_RDWR);
    if (bfd < 0) {
#ifdef DEBUG
        printf("usb_host_device_open: failed to open usb bus - %s\n",
               strerror(errno));
#endif
        goto fail;
    }

    bus_info.udi_addr = address;
    if (ioctl(bfd, USB_DEVICEINFO, &bus_info) < 0) {
#ifdef DEBUG
        printf("usb_host_device_open: failed to grab bus information - %s\n",
               strerror(errno));
#endif
        goto fail_bfd;
    }

#if defined(__FreeBSD__) || defined(__FreeBSD_kernel__) || defined(__DragonFly__)
    snprintf(ctlpath, PATH_MAX, "/dev/%s", bus_info.udi_devnames[0]);
#else
    snprintf(ctlpath, PATH_MAX, "/dev/%s.00", bus_info.udi_devnames[0]);
#endif

    dfd  = open(ctlpath, O_RDWR);
    if (dfd < 0) {
        dfd = open(ctlpath, O_RDONLY);
        if (dfd < 0) {
#ifdef DEBUG
            printf("usb_host_device_open: failed to open usb device %s - %s\n",
                   ctlpath, strerror(errno));
#endif
        }
        goto fail_dfd;
    }

    if (ioctl(dfd, USB_GET_DEVICEINFO, &dev_info) < 0) {
#ifdef DEBUG
        printf("usb_host_device_open: failed to grab device info - %s\n",
               strerror(errno));
#endif
        goto fail_dfd;
    }

    d = usb_create(NULL /* FIXME */, "usb-host");
    dev = DO_UPCAST(USBHostDevice, dev, d);

    if (dev_info.udi_speed == 1) {
        dev->dev.speed = USB_SPEED_LOW - 1;
        dev->dev.speedmask = USB_SPEED_MASK_LOW;
    } else {
        dev->dev.speed = USB_SPEED_FULL - 1;
        dev->dev.speedmask = USB_SPEED_MASK_FULL;
    }

    if (strncmp(dev_info.udi_product, "product", 7) != 0) {
        pstrcpy(dev->dev.product_desc, sizeof(dev->dev.product_desc),
                dev_info.udi_product);
    } else {
        snprintf(dev->dev.product_desc, sizeof(dev->dev.product_desc),
                 "host:%s", devname);
    }

    pstrcpy(dev->devpath, sizeof(dev->devpath), "/dev/");
    pstrcat(dev->devpath, sizeof(dev->devpath), dev_info.udi_devnames[0]);

    /* Mark the endpoints as not yet open */
    for (i = 0; i < USB_MAX_ENDPOINTS; i++) {
        dev->ep_fd[i] = -1;
    }

    ioctl(dfd, USB_SETDEBUG, &ugendebug);

    ret = (USBDevice *)dev;

fail_dfd:
    close(dfd);
fail_bfd:
    close(bfd);
fail:
    return ret;
}

static void usb_host_class_initfn(ObjectClass *klass, void *data)
{
    USBDeviceClass *uc = USB_DEVICE_CLASS(klass);

    uc->product_desc   = "USB Host Device";
    uc->init           = usb_host_initfn;
    uc->handle_packet  = usb_generic_handle_packet;
    uc->handle_reset   = usb_host_handle_reset;
    uc->handle_control = usb_host_handle_control;
    uc->handle_data    = usb_host_handle_data;
    uc->handle_destroy = usb_host_handle_destroy;
}

static struct DeviceInfo usb_host_dev_info = {
    .name      = "usb-host",
    .size      = sizeof(USBHostDevice),
    .class_init= usb_host_initfn,
};

static void usb_host_register_devices(void)
{
    usb_qdev_register(&usb_host_dev_info, NULL, NULL);
}
device_init(usb_host_register_devices)

static int usb_host_scan(void *opaque, USBScanFunc *func)
{
    struct usb_device_info bus_info;
    struct usb_device_info dev_info;
    uint16_t vendor_id, product_id, class_id, speed;
    int bfd, dfd, bus, address;
    char busbuf[20], devbuf[20], product_name[256];
    int ret = 0;

    for (bus = 0; bus < 10; bus++) {

        snprintf(busbuf, sizeof(busbuf) - 1, "/dev/usb%d", bus);
        bfd = open(busbuf, O_RDWR);
        if (bfd < 0)
	    continue;

        for (address = 1; address < 127; address++) {

            bus_info.udi_addr = address;
            if (ioctl(bfd, USB_DEVICEINFO, &bus_info) < 0)
                continue;

            /* only list devices that can be used by generic layer */
            if (strncmp(bus_info.udi_devnames[0], "ugen", 4) != 0)
                continue;

#if defined(__FreeBSD__) || defined(__FreeBSD_kernel__) || defined(__DragonFly__)
            snprintf(devbuf, sizeof(devbuf) - 1, "/dev/%s", bus_info.udi_devnames[0]);
#else
            snprintf(devbuf, sizeof(devbuf) - 1, "/dev/%s.00", bus_info.udi_devnames[0]);
#endif

            dfd = open(devbuf, O_RDONLY);
            if (dfd < 0) {
#ifdef DEBUG
                printf("usb_host_scan: couldn't open device %s - %s\n", devbuf,
                       strerror(errno));
#endif
                continue;
            }

            if (ioctl(dfd, USB_GET_DEVICEINFO, &dev_info) < 0)
                printf("usb_host_scan: couldn't get device information for %s - %s\n",
                       devbuf, strerror(errno));

            /* XXX: might need to fixup endianness of word values before copying over */

            vendor_id = dev_info.udi_vendorNo;
            product_id = dev_info.udi_productNo;
            class_id = dev_info.udi_class;
            speed = dev_info.udi_speed;

            if (strncmp(dev_info.udi_product, "product", 7) != 0)
                pstrcpy(product_name, sizeof(product_name),
                        dev_info.udi_product);
            else
                product_name[0] = '\0';

            ret = func(opaque, bus, address, class_id, vendor_id,
                       product_id, product_name, speed);

            close(dfd);

            if (ret)
                goto the_end;
        }

        close(bfd);
    }

the_end:
    return ret;
}

typedef struct FindDeviceState {
    int vendor_id;
    int product_id;
    int bus_num;
    int addr;
} FindDeviceState;

static int usb_host_find_device_scan(void *opaque, int bus_num, int addr,
                                     int class_id,
                                     int vendor_id, int product_id,
                                     const char *product_name, int speed)
{
    FindDeviceState *s = opaque;
    if (vendor_id == s->vendor_id &&
        product_id == s->product_id) {
        s->bus_num = bus_num;
        s->addr = addr;
        return 1;
     } else {
        return 0;
     }
}


/* the syntax is :
   'bus.addr' (decimal numbers) or
   'vendor_id:product_id' (hexa numbers) */
static int usb_host_find_device(int *pbus_num, int *paddr,
                                const char *devname)
{
    const char *p;
    int ret;
    FindDeviceState fs;

    p = strchr(devname, '.');
    if (p) {
        *pbus_num = strtoul(devname, NULL, 0);
        *paddr = strtoul(p + 1, NULL, 0);
        return 0;
    }
    p = strchr(devname, ':');
    if (p) {
        fs.vendor_id = strtoul(devname, NULL, 16);
        fs.product_id = strtoul(p + 1, NULL, 16);
        ret = usb_host_scan(&fs, usb_host_find_device_scan);
        if (ret) {
            *pbus_num = fs.bus_num;
            *paddr = fs.addr;
            return 0;
        }
     }
     return -1;
}

/**********************/
/* USB host device info */

struct usb_class_info {
    int class;
    const char *class_name;
};

static const struct usb_class_info usb_class_info[] = {
    { USB_CLASS_AUDIO, "Audio"},
    { USB_CLASS_COMM, "Communication"},
    { USB_CLASS_HID, "HID"},
    { USB_CLASS_HUB, "Hub" },
    { USB_CLASS_PHYSICAL, "Physical" },
    { USB_CLASS_PRINTER, "Printer" },
    { USB_CLASS_MASS_STORAGE, "Storage" },
    { USB_CLASS_CDC_DATA, "Data" },
    { USB_CLASS_APP_SPEC, "Application Specific" },
    { USB_CLASS_VENDOR_SPEC, "Vendor Specific" },
    { USB_CLASS_STILL_IMAGE, "Still Image" },
    { USB_CLASS_CSCID, "Smart Card" },
    { USB_CLASS_CONTENT_SEC, "Content Security" },
    { -1, NULL }
};

static const char *usb_class_str(uint8_t class)
{
    const struct usb_class_info *p;
    for (p = usb_class_info; p->class != -1; p++) {
        if (p->class == class)
            break;
    }
    return p->class_name;
}

static void usb_info_device(Monitor *mon, int bus_num, int addr, int class_id,
                            int vendor_id, int product_id,
                            const char *product_name,
                            int speed)
{
    const char *class_str, *speed_str;

    switch(speed) {
    case USB_SPEED_LOW:
        speed_str = "1.5";
        break;
    case USB_SPEED_FULL:
        speed_str = "12";
        break;
    case USB_SPEED_HIGH:
        speed_str = "480";
        break;
    default:
        speed_str = "?";
        break;
    }

    monitor_printf(mon, "  Device %d.%d, speed %s Mb/s\n",
                   bus_num, addr, speed_str);
    class_str = usb_class_str(class_id);
    if (class_str)
        monitor_printf(mon, "    %s:", class_str);
    else
        monitor_printf(mon, "    Class %02x:", class_id);
    monitor_printf(mon, " USB device %04x:%04x", vendor_id, product_id);
    if (product_name[0] != '\0')
        monitor_printf(mon, ", %s", product_name);
    monitor_printf(mon, "\n");
}

static int usb_host_info_device(void *opaque,
                                int bus_num, int addr,
                                int class_id,
                                int vendor_id, int product_id,
                                const char *product_name,
                                int speed)
{
    Monitor *mon = opaque;

    usb_info_device(mon, bus_num, addr, class_id, vendor_id, product_id,
                    product_name, speed);
    return 0;
}

void usb_host_info(Monitor *mon)
{
    usb_host_scan(mon, usb_host_info_device);
}

/* XXX add this */
int usb_host_device_close(const char *devname)
{
    return 0;
}
