OLD | NEW |
1 /* | 1 /* |
2 * \file libusb-glue.c | 2 * \file libusb-glue.c |
3 * Low-level USB interface glue towards libusb. | 3 * Low-level USB interface glue towards libusb. |
4 * | 4 * |
5 * Copyright (C) 2005-2007 Richard A. Low <richard@wentnet.com> | 5 * Copyright (C) 2005-2007 Richard A. Low <richard@wentnet.com> |
6 * Copyright (C) 2005-2012 Linus Walleij <triad@df.lth.se> | 6 * Copyright (C) 2005-2012 Linus Walleij <triad@df.lth.se> |
7 * Copyright (C) 2006-2007 Marcus Meissner | 7 * Copyright (C) 2006-2007 Marcus Meissner |
8 * Copyright (C) 2007 Ted Bullock | 8 * Copyright (C) 2007 Ted Bullock |
9 * Copyright (C) 2008 Chris Bagwell <chris@cnpbagwell.com> | 9 * Copyright (C) 2008 Chris Bagwell <chris@cnpbagwell.com> |
10 * | 10 * |
(...skipping 82 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
93 static const LIBMTP_device_entry_t mtp_device_table[] = { | 93 static const LIBMTP_device_entry_t mtp_device_table[] = { |
94 /* We include an .h file which is shared between us and libgphoto2 */ | 94 /* We include an .h file which is shared between us and libgphoto2 */ |
95 #include "music-players.h" | 95 #include "music-players.h" |
96 }; | 96 }; |
97 static const int mtp_device_table_size = sizeof(mtp_device_table) / sizeof(LIBMT
P_device_entry_t); | 97 static const int mtp_device_table_size = sizeof(mtp_device_table) / sizeof(LIBMT
P_device_entry_t); |
98 | 98 |
99 // Local functions | 99 // Local functions |
100 static struct usb_bus* init_usb(); | 100 static struct usb_bus* init_usb(); |
101 static void close_usb(PTP_USB* ptp_usb); | 101 static void close_usb(PTP_USB* ptp_usb); |
102 static int find_interface_and_endpoints(struct usb_device *dev, | 102 static int find_interface_and_endpoints(struct usb_device *dev, |
| 103 uint8_t *conf, |
103 uint8_t *interface, | 104 uint8_t *interface, |
| 105 uint8_t *altsetting, |
104 int* inep, | 106 int* inep, |
105 int* inep_maxpacket, | 107 int* inep_maxpacket, |
106 int* outep, | 108 int* outep, |
107 int* outep_maxpacket, | 109 int* outep_maxpacket, |
108 int* intep); | 110 int* intep); |
109 static void clear_stall(PTP_USB* ptp_usb); | 111 static void clear_stall(PTP_USB* ptp_usb); |
110 static int init_ptp_usb (PTPParams* params, PTP_USB* ptp_usb, struct usb_device*
dev); | 112 static int init_ptp_usb(PTPParams* params, PTP_USB* ptp_usb, struct usb_device*
dev); |
111 static short ptp_write_func (unsigned long,PTPDataHandler*,void *data,unsigned l
ong*); | 113 static short ptp_write_func(unsigned long,PTPDataHandler*,void *data,unsigned lo
ng*); |
112 static short ptp_read_func (unsigned long,PTPDataHandler*,void *data,unsigned lo
ng*,int); | 114 static short ptp_read_func(unsigned long,PTPDataHandler*,void *data,unsigned lon
g*,int); |
113 static int usb_clear_stall_feature(PTP_USB* ptp_usb, int ep); | 115 static int usb_clear_stall_feature(PTP_USB* ptp_usb, int ep); |
114 static int usb_get_endpoint_status(PTP_USB* ptp_usb, int ep, uint16_t* status); | 116 static int usb_get_endpoint_status(PTP_USB* ptp_usb, int ep, uint16_t* status); |
115 | 117 |
116 /** | 118 /** |
117 * Get a list of the supported USB devices. | 119 * Get a list of the supported USB devices. |
118 * | 120 * |
119 * The developers depend on users of this library to constantly | 121 * The developers depend on users of this library to constantly |
120 * add in to the list of supported devices. What we need is the | 122 * add in to the list of supported devices. What we need is the |
121 * device name, USB Vendor ID (VID) and USB Product ID (PID). | 123 * device name, USB Vendor ID (VID) and USB Product ID (PID). |
122 * put this into a bug ticket at the project homepage, please. | 124 * put this into a bug ticket at the project homepage, please. |
(...skipping 1492 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1615 USB_TYPE_CLASS | USB_RECIP_INTERFACE, | 1617 USB_TYPE_CLASS | USB_RECIP_INTERFACE, |
1616 0x64, 0x0000, 0x0000, | 1618 0x64, 0x0000, 0x0000, |
1617 (char *) buffer, | 1619 (char *) buffer, |
1618 sizeof(buffer), | 1620 sizeof(buffer), |
1619 ptp_usb->timeout); | 1621 ptp_usb->timeout); |
1620 if (ret < sizeof(buffer)) | 1622 if (ret < sizeof(buffer)) |
1621 return PTP_ERROR_IO; | 1623 return PTP_ERROR_IO; |
1622 return PTP_RC_OK; | 1624 return PTP_RC_OK; |
1623 } | 1625 } |
1624 | 1626 |
1625 static int init_ptp_usb (PTPParams* params, PTP_USB* ptp_usb, struct usb_device*
dev) | 1627 static int init_ptp_usb(PTPParams* params, PTP_USB* ptp_usb, struct usb_device*
dev) |
1626 { | 1628 { |
1627 usb_dev_handle *device_handle; | 1629 usb_dev_handle *device_handle; |
1628 char buf[255]; | 1630 char buf[255]; |
1629 int usbresult; | 1631 int usbresult; |
1630 | 1632 |
1631 params->sendreq_func=ptp_usb_sendreq; | 1633 params->sendreq_func=ptp_usb_sendreq; |
1632 params->senddata_func=ptp_usb_senddata; | 1634 params->senddata_func=ptp_usb_senddata; |
1633 params->getresp_func=ptp_usb_getresp; | 1635 params->getresp_func=ptp_usb_getresp; |
1634 params->getdata_func=ptp_usb_getdata; | 1636 params->getdata_func=ptp_usb_getdata; |
1635 params->cancelreq_func=ptp_usb_control_cancel_request; | 1637 params->cancelreq_func=ptp_usb_control_cancel_request; |
1636 params->data=ptp_usb; | 1638 params->data=ptp_usb; |
1637 params->transaction_id=0; | 1639 params->transaction_id=0; |
1638 /* | 1640 /* |
1639 * This is hardcoded here since we have no devices whatsoever that are BE. | 1641 * This is hardcoded here since we have no devices whatsoever that are BE. |
1640 * Change this the day we run into our first BE device (if ever). | 1642 * Change this the day we run into our first BE device (if ever). |
1641 */ | 1643 */ |
1642 params->byteorder = PTP_DL_LE; | 1644 params->byteorder = PTP_DL_LE; |
1643 | 1645 |
1644 ptp_usb->timeout = get_timeout(ptp_usb); | 1646 ptp_usb->timeout = get_timeout(ptp_usb); |
1645 | 1647 |
1646 device_handle = usb_open(dev); | 1648 device_handle = usb_open(dev); |
1647 if (!device_handle) { | 1649 if (!device_handle) { |
1648 perror("usb_open()"); | 1650 perror("usb_open()"); |
1649 return -1; | 1651 return -1; |
1650 } | 1652 } |
1651 ptp_usb->handle = device_handle; | 1653 ptp_usb->handle = device_handle; |
| 1654 |
1652 #ifdef LIBUSB_HAS_DETACH_KERNEL_DRIVER_NP | 1655 #ifdef LIBUSB_HAS_DETACH_KERNEL_DRIVER_NP |
1653 /* | 1656 /* |
1654 * If this device is known to be wrongfully claimed by other kernel | 1657 * If this device is known to be wrongfully claimed by other kernel |
1655 * drivers (such as mass storage), then try to unload it to make it | 1658 * drivers (such as mass storage), then try to unload it to make it |
1656 * accessible from user space. | 1659 * accessible from user space. |
1657 */ | 1660 */ |
1658 if (FLAG_UNLOAD_DRIVER(ptp_usb)) { | 1661 if (FLAG_UNLOAD_DRIVER(ptp_usb)) { |
1659 if (usb_get_driver_np(device_handle, (int) ptp_usb->interface, | 1662 if (usb_get_driver_np(device_handle, (int) ptp_usb->interface, |
1660 buf, sizeof(buf)) == 0) { | 1663 buf, sizeof(buf)) == 0) { |
1661 if (usb_detach_kernel_driver_np(device_handle, | 1664 if (usb_detach_kernel_driver_np(device_handle, |
1662 (int) ptp_usb->interface)) { | 1665 (int) ptp_usb->interface)) { |
1663 perror("usb_detach_kernel_driver_np()"); | 1666 perror("usb_detach_kernel_driver_np()"); |
1664 return -1; | 1667 return -1; |
1665 } | 1668 } |
1666 } | 1669 } |
1667 } | 1670 } |
1668 #endif | 1671 #endif |
1669 #ifdef __WIN32__ | 1672 |
1670 // Only needed on Windows, and cause problems on other platforms. | 1673 /* |
1671 if (usb_set_configuration(device_handle, dev->config->bConfigurationValue)) { | 1674 * Check if the config is set to something else than what we want |
1672 perror("usb_set_configuration()"); | 1675 * to use. Only set the configuration if we absolutely have to. |
1673 return -1; | 1676 * Also do not bail out if we fail. |
| 1677 */ |
| 1678 if (dev->config->bConfigurationValue != ptp_usb->config) { |
| 1679 if (usb_set_configuration(device_handle, dev->config->bConfigurationValue))
{ |
| 1680 perror("error in usb_set_configuration()- continuing anyway"); |
| 1681 } |
1674 } | 1682 } |
1675 #endif | 1683 |
1676 // It seems like on kernel 2.6.31 if we already have it open on another | 1684 /* |
1677 // pthread in our app, we'll get an error if we try to claim it again, | 1685 * It seems like on kernel 2.6.31 if we already have it open on another |
1678 // but that error is harmless because our process already claimed the interfac
e | 1686 * pthread in our app, we'll get an error if we try to claim it again, |
| 1687 * but that error is harmless because our process already claimed the interfac
e |
| 1688 */ |
1679 usbresult = usb_claim_interface(device_handle, (int) ptp_usb->interface); | 1689 usbresult = usb_claim_interface(device_handle, (int) ptp_usb->interface); |
1680 | 1690 |
1681 if (usbresult != 0) | 1691 if (usbresult != 0) |
1682 fprintf(stderr, "ignoring usb_claim_interface = %d", usbresult); | 1692 fprintf(stderr, "ignoring usb_claim_interface = %d", usbresult); |
1683 | 1693 |
1684 // FIXME : Discovered in the Barry project | 1694 /* |
1685 // kernels >= 2.6.28 don't set the interface the same way as | 1695 * If the altsetting is set to something different than we want, switch |
1686 // previous versions did, and the Blackberry gets confused | 1696 * it. |
1687 // if it isn't explicitly set | 1697 * |
1688 // See above, same issue with pthreads means that if this fails it is not | 1698 * FIXME: this seems to cause trouble on the Mac:s so disable it. Retry |
1689 // fatal | 1699 * this on the Mac now that it only sets this when the altsetting differs. |
1690 // However, this causes problems on Macs so disable here | 1700 */ |
1691 #ifndef __APPLE__ | 1701 #ifndef __APPLE__ |
1692 usbresult = usb_set_altinterface(device_handle, 0); | 1702 #if 0 /* Disable this always, no idea on how to handle it */ |
1693 if (usbresult) | 1703 if (dev->config->interface[].altsetting[] != |
1694 fprintf(stderr, "ignoring usb_claim_interface = %d", usbresult); | 1704 ptp_usb->altsetting) { |
| 1705 fprintf(stderr, "desired altsetting different from current, trying to set al
tsetting\n"); |
| 1706 usbresult = usb_set_altinterface(device_handle, 0); |
| 1707 if (usbresult) |
| 1708 fprintf(stderr, "ignoring error from usb_claim_interface = %d\n", usbresul
t); |
| 1709 } |
| 1710 #endif |
1695 #endif | 1711 #endif |
1696 | 1712 |
1697 if (FLAG_SWITCH_MODE_BLACKBERRY(ptp_usb)) { | 1713 if (FLAG_SWITCH_MODE_BLACKBERRY(ptp_usb)) { |
1698 int ret; | 1714 int ret; |
1699 | 1715 |
1700 // FIXME : Only for BlackBerry Storm | 1716 // FIXME : Only for BlackBerry Storm |
1701 // What does it mean? Maybe switch mode... | 1717 // What does it mean? Maybe switch mode... |
1702 // This first control message is absolutely necessary | 1718 // This first control message is absolutely necessary |
1703 usleep(1000); | 1719 usleep(1000); |
1704 ret = usb_control_msg(device_handle, | 1720 ret = usb_control_msg(device_handle, |
(...skipping 115 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1820 */ | 1836 */ |
1821 usb_reset(ptp_usb->handle); | 1837 usb_reset(ptp_usb->handle); |
1822 } | 1838 } |
1823 usb_close(ptp_usb->handle); | 1839 usb_close(ptp_usb->handle); |
1824 } | 1840 } |
1825 | 1841 |
1826 /** | 1842 /** |
1827 * Self-explanatory? | 1843 * Self-explanatory? |
1828 */ | 1844 */ |
1829 static int find_interface_and_endpoints(struct usb_device *dev, | 1845 static int find_interface_and_endpoints(struct usb_device *dev, |
| 1846 uint8_t *conf, |
1830 uint8_t *interface, | 1847 uint8_t *interface, |
| 1848 uint8_t *altsetting, |
1831 int* inep, | 1849 int* inep, |
1832 int* inep_maxpacket, | 1850 int* inep_maxpacket, |
1833 int* outep, | 1851 int* outep, |
1834 int *outep_maxpacket, | 1852 int *outep_maxpacket, |
1835 int* intep) | 1853 int* intep) |
1836 { | 1854 { |
1837 int i; | 1855 uint8_t i; |
1838 | 1856 |
1839 // Loop over the device configurations | 1857 // Loop over the device configurations |
1840 for (i = 0; i < dev->descriptor.bNumConfigurations; i++) { | 1858 for (i = 0; i < dev->descriptor.bNumConfigurations; i++) { |
1841 uint8_t j; | 1859 uint8_t j; |
1842 | 1860 |
| 1861 *conf = dev->config->bConfigurationValue;; |
| 1862 |
1843 // Loop over each configurations interfaces | 1863 // Loop over each configurations interfaces |
1844 for (j = 0; j < dev->config[i].bNumInterfaces; j++) { | 1864 for (j = 0; j < dev->config[i].bNumInterfaces; j++) { |
1845 uint8_t k; | 1865 uint8_t k, l; |
1846 uint8_t no_ep; | 1866 uint8_t no_ep; |
1847 int found_inep = 0; | 1867 int found_inep = 0; |
1848 int found_outep = 0; | 1868 int found_outep = 0; |
1849 int found_intep = 0; | 1869 int found_intep = 0; |
1850 struct usb_endpoint_descriptor *ep; | 1870 struct usb_endpoint_descriptor *ep; |
1851 | 1871 |
1852 // MTP devices shall have 3 endpoints, ignore those interfaces | 1872 // Inspect the altsettings of this interface |
1853 // that haven't. | 1873 for (k = 0; k < dev->config[i].interface[j].num_altsetting; k++) { |
1854 no_ep = dev->config[i].interface[j].altsetting->bNumEndpoints; | |
1855 if (no_ep != 3) | |
1856 » continue; | |
1857 | 1874 |
1858 *interface = dev->config[i].interface[j].altsetting->bInterfaceNumber; | 1875 » // MTP devices shall have 3 endpoints, ignore those interfaces |
1859 ep = dev->config[i].interface[j].altsetting->endpoint; | 1876 » // that haven't. |
| 1877 » no_ep = dev->config[i].interface[j].altsetting[k].bNumEndpoints; |
| 1878 » if (no_ep != 3) |
| 1879 » continue; |
1860 | 1880 |
1861 // Loop over the three endpoints to locate two bulk and | 1881 » *interface = dev->config[i].interface[j].altsetting[k].bInterfaceNumber; |
1862 // one interrupt endpoint and FAIL if we cannot, and continue. | 1882 » *altsetting = dev->config[i].interface[j].altsetting[k].bAlternateSettin
g; |
1863 for (k = 0; k < no_ep; k++) { | 1883 » ep = dev->config[i].interface[j].altsetting[k].endpoint; |
1864 » if (ep[k].bmAttributes == USB_ENDPOINT_TYPE_BULK) { | 1884 |
1865 » if ((ep[k].bEndpointAddress & USB_ENDPOINT_DIR_MASK) == | 1885 » // Loop over the three endpoints to locate two bulk and |
1866 » USB_ENDPOINT_DIR_MASK) { | 1886 » // one interrupt endpoint and FAIL if we cannot, and continue. |
1867 » *inep = ep[k].bEndpointAddress; | 1887 » for (l = 0; l < no_ep; l++) { |
1868 » *inep_maxpacket = ep[k].wMaxPacketSize; | 1888 » if (ep[l].bmAttributes == USB_ENDPOINT_TYPE_BULK) { |
1869 » found_inep = 1; | 1889 » if ((ep[l].bEndpointAddress & USB_ENDPOINT_DIR_MASK) == |
1870 » } | 1890 » » USB_ENDPOINT_DIR_MASK) { |
1871 » if ((ep[k].bEndpointAddress & USB_ENDPOINT_DIR_MASK) == 0) { | 1891 » *inep = ep[l].bEndpointAddress; |
1872 » *outep = ep[k].bEndpointAddress; | 1892 » *inep_maxpacket = ep[l].wMaxPacketSize; |
1873 » *outep_maxpacket = ep[k].wMaxPacketSize; | 1893 » found_inep = 1; |
1874 » found_outep = 1; | 1894 » } |
1875 » } | 1895 » if ((ep[l].bEndpointAddress & USB_ENDPOINT_DIR_MASK) == 0) { |
1876 » } else if (ep[k].bmAttributes == USB_ENDPOINT_TYPE_INTERRUPT) { | 1896 » *outep = ep[l].bEndpointAddress; |
1877 » if ((ep[k].bEndpointAddress & USB_ENDPOINT_DIR_MASK) == | 1897 » *outep_maxpacket = ep[l].wMaxPacketSize; |
1878 » USB_ENDPOINT_DIR_MASK) { | 1898 » found_outep = 1; |
1879 » *intep = ep[k].bEndpointAddress; | 1899 » } |
1880 » found_intep = 1; | 1900 » } else if (ep[l].bmAttributes == USB_ENDPOINT_TYPE_INTERRUPT) { |
| 1901 » if ((ep[l].bEndpointAddress & USB_ENDPOINT_DIR_MASK) == |
| 1902 » » USB_ENDPOINT_DIR_MASK) { |
| 1903 » *intep = ep[l].bEndpointAddress; |
| 1904 » found_intep = 1; |
| 1905 » } |
1881 } | 1906 } |
1882 } | 1907 } |
1883 } | 1908 » if (found_inep && found_outep && found_intep) |
1884 if (found_inep && found_outep && found_intep) | 1909 » // We assigned the endpoints so return here. |
1885 » // We assigned the endpoints so return here. | 1910 » return 0; |
1886 » return 0; | 1911 » // Else loop to next interface/config |
1887 // Else loop to next interface/config | 1912 } /* Next altsetting */ |
1888 } | 1913 } /* Next interface */ |
1889 } | 1914 } /* Next config */ |
1890 return -1; | 1915 return -1; |
1891 } | 1916 } |
1892 | 1917 |
1893 /** | 1918 /** |
1894 * This function assigns params and usbinfo given a raw device | 1919 * This function assigns params and usbinfo given a raw device |
1895 * as input. | 1920 * as input. |
1896 * @param device the device to be assigned. | 1921 * @param device the device to be assigned. |
1897 * @param usbinfo a pointer to the new usbinfo. | 1922 * @param usbinfo a pointer to the new usbinfo. |
1898 * @return an error code. | 1923 * @return an error code. |
1899 */ | 1924 */ |
(...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1947 * Some devices must have their "OS Descriptor" massaged in order | 1972 * Some devices must have their "OS Descriptor" massaged in order |
1948 * to work. | 1973 * to work. |
1949 */ | 1974 */ |
1950 if (FLAG_ALWAYS_PROBE_DESCRIPTOR(ptp_usb)) { | 1975 if (FLAG_ALWAYS_PROBE_DESCRIPTOR(ptp_usb)) { |
1951 // Massage the device descriptor | 1976 // Massage the device descriptor |
1952 (void) probe_device_descriptor(libusb_device, NULL); | 1977 (void) probe_device_descriptor(libusb_device, NULL); |
1953 } | 1978 } |
1954 | 1979 |
1955 /* Assign interface and endpoints to usbinfo... */ | 1980 /* Assign interface and endpoints to usbinfo... */ |
1956 err = find_interface_and_endpoints(libusb_device, | 1981 err = find_interface_and_endpoints(libusb_device, |
| 1982 &ptp_usb->config, |
1957 &ptp_usb->interface, | 1983 &ptp_usb->interface, |
| 1984 &ptp_usb->altsetting, |
1958 &ptp_usb->inep, | 1985 &ptp_usb->inep, |
1959 &ptp_usb->inep_maxpacket, | 1986 &ptp_usb->inep_maxpacket, |
1960 &ptp_usb->outep, | 1987 &ptp_usb->outep, |
1961 &ptp_usb->outep_maxpacket, | 1988 &ptp_usb->outep_maxpacket, |
1962 &ptp_usb->intep); | 1989 &ptp_usb->intep); |
1963 | 1990 |
1964 if (err) { | 1991 if (err) { |
1965 LIBMTP_ERROR("LIBMTP PANIC: Unable to find interface & endpoints of device\n
"); | 1992 LIBMTP_ERROR("LIBMTP PANIC: Unable to find interface & endpoints of device\n
"); |
1966 return LIBMTP_ERROR_CONNECTING; | 1993 return LIBMTP_ERROR_CONNECTING; |
1967 } | 1994 } |
(...skipping 113 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2081 { | 2108 { |
2082 return (usb_control_msg(ptp_usb->handle, | 2109 return (usb_control_msg(ptp_usb->handle, |
2083 USB_DP_DTH|USB_RECIP_ENDPOINT, | 2110 USB_DP_DTH|USB_RECIP_ENDPOINT, |
2084 USB_REQ_GET_STATUS, | 2111 USB_REQ_GET_STATUS, |
2085 USB_FEATURE_HALT, | 2112 USB_FEATURE_HALT, |
2086 ep, | 2113 ep, |
2087 (char *) status, | 2114 (char *) status, |
2088 2, | 2115 2, |
2089 ptp_usb->timeout)); | 2116 ptp_usb->timeout)); |
2090 } | 2117 } |
OLD | NEW |