25#include <winpr/assert.h>
26#include <winpr/cast.h>
27#include <winpr/wtypes.h>
28#include <winpr/sysinfo.h>
29#include <winpr/collections.h>
33#include "libusb_udevice.h"
35#include "../common/urbdrc_types.h"
37#define BASIC_STATE_FUNC_DEFINED(_arg, _type) \
38 WINPR_ATTR_NODISCARD \
39 static _type udev_get_##_arg(IUDEVICE* idev) \
41 UDEVICE* pdev = (UDEVICE*)idev; \
44 static void udev_set_##_arg(IUDEVICE* idev, _type _t) \
46 UDEVICE* pdev = (UDEVICE*)idev; \
50#define BASIC_POINT_FUNC_DEFINED(_arg, _type) \
51 WINPR_ATTR_NODISCARD \
52 static _type udev_get_p_##_arg(IUDEVICE* idev) \
54 UDEVICE* pdev = (UDEVICE*)idev; \
57 static void udev_set_p_##_arg(IUDEVICE* idev, _type _t) \
59 UDEVICE* pdev = (UDEVICE*)idev; \
63#define BASIC_STATE_FUNC_REGISTER(_arg, _dev) \
64 _dev->iface.get_##_arg = udev_get_##_arg; \
65 (_dev)->iface.set_##_arg = udev_set_##_arg
67#if LIBUSB_API_VERSION >= 0x01000103
68#define HAVE_STREAM_ID_API 1
79 UINT32 OutputBufferSize;
83 t_isoch_transfer_cb cb;
85#if !defined(HAVE_STREAM_ID_API)
88} ASYNC_TRANSFER_USER_DATA;
90static void request_free(
void* value);
93static struct libusb_transfer* list_contains(wArrayList* list, UINT32 streamID)
98 count = ArrayList_Count(list);
99 for (
size_t x = 0; x < count; x++)
101 struct libusb_transfer* transfer = ArrayList_GetItem(list, x);
103#if defined(HAVE_STREAM_ID_API)
104 const UINT32 currentID = libusb_transfer_get_stream_id(transfer);
106 const ASYNC_TRANSFER_USER_DATA* user_data = (ASYNC_TRANSFER_USER_DATA*)transfer->user_data;
107 const UINT32 currentID = user_data->streamID;
109 if (currentID == streamID)
116static UINT32 stream_id_from_buffer(
struct libusb_transfer* transfer)
120#if defined(HAVE_STREAM_ID_API)
121 return libusb_transfer_get_stream_id(transfer);
123 ASYNC_TRANSFER_USER_DATA* user_data = (ASYNC_TRANSFER_USER_DATA*)transfer->user_data;
126 return user_data->streamID;
130static void set_stream_id_for_buffer(
struct libusb_transfer* transfer, UINT32 streamID)
132#if defined(HAVE_STREAM_ID_API)
133 libusb_transfer_set_stream_id(transfer, streamID);
135 ASYNC_TRANSFER_USER_DATA* user_data = (ASYNC_TRANSFER_USER_DATA*)transfer->user_data;
138 user_data->streamID = streamID;
142WINPR_ATTR_FORMAT_ARG(3, 8)
143static BOOL log_libusb_result_(wLog* log, DWORD lvl, WINPR_FORMAT_ARG const
char* fmt,
144 const
char* fkt, const
char* file,
size_t line,
int error, ...)
150 char buffer[8192] = WINPR_C_ARRAY_INIT;
151 va_list ap = WINPR_C_ARRAY_INIT;
153 (void)vsnprintf(buffer,
sizeof(buffer), fmt, ap);
156 WLog_Print(log, lvl,
"[%s:%" PRIuz
"]: %s: error %s[%d]", fkt, line, buffer,
157 libusb_error_name(error), error);
163#define log_libusb_result(log, lvl, fmt, error, ...) \
164 log_libusb_result_((log), (lvl), (fmt), __func__, __FILE__, __LINE__, error, ##__VA_ARGS__)
167const char* usb_interface_class_to_string(uint8_t c_class)
171 case LIBUSB_CLASS_PER_INTERFACE:
172 return "LIBUSB_CLASS_PER_INTERFACE";
173 case LIBUSB_CLASS_AUDIO:
174 return "LIBUSB_CLASS_AUDIO";
175 case LIBUSB_CLASS_COMM:
176 return "LIBUSB_CLASS_COMM";
177 case LIBUSB_CLASS_HID:
178 return "LIBUSB_CLASS_HID";
179 case LIBUSB_CLASS_PHYSICAL:
180 return "LIBUSB_CLASS_PHYSICAL";
181 case LIBUSB_CLASS_PRINTER:
182 return "LIBUSB_CLASS_PRINTER";
183 case LIBUSB_CLASS_IMAGE:
184 return "LIBUSB_CLASS_IMAGE";
185 case LIBUSB_CLASS_MASS_STORAGE:
186 return "LIBUSB_CLASS_MASS_STORAGE";
187 case LIBUSB_CLASS_HUB:
188 return "LIBUSB_CLASS_HUB";
189 case LIBUSB_CLASS_DATA:
190 return "LIBUSB_CLASS_DATA";
191 case LIBUSB_CLASS_SMART_CARD:
192 return "LIBUSB_CLASS_SMART_CARD";
193 case LIBUSB_CLASS_CONTENT_SECURITY:
194 return "LIBUSB_CLASS_CONTENT_SECURITY";
195 case LIBUSB_CLASS_VIDEO:
196 return "LIBUSB_CLASS_VIDEO";
197 case LIBUSB_CLASS_PERSONAL_HEALTHCARE:
198 return "LIBUSB_CLASS_PERSONAL_HEALTHCARE";
199 case LIBUSB_CLASS_DIAGNOSTIC_DEVICE:
200 return "LIBUSB_CLASS_DIAGNOSTIC_DEVICE";
201 case LIBUSB_CLASS_WIRELESS:
202 return "LIBUSB_CLASS_WIRELESS";
203 case LIBUSB_CLASS_APPLICATION:
204 return "LIBUSB_CLASS_APPLICATION";
205 case LIBUSB_CLASS_VENDOR_SPEC:
206 return "LIBUSB_CLASS_VENDOR_SPEC";
208 return "UNKNOWN_DEVICE_CLASS";
212static void async_transfer_user_data_free(ASYNC_TRANSFER_USER_DATA* user_data)
216 Stream_Free(user_data->data, TRUE);
221WINPR_ATTR_MALLOC(async_transfer_user_data_free, 1)
222static ASYNC_TRANSFER_USER_DATA*
223async_transfer_user_data_new(IUDEVICE* idev, UINT32 MessageId,
size_t offset,
size_t BufferSize,
224 const BYTE* data,
size_t packetSize, BOOL NoAck,
int transferDir,
227 ASYNC_TRANSFER_USER_DATA* user_data =
nullptr;
230 if (BufferSize > UINT32_MAX)
233 user_data = calloc(1,
sizeof(ASYNC_TRANSFER_USER_DATA));
237 user_data->data = Stream_New(
nullptr, offset + BufferSize + packetSize);
239 if (!user_data->data)
245 Stream_Seek(user_data->data, offset);
247 memcpy(Stream_Pointer(user_data->data), data, BufferSize);
249 user_data->noack = NoAck;
250 user_data->transferDir = transferDir;
252 user_data->callback = callback;
253 user_data->idev = idev;
254 user_data->MessageId = MessageId;
256 user_data->queue = pdev->request_queue;
261static void LIBUSB_CALL func_iso_callback(
struct libusb_transfer* transfer)
263 ASYNC_TRANSFER_USER_DATA* user_data = (ASYNC_TRANSFER_USER_DATA*)transfer->user_data;
264 const UINT32 streamID = stream_id_from_buffer(transfer);
265 wArrayList* list = user_data->queue;
267 ArrayList_Lock(list);
268 switch (transfer->status)
270 case LIBUSB_TRANSFER_COMPLETED:
273 BYTE* dataStart = Stream_Pointer(user_data->data);
274 if (!Stream_SetPosition(user_data->data,
278 for (uint32_t i = 0; i < WINPR_ASSERTING_INT_CAST(uint32_t, transfer->num_iso_packets);
281 const UINT32 act_len = transfer->iso_packet_desc[i].actual_length;
282 Stream_Write_UINT32(user_data->data, index);
283 Stream_Write_UINT32(user_data->data, act_len);
284 Stream_Write_UINT32(user_data->data, transfer->iso_packet_desc[i].status);
286 if (transfer->iso_packet_desc[i].status != USBD_STATUS_SUCCESS)
287 user_data->ErrorCount++;
290 const unsigned char* packetBuffer =
291 libusb_get_iso_packet_buffer_simple(transfer, i);
292 BYTE* data = dataStart + index;
294 if (data != packetBuffer)
295 memmove(data, packetBuffer, act_len);
300 user_data->OutputBufferSize = index;
304 case LIBUSB_TRANSFER_CANCELLED:
307 case LIBUSB_TRANSFER_TIMED_OUT:
310 case LIBUSB_TRANSFER_ERROR:
316 const UINT32 InterfaceId =
317 ((STREAM_ID_PROXY << 30) | user_data->idev->get_ReqCompletion(user_data->idev));
319 if (list_contains(list, streamID))
321 if (!user_data->noack)
323 const UINT32 RequestID = streamID & INTERFACE_ID_MASK;
324 user_data->cb(user_data->idev, user_data->callback, user_data->data,
325 InterfaceId, user_data->noack, user_data->MessageId, RequestID,
326 WINPR_ASSERTING_INT_CAST(uint32_t, transfer->num_iso_packets),
327 transfer->status, user_data->StartFrame, user_data->ErrorCount,
328 user_data->OutputBufferSize, user_data->transferDir);
329 user_data->data =
nullptr;
331 ArrayList_Remove(list, transfer);
336 ArrayList_Unlock(list);
340static int func_get_interface_number(
const LIBUSB_CONFIG_DESCRIPTOR* config,
unsigned index)
342 if (!config || !config->interface || (index >= config->bNumInterfaces))
343 return LIBUSB_ERROR_NOT_FOUND;
345 const LIBUSB_INTERFACE*
interface = &config->interface[index];
346 if (!interface->altsetting || (interface->num_altsetting <= 0))
347 return LIBUSB_ERROR_NOT_FOUND;
348 return interface->altsetting[0].bInterfaceNumber;
352static const LIBUSB_INTERFACE_DESCRIPTOR*
353func_get_interface_descriptor(
const LIBUSB_CONFIG_DESCRIPTOR* config, BYTE number, BYTE alternate)
355 if (!config || !config->interface)
358 for (
int index = 0; index < config->bNumInterfaces; index++)
360 const LIBUSB_INTERFACE*
interface = &config->interface[index];
361 if (!interface->altsetting)
363 for (
int alt = 0; alt < interface->num_altsetting; alt++)
365 const LIBUSB_INTERFACE_DESCRIPTOR* descriptor = &interface->altsetting[alt];
366 if ((descriptor->bInterfaceNumber == number) &&
367 (descriptor->bAlternateSetting == alternate))
375static const LIBUSB_ENDPOINT_DESCEIPTOR* func_get_ep_desc(LIBUSB_CONFIG_DESCRIPTOR* LibusbConfig,
377 UINT32 EndpointAddress)
380 const LIBUSB_INTERFACE*
interface = LibusbConfig->interface;
382 for (UINT32 inum = 0; inum < MsConfig->NumInterfaces; inum++)
384 if (inum >= LibusbConfig->bNumInterfaces)
387 const LIBUSB_INTERFACE* ifc = &interface[inum];
388 BYTE alt = MsInterfaces[inum]->AlternateSetting;
389 if (alt >= ifc->num_altsetting)
392 const struct libusb_interface_descriptor* altifc = &ifc->altsetting[alt];
393 const LIBUSB_ENDPOINT_DESCEIPTOR* endpoint = altifc->endpoint;
395 for (UINT32 pnum = 0; pnum < MsInterfaces[inum]->NumberOfPipes; pnum++)
397 if (pnum >= altifc->bNumEndpoints)
400 if (endpoint[pnum].bEndpointAddress == EndpointAddress)
402 return &endpoint[pnum];
410static void LIBUSB_CALL func_bulk_transfer_cb(
struct libusb_transfer* transfer)
412 uint32_t streamID = 0;
414 ASYNC_TRANSFER_USER_DATA* user_data = (ASYNC_TRANSFER_USER_DATA*)transfer->user_data;
417 WLog_ERR(TAG,
"Invalid transfer->user_data!");
420 wArrayList* list = user_data->queue;
421 ArrayList_Lock(list);
422 streamID = stream_id_from_buffer(transfer);
424 if (list_contains(list, streamID))
426 const UINT32 InterfaceId =
427 ((STREAM_ID_PROXY << 30) | user_data->idev->get_ReqCompletion(user_data->idev));
428 const UINT32 RequestID = streamID & INTERFACE_ID_MASK;
430 UINT32 status = USBD_STATUS_SUCCESS;
431 switch (transfer->status)
433 case LIBUSB_TRANSFER_COMPLETED:
434 status = USBD_STATUS_SUCCESS;
437 case LIBUSB_TRANSFER_ERROR:
438 status = USBD_STATUS_CANCELED;
441 case LIBUSB_TRANSFER_TIMED_OUT:
442 status = USBD_STATUS_TIMEOUT;
446 case LIBUSB_TRANSFER_CANCELLED:
447 status = USBD_STATUS_SUCCESS;
450 case LIBUSB_TRANSFER_STALL:
451 status = USBD_STATUS_STALL_PID;
454 case LIBUSB_TRANSFER_NO_DEVICE:
455 status = USBD_STATUS_DEVICE_GONE;
458 case LIBUSB_TRANSFER_OVERFLOW:
459 status = USBD_STATUS_BABBLE_DETECTED;
463 status = USBD_STATUS_CANCELED;
467 user_data->cb(user_data->idev, user_data->callback, user_data->data, InterfaceId,
468 user_data->noack, user_data->MessageId, RequestID,
469 WINPR_ASSERTING_INT_CAST(uint32_t, transfer->num_iso_packets), status,
470 user_data->StartFrame, user_data->ErrorCount,
471 WINPR_ASSERTING_INT_CAST(uint32_t, transfer->actual_length),
472 user_data->transferDir);
473 user_data->data =
nullptr;
474 ArrayList_Remove(list, transfer);
476 ArrayList_Unlock(list);
483 if (!urbdrc || !status)
489 *status = USBD_STATUS_SUCCESS;
492 case LIBUSB_ERROR_IO:
493 *status = USBD_STATUS_STALL_PID;
496 case LIBUSB_ERROR_INVALID_PARAM:
497 *status = USBD_STATUS_INVALID_PARAMETER;
500 case LIBUSB_ERROR_ACCESS:
501 *status = USBD_STATUS_NOT_ACCESSED;
504 case LIBUSB_ERROR_NO_DEVICE:
505 *status = USBD_STATUS_DEVICE_GONE;
509 if (!(pdev->status & URBDRC_DEVICE_NOT_FOUND))
510 pdev->status |= URBDRC_DEVICE_NOT_FOUND;
515 case LIBUSB_ERROR_NOT_FOUND:
516 *status = USBD_STATUS_STALL_PID;
519 case LIBUSB_ERROR_BUSY:
520 *status = USBD_STATUS_STALL_PID;
523 case LIBUSB_ERROR_TIMEOUT:
524 *status = USBD_STATUS_TIMEOUT;
527 case LIBUSB_ERROR_OVERFLOW:
528 *status = USBD_STATUS_STALL_PID;
531 case LIBUSB_ERROR_PIPE:
532 *status = USBD_STATUS_STALL_PID;
535 case LIBUSB_ERROR_INTERRUPTED:
536 *status = USBD_STATUS_STALL_PID;
539 case LIBUSB_ERROR_NO_MEM:
540 *status = USBD_STATUS_NO_MEMORY;
543 case LIBUSB_ERROR_NOT_SUPPORTED:
544 *status = USBD_STATUS_NOT_SUPPORTED;
547 case LIBUSB_ERROR_OTHER:
548 *status = USBD_STATUS_STALL_PID;
552 *status = USBD_STATUS_SUCCESS;
559static int func_config_release_all_interface(
URBDRC_PLUGIN* urbdrc,
560 LIBUSB_DEVICE_HANDLE* libusb_handle,
561 const LIBUSB_CONFIG_DESCRIPTOR* config)
563 WINPR_ASSERT(urbdrc);
566 (void)log_libusb_result(urbdrc->log, WLOG_ERROR,
567 "func_config_release_all_interface(config=nullptr)",
568 LIBUSB_ERROR_INVALID_PARAM);
571 for (
unsigned index = 0; index < config->bNumInterfaces; index++)
573 const int number = func_get_interface_number(config, index);
576 const int ret = libusb_release_interface(libusb_handle, number);
577 if (log_libusb_result(urbdrc->log, WLOG_WARN,
"libusb_release_interface", ret))
583static int func_claim_all_interface(
URBDRC_PLUGIN* urbdrc, LIBUSB_DEVICE_HANDLE* libusb_handle,
584 const LIBUSB_CONFIG_DESCRIPTOR* config)
586 WINPR_ASSERT(urbdrc);
589 (void)log_libusb_result(urbdrc->log, WLOG_ERROR,
"func_claim_all_interface(config=nullptr)",
590 LIBUSB_ERROR_INVALID_PARAM);
593 for (
unsigned index = 0; index < config->bNumInterfaces; index++)
595 const int number = func_get_interface_number(config, index);
598 int ret = libusb_claim_interface(libusb_handle, number);
599 if (log_libusb_result(urbdrc->log, WLOG_DEBUG,
"libusb_claim_interface", ret))
604 if (libusb_set_auto_detach_kernel_driver(libusb_handle, 0) == LIBUSB_SUCCESS)
605 ret = libusb_claim_interface(libusb_handle, number);
606 if (log_libusb_result(urbdrc->log, WLOG_ERROR,
"libusb_claim_interface", ret))
614static LIBUSB_DEVICE* udev_get_libusb_dev(libusb_context* context, uint8_t bus_number,
617 LIBUSB_DEVICE** libusb_list =
nullptr;
618 LIBUSB_DEVICE* device =
nullptr;
619 const ssize_t total_device = libusb_get_device_list(context, &libusb_list);
621 for (ssize_t i = 0; i < total_device; i++)
623 LIBUSB_DEVICE* dev = libusb_list[i];
624 if ((bus_number == libusb_get_bus_number(dev)) &&
625 (dev_number == libusb_get_device_address(dev)))
628 libusb_unref_device(dev);
631 libusb_free_device_list(libusb_list, 0);
635WINPR_ATTR_MALLOC(free, 1)
636static LIBUSB_DEVICE_DESCRIPTOR* udev_new_descript(
URBDRC_PLUGIN* urbdrc, LIBUSB_DEVICE* libusb_dev)
639 LIBUSB_DEVICE_DESCRIPTOR* descriptor =
640 (LIBUSB_DEVICE_DESCRIPTOR*)calloc(1,
sizeof(LIBUSB_DEVICE_DESCRIPTOR));
643 ret = libusb_get_device_descriptor(libusb_dev, descriptor);
645 if (log_libusb_result(urbdrc->log, WLOG_ERROR,
"libusb_get_device_descriptor", ret))
655static int libusb_udev_select_interface(IUDEVICE* idev, BYTE InterfaceNumber, BYTE AlternateSetting)
659 if (!pdev || !pdev->urbdrc)
665 libusb_set_interface_alt_setting(pdev->libusb_handle, InterfaceNumber, AlternateSetting);
667 log_libusb_result(urbdrc->log, WLOG_ERROR,
"libusb_set_interface_alt_setting", error);
677 UINT32 MsOutSize = 0;
679 if (!pdev || !pdev->LibusbConfig || !pdev->urbdrc || !MsConfig)
683 LIBUSB_CONFIG_DESCRIPTOR* LibusbConfig = pdev->LibusbConfig;
685 if (LibusbConfig->bNumInterfaces != MsConfig->NumInterfaces)
687 WLog_Print(urbdrc->log, WLOG_ERROR,
688 "Select Configuration: Libusb NumberInterfaces(%" PRIu8
") is different "
689 "with MsConfig NumberInterfaces(%" PRIu32
")",
690 LibusbConfig->bNumInterfaces, MsConfig->NumInterfaces);
699 for (UINT32 inum = 0; inum < MsConfig->NumInterfaces; inum++)
704 if (!func_get_interface_descriptor(LibusbConfig, MsInterface->InterfaceNumber,
705 MsInterface->AlternateSetting))
707 WLog_Print(urbdrc->log, WLOG_ERROR,
708 "USB interface %" PRIu8
" alternate setting %" PRIu8
" not found",
709 MsInterface->InterfaceNumber, MsInterface->AlternateSetting);
714 for (UINT32 inum = 0; inum < MsConfig->NumInterfaces; inum++)
719 const LIBUSB_INTERFACE_DESCRIPTOR* LibusbAltsetting = func_get_interface_descriptor(
720 LibusbConfig, MsInterface->InterfaceNumber, MsInterface->AlternateSetting);
721 WINPR_ASSERT(LibusbAltsetting);
722 const BYTE LibusbNumEndpoint = LibusbAltsetting->bNumEndpoints;
726 for (UINT32 pnum = 0; pnum < LibusbNumEndpoint; pnum++)
731 if (pnum < MsInterface->NumberOfPipes && MsInterface->MsPipes)
734 t_MsPipe->MaximumPacketSize = MsPipe->MaximumPacketSize;
735 t_MsPipe->MaximumTransferSize = MsPipe->MaximumTransferSize;
736 t_MsPipe->PipeFlags = MsPipe->PipeFlags;
740 t_MsPipe->MaximumPacketSize = 0;
741 t_MsPipe->MaximumTransferSize = 0xffffffff;
742 t_MsPipe->PipeFlags = 0;
745 t_MsPipe->PipeHandle = 0;
746 t_MsPipe->bEndpointAddress = 0;
747 t_MsPipe->bInterval = 0;
748 t_MsPipe->PipeType = 0;
749 t_MsPipe->InitCompleted = 0;
750 t_MsPipes[pnum] = t_MsPipe;
753 msusb_mspipes_replace(MsInterface, t_MsPipes, LibusbNumEndpoint);
764 MsConfig->ConfigurationHandle = (uint32_t)MsConfig->bConfigurationValue |
765 ((uint32_t)pdev->bus_number << 24) |
766 (((uint32_t)pdev->dev_number << 16) & 0xFF0000);
767 MsInterfaces = MsConfig->MsInterfaces;
769 for (UINT32 inum = 0; inum < MsConfig->NumInterfaces; inum++)
774 const LIBUSB_INTERFACE_DESCRIPTOR* LibusbAltsetting = func_get_interface_descriptor(
775 LibusbConfig, MsInterface->InterfaceNumber, MsInterface->AlternateSetting);
776 WINPR_ASSERT(LibusbAltsetting);
783 MsInterface->InterfaceHandle =
784 WINPR_ASSERTING_INT_CAST(UINT32, (LibusbAltsetting->bInterfaceNumber |
785 (LibusbAltsetting->bAlternateSetting << 8) |
786 (pdev->dev_number << 16) | (pdev->bus_number << 24)));
787 const size_t len = 16 + (MsInterface->NumberOfPipes * 20);
788 MsInterface->Length = WINPR_ASSERTING_INT_CAST(UINT16, len);
789 MsInterface->bInterfaceClass = LibusbAltsetting->bInterfaceClass;
790 MsInterface->bInterfaceSubClass = LibusbAltsetting->bInterfaceSubClass;
791 MsInterface->bInterfaceProtocol = LibusbAltsetting->bInterfaceProtocol;
792 MsInterface->InitCompleted = 1;
794 const BYTE LibusbNumEndpoint = LibusbAltsetting->bNumEndpoints;
796 for (UINT32 pnum = 0; pnum < LibusbNumEndpoint; pnum++)
802 const LIBUSB_ENDPOINT_DESCEIPTOR* LibusbEndpoint = &LibusbAltsetting->endpoint[pnum];
809 MsPipe->PipeHandle = LibusbEndpoint->bEndpointAddress |
810 (((uint32_t)pdev->dev_number << 16) & 0xFF0000) |
811 (((uint32_t)pdev->bus_number << 24) & 0xFF000000);
813 unsigned max = LibusbEndpoint->wMaxPacketSize & 0x07ff;
814 BYTE attr = LibusbEndpoint->bmAttributes;
816 if ((attr & 0x3) == 1 || (attr & 0x3) == 3)
818 max *= (1 + ((LibusbEndpoint->wMaxPacketSize >> 11) & 3));
821 MsPipe->MaximumPacketSize = WINPR_ASSERTING_INT_CAST(uint16_t, max);
822 MsPipe->bEndpointAddress = LibusbEndpoint->bEndpointAddress;
823 MsPipe->bInterval = LibusbEndpoint->bInterval;
824 MsPipe->PipeType = attr & 0x3;
825 MsPipe->InitCompleted = 1;
829 MsConfig->MsOutSize = WINPR_ASSERTING_INT_CAST(
int, MsOutSize);
830 MsConfig->InitCompleted = 1;
833 if (MsConfig != pdev->MsConfig)
835 msusb_msconfig_free(pdev->MsConfig);
836 pdev->MsConfig = MsConfig;
843static BOOL libusb_udev_detach_kernel_driver(IUDEVICE* idev);
846static int libusb_udev_select_configuration(IUDEVICE* idev, UINT32 bConfigurationValue)
850 LIBUSB_DEVICE_HANDLE* libusb_handle =
nullptr;
851 LIBUSB_DEVICE* libusb_dev =
nullptr;
853 LIBUSB_CONFIG_DESCRIPTOR** LibusbConfig =
nullptr;
856 if (!pdev || !pdev->MsConfig || !pdev->LibusbConfig || !pdev->urbdrc)
859 urbdrc = pdev->urbdrc;
860 MsConfig = pdev->MsConfig;
861 libusb_handle = pdev->libusb_handle;
862 libusb_dev = pdev->libusb_dev;
863 LibusbConfig = &pdev->LibusbConfig;
865 if (MsConfig->InitCompleted)
867 func_config_release_all_interface(pdev->urbdrc, libusb_handle, *LibusbConfig);
875 pdev->status &= (UINT16)~URBDRC_DEVICE_DETACH_KERNEL;
876 if (!libusb_udev_detach_kernel_driver(idev))
877 WLog_Print(urbdrc->log, WLOG_WARN,
"libusb_udev_detach_kernel_driver failed, ignoring");
880 if (bConfigurationValue == 0)
881 ret = libusb_set_configuration(libusb_handle, -1);
883 ret = libusb_set_configuration(libusb_handle,
884 WINPR_ASSERTING_INT_CAST(
int, bConfigurationValue));
886 if (log_libusb_result(urbdrc->log, WLOG_ERROR,
"libusb_set_configuration", ret))
888 func_claim_all_interface(urbdrc, libusb_handle, *LibusbConfig);
893 ret = libusb_get_active_config_descriptor(libusb_dev, LibusbConfig);
895 if (log_libusb_result(urbdrc->log, WLOG_ERROR,
"libusb_set_configuration", ret))
897 func_claim_all_interface(urbdrc, libusb_handle, *LibusbConfig);
902 return func_claim_all_interface(urbdrc, libusb_handle, *LibusbConfig);
906static int libusb_udev_control_pipe_request(IUDEVICE* idev, WINPR_ATTR_UNUSED UINT32 RequestId,
907 UINT32 EndpointAddress, UINT32* UsbdStatus,
int command)
912 WINPR_ASSERT(EndpointAddress <= UINT8_MAX);
920 idev->cancel_all_transfer_request(idev);
926 error = libusb_control_transfer(pdev->libusb_handle,
927 (uint8_t)LIBUSB_ENDPOINT_OUT |
928 (uint8_t)LIBUSB_RECIPIENT_ENDPOINT,
929 LIBUSB_REQUEST_SET_FEATURE, ENDPOINT_HALT,
930 (uint16_t)EndpointAddress,
nullptr, 0, 1000);
934 idev->cancel_all_transfer_request(idev);
935 error = libusb_clear_halt(pdev->libusb_handle, (uint8_t)EndpointAddress);
949static UINT32 libusb_udev_control_query_device_text(IUDEVICE* idev, UINT32 TextType,
950 UINT16 LocaleId, UINT8* BufferSize,
954 LIBUSB_DEVICE_DESCRIPTOR* devDescriptor =
nullptr;
955 const char strDesc[] =
"Generic Usb String";
956 char deviceLocation[25] = WINPR_C_ARRAY_INIT;
958 BYTE device_address = 0;
961 WCHAR* text = WINPR_PACKED_ALIGN_CAST(WCHAR*, Buffer);
964 const UINT8 inSize = *BufferSize;
967 if (!pdev || !pdev->devDescriptor || !pdev->urbdrc)
968 return ERROR_INVALID_DATA;
970 urbdrc = pdev->urbdrc;
971 devDescriptor = pdev->devDescriptor;
975 case DeviceTextDescription:
977 BYTE data[0x100] = WINPR_C_ARRAY_INIT;
978 ret = libusb_get_string_descriptor(pdev->libusb_handle, devDescriptor->iProduct,
979 LocaleId, data, 0xFF);
988 if ((ret <= 0) || (ret <= 4) || (slen <= 4) || (locale != LIBUSB_DT_STRING) ||
991 const char* msg =
"SHORT_DESCRIPTOR";
993 msg = libusb_error_name(ret);
994 WLog_Print(urbdrc->log, WLOG_DEBUG,
995 "libusb_get_string_descriptor: "
996 "%s [%d], iProduct: %" PRIu8
"!",
997 msg, ret, devDescriptor->iProduct);
999 size_t len = MIN(
sizeof(strDesc), inSize);
1000 for (
size_t i = 0; i < len; i++)
1001 text[i] = (WCHAR)strDesc[i];
1003 *BufferSize = (BYTE)(len *
sizeof(WCHAR));
1007 size_t maxlen = inSize;
1009 if (inSize >
sizeof(WCHAR))
1011 maxlen -=
sizeof(WCHAR);
1018 const size_t rchar =
1019 _wcsnlen((WCHAR*)&data[2], (
sizeof(data) /
sizeof(WCHAR)) - 1);
1020 len = MIN((BYTE)ret - 2, slen);
1021 len = MIN(len, rchar *
sizeof(WCHAR));
1022 len = MIN(len, maxlen);
1024 memcpy(Buffer, &data[2], len);
1028 if (Buffer[len] !=
'\0')
1030 Buffer[len++] =
'\0';
1031 Buffer[len++] =
'\0';
1034 *BufferSize = (BYTE)len;
1039 case DeviceTextLocationInformation:
1041 bus_number = libusb_get_bus_number(pdev->libusb_dev);
1042 device_address = libusb_get_device_address(pdev->libusb_dev);
1043 (void)sprintf_s(deviceLocation,
sizeof(deviceLocation),
1044 "Port_#%04" PRIu8
".Hub_#%04" PRIu8
"", device_address, bus_number);
1046 size_t len = strnlen(deviceLocation,
1047 MIN(
sizeof(deviceLocation), (inSize > 0) ? inSize - 1U : 0));
1048 for (
size_t i = 0; i < len; i++)
1049 text[i] = (WCHAR)deviceLocation[i];
1051 *BufferSize = (UINT8)(len *
sizeof(WCHAR));
1056 WLog_Print(urbdrc->log, WLOG_DEBUG,
"Query Text: unknown TextType %" PRIu32
"",
1058 return ERROR_INVALID_DATA;
1065static int libusb_udev_os_feature_descriptor_request(IUDEVICE* idev,
1066 WINPR_ATTR_UNUSED UINT32 RequestId,
1067 BYTE Recipient, BYTE InterfaceNumber,
1068 BYTE Ms_PageIndex, UINT16 Ms_featureDescIndex,
1069 UINT32* UsbdStatus, UINT32* BufferSize,
1070 BYTE* Buffer, UINT32 Timeout)
1073 BYTE ms_string_desc[0x13] = WINPR_C_ARRAY_INIT;
1077 WINPR_ASSERT(pdev->urbdrc);
1078 WINPR_ASSERT(UsbdStatus);
1079 WINPR_ASSERT(BufferSize);
1081 if (*BufferSize > UINT16_MAX)
1083 WLog_Print(pdev->urbdrc->log, WLOG_ERROR,
"BufferSize %" PRIu32
" > %d", *BufferSize,
1088 const UINT16 requestedSize = WINPR_ASSERTING_INT_CAST(UINT16, *BufferSize);
1094 error = libusb_control_transfer(pdev->libusb_handle, LIBUSB_ENDPOINT_IN | Recipient,
1095 LIBUSB_REQUEST_GET_DESCRIPTOR, 0x03ee, 0, ms_string_desc, 0x12,
1098 log_libusb_result(pdev->urbdrc->log, WLOG_DEBUG,
"libusb_control_transfer", error);
1102 const BYTE bMS_Vendorcode = ms_string_desc[16];
1104 error = libusb_control_transfer(
1105 pdev->libusb_handle,
1106 (uint8_t)LIBUSB_ENDPOINT_IN | (uint8_t)LIBUSB_REQUEST_TYPE_VENDOR | Recipient,
1107 bMS_Vendorcode, (UINT16)((InterfaceNumber << 8) | Ms_PageIndex), Ms_featureDescIndex,
1108 Buffer, requestedSize, Timeout);
1109 log_libusb_result(pdev->urbdrc->log, WLOG_DEBUG,
"libusb_control_transfer", error);
1112 *BufferSize = (UINT32)error;
1116 *UsbdStatus = USBD_STATUS_STALL_PID;
1118 *UsbdStatus = USBD_STATUS_SUCCESS;
1120 return ERROR_SUCCESS;
1124static enum device_speed libusb_udev_query_device_speed(IUDEVICE* idev)
1128 if (!pdev || !pdev->libusb_dev)
1129 return DEVICE_SPEED_UNKNOWN;
1131 switch (libusb_get_device_speed(pdev->libusb_dev))
1133 case LIBUSB_SPEED_LOW:
1134 return DEVICE_SPEED_LOW;
1136 case LIBUSB_SPEED_FULL:
1137 return DEVICE_SPEED_FULL;
1139 case LIBUSB_SPEED_HIGH:
1140 return DEVICE_SPEED_HIGH;
1142 case LIBUSB_SPEED_SUPER:
1143 return DEVICE_SPEED_SUPER;
1145#if LIBUSB_API_VERSION >= 0x01000106
1146 case LIBUSB_SPEED_SUPER_PLUS:
1147 return DEVICE_SPEED_SUPER_PLUS;
1151 return DEVICE_SPEED_UNKNOWN;
1156static int libusb_udev_query_device_descriptor(IUDEVICE* idev,
int offset)
1163 return pdev->devDescriptor->bLength;
1165 case B_DESCRIPTOR_TYPE:
1166 return pdev->devDescriptor->bDescriptorType;
1169 return pdev->devDescriptor->bcdUSB;
1171 case B_DEVICE_CLASS:
1172 return pdev->devDescriptor->bDeviceClass;
1174 case B_DEVICE_SUBCLASS:
1175 return pdev->devDescriptor->bDeviceSubClass;
1177 case B_DEVICE_PROTOCOL:
1178 return pdev->devDescriptor->bDeviceProtocol;
1180 case B_MAX_PACKET_SIZE0:
1181 return pdev->devDescriptor->bMaxPacketSize0;
1184 return pdev->devDescriptor->idVendor;
1187 return pdev->devDescriptor->idProduct;
1190 return pdev->devDescriptor->bcdDevice;
1192 case I_MANUFACTURER:
1193 return pdev->devDescriptor->iManufacturer;
1196 return pdev->devDescriptor->iProduct;
1198 case I_SERIAL_NUMBER:
1199 return pdev->devDescriptor->iSerialNumber;
1201 case B_NUM_CONFIGURATIONS:
1202 return pdev->devDescriptor->bNumConfigurations;
1210static BOOL libusb_udev_detach_kernel_driver(IUDEVICE* idev)
1216 if (!pdev || !pdev->LibusbConfig || !pdev->libusb_handle || !pdev->urbdrc)
1222 urbdrc = pdev->urbdrc;
1224 if ((pdev->status & URBDRC_DEVICE_DETACH_KERNEL) == 0)
1226 for (
unsigned i = 0; i < pdev->LibusbConfig->bNumInterfaces; i++)
1228 const int number = func_get_interface_number(pdev->LibusbConfig, i);
1231 err = libusb_kernel_driver_active(pdev->libusb_handle, number);
1232 log_libusb_result(urbdrc->log, WLOG_DEBUG,
"libusb_kernel_driver_active", err);
1236 err = libusb_detach_kernel_driver(pdev->libusb_handle, number);
1237 log_libusb_result(urbdrc->log, WLOG_DEBUG,
"libusb_detach_kernel_driver", err);
1241 pdev->status |= URBDRC_DEVICE_DETACH_KERNEL;
1249static BOOL libusb_udev_attach_kernel_driver(IUDEVICE* idev)
1254 if (!pdev || !pdev->LibusbConfig || !pdev->libusb_handle || !pdev->urbdrc)
1257 for (
unsigned i = 0; i < pdev->LibusbConfig->bNumInterfaces && err != LIBUSB_ERROR_NO_DEVICE;
1260 const int number = func_get_interface_number(pdev->LibusbConfig, i);
1263 err = libusb_release_interface(pdev->libusb_handle, number);
1265 log_libusb_result(pdev->urbdrc->log, WLOG_DEBUG,
"libusb_release_interface", err);
1268 if (err != LIBUSB_ERROR_NO_DEVICE)
1270 err = libusb_attach_kernel_driver(pdev->libusb_handle, number);
1271 log_libusb_result(pdev->urbdrc->log, WLOG_DEBUG,
"libusb_attach_kernel_driver if=%d",
1281static int libusb_udev_is_composite_device(IUDEVICE* idev)
1284 return pdev->isCompositeDevice;
1288static int libusb_udev_is_exist(IUDEVICE* idev)
1291 return (pdev->status & URBDRC_DEVICE_NOT_FOUND) ? 0 : 1;
1295static int libusb_udev_is_channel_closed(IUDEVICE* idev)
1298 IUDEVMAN* udevman =
nullptr;
1299 if (!pdev || !pdev->urbdrc)
1302 udevman = pdev->urbdrc->udevman;
1305 if (udevman->status & URBDRC_DEVICE_CHANNEL_CLOSED)
1309 if (pdev->status & URBDRC_DEVICE_CHANNEL_CLOSED)
1316static int libusb_udev_is_already_send(IUDEVICE* idev)
1319 return (pdev->status & URBDRC_DEVICE_ALREADY_SEND) ? 1 : 0;
1324static void libusb_udev_mark_channel_closed(IUDEVICE* idev)
1327 if (pdev && ((pdev->status & URBDRC_DEVICE_CHANNEL_CLOSED) == 0))
1330 const uint8_t busNr = idev->get_bus_number(idev);
1331 const uint8_t devNr = idev->get_dev_number(idev);
1333 pdev->status |= URBDRC_DEVICE_CHANNEL_CLOSED;
1334 pdev->iface.cancel_all_transfer_request(&pdev->iface);
1335 if (!urbdrc->udevman->unregister_udevice(urbdrc->udevman, busNr, devNr))
1337 WLog_Print(pdev->urbdrc->log, WLOG_WARN,
"unregister_udevice failed for %d, %d", busNr,
1345static void libusb_udev_channel_closed(IUDEVICE* idev)
1348 if (pdev && ((pdev->status & URBDRC_DEVICE_CHANNEL_CLOSED) == 0))
1351 const uint8_t busNr = idev->get_bus_number(idev);
1352 const uint8_t devNr = idev->get_dev_number(idev);
1353 IWTSVirtualChannel* channel =
nullptr;
1355 IUDEVMAN* udevman = pdev->urbdrc->udevman;
1356 WINPR_ASSERT(udevman);
1358 udevman->loading_lock(udevman);
1359 if ((pdev->status & URBDRC_DEVICE_CHANNEL_CLOSED) == 0)
1361 if (pdev->channelManager)
1362 channel = IFCALLRESULT(
nullptr, pdev->channelManager->FindChannelById,
1363 pdev->channelManager, pdev->channelID);
1365 pdev->status |= URBDRC_DEVICE_CHANNEL_CLOSED;
1369 const UINT rc = channel->Write(channel, 0,
nullptr,
nullptr);
1370 if (rc != CHANNEL_RC_OK)
1371 WLog_Print(urbdrc->log, WLOG_WARN,
"channel->Write failed with %" PRIu32, rc);
1374 udevman->loading_unlock(udevman);
1376 if (!urbdrc->udevman->unregister_udevice(urbdrc->udevman, busNr, devNr))
1377 WLog_Print(urbdrc->log, WLOG_WARN,
"unregister_udevice failed for %d, %d", busNr,
1382static void libusb_udev_set_already_send(IUDEVICE* idev)
1385 pdev->status |= URBDRC_DEVICE_ALREADY_SEND;
1389static const char* libusb_udev_get_path(IUDEVICE* idev)
1396static int libusb_udev_query_device_port_status(IUDEVICE* idev, UINT32* UsbdStatus,
1397 UINT32* BufferSize, BYTE* Buffer)
1404 WINPR_ASSERT(BufferSize);
1406 if (!pdev || !pdev->urbdrc)
1409 urbdrc = pdev->urbdrc;
1411 if (pdev->hub_handle !=
nullptr)
1413 ret = idev->control_transfer(
1415 (uint8_t)LIBUSB_ENDPOINT_IN | (uint8_t)LIBUSB_REQUEST_TYPE_CLASS |
1416 (uint8_t)LIBUSB_RECIPIENT_OTHER,
1417 LIBUSB_REQUEST_GET_STATUS, 0, pdev->port_number, UsbdStatus, BufferSize, Buffer, 1000);
1419 if (log_libusb_result(urbdrc->log, WLOG_DEBUG,
"libusb_control_transfer", ret))
1423 WLog_Print(urbdrc->log, WLOG_DEBUG,
1424 "PORT STATUS:0x%02" PRIx8
"%02" PRIx8
"%02" PRIx8
"%02" PRIx8
"", Buffer[3],
1425 Buffer[2], Buffer[1], Buffer[0]);
1434static int libusb_udev_reset_device(IUDEVICE* idev)
1438 if (!pdev || !pdev->urbdrc)
1442 const int ret = libusb_reset_device(pdev->libusb_handle);
1443 log_libusb_result(urbdrc->log, WLOG_DEBUG,
"libusb_reset_device", ret);
1449 UINT32 MessageId, UINT32 RequestId, UINT32 EndpointAddress,
1450 WINPR_ATTR_UNUSED UINT32 TransferFlags, UINT32 StartFrame,
1451 UINT32 ErrorCount, BOOL NoAck,
1452 WINPR_ATTR_UNUSED
const BYTE* packetDescriptorData,
1453 UINT32 NumberOfPackets, UINT32 BufferSize,
const BYTE* Buffer,
1454 int transferDir, t_isoch_transfer_cb cb, UINT32 Timeout)
1457 UINT32 iso_packet_size = 0;
1459 struct libusb_transfer* iso_transfer =
nullptr;
1460 size_t outSize = (12ULL * NumberOfPackets);
1461 uint32_t streamID = 0x40000000 | RequestId;
1463 if (!pdev || !pdev->urbdrc)
1468 if ((NumberOfPackets > INT32_MAX) || (BufferSize > INT32_MAX))
1470 WLog_Print(urbdrc->log, WLOG_ERROR,
1471 "[NumberOfPackets=%" PRIu32
", BufferSize=%" PRIu32
1472 " ] out of bounds, maximum allowed is %d",
1473 NumberOfPackets, BufferSize, INT32_MAX);
1477 ASYNC_TRANSFER_USER_DATA* user_data = async_transfer_user_data_new(
1478 idev, MessageId, 48, BufferSize, Buffer, outSize + 1024, NoAck, transferDir, cb, callback);
1483 user_data->ErrorCount = ErrorCount;
1484 user_data->StartFrame = StartFrame;
1487 Stream_Seek(user_data->data, (12ULL * NumberOfPackets));
1489 if (NumberOfPackets > 0)
1491 iso_packet_size = BufferSize / NumberOfPackets;
1492 iso_transfer = libusb_alloc_transfer((
int)NumberOfPackets);
1495 if (iso_transfer ==
nullptr)
1497 WLog_Print(urbdrc->log, WLOG_ERROR,
1498 "Error: libusb_alloc_transfer [NumberOfPackets=%" PRIu32
", BufferSize=%" PRIu32
1500 NumberOfPackets, BufferSize);
1501 async_transfer_user_data_free(user_data);
1506 libusb_fill_iso_transfer(
1507 iso_transfer, pdev->libusb_handle, WINPR_ASSERTING_INT_CAST(uint8_t, EndpointAddress),
1508 Stream_Pointer(user_data->data), WINPR_ASSERTING_INT_CAST(
int, BufferSize),
1509 WINPR_ASSERTING_INT_CAST(
int, NumberOfPackets), func_iso_callback, user_data, Timeout);
1510 set_stream_id_for_buffer(iso_transfer, streamID);
1511 libusb_set_iso_packet_lengths(iso_transfer, iso_packet_size);
1513 if (!ArrayList_Append(pdev->request_queue, iso_transfer))
1515 WLog_Print(urbdrc->log, WLOG_WARN,
1516 "Failed to queue iso transfer, streamID %08" PRIx32
" already in use!",
1518 request_free(iso_transfer);
1521 rc = libusb_submit_transfer(iso_transfer);
1522 if (log_libusb_result(urbdrc->log, WLOG_ERROR,
"libusb_submit_transfer", rc))
1525 ArrayList_Remove(pdev->request_queue, iso_transfer);
1532static BOOL libusb_udev_control_transfer(IUDEVICE* idev, WINPR_ATTR_UNUSED UINT32 RequestId,
1533 WINPR_ATTR_UNUSED UINT32 EndpointAddress,
1534 WINPR_ATTR_UNUSED UINT32 TransferFlags, BYTE bmRequestType,
1535 BYTE Request, UINT16 Value, UINT16 Index,
1536 UINT32* UrbdStatus, UINT32* BufferSize, BYTE* Buffer,
1542 WINPR_ASSERT(BufferSize);
1544 if (!pdev || !pdev->urbdrc)
1547 if (*BufferSize > UINT16_MAX)
1549 WLog_Print(pdev->urbdrc->log, WLOG_ERROR,
"BufferSize %" PRIu32
" > %d", *BufferSize,
1555 libusb_control_transfer(pdev->libusb_handle, bmRequestType, Request, Value, Index, Buffer,
1556 WINPR_ASSERTING_INT_CAST(UINT16, *BufferSize), Timeout);
1559 *BufferSize = (UINT32)status;
1563 log_libusb_result(pdev->urbdrc->log, WLOG_ERROR,
"libusb_control_transfer", status);
1566 if (!func_set_usbd_status(pdev->urbdrc, pdev, UrbdStatus, status))
1573static int libusb_udev_bulk_or_interrupt_transfer(
1575 UINT32 EndpointAddress, UINT32 TransferFlags, BOOL NoAck, UINT32 BufferSize,
const BYTE* data,
1576 int transferDir, t_isoch_transfer_cb cb, UINT32 Timeout)
1579 UINT32 transfer_type = 0;
1581 const LIBUSB_ENDPOINT_DESCEIPTOR* ep_desc =
nullptr;
1582 struct libusb_transfer* transfer =
nullptr;
1583 ASYNC_TRANSFER_USER_DATA* user_data =
nullptr;
1584 uint32_t streamID = 0x80000000 | RequestId;
1586 if (!pdev || !pdev->LibusbConfig || !pdev->urbdrc)
1589 if (BufferSize > INT32_MAX)
1593 user_data = async_transfer_user_data_new(idev, MessageId, 36, BufferSize, data, 0, NoAck,
1594 transferDir, cb, callback);
1600 transfer = libusb_alloc_transfer(0);
1603 async_transfer_user_data_free(user_data);
1606 transfer->user_data = user_data;
1608 ep_desc = func_get_ep_desc(pdev->LibusbConfig, pdev->MsConfig, EndpointAddress);
1612 WLog_Print(urbdrc->log, WLOG_ERROR,
"func_get_ep_desc: endpoint 0x%" PRIx32
" not found",
1614 request_free(transfer);
1618 transfer_type = (ep_desc->bmAttributes) & 0x3;
1619 WLog_Print(urbdrc->log, WLOG_DEBUG,
1620 "urb_bulk_or_interrupt_transfer: ep:0x%" PRIx32
" "
1621 "transfer_type %" PRIu32
" flag:%" PRIu32
" OutputBufferSize:0x%" PRIx32
"",
1622 EndpointAddress, transfer_type, TransferFlags, BufferSize);
1624 switch (transfer_type)
1628 libusb_fill_bulk_transfer(
1629 transfer, pdev->libusb_handle, WINPR_ASSERTING_INT_CAST(uint8_t, EndpointAddress),
1630 Stream_Pointer(user_data->data), WINPR_ASSERTING_INT_CAST(
int, BufferSize),
1631 func_bulk_transfer_cb, user_data, Timeout);
1634 case INTERRUPT_TRANSFER:
1636 libusb_fill_interrupt_transfer(
1637 transfer, pdev->libusb_handle, WINPR_ASSERTING_INT_CAST(uint8_t, EndpointAddress),
1638 Stream_Pointer(user_data->data), WINPR_ASSERTING_INT_CAST(
int, BufferSize),
1639 func_bulk_transfer_cb, user_data, Timeout);
1643 WLog_Print(urbdrc->log, WLOG_DEBUG,
1644 "urb_bulk_or_interrupt_transfer:"
1645 " other transfer type 0x%" PRIX32
"",
1647 request_free(transfer);
1651 set_stream_id_for_buffer(transfer, streamID);
1653 if (!ArrayList_Append(pdev->request_queue, transfer))
1655 WLog_Print(urbdrc->log, WLOG_WARN,
1656 "Failed to queue transfer, streamID %08" PRIx32
" already in use!", streamID);
1657 request_free(transfer);
1660 rc = libusb_submit_transfer(transfer);
1661 if (log_libusb_result(urbdrc->log, WLOG_ERROR,
"libusb_submit_transfer", rc))
1664 ArrayList_Remove(pdev->request_queue, transfer);
1670static int func_cancel_xact_request(
URBDRC_PLUGIN* urbdrc,
struct libusb_transfer* transfer)
1674 if (!urbdrc || !transfer)
1677 status = libusb_cancel_transfer(transfer);
1679 if (log_libusb_result(urbdrc->log, WLOG_WARN,
"libusb_cancel_transfer", status))
1681 if (status == LIBUSB_ERROR_NOT_FOUND)
1690static void libusb_udev_cancel_all_transfer_request(IUDEVICE* idev)
1695 if (!pdev || !pdev->request_queue || !pdev->urbdrc)
1698 ArrayList_Lock(pdev->request_queue);
1699 count = ArrayList_Count(pdev->request_queue);
1701 for (
size_t x = 0; x < count; x++)
1703 struct libusb_transfer* transfer = ArrayList_GetItem(pdev->request_queue, x);
1704 func_cancel_xact_request(pdev->urbdrc, transfer);
1707 ArrayList_Unlock(pdev->request_queue);
1711static int libusb_udev_cancel_transfer_request(IUDEVICE* idev, UINT32 RequestId)
1715 struct libusb_transfer* transfer =
nullptr;
1716 uint32_t cancelID1 = 0x40000000 | RequestId;
1717 uint32_t cancelID2 = 0x80000000 | RequestId;
1719 if (!idev || !pdev->urbdrc || !pdev->request_queue)
1722 ArrayList_Lock(pdev->request_queue);
1723 transfer = list_contains(pdev->request_queue, cancelID1);
1725 transfer = list_contains(pdev->request_queue, cancelID2);
1731 rc = func_cancel_xact_request(urbdrc, transfer);
1733 ArrayList_Unlock(pdev->request_queue);
1737BASIC_STATE_FUNC_DEFINED(channelManager, IWTSVirtualChannelManager*)
1738BASIC_STATE_FUNC_DEFINED(channelID, UINT32)
1740BASIC_STATE_FUNC_DEFINED(ReqCompletion, UINT32)
1741BASIC_STATE_FUNC_DEFINED(bus_number, BYTE)
1742BASIC_STATE_FUNC_DEFINED(dev_number, BYTE)
1743BASIC_STATE_FUNC_DEFINED(port_number, UINT8)
1746BASIC_POINT_FUNC_DEFINED(udev,
void*)
1747BASIC_POINT_FUNC_DEFINED(prev,
void*)
1748BASIC_POINT_FUNC_DEFINED(next,
void*)
1751static UINT32 udev_get_UsbDevice(IUDEVICE* idev)
1758 return pdev->UsbDevice;
1761static void udev_set_UsbDevice(IUDEVICE* idev, UINT32 val)
1768 pdev->UsbDevice = val;
1771static void udev_free(IUDEVICE* idev)
1777 if (!idev || !udev->urbdrc)
1780 urbdrc = udev->urbdrc;
1782 libusb_udev_cancel_all_transfer_request(&udev->iface);
1783 if (udev->libusb_handle)
1785 rc = libusb_reset_device(udev->libusb_handle);
1787 log_libusb_result(urbdrc->log, WLOG_ERROR,
"libusb_reset_device", rc);
1790 while (ArrayList_Count(udev->request_queue) > 0)
1799 if (!udev->iface.attach_kernel_driver(idev))
1800 WLog_Print(udev->urbdrc->log, WLOG_WARN,
"attach_kernel_driver failed for device");
1801 libusb_unref_device(udev->libusb_dev);
1802 libusb_close(udev->libusb_handle);
1803 libusb_close(udev->hub_handle);
1805 ArrayList_Free(udev->request_queue);
1807 msusb_msconfig_free(udev->MsConfig);
1808 free(udev->devDescriptor);
1812static void udev_load_interface(
UDEVICE* pdev)
1818 BASIC_STATE_FUNC_REGISTER(channelManager, pdev);
1819 BASIC_STATE_FUNC_REGISTER(channelID, pdev);
1820 BASIC_STATE_FUNC_REGISTER(channelCallback, pdev);
1821 BASIC_STATE_FUNC_REGISTER(UsbDevice, pdev);
1822 BASIC_STATE_FUNC_REGISTER(ReqCompletion, pdev);
1823 BASIC_STATE_FUNC_REGISTER(bus_number, pdev);
1824 BASIC_STATE_FUNC_REGISTER(dev_number, pdev);
1825 BASIC_STATE_FUNC_REGISTER(port_number, pdev);
1826 BASIC_STATE_FUNC_REGISTER(MsConfig, pdev);
1827 BASIC_STATE_FUNC_REGISTER(p_udev, pdev);
1828 BASIC_STATE_FUNC_REGISTER(p_prev, pdev);
1829 BASIC_STATE_FUNC_REGISTER(p_next, pdev);
1830 pdev->iface.isCompositeDevice = libusb_udev_is_composite_device;
1831 pdev->iface.isExist = libusb_udev_is_exist;
1832 pdev->iface.isAlreadySend = libusb_udev_is_already_send;
1833 pdev->iface.isChannelClosed = libusb_udev_is_channel_closed;
1834 pdev->iface.setAlreadySend = libusb_udev_set_already_send;
1835 pdev->iface.setChannelClosed = libusb_udev_channel_closed;
1836 pdev->iface.markChannelClosed = libusb_udev_mark_channel_closed;
1837 pdev->iface.getPath = libusb_udev_get_path;
1839 pdev->iface.isoch_transfer = libusb_udev_isoch_transfer;
1840 pdev->iface.control_transfer = libusb_udev_control_transfer;
1841 pdev->iface.bulk_or_interrupt_transfer = libusb_udev_bulk_or_interrupt_transfer;
1842 pdev->iface.select_interface = libusb_udev_select_interface;
1843 pdev->iface.select_configuration = libusb_udev_select_configuration;
1844 pdev->iface.complete_msconfig_setup = libusb_udev_complete_msconfig_setup;
1845 pdev->iface.control_pipe_request = libusb_udev_control_pipe_request;
1846 pdev->iface.control_query_device_text = libusb_udev_control_query_device_text;
1847 pdev->iface.os_feature_descriptor_request = libusb_udev_os_feature_descriptor_request;
1848 pdev->iface.cancel_all_transfer_request = libusb_udev_cancel_all_transfer_request;
1849 pdev->iface.cancel_transfer_request = libusb_udev_cancel_transfer_request;
1850 pdev->iface.query_device_descriptor = libusb_udev_query_device_descriptor;
1851 pdev->iface.query_device_speed = libusb_udev_query_device_speed;
1852 pdev->iface.detach_kernel_driver = libusb_udev_detach_kernel_driver;
1853 pdev->iface.attach_kernel_driver = libusb_udev_attach_kernel_driver;
1854 pdev->iface.query_device_port_status = libusb_udev_query_device_port_status;
1855 pdev->iface.reset_device = libusb_udev_reset_device;
1856 pdev->iface.free = udev_free;
1861 UINT16 bus_number, UINT16 dev_number)
1864 uint8_t port_numbers[16] = WINPR_C_ARRAY_INIT;
1865 LIBUSB_DEVICE** libusb_list =
nullptr;
1866 const ssize_t total_device = libusb_get_device_list(ctx, &libusb_list);
1868 WINPR_ASSERT(urbdrc);
1871 for (ssize_t i = 0; i < total_device; i++)
1873 LIBUSB_DEVICE* dev = libusb_list[i];
1875 if ((bus_number != libusb_get_bus_number(dev)) ||
1876 (dev_number != libusb_get_device_address(dev)))
1877 libusb_unref_device(dev);
1880 error = libusb_open(dev, &pdev->libusb_handle);
1882 if (log_libusb_result(urbdrc->log, WLOG_ERROR,
"libusb_open", error))
1884 libusb_unref_device(dev);
1889 (void)libusb_set_auto_detach_kernel_driver(pdev->libusb_handle, 1);
1892 error = libusb_get_port_numbers(dev, port_numbers,
sizeof(port_numbers));
1896 log_libusb_result(urbdrc->log, WLOG_ERROR,
"libusb_get_port_numbers", error);
1897 libusb_unref_device(dev);
1901 pdev->port_number = port_numbers[(error - 1)];
1903 WLog_Print(urbdrc->log, WLOG_DEBUG,
" Port: %" PRIu8, pdev->port_number);
1905 (void)_snprintf(pdev->path,
sizeof(pdev->path),
"%" PRIu16
"-%d", bus_number,
1908 WLog_Print(urbdrc->log, WLOG_DEBUG,
" DevPath: %s", pdev->path);
1911 libusb_free_device_list(libusb_list, 0);
1920 UINT16 bus_number, WINPR_ATTR_UNUSED UINT16 dev_number)
1923 LIBUSB_DEVICE** libusb_list =
nullptr;
1924 LIBUSB_DEVICE_HANDLE* handle =
nullptr;
1925 const ssize_t total_device = libusb_get_device_list(ctx, &libusb_list);
1927 WINPR_ASSERT(urbdrc);
1930 for (ssize_t i = 0; i < total_device; i++)
1932 LIBUSB_DEVICE* dev = libusb_list[i];
1934 if ((bus_number != libusb_get_bus_number(dev)) ||
1935 (1 != libusb_get_device_address(dev)))
1936 libusb_unref_device(dev);
1939 WLog_Print(urbdrc->log, WLOG_DEBUG,
" Open hub: %" PRIu16
"", bus_number);
1940 error = libusb_open(dev, &handle);
1942 if (!log_libusb_result(urbdrc->log, WLOG_ERROR,
"libusb_open", error))
1943 pdev->hub_handle = handle;
1945 libusb_unref_device(dev);
1949 libusb_free_device_list(libusb_list, 0);
1957static void request_free(
void* value)
1959 ASYNC_TRANSFER_USER_DATA* user_data =
nullptr;
1960 struct libusb_transfer* transfer = (
struct libusb_transfer*)value;
1964 user_data = (ASYNC_TRANSFER_USER_DATA*)transfer->user_data;
1965 async_transfer_user_data_free(user_data);
1966 transfer->user_data =
nullptr;
1967 libusb_free_transfer(transfer);
1971static IUDEVICE* udev_init(
URBDRC_PLUGIN* urbdrc, libusb_context* context, LIBUSB_DEVICE* device,
1972 BYTE bus_number, BYTE dev_number)
1975 int status = LIBUSB_ERROR_OTHER;
1976 LIBUSB_DEVICE_DESCRIPTOR* devDescriptor =
nullptr;
1977 LIBUSB_CONFIG_DESCRIPTOR* config_temp =
nullptr;
1978 LIBUSB_INTERFACE_DESCRIPTOR interface_temp;
1980 WINPR_ASSERT(urbdrc);
1987 pdev->urbdrc = urbdrc;
1988 udev_load_interface(pdev);
1991 pdev->libusb_dev = device;
1993 pdev->libusb_dev = udev_get_libusb_dev(context, bus_number, dev_number);
1995 if (pdev->libusb_dev ==
nullptr)
1998 if (urbdrc->listener_callback)
1999 udev_set_channelManager(&pdev->iface, urbdrc->listener_callback->channel_mgr);
2002 status = udev_get_device_handle(urbdrc, context, pdev, bus_number, dev_number);
2003 if (status != LIBUSB_SUCCESS)
2005 struct libusb_device_descriptor desc;
2006 const uint8_t port = libusb_get_port_number(pdev->libusb_dev);
2007 libusb_get_device_descriptor(pdev->libusb_dev, &desc);
2009 log_libusb_result(urbdrc->log, WLOG_ERROR,
2010 "libusb_open [b=0x%02X,p=0x%02X,a=0x%02X,VID=0x%04X,PID=0x%04X]", status,
2011 bus_number, port, dev_number, desc.idVendor, desc.idProduct);
2016 status = udev_get_hub_handle(urbdrc, context, pdev, bus_number, dev_number);
2019 pdev->hub_handle =
nullptr;
2021 pdev->devDescriptor = udev_new_descript(urbdrc, pdev->libusb_dev);
2023 if (!pdev->devDescriptor)
2026 status = libusb_get_active_config_descriptor(pdev->libusb_dev, &pdev->LibusbConfig);
2028 if (status == LIBUSB_ERROR_NOT_FOUND)
2029 status = libusb_get_config_descriptor(pdev->libusb_dev, 0, &pdev->LibusbConfig);
2033 log_libusb_result(urbdrc->log, WLOG_ERROR,
"libusb_get_config_descriptor", status);
2037 config_temp = pdev->LibusbConfig;
2039 interface_temp = config_temp->interface[0].altsetting[0];
2040 WLog_Print(urbdrc->log, WLOG_DEBUG,
2041 "Registered Device: Vid: 0x%04" PRIX16
" Pid: 0x%04" PRIX16
""
2042 " InterfaceClass = %s",
2043 pdev->devDescriptor->idVendor, pdev->devDescriptor->idProduct,
2044 usb_interface_class_to_string(interface_temp.bInterfaceClass));
2046 devDescriptor = pdev->devDescriptor;
2048 if ((devDescriptor->bNumConfigurations == 1) && (config_temp->bNumInterfaces > 1) &&
2049 (devDescriptor->bDeviceClass == LIBUSB_CLASS_PER_INTERFACE))
2051 pdev->isCompositeDevice = 1;
2053 else if ((devDescriptor->bDeviceClass == 0xef) &&
2054 (devDescriptor->bDeviceSubClass == LIBUSB_CLASS_COMM) &&
2055 (devDescriptor->bDeviceProtocol == 0x01))
2057 pdev->isCompositeDevice = 1;
2060 pdev->isCompositeDevice = 0;
2063 devDescriptor->bDeviceClass = interface_temp.bInterfaceClass;
2064 devDescriptor->bDeviceSubClass = interface_temp.bInterfaceSubClass;
2065 devDescriptor->bDeviceProtocol = interface_temp.bInterfaceProtocol;
2067 pdev->bus_number = bus_number;
2068 pdev->dev_number = dev_number;
2069 pdev->request_queue = ArrayList_New(TRUE);
2071 if (!pdev->request_queue)
2074 ArrayList_Object(pdev->request_queue)->
fnObjectFree = request_free;
2077 pdev->MsConfig = msusb_msconfig_new();
2079 if (!pdev->MsConfig)
2083 return &pdev->iface;
2085 pdev->iface.free(&pdev->iface);
2089size_t udev_new_by_id(
URBDRC_PLUGIN* urbdrc, libusb_context* ctx, UINT16 idVendor, UINT16 idProduct,
2090 IUDEVICE*** devArray)
2092 WINPR_ASSERT(urbdrc);
2093 WINPR_ASSERT(devArray);
2096 LIBUSB_DEVICE** libusb_list =
nullptr;
2098 *devArray =
nullptr;
2100 WLog_Print(urbdrc->log, WLOG_INFO,
"VID: 0x%04" PRIX16
", PID: 0x%04" PRIX16
"", idVendor,
2102 const ssize_t total_device = libusb_get_device_list(ctx, &libusb_list);
2103 if (total_device < 0)
2105 WLog_Print(urbdrc->log, WLOG_ERROR,
"libusb_get_device_list -> [%" PRIdz
"]", total_device);
2108 if (total_device == 0)
2110 WLog_Print(urbdrc->log, WLOG_WARN,
"libusb_get_device_list -> [%" PRIdz
"]", total_device);
2119 for (ssize_t i = 0; i < total_device; i++)
2121 LIBUSB_DEVICE* dev = libusb_list[i];
2122 LIBUSB_DEVICE_DESCRIPTOR* descriptor = udev_new_descript(urbdrc, dev);
2124 if ((descriptor->idVendor == idVendor) && (descriptor->idProduct == idProduct))
2126 const uint8_t nr = libusb_get_bus_number(dev);
2127 const uint8_t addr = libusb_get_device_address(dev);
2128 array[num] = (
PUDEVICE)udev_init(urbdrc, ctx, dev, nr, addr);
2130 if (array[num] !=
nullptr)
2134 WLog_Print(urbdrc->log, WLOG_WARN,
2135 "udev_init(nr=%" PRIu8
", addr=%" PRIu8
") failed", nr, addr);
2139 libusb_unref_device(dev);
2145 libusb_free_device_list(libusb_list, 0);
2146 *devArray = (IUDEVICE**)array;
2150IUDEVICE* udev_new_by_addr(
URBDRC_PLUGIN* urbdrc, libusb_context* context, BYTE bus_number,
2153 WLog_Print(urbdrc->log, WLOG_DEBUG,
"bus:%d dev:%d", bus_number, dev_number);
2154 return udev_init(urbdrc, context,
nullptr, bus_number, dev_number);
OBJECT_FREE_FN fnObjectFree