---
 acinclude.m4         |   25 +++-
 configure.ac         |    1 +
 doc/Doxyfile         |    2 +-
 doc/Doxyfile.in      |    2 +-
 lib/Makefile.am      |    7 +-
 lib/obex_transport.c |   19 +++
 lib/usb1obex.c       |  419 ++++++++++++++++++++++++++++++++++++++++++++++++++
 lib/usbobex.c        |   55 +------
 lib/usbobex.h        |   16 ++-
 lib/usbutils.c       |   82 ++++++++++
 lib/usbutils.h       |   30 ++++
 11 files changed, 599 insertions(+), 59 deletions(-)
 create mode 100644 lib/usb1obex.c
 create mode 100644 lib/usbutils.c
 create mode 100644 lib/usbutils.h

diff --git a/acinclude.m4 b/acinclude.m4
index 06646bf..6955907 100644
--- a/acinclude.m4
+++ b/acinclude.m4
@@ -188,6 +188,23 @@ AC_DEFUN([AC_PATH_USB], [
        fi
 ])
 
+AC_DEFUN([AC_PATH_USB1], [
+       usb1_lib_found=no
+       PKG_CHECK_MODULES(USB1, libusb-1.0, usb1_lib_found=yes, 
AC_MSG_RESULT(no))
+       AC_CHECK_FILE(${prefix}/lib/pkgconfig/libusb-1.0.pc, REQUIRES="libusb1")
+       AC_SUBST(USB1_CFLAGS)
+       AC_SUBST(USB1_LIBS)
+
+       usb1_get_device_list=no
+       AC_CHECK_LIB(usb-1.0, libusb_get_device_list, usb1_get_device_list=yes, 
AC_DEFINE(NEED_USB1_GET_DEVICE_LIST, 1, [Define to 1 if you need the 
libusb_get_device_list() function.]))
+
+       if (test "$usb1_lib_found" = "yes" && test "$usb1_get_device_list" = 
"yes"); then
+               usb1_found=yes
+       else
+               usb1_found=no
+       fi
+])
+
 dnl AC_DEFUN([AC_PATH_GLIB], [
 dnl    PKG_CHECK_MODULES(GLIB, glib-2.0 gobject-2.0 gthread-2.0, 
glib_found=yes, AC_MSG_RESULT(no))
 dnl    AC_SUBST(GLIB_CFLAGS)
@@ -293,8 +310,12 @@ AC_DEFUN([AC_ARG_OPENOBEX], [
                AC_DEFINE(HAVE_BLUETOOTH_LINUX, 1, [Define if system supports 
Bluetooth stack for Linux])
        fi
 
-       if (test "${usb_enable}" = "yes" && test "${usb_found}" = "yes"); then
-               AC_DEFINE(HAVE_USB, 1, [Define if system supports USB and it's 
enabled])
+       if (test "${usb_enable}" = "yes" && (test "${usb_found}" = "yes" || 
test "${usb1_found}" = "yes")); then
+               AC_DEFINE(HAVE_USB, 1, [Define if system has libusb 0.x or 
libusb 1.0 and it's enabled])
+       fi
+
+       if (test "${usb_enable}" = "yes" && test "${usb1_found}" = "yes"); then
+               AC_DEFINE(HAVE_USB1, 1, [Define if system has libusb 1.0 and 
it's enabled])
        fi
 
        AM_CONDITIONAL(GLIB, test "${glib_enable}" = "yes" && test 
"${glib_found}" = "yes")
diff --git a/configure.ac b/configure.ac
index 477a27d..8e09960 100644
--- a/configure.ac
+++ b/configure.ac
@@ -30,6 +30,7 @@ AC_PATH_WIN32
 AC_PATH_IRDA
 AC_PATH_BLUETOOTH
 AC_PATH_USB
+AC_PATH_USB1
 
 AC_ARG_OPENOBEX
 
diff --git a/doc/Doxyfile b/doc/Doxyfile
index 41b820a..7b0b8ac 100644
--- a/doc/Doxyfile
+++ b/doc/Doxyfile
@@ -198,7 +198,7 @@ EXPAND_ONLY_PREDEF     = YES
 SEARCH_INCLUDES        = YES
 INCLUDE_PATH           = 
 INCLUDE_FILE_PATTERNS  = 
-PREDEFINED             = "LIB_SYMBOL=" "CALLAPI=" 
"OPENOBEX_SYMBOL(retval)=retval" HAVE_IRDA HAVE_USB HAVE_BLUETOOTH
+PREDEFINED             = "LIB_SYMBOL=" "CALLAPI=" 
"OPENOBEX_SYMBOL(retval)=retval" HAVE_IRDA HAVE_USB HAVE_USB1 HAVE_BLUETOOTH
 EXPAND_AS_DEFINED      = 
 SKIP_FUNCTION_MACROS   = YES
 #---------------------------------------------------------------------------
diff --git a/doc/Doxyfile.in b/doc/Doxyfile.in
index be9e955..dbbfb1f 100644
--- a/doc/Doxyfile.in
+++ b/doc/Doxyfile.in
@@ -197,7 +197,7 @@ EXPAND_ONLY_PREDEF     = YES
 SEARCH_INCLUDES        = YES
 INCLUDE_PATH           = 
 INCLUDE_FILE_PATTERNS  = 
-PREDEFINED             = "LIB_SYMBOL=" "CALLAPI=" 
"OPENOBEX_SYMBOL(retval)=retval" HAVE_IRDA HAVE_USB HAVE_BLUETOOTH
+PREDEFINED             = "LIB_SYMBOL=" "CALLAPI=" 
"OPENOBEX_SYMBOL(retval)=retval" HAVE_IRDA HAVE_USB HAVE_USB1 HAVE_BLUETOOTH
 EXPAND_AS_DEFINED      = 
 SKIP_FUNCTION_MACROS   = YES
 #---------------------------------------------------------------------------
diff --git a/lib/Makefile.am b/lib/Makefile.am
index f45e7da..7510ee9 100644
--- a/lib/Makefile.am
+++ b/lib/Makefile.am
@@ -15,17 +15,18 @@ libopenobex_la_SOURCES = \
        btobex.c btobex.h \
        databuffer.c databuffer.h \
        irda.h irda_wrap.h \
-       usbobex.c usbobex.h \
+       usbutils.c usbutils.h \
+       usbobex.c usb1obex.c usbobex.h \
        bluez_compat.h
 
-libopenobex_la_CFLAGS = @CFLAG_VISIBILITY@
+libopenobex_la_CFLAGS = @CFLAG_VISIBILITY@ @USB1_CFLAGS@
 
 libopenobex_la_LDFLAGS = \
        -no-undefined \
        -version-info 6:0:0 \
        -export-symbols $(top_srcdir)/lib/obex.sym
 
-libopenobex_la_LIBADD = @USB_LIBS@ @EXTRA_LIBS@
+libopenobex_la_LIBADD = @USB_LIBS@ @USB1_LIBS@ @EXTRA_LIBS@
 
 INCLUDES = -I$(top_srcdir)/include
 
diff --git a/lib/obex_transport.c b/lib/obex_transport.c
index 690a79f..e3881e9 100644
--- a/lib/obex_transport.c
+++ b/lib/obex_transport.c
@@ -433,10 +433,19 @@ int obex_transport_write(obex_t *self, buf_t *msg)
                if (self->trans.connected != TRUE)
                        break;
                DEBUG(4, "Endpoint %d\n", 
self->trans.self.usb.data_endpoint_write);
+#ifdef HAVE_USB1
+               int usberror = libusb_bulk_transfer(self->trans.self.usb.dev,
+                                       
self->trans.self.usb.data_endpoint_write,
+                                       (unsigned char *) msg->data, 
msg->data_size,
+                                       &actual, USB_OBEX_TIMEOUT);
+               if (usberror)
+                       actual = usberror;
+#else
                actual = usb_bulk_write(self->trans.self.usb.dev,
                                        
self->trans.self.usb.data_endpoint_write,
                                        (char *) msg->data, msg->data_size,
                                        USB_OBEX_TIMEOUT);
+#endif
                break;
 #endif /*HAVE_USB*/
        case OBEX_TRANS_CUSTOM:
@@ -493,10 +502,20 @@ int obex_transport_read(obex_t *self, int max, uint8_t 
*buf, int buflen)
                if (self->trans.connected != TRUE)
                        break;
                DEBUG(4, "Endpoint %d\n", 
self->trans.self.usb.data_endpoint_read);
+#ifdef HAVE_USB1
+               int usberror = libusb_bulk_transfer(self->trans.self.usb.dev,
+                                       self->trans.self.usb.data_endpoint_read,
+                                       buf_reserve_end(msg, self->mtu_rx),
+                                       self->mtu_rx, &actual,
+                                       USB_OBEX_TIMEOUT);
+               if (usberror)
+                       actual = usberror;
+#else
                actual = usb_bulk_read(self->trans.self.usb.dev,
                                        self->trans.self.usb.data_endpoint_read,
                                        buf_reserve_end(msg, self->mtu_rx),
                                        self->mtu_rx, USB_OBEX_TIMEOUT);
+#endif
                buf_remove_end(msg, self->mtu_rx - actual);
                break;
 #endif /*HAVE_USB*/
diff --git a/lib/usb1obex.c b/lib/usb1obex.c
new file mode 100644
index 0000000..1dffa27
--- /dev/null
+++ b/lib/usb1obex.c
@@ -0,0 +1,419 @@
+/**
+       \file usbobex.c
+       USB OBEX, USB transport for OBEX, libusb 1.x support.
+       OpenOBEX library - Free implementation of the Object Exchange protocol.
+
+       Copyright (c) 2009 Alex Kanavin, All Rights Reserved.
+
+       OpenOBEX is free software; you can redistribute it and/or modify
+       it under the terms of the GNU Lesser General Public License as
+       published by the Free Software Foundation; either version 2.1 of
+       the License, or (at your option) any later version.
+
+       This program is distributed in the hope that it will be useful,
+       but WITHOUT ANY WARRANTY; without even the implied warranty of
+       MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+       GNU Lesser General Public License for more details.
+
+       You should have received a copy of the GNU Lesser General Public
+       License along with OpenOBEX. If not, see <http://www.gnu.org/>.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include <config.h>
+#endif
+
+#ifdef HAVE_USB1
+
+#include <string.h>
+#include <unistd.h>
+#include <stdio.h>             /* perror */
+#include <errno.h>             /* errno and EADDRNOTAVAIL */
+#include <stdlib.h>
+
+#include <libusb.h>
+
+#include "obex_main.h"
+#include "usbobex.h"
+#include "usbutils.h"
+
+static struct libusb_context *libusb_ctx = NULL;
+
+/*
+ * Function usbobex_prepare_connect (self, interface)
+ *
+ *    Prepare for USB OBEX connect
+ *
+ */
+void usbobex_prepare_connect(obex_t *self, struct obex_usb_intf_transport_t 
*intf)
+{
+       self->trans.self.usb = *intf;
+}
+
+/*
+ * Helper function to usbobex_find_interfaces
+ */
+static void find_eps(struct obex_usb_intf_transport_t *intf, struct 
libusb_interface_descriptor data_intf, int *found_active, int *found_idle)
+{
+       struct libusb_endpoint_descriptor ep0, ep1;
+
+       if (data_intf.bNumEndpoints == 2) {
+               ep0 = data_intf.endpoint[0];
+               ep1 = data_intf.endpoint[1];
+               if ((ep0.bEndpointAddress & LIBUSB_ENDPOINT_IN) &&
+                   ((ep0.bmAttributes & LIBUSB_TRANSFER_TYPE_MASK) == 
LIBUSB_TRANSFER_TYPE_BULK) &&
+                   !(ep1.bEndpointAddress & LIBUSB_ENDPOINT_IN) &&
+                   ((ep1.bmAttributes & LIBUSB_TRANSFER_TYPE_MASK) == 
LIBUSB_TRANSFER_TYPE_BULK)) {
+                       *found_active = 1;
+                       intf->data_active_setting = data_intf.bAlternateSetting;
+                       intf->data_interface_active_description = 
data_intf.iInterface;
+                       intf->data_endpoint_read = ep0.bEndpointAddress;
+                       intf->data_endpoint_write = ep1.bEndpointAddress;
+               }
+               if (!(ep0.bEndpointAddress & LIBUSB_ENDPOINT_IN) &&
+                   ((ep0.bmAttributes & LIBUSB_TRANSFER_TYPE_MASK) == 
LIBUSB_TRANSFER_TYPE_BULK) &&
+                   (ep1.bEndpointAddress & LIBUSB_ENDPOINT_IN) &&
+                   ((ep1.bmAttributes & LIBUSB_TRANSFER_TYPE_MASK) == 
LIBUSB_TRANSFER_TYPE_BULK)) {
+                       *found_active = 1;
+                       intf->data_active_setting = data_intf.bAlternateSetting;
+                       intf->data_interface_active_description = 
data_intf.iInterface;
+                       intf->data_endpoint_read = ep1.bEndpointAddress;
+                       intf->data_endpoint_write = ep0.bEndpointAddress;
+               }
+       }
+       if (data_intf.bNumEndpoints == 0) {
+               *found_idle = 1;
+               intf->data_idle_setting = data_intf.bAlternateSetting;
+               intf->data_interface_idle_description = data_intf.iInterface;
+       }
+}
+
+/*
+ * Helper function to usbobex_find_interfaces
+ */
+static int find_obex_data_interface(const unsigned char *buffer, int buflen, 
struct libusb_config_descriptor *config, struct obex_usb_intf_transport_t *intf)
+{
+       struct cdc_union_desc *union_header = NULL;
+       int i, a;
+       int found_active = 0;
+       int found_idle = 0;
+
+       if (!buffer) {
+               DEBUG(2,"Weird descriptor references");
+               return -EINVAL;
+       }
+
+       while (buflen > 0) {
+               if (buffer [1] != USB_DT_CS_INTERFACE) {
+                       DEBUG(2,"skipping garbage");
+                       goto next_desc;
+               }
+               switch (buffer [2]) {
+               case CDC_UNION_TYPE: /* we've found it */
+                       if (union_header) {
+                               DEBUG(2,"More than one union descriptor, 
skiping ...");
+                               goto next_desc;
+                       }
+                       union_header = (struct cdc_union_desc *)buffer;
+                       break;
+               case CDC_OBEX_TYPE: /* maybe check version */
+               case CDC_OBEX_SERVICE_ID_TYPE: /* This one is handled later */
+               case CDC_HEADER_TYPE:
+                       break; /* for now we ignore it */
+               default:
+                       DEBUG(2, "Ignoring extra header, type %d, length %d", 
buffer[2], buffer[0]);
+                       break;
+               }
+next_desc:
+               buflen -= buffer[0];
+               buffer += buffer[0];
+       }
+
+       if (!union_header) {
+               DEBUG(2,"No union descriptor, giving up\n");
+               return -ENODEV;
+       }
+       /* Found the slave interface, now find active/idle settings and 
endpoints */
+       intf->data_interface = union_header->bSlaveInterface0;
+       /* Loop through all of the interfaces */
+       for (i = 0; i < config->bNumInterfaces; i++) {
+               /* Loop through all of the alternate settings */
+               for (a = 0; a < config->interface[i].num_altsetting; a++) {
+                       /* Check if this interface is OBEX data interface*/
+                       /* and find endpoints */
+                       if (config->interface[i].altsetting[a].bInterfaceNumber 
== intf->data_interface)
+                               find_eps(intf, 
config->interface[i].altsetting[a], &found_active, &found_idle);
+               }
+       }
+       if (!found_idle) {
+               DEBUG(2,"No idle setting\n");
+               return -ENODEV;
+       }
+       if (!found_active) {
+               DEBUG(2,"No active setting\n");
+               return -ENODEV;
+       }
+
+       return 0;
+}
+
+
+/*
+ * Helper function to usbobex_find_interfaces
+ */
+static int get_intf_string(struct libusb_device_handle *usb_handle, char 
**string, int id)
+{
+       if (id) {
+               if ((*string = malloc(USB_MAX_STRING_SIZE)) == NULL)
+                       return -ENOMEM;
+               *string[0] = '\0';
+               return libusb_get_string_descriptor_ascii(usb_handle, id, 
(unsigned char*)*string, USB_MAX_STRING_SIZE);
+       }
+
+       return 0;
+}
+
+/*
+ * Helper function to usbobex_find_interfaces
+ */
+static struct obex_usb_intf_transport_t *check_intf(struct libusb_device *dev,
+                                       struct libusb_config_descriptor 
*conf_desc, int i, int a,
+                                       struct obex_usb_intf_transport_t 
*current)
+{
+       struct obex_usb_intf_transport_t *next = NULL;
+       if ((conf_desc->interface[i].altsetting[a].bInterfaceClass == 
USB_CDC_CLASS)
+           && (conf_desc->interface[i].altsetting[a].bInterfaceSubClass == 
USB_CDC_OBEX_SUBCLASS)) {
+               int err;
+               const unsigned char *buffer = 
conf_desc->interface[i].altsetting[a].extra;
+               int buflen = conf_desc->interface[i].altsetting[a].extra_length;
+
+               next = malloc(sizeof(struct obex_usb_intf_transport_t));
+               if (next == NULL)
+                       return current;
+               next->device = dev;
+               libusb_ref_device(dev);
+               next->configuration = conf_desc->bConfigurationValue;
+               next->configuration_description = conf_desc->iConfiguration;
+               next->control_interface = 
conf_desc->interface[i].altsetting[a].bInterfaceNumber;
+               next->control_interface_description = 
conf_desc->interface[i].altsetting[a].iInterface;
+               next->control_setting = 
conf_desc->interface[i].altsetting[a].bAlternateSetting;
+               next->extra_descriptors = malloc(buflen);
+               if (next->extra_descriptors)
+                       memcpy(next->extra_descriptors, buffer, buflen);
+               next->extra_descriptors_len = buflen;
+
+               err = find_obex_data_interface(buffer, buflen, conf_desc, next);
+               if (err)
+                       free(next);
+               else {
+                       if (current)
+                               current->next = next;
+                       next->prev = current;
+                       next->next = NULL;
+                       current = next;
+               }
+       }
+       return current;
+}
+
+/*
+ * Function usbobex_find_interfaces ()
+ *
+ *    Find available USBOBEX interfaces on the system
+ */
+int usbobex_find_interfaces(obex_interface_t **interfaces)
+{
+       int usbinit_error = 0;
+       struct obex_usb_intf_transport_t *current = NULL, *tmp = NULL;
+       int i, a, num;
+       obex_interface_t *intf_array = NULL;
+
+       if (libusb_ctx == NULL)
+               usbinit_error = libusb_init(&libusb_ctx);
+       if (usbinit_error == 0) {
+               libusb_device **list;
+               size_t cnt_dev = libusb_get_device_list(libusb_ctx, &list);
+               size_t d = 0;
+               for (d = 0; d < cnt_dev; d++) {
+                       struct libusb_config_descriptor *conf_desc;
+                       if (libusb_get_active_config_descriptor(list[d], 
&conf_desc) == 0) {
+                               for (i = 0; i < conf_desc->bNumInterfaces; i++) 
{
+                                       for (a = 0; a < 
conf_desc->interface[i].num_altsetting; a++) {
+                                               current = check_intf(list[d], 
conf_desc, i, a, current);
+                                       }
+                               }
+                               libusb_free_config_descriptor(conf_desc);
+                       }
+               }
+               libusb_free_device_list(list, 1);
+       }
+
+       num = 0;
+       if (current)
+               num++;
+       while (current && current->prev) {
+               current = current->prev;
+               num++;
+       }
+       intf_array = malloc(sizeof(obex_interface_t) * num);
+       if (intf_array == NULL)
+               goto cleanup_list;
+       memset(intf_array, 0, sizeof(obex_interface_t) * num);
+       num = 0;
+       while (current) {
+               intf_array[num].usb.intf = current;
+               struct libusb_device_handle *usb_handle;
+               if (libusb_open(current->device, &usb_handle) == 0) {
+                       struct libusb_device_descriptor dev_desc;
+                       if (libusb_get_device_descriptor(current->device, 
&dev_desc) == 0) {
+                               get_intf_string(usb_handle, 
&intf_array[num].usb.manufacturer,
+                                       dev_desc.iManufacturer);
+                               get_intf_string(usb_handle, 
&intf_array[num].usb.product,
+                                       dev_desc.iProduct);
+                               get_intf_string(usb_handle, 
&intf_array[num].usb.serial,
+                                       dev_desc.iSerialNumber);
+                               get_intf_string(usb_handle, 
&intf_array[num].usb.configuration,
+                                       current->configuration_description);
+                               get_intf_string(usb_handle, 
&intf_array[num].usb.control_interface,
+                                       current->control_interface_description);
+                               get_intf_string(usb_handle, 
&intf_array[num].usb.data_interface_idle,
+                                       
current->data_interface_idle_description);
+                               get_intf_string(usb_handle, 
&intf_array[num].usb.data_interface_active,
+                                       
current->data_interface_active_description);
+                       }
+                       find_obex_service_descriptor(current->extra_descriptors,
+                                       current->extra_descriptors_len,
+                                       &intf_array[num].usb.service);
+                       libusb_close(usb_handle);
+               }
+               current = current->next; num++;
+       }
+       *interfaces = intf_array;
+       return num;
+
+cleanup_list:
+       while (current) {
+               tmp = current->next;
+               free(current);
+               current = tmp;
+       }
+       return 0;
+}
+
+/*
+ * Function usbobex_free_interfaces ()
+ *
+ *    Free the list of discovered USBOBEX interfaces on the system
+ */
+void usbobex_free_interfaces(int num, obex_interface_t *intf)
+{
+       int i;
+
+       if (intf == NULL)
+               return;
+
+       for (i = 0; i < num; i++) {
+               free(intf[i].usb.manufacturer);
+               free(intf[i].usb.product);
+               free(intf[i].usb.serial);
+               free(intf[i].usb.configuration);
+               free(intf[i].usb.control_interface);
+               free(intf[i].usb.data_interface_idle);
+               free(intf[i].usb.data_interface_active);
+               free(intf[i].usb.service);
+               free(intf[i].usb.intf->extra_descriptors);
+               libusb_unref_device(intf[i].usb.intf->device);
+               free(intf[i].usb.intf);
+       }
+
+       free(intf);
+       if (libusb_ctx)
+               libusb_exit(libusb_ctx);
+
+}
+
+/*
+ * Function usbobex_connect_request (self)
+ *
+ *    Open the USB connection
+ *
+ */
+int usbobex_connect_request(obex_t *self)
+{
+       int ret;
+
+       DEBUG(4, "\n");
+
+       ret = libusb_open(self->trans.self.usb.device, 
&self->trans.self.usb.dev);
+       if (ret != 0)
+               return ret;
+
+       ret = libusb_claim_interface(self->trans.self.usb.dev, 
self->trans.self.usb.control_interface);
+       if (ret < 0) {
+               DEBUG(4, "Can't claim control interface %d", ret);
+               goto err1;
+       }
+
+       ret = libusb_set_interface_alt_setting(self->trans.self.usb.dev, 
self->trans.self.usb.control_interface, self->trans.self.usb.control_setting);
+       if (ret < 0) {
+               DEBUG(4, "Can't set control setting %d", ret);
+               goto err2;
+       }
+
+       ret = libusb_claim_interface(self->trans.self.usb.dev, 
self->trans.self.usb.data_interface);
+       if (ret < 0) {
+               DEBUG(4, "Can't claim data interface %d", ret);
+               goto err2;
+       }
+
+       ret = libusb_set_interface_alt_setting(self->trans.self.usb.dev, 
self->trans.self.usb.data_interface, self->trans.self.usb.data_active_setting);
+       if (ret < 0) {
+               DEBUG(4, "Can't set data active setting %d", ret);
+               goto err3;
+       }
+
+       self->trans.mtu = OBEX_MAXIMUM_MTU;
+       DEBUG(2, "transport mtu=%d\n", self->trans.mtu);
+       return 1;
+
+err3:
+       libusb_release_interface(self->trans.self.usb.dev, 
self->trans.self.usb.data_interface);
+err2:
+       libusb_release_interface(self->trans.self.usb.dev, 
self->trans.self.usb.control_interface);
+err1:
+       libusb_close(self->trans.self.usb.dev);
+       return ret;
+}
+
+/*
+ * Function usbobex_disconnect_request (self)
+ *
+ *    Shutdown the USB link
+ *
+ */
+int usbobex_disconnect_request(obex_t *self)
+{
+       int ret;
+       if (self->trans.connected == FALSE)
+               return 0;
+
+       DEBUG(4, "\n");
+
+       libusb_clear_halt(self->trans.self.usb.dev, 
self->trans.self.usb.data_endpoint_read);
+       libusb_clear_halt(self->trans.self.usb.dev, 
self->trans.self.usb.data_endpoint_write);
+
+       ret = libusb_set_interface_alt_setting(self->trans.self.usb.dev, 
self->trans.self.usb.data_interface, self->trans.self.usb.data_idle_setting);
+       if (ret < 0)
+               DEBUG(4, "Can't set data idle setting %d", ret);
+       ret = libusb_release_interface(self->trans.self.usb.dev, 
self->trans.self.usb.data_interface);
+       if (ret < 0)
+               DEBUG(4, "Can't release data interface %d", ret);
+       ret = libusb_release_interface(self->trans.self.usb.dev, 
self->trans.self.usb.control_interface);
+       if (ret < 0)
+               DEBUG(4, "Can't release control interface %d", ret);
+       libusb_close(self->trans.self.usb.dev);
+       return 1;
+}
+
+
+#endif /* HAVE_USB1 */
diff --git a/lib/usbobex.c b/lib/usbobex.c
index b87458d..2ad91a0 100644
--- a/lib/usbobex.c
+++ b/lib/usbobex.c
@@ -23,7 +23,7 @@
 #include <config.h>
 #endif
 
-#ifdef HAVE_USB
+#if defined HAVE_USB && !defined HAVE_USB1
 
 #ifdef _WIN32
 #include <winsock2.h>
@@ -43,6 +43,7 @@
 
 #include "obex_main.h"
 #include "usbobex.h"
+#include "usbutils.h"
 
 /*
  * Function usbobex_prepare_connect (self, interface)
@@ -203,7 +204,9 @@ static struct obex_usb_intf_transport_t *check_intf(struct 
usb_device *dev,
                next->control_interface = 
dev->config[c].interface[i].altsetting[a].bInterfaceNumber;
                next->control_interface_description = 
dev->config[c].interface[i].altsetting[a].iInterface;
                next->control_setting = 
dev->config[c].interface[i].altsetting[a].bAlternateSetting;
-               next->extra_descriptors = buffer;
+               next->extra_descriptors = malloc(buflen);
+               if (next->extra_descriptors)
+                       memcpy(next->extra_descriptors, buffer, buflen);
                next->extra_descriptors_len = buflen;
 
                err = find_obex_data_interface(buffer, buflen, dev->config[c], 
next);
@@ -222,53 +225,6 @@ static struct obex_usb_intf_transport_t *check_intf(struct 
usb_device *dev,
 }
 
 /*
- * Helper function to usbobex_find_interfaces
- */
-static void find_obex_service_descriptor(unsigned char *buffer, int buflen, 
obex_usb_intf_service_t **service)
-{
-       if (!buffer) {
-               DEBUG(2, "Weird descriptor references");
-               return ;
-       }
-       while (buflen > 0) {
-               if (buffer[1] != USB_DT_CS_INTERFACE) {
-                       DEBUG(2, "skipping garbage");
-                       goto next_desc;
-               }
-               switch (buffer[2]) {
-               case CDC_OBEX_SERVICE_ID_TYPE: /* we've found it */
-                       if (buflen < 22) /* Check descriptor size */
-                               DEBUG(2, "Invalid service id descriptor");
-                       else if (*service == NULL) {
-                               *service = 
malloc(sizeof(obex_usb_intf_service_t));
-                               if (*service != NULL) {
-                                       const uint8_t default_uuid[16] = 
WMC_DEFAULT_OBEX_SERVER_UUID;
-                                       (*service)->role = buffer[3];
-                                       memcpy((*service)->uuid, buffer+4, 16);
-                                       (*service)->version = 
(buffer[20]<<8)|(buffer[21]);
-                                       if (memcmp((*service)->uuid, 
default_uuid, 16) == 0 )
-                                               (*service)->is_default_uuid = 1;
-                                       else
-                                               (*service)->is_default_uuid = 0;
-                               }
-                       }
-                       break;
-               case CDC_OBEX_TYPE: /* maybe check version */
-               case CDC_UNION_TYPE:
-               case CDC_HEADER_TYPE:
-                       break;
-               default:
-                       DEBUG(2, "Ignoring extra header, type %d, length %d", 
buffer[2], buffer[0]);
-                       break;
-               }
-next_desc:
-               buflen -= buffer[0];
-               buffer += buffer[0];
-       }
-}
-
-
-/*
  * Function usbobex_find_interfaces ()
  *
  *    Find available USBOBEX interfaces on the system
@@ -374,6 +330,7 @@ void usbobex_free_interfaces(int num, obex_interface_t 
*intf)
                free(intf[i].usb.data_interface_idle);
                free(intf[i].usb.data_interface_active);
                free(intf[i].usb.service);
+               free(intf[i].usb.intf->extra_descriptors);
                free(intf[i].usb.intf);
        }
 
diff --git a/lib/usbobex.h b/lib/usbobex.h
index 9fb1797..80203ae 100644
--- a/lib/usbobex.h
+++ b/lib/usbobex.h
@@ -23,12 +23,16 @@
 #define USBOBEX_H
 
 #include <openobex/obex_const.h>
+
+#ifdef HAVE_USB1
+#include <libusb.h>
+#else
 #include <usb.h>
+#endif
 
 /* Information about a USB OBEX interface present on the system */
 struct obex_usb_intf_transport_t {
        struct obex_usb_intf_transport_t *prev, *next;  /* Next and previous 
interfaces in the list */
-       struct usb_device *device;              /* USB device that has the 
interface */
        int configuration;                      /* Device configuration */
        int configuration_description;          /* Configuration string 
descriptor number */
        int control_interface;                  /* OBEX master interface */
@@ -37,7 +41,7 @@ struct obex_usb_intf_transport_t {
                                                 * If non-zero, use 
usb_get_string_simple() from 
                                                 * libusb to retrieve 
human-readable description
                                                 */
-       unsigned char *extra_descriptors;               /* Extra master 
interface descriptors */
+       char *extra_descriptors;                /* Extra master interface 
descriptors */
        int extra_descriptors_len;              /* Length of extra descriptors 
*/
        int data_interface;                     /* OBEX data/slave interface */
        int data_idle_setting;                  /* OBEX data/slave idle setting 
*/
@@ -48,7 +52,13 @@ struct obex_usb_intf_transport_t {
                                                 * in active setting */
        int data_endpoint_read;                 /* OBEX data/slave interface 
read endpoint */
        int data_endpoint_write;                /* OBEX data/slave interface 
write endpoint */
-       usb_dev_handle *dev;                    /* libusb handler */
+#ifdef HAVE_USB1
+       struct libusb_device *device;           /* libusb 1.x device */
+       struct libusb_device_handle *dev;       /* libusb 1.x device handle */
+#else
+       struct usb_device *device;              /* libusb 0.x device */
+       usb_dev_handle *dev;                    /* libusb 0.x device handle */
+#endif
 };
 
 /* "Union Functional Descriptor" from CDC spec 5.2.3.X
diff --git a/lib/usbutils.c b/lib/usbutils.c
new file mode 100644
index 0000000..92bb4bf
--- /dev/null
+++ b/lib/usbutils.c
@@ -0,0 +1,82 @@
+/**
+       \file usbutils.c
+       USB OBEX, USB transport for OBEX, support functions.
+       OpenOBEX library - Free implementation of the Object Exchange protocol.
+
+       Copyright (c) 2009 Alex Kanavin, All Rights Reserved.
+
+       OpenOBEX is free software; you can redistribute it and/or modify
+       it under the terms of the GNU Lesser General Public License as
+       published by the Free Software Foundation; either version 2.1 of
+       the License, or (at your option) any later version.
+
+       This program is distributed in the hope that it will be useful,
+       but WITHOUT ANY WARRANTY; without even the implied warranty of
+       MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+       GNU Lesser General Public License for more details.
+
+       You should have received a copy of the GNU Lesser General Public
+       License along with OpenOBEX. If not, see <http://www.gnu.org/>.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include <config.h>
+#endif
+
+#ifdef HAVE_USB
+
+#include <string.h>
+#include <unistd.h>
+#include <stdio.h>             /* perror */
+#include <errno.h>             /* errno and EADDRNOTAVAIL */
+#include <stdlib.h>
+#include "obex_main.h"
+#include "usbobex.h"
+
+/*
+ * Helper function to usbobex_find_interfaces
+ */
+void find_obex_service_descriptor(const char *buffer, int buflen, 
obex_usb_intf_service_t **service)
+{
+       if (!buffer) {
+               DEBUG(2, "Weird descriptor references");
+               return ;
+       }
+       while (buflen > 0) {
+               if (buffer[1] != USB_DT_CS_INTERFACE) {
+                       DEBUG(2, "skipping garbage");
+                       goto next_desc;
+               }
+               switch (buffer[2]) {
+               case CDC_OBEX_SERVICE_ID_TYPE: /* we've found it */
+                       if (buflen < 22) /* Check descriptor size */
+                               DEBUG(2, "Invalid service id descriptor");
+                       else if (*service == NULL) {
+                               *service = 
malloc(sizeof(obex_usb_intf_service_t));
+                               if (*service != NULL) {
+                                       const uint8_t default_uuid[16] = 
WMC_DEFAULT_OBEX_SERVER_UUID;
+                                       (*service)->role = buffer[3];
+                                       memcpy((*service)->uuid, buffer+4, 16);
+                                       (*service)->version = 
(buffer[20]<<8)|(buffer[21]);
+                                       if (memcmp((*service)->uuid, 
default_uuid, 16) == 0 )
+                                               (*service)->is_default_uuid = 1;
+                                       else
+                                               (*service)->is_default_uuid = 0;
+                               }
+                       }
+                       break;
+               case CDC_OBEX_TYPE: /* maybe check version */
+               case CDC_UNION_TYPE:
+               case CDC_HEADER_TYPE:
+                       break;
+               default:
+                       DEBUG(2, "Ignoring extra header, type %d, length %d", 
buffer[2], buffer[0]);
+                       break;
+               }
+next_desc:
+               buflen -= buffer[0];
+               buffer += buffer[0];
+       }
+}
+
+#endif
diff --git a/lib/usbutils.h b/lib/usbutils.h
new file mode 100644
index 0000000..02cb6e3
--- /dev/null
+++ b/lib/usbutils.h
@@ -0,0 +1,30 @@
+/**
+       \file usbutils.h
+       USB OBEX, USB transport for OBEX, support functions.
+       OpenOBEX library - Free implementation of the Object Exchange protocol.
+
+       Copyright (c) 2009 Alex Kanavin, All Rights Reserved.
+
+       OpenOBEX is free software; you can redistribute it and/or modify
+       it under the terms of the GNU Lesser General Public License as
+       published by the Free Software Foundation; either version 2.1 of
+       the License, or (at your option) any later version.
+
+       This program is distributed in the hope that it will be useful,
+       but WITHOUT ANY WARRANTY; without even the implied warranty of
+       MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+       GNU Lesser General Public License for more details.
+
+       You should have received a copy of the GNU Lesser General Public
+       License along with OpenOBEX. If not, see <http://www.gnu.org/>.
+ */
+
+#ifndef USBUTILS_H
+#define USBUTILS_H
+
+#include <openobex/obex_const.h>
+
+void find_obex_service_descriptor(const char *buffer, int buflen, 
obex_usb_intf_service_t **service);
+
+#endif
+
-- 
1.6.0.6


------------------------------------------------------------------------------
Crystal Reports - New Free Runtime and 30 Day Trial
Check out the new simplified licensing option that enables 
unlimited royalty-free distribution of the report engine 
for externally facing server and web deployment. 
http://p.sf.net/sfu/businessobjects
_______________________________________________
Openobex-users mailing list
Openobex-users@lists.sourceforge.net
http://lists.sourceforge.net/lists/listinfo/openobex-users

Reply via email to