/* For TECHNO KIT */
 #define USB_VENDOR  0x12ed
 #define USB_PRODUCT 0x1003
/* For USB-An */
//#define USB_VENDOR  0x1352
//#define USB_PRODUCT 0x0100

/* Init USB */
struct usb_bus *morphy_init()
{
    usb_init();
    usb_find_busses();
    usb_find_devices();
    return( usb_get_busses() );
}

/* Find Morphy-USBIO  */
struct usb_device *morphy_find(struct usb_bus *busses, struct usb_device *dev)
{
    struct usb_bus *bus;
    for(bus=busses; bus; bus=bus->next){
        for(dev=bus->devices; dev; dev=dev->next) {
            if( (dev->descriptor.idVendor==USB_VENDOR) && (dev->descriptor.idProduct==USB_PRODUCT) ){
                return( dev );
            }
        }
    }
    return( NULL );
}

/* USBIO Open */
struct usb_dev_handle *morphy_open(struct usb_device *dev)
{
    struct usb_dev_handle *udev = NULL;

    udev=usb_open(dev);
    if( udev==NULL ){
        printf("usb_open Error.(%s)\n",usb_strerror());
        exit(1);
    }

    if( usb_set_configuration(udev,dev->config->bConfigurationValue)<0 ){
//        if( usb_detach_kernel_driver_np(udev,dev->config->interface->altsetting->bInterfaceNumber)<0 ){
            printf("usb_set_configuration Error.\n");
//            printf("usb_detach_kernel_driver_np Error.(%s)\n",usb_strerror());
//        }
    }

    if( usb_claim_interface(udev,dev->config->interface->altsetting->bInterfaceNumber)<0 ){
//        if( usb_detach_kernel_driver_np(udev,dev->config->interface->altsetting->bInterfaceNumber)<0 ){
            printf("usb_claim_interface Error.\n");
//            printf("usb_detach_kernel_driver_np Error.(%s)\n",usb_strerror());
//        }
    }

    if( usb_claim_interface(udev,dev->config->interface->altsetting->bInterfaceNumber)<0 ){
        printf("usb_claim_interface Error.(%s)\n",usb_strerror());
    }

    return(udev);
}

/* USBIO Close */
void morphy_close(struct usb_dev_handle *udev)
{
    if( usb_close(udev)<0 ){
        printf("usb_close Error.(%s)\n",usb_strerror());
    }
}

/* USBIO out */
void uio_out(struct usb_dev_handle *udev, int PortNo, int OutData)
{
    unsigned char ctl[8];

    ctl[0]=0x01+(PortNo&1);
    ctl[1]=OutData;
    ctl[2]=ctl[3]=ctl[4]=ctl[5]=ctl[6]=ctl[7]=0;
    usb_control_msg(udev,0x21,0x09,0x00,0x00,ctl,8,5000);


}
/* USBIO in*/
int uio_in(struct usb_dev_handle *udev, int PortNo )
{
    int i,ret;
    unsigned char ctl[8];
    unsigned char indat[8];
    static n=0;

    n++;

    /* CMD:Read */
    ctl[0]=0x03+(PortNo&1);
    ctl[1]=ctl[2]=ctl[3]=ctl[4]=ctl[5]=ctl[6]=0;
    ctl[7]=n;

    ret=usb_control_msg(udev,0x21,0x09,0x00,0x00,ctl,8,5000);
    if( ret<0 ){
        printf("Read-CmdError\n");
        return (-1);
    }
    i=0;
    do { 
        ret=usb_interrupt_read(udev,1,indat,8,5000);
        if( ret<0 ){
            printf("Int-Read Error\n");
            return (-2);
        }
        if (++i>100){ 
            printf("Int-Read Error\n");
            return (-3);
        }
    }while (ctl[7]!=indat[7]);
    ret=usb_interrupt_read(udev,1,indat,8,5000);

    return (indat[1]);
}


