struct libusb_device **ret;
int r = 0;
ssize_t i, len;
- USBI_GET_CONTEXT(ctx);
+
usbi_dbg(" ");
if (!discdevs)
return LIBUSB_ERROR_NO_MEM;
+ ctx = usbi_get_context(ctx);
+
if (libusb_has_capability(LIBUSB_CAP_HAS_HOTPLUG)) {
/* backend provides hotplug support */
struct libusb_device *dev;
struct libusb_device_handle *_dev_handle;
size_t priv_size = usbi_backend.device_handle_priv_size;
int r;
+
usbi_dbg("wrap_sys_device %p", (void *)sys_dev);
- USBI_GET_CONTEXT(ctx);
+ ctx = usbi_get_context(ctx);
if (!usbi_backend.wrap_sys_device)
return LIBUSB_ERROR_NOT_SUPPORTED;
void API_EXPORTED libusb_set_debug(libusb_context *ctx, int level)
{
#if defined(ENABLE_LOGGING) && !defined(ENABLE_DEBUG_LOGGING)
- USBI_GET_CONTEXT(ctx);
+ ctx = usbi_get_context(ctx);
if (!ctx->debug_fixed) {
level = CLAMP(level, LIBUSB_LOG_LEVEL_NONE, LIBUSB_LOG_LEVEL_DEBUG);
ctx->debug = (enum libusb_log_level)level;
#endif
#if !defined(ENABLE_DEBUG_LOGGING)
if (mode & LIBUSB_LOG_CB_CONTEXT) {
- USBI_GET_CONTEXT(ctx);
+ ctx = usbi_get_context(ctx);
ctx->log_handler = cb;
}
#else
int arg, r = LIBUSB_SUCCESS;
va_list ap;
- USBI_GET_CONTEXT(ctx);
+ ctx = usbi_get_context(ctx);
va_start(ap, option);
switch (option) {
int destroying_default_context = 0;
usbi_dbg(" ");
- USBI_GET_CONTEXT(ctx);
+
+ ctx = usbi_get_context(ctx);
/* if working with default context, only actually do the deinitialization
* if we're the last user */
#else
enum libusb_log_level ctx_level = LIBUSB_LOG_LEVEL_NONE;
- USBI_GET_CONTEXT(ctx);
+ ctx = usbi_get_context(ctx);
if (ctx)
ctx_level = ctx->debug;
else
return LIBUSB_ERROR_NOT_SUPPORTED;
}
- USBI_GET_CONTEXT(ctx);
+ ctx = usbi_get_context(ctx);
new_callback = calloc(1, sizeof(*new_callback));
if (!new_callback) {
return;
}
- USBI_GET_CONTEXT(ctx);
-
usbi_dbg("deregister hotplug cb %d", callback_handle);
+ ctx = usbi_get_context(ctx);
+
usbi_mutex_lock(&ctx->hotplug_cbs_lock);
list_for_each_entry(hotplug_cb, &ctx->hotplug_cbs, list, struct libusb_hotplug_callback) {
if (callback_handle == hotplug_cb->handle) {
return NULL;
}
- USBI_GET_CONTEXT(ctx);
-
usbi_dbg("get hotplug user data %d", callback_handle);
+ ctx = usbi_get_context(ctx);
+
usbi_mutex_lock(&ctx->hotplug_cbs_lock);
list_for_each_entry(hotplug_cb, &ctx->hotplug_cbs, list, struct libusb_hotplug_callback) {
if (callback_handle == hotplug_cb->handle) {
{
int r;
unsigned int ru;
- USBI_GET_CONTEXT(ctx);
+
+ ctx = usbi_get_context(ctx);
/* is someone else waiting to close a device? if so, don't let this thread
* start event handling */
*/
void API_EXPORTED libusb_lock_events(libusb_context *ctx)
{
- USBI_GET_CONTEXT(ctx);
+ ctx = usbi_get_context(ctx);
usbi_mutex_lock(&ctx->events_lock);
ctx->event_handler_active = 1;
}
*/
void API_EXPORTED libusb_unlock_events(libusb_context *ctx)
{
- USBI_GET_CONTEXT(ctx);
+ ctx = usbi_get_context(ctx);
ctx->event_handler_active = 0;
usbi_mutex_unlock(&ctx->events_lock);
int API_EXPORTED libusb_event_handling_ok(libusb_context *ctx)
{
unsigned int r;
- USBI_GET_CONTEXT(ctx);
+
+ ctx = usbi_get_context(ctx);
/* is someone else waiting to close a device? if so, don't let this thread
* continue event handling */
int API_EXPORTED libusb_event_handler_active(libusb_context *ctx)
{
unsigned int r;
- USBI_GET_CONTEXT(ctx);
+
+ ctx = usbi_get_context(ctx);
/* is someone else waiting to close a device? if so, don't let this thread
* start event handling -- indicate that event handling is happening */
void API_EXPORTED libusb_interrupt_event_handler(libusb_context *ctx)
{
int pending_events;
- USBI_GET_CONTEXT(ctx);
usbi_dbg(" ");
+
+ ctx = usbi_get_context(ctx);
usbi_mutex_lock(&ctx->event_data_lock);
pending_events = usbi_pending_events(ctx);
*/
void API_EXPORTED libusb_lock_event_waiters(libusb_context *ctx)
{
- USBI_GET_CONTEXT(ctx);
+ ctx = usbi_get_context(ctx);
usbi_mutex_lock(&ctx->event_waiters_lock);
}
*/
void API_EXPORTED libusb_unlock_event_waiters(libusb_context *ctx)
{
- USBI_GET_CONTEXT(ctx);
+ ctx = usbi_get_context(ctx);
usbi_mutex_unlock(&ctx->event_waiters_lock);
}
{
int r;
- USBI_GET_CONTEXT(ctx);
+ ctx = usbi_get_context(ctx);
if (tv == NULL) {
usbi_cond_wait(&ctx->event_waiters_cond, &ctx->event_waiters_lock);
return 0;
static int handle_timeouts(struct libusb_context *ctx)
{
int r;
- USBI_GET_CONTEXT(ctx);
+
+ ctx = usbi_get_context(ctx);
usbi_mutex_lock(&ctx->flying_transfers_lock);
r = handle_timeouts_locked(ctx);
usbi_mutex_unlock(&ctx->flying_transfers_lock);
int r;
struct timeval poll_timeout;
- USBI_GET_CONTEXT(ctx);
+ ctx = usbi_get_context(ctx);
r = get_next_timeout(ctx, tv, &poll_timeout);
if (r) {
/* timeout already expired */
int r;
struct timeval poll_timeout;
- USBI_GET_CONTEXT(ctx);
+ ctx = usbi_get_context(ctx);
r = get_next_timeout(ctx, tv, &poll_timeout);
if (r) {
/* timeout already expired */
int API_EXPORTED libusb_pollfds_handle_timeouts(libusb_context *ctx)
{
#ifdef HAVE_TIMERFD
- USBI_GET_CONTEXT(ctx);
+ ctx = usbi_get_context(ctx);
return usbi_using_timerfd(ctx);
#else
UNUSED(ctx);
struct timeval next_timeout = { 0, 0 };
int r;
- USBI_GET_CONTEXT(ctx);
+ ctx = usbi_get_context(ctx);
if (usbi_using_timerfd(ctx))
return 0;
libusb_pollfd_added_cb added_cb, libusb_pollfd_removed_cb removed_cb,
void *user_data)
{
- USBI_GET_CONTEXT(ctx);
+ ctx = usbi_get_context(ctx);
ctx->fd_added_cb = added_cb;
ctx->fd_removed_cb = removed_cb;
ctx->fd_cb_user_data = user_data;
struct libusb_pollfd **ret = NULL;
struct usbi_pollfd *ipollfd;
size_t i = 0;
- USBI_GET_CONTEXT(ctx);
+
+ ctx = usbi_get_context(ctx);
usbi_mutex_lock(&ctx->event_data_lock);
#ifdef ENABLE_LOGGING
#if defined(_MSC_VER) && (_MSC_VER < 1900)
+#include <stdio.h>
#define snprintf usbi_snprintf
#define vsnprintf usbi_vsnprintf
int usbi_snprintf(char *dst, size_t size, const char *format, ...);
#endif /* ENABLE_LOGGING */
-#define USBI_GET_CONTEXT(ctx) \
- do { \
- if (!(ctx)) \
- (ctx) = usbi_default_context; \
- } while(0)
-
#define DEVICE_CTX(dev) ((dev)->ctx)
#define HANDLE_CTX(handle) (DEVICE_CTX((handle)->dev))
#define TRANSFER_CTX(transfer) (HANDLE_CTX((transfer)->dev_handle))
PTR_ALIGNED unsigned char os_priv[ZERO_SIZED_ARRAY];
};
+extern struct libusb_context *usbi_default_context;
+
+static inline struct libusb_context *usbi_get_context(struct libusb_context *ctx)
+{
+ return ctx ? ctx : usbi_default_context;
+}
+
enum usbi_event_flags {
/* The list of pollfds has been modified */
USBI_EVENT_POLLFDS_MODIFIED = 1U << 0,
};
/* Macros for managing event handling state */
-#define usbi_handling_events(ctx) \
- (usbi_tls_key_get((ctx)->event_handling_key) != NULL)
+static inline int usbi_handling_events(struct libusb_context *ctx)
+{
+ return usbi_tls_key_get(ctx->event_handling_key) != NULL;
+}
-#define usbi_start_event_handling(ctx) \
- usbi_tls_key_set((ctx)->event_handling_key, ctx)
+static inline void usbi_start_event_handling(struct libusb_context *ctx)
+{
+ usbi_tls_key_set(ctx->event_handling_key, ctx);
+}
-#define usbi_end_event_handling(ctx) \
- usbi_tls_key_set((ctx)->event_handling_key, NULL)
+static inline void usbi_end_event_handling(struct libusb_context *ctx)
+{
+ usbi_tls_key_set(ctx->event_handling_key, NULL);
+}
-/* Update the following macro if new event sources are added */
-#define usbi_pending_events(ctx) \
- ((ctx)->event_flags || (ctx)->device_close \
- || !list_empty(&(ctx)->hotplug_msgs) || !list_empty(&(ctx)->completed_transfers))
+/* Update the following function if new event sources are added */
+static inline int usbi_pending_events(struct libusb_context *ctx)
+{
+ return ctx->event_flags ||
+ ctx->device_close ||
+ !list_empty(&ctx->hotplug_msgs) ||
+ !list_empty(&ctx->completed_transfers);
+}
+static inline int usbi_using_timerfd(struct libusb_context *ctx)
+{
#ifdef HAVE_TIMERFD
-#define usbi_using_timerfd(ctx) ((ctx)->timerfd >= 0)
+ return ctx->timerfd >= 0);
#else
-#define usbi_using_timerfd(ctx) (0)
+ UNUSED(ctx);
+ return 0;
#endif
+}
struct libusb_device {
/* lock protects refcnt, everything else is finalized at initialization
extern struct list_head active_contexts_list;
extern usbi_mutex_static_t active_contexts_lock;
-extern struct libusb_context *usbi_default_context;
-
#ifdef __cplusplus
}
#endif
* with a fake pipe. The read/write functions are only meant to be used in that
* context.
*/
-#include <config.h>
-#include <assert.h>
+#include "libusbi.h"
+
#include <errno.h>
#include <intrin.h>
#include <malloc.h>
+#include <stdbool.h>
#include <stdlib.h>
-#include "libusbi.h"
-#include "windows_common.h"
-
// public fd data
const struct winfd INVALID_WINFD = { -1, NULL };
for (n = 0; n < fd_table_size; n += BITMAP_BITS_PER_WORD) {
unsigned int idx = n / BITMAP_BITS_PER_WORD;
- unsigned long mask, pos;
+ unsigned long mask, pos = 0UL;
mask = ~fd_table_bitmap[idx];
if (mask == 0UL)
/*
* Timeval operations
*/
-#if !defined(TIMESPEC_TO_TIMEVAL)
-#define TIMESPEC_TO_TIMEVAL(tv, ts) \
-do { \
- (tv)->tv_sec = (long)(ts)->tv_sec; \
- (tv)->tv_usec = (long)(ts)->tv_nsec / 1000; \
-} while (0)
-#endif
#if !defined(timersub)
-#define timersub(a, b, result) \
-do { \
- (result)->tv_sec = (a)->tv_sec - (b)->tv_sec; \
- (result)->tv_usec = (a)->tv_usec - (b)->tv_usec; \
- if ((result)->tv_usec < 0) { \
- --(result)->tv_sec; \
- (result)->tv_usec += 1000000; \
- } \
-} while (0)
+#define timersub(a, b, result) \
+ do { \
+ (result)->tv_sec = (a)->tv_sec - (b)->tv_sec; \
+ (result)->tv_usec = (a)->tv_usec - (b)->tv_usec; \
+ if ((result)->tv_usec < 0L) { \
+ --(result)->tv_sec; \
+ (result)->tv_usec += 1000000L; \
+ } \
+ } while (0)
#endif
#endif
#include "libusbi.h"
-#include <errno.h>
-
int usbi_cond_timedwait(usbi_cond_t *cond,
usbi_mutex_t *mutex, const struct timeval *tv)
{
#ifndef LIBUSB_THREADS_WINDOWS_H
#define LIBUSB_THREADS_WINDOWS_H
+#include <errno.h>
+
#define USBI_MUTEX_INITIALIZER 0L
typedef LONG usbi_mutex_static_t;
static inline void usbi_mutex_static_lock(usbi_mutex_static_t *mutex)
{
int i;
+ UNUSED(ctx);
+
for (i = 0; i < USB_API_MAX; i++) {
if (usb_api_backend[i].exit)
usb_api_backend[i].exit();
}
// Returns the api type, or 0 if not found/unsupported
-static void get_api_type(struct libusb_context *ctx, HDEVINFO *dev_info,
- SP_DEVINFO_DATA *dev_info_data, int *api, int *sub_api)
+static void get_api_type(HDEVINFO *dev_info, SP_DEVINFO_DATA *dev_info_data,
+ int *api, int *sub_api)
{
// Precedence for filter drivers vs driver is in the order of this array
struct driver_lookup lookup[3] = {
dev_id, (unsigned int)install_state);
continue;
}
- get_api_type(ctx, dev_info, &dev_info_data, &api, &sub_api);
+ get_api_type(dev_info, &dev_info_data, &api, &sub_api);
break;
}
pLibK_GetProcAddress((PVOID *)&WinUSBX[i].fn, i, KUSB_FNID_##fn); \
} while (0)
-#define NativeWinUSBOnly_Set(fn) \
+#define NativeWinUSBOnly_Set(fn) \
do { \
if (native_winusb) \
WinUSBX[i].fn = (WinUsb_##fn##_t)GetProcAddress(h, "WinUsb_" #fn); \
*/
static int winusbx_abort_control(int sub_api, struct usbi_transfer *itransfer)
{
+ UNUSED(sub_api);
+ UNUSED(itransfer);
// Cancelling of the I/O is done in the parent
return LIBUSB_SUCCESS;
}
static int _hid_get_descriptor(struct hid_device_priv *dev, HANDLE hid_handle, int recipient,
int type, int _index, void *data, size_t *size)
{
+ UNUSED(recipient);
+
switch (type) {
case LIBUSB_DT_DEVICE:
usbi_dbg("LIBUSB_DT_DEVICE");
DWORD ioctl_code, read_size, expected_size = (DWORD)*size;
int r = LIBUSB_SUCCESS;
+ UNUSED(dev);
+
if (tp->hid_buffer != NULL)
usbi_dbg("program assertion failed: hid_buffer is not NULL");
// If an id is reported, we must allow MAX_HID_REPORT_SIZE + 1
size_t max_report_size = MAX_HID_REPORT_SIZE + (id ? 1 : 0);
+ UNUSED(dev);
+
if (tp->hid_buffer != NULL)
usbi_dbg("program assertion failed: hid_buffer is not NULL");
int report_type = (value >> 8) & 0xFF;
int report_id = value & 0xFF;
+ UNUSED(_index);
+
if ((LIBUSB_REQ_RECIPIENT(request_type) != LIBUSB_RECIPIENT_INTERFACE)
&& (LIBUSB_REQ_RECIPIENT(request_type) != LIBUSB_RECIPIENT_DEVICE))
return LIBUSB_ERROR_INVALID_PARAM;
*/
static int hid_init(struct libusb_context *ctx)
{
+ UNUSED(ctx);
+
DLL_GET_HANDLE(hid);
DLL_LOAD_FUNC(hid, HidD_GetAttributes, TRUE);
const char * const type[3] = {"input", "output", "feature"};
#endif
+ UNUSED(sub_api);
CHECK_HID_AVAILABLE;
if (priv->hid == NULL) {
HANDLE file_handle;
int i;
+ UNUSED(sub_api);
if (!api_hid_available)
return;
struct winusb_device_handle_priv *handle_priv = _device_handle_priv(dev_handle);
struct winusb_device_priv *priv = _device_priv(dev_handle->dev);
+ UNUSED(sub_api);
CHECK_HID_AVAILABLE;
// NB: Disconnection detection is not possible in this function
struct winusb_device_handle_priv *handle_priv = _device_handle_priv(dev_handle);
struct winusb_device_priv *priv = _device_priv(dev_handle->dev);
+ UNUSED(sub_api);
CHECK_HID_AVAILABLE;
if (priv->usb_interface[iface].path == NULL)
{
struct libusb_context *ctx = DEVICE_CTX(dev_handle->dev);
+ UNUSED(sub_api);
+ UNUSED(iface);
+
CHECK_HID_AVAILABLE;
if (altsetting > 255)
size_t size;
int r = LIBUSB_ERROR_INVALID_PARAM;
+ UNUSED(sub_api);
CHECK_HID_AVAILABLE;
safe_free(transfer_priv->hid_buffer);
DWORD size;
int r = LIBUSB_SUCCESS;
+ UNUSED(sub_api);
CHECK_HID_AVAILABLE;
transfer_priv->hid_dest = NULL;
HANDLE hid_handle;
int current_interface;
+ UNUSED(sub_api);
CHECK_HID_AVAILABLE;
current_interface = transfer_priv->interface_number;
HANDLE hid_handle;
int current_interface;
+ UNUSED(sub_api);
CHECK_HID_AVAILABLE;
// Flushing the queues on all interfaces is the best we can achieve
HANDLE hid_handle;
int current_interface;
+ UNUSED(sub_api);
CHECK_HID_AVAILABLE;
current_interface = interface_by_endpoint(priv, handle_priv, endpoint);
int r = LIBUSB_TRANSFER_COMPLETED;
uint32_t corrected_size = io_size;
+ UNUSED(sub_api);
+
if (transfer_priv->hid_buffer != NULL) {
// If we have a valid hid_buffer, it means the transfer was async
if (transfer_priv->hid_dest != NULL) { // Data readout
// SUB_API_MAX + 1 as the SUB_API_MAX pos is used to indicate availability of HID
bool available[SUB_API_MAX + 1] = { 0 };
+ UNUSED(sub_api);
+
for (i = 0; i < USB_MAXINTERFACES; i++) {
switch (priv->usb_interface[i].apib->id) {
case USB_API_WINUSBX:
// SUB_API_MAX + 1 as the SUB_API_MAX pos is used to indicate availability of HID
bool available[SUB_API_MAX + 1] = { 0 };
+ UNUSED(sub_api);
+
for (i = 0; i < USB_MAXINTERFACES; i++) {
switch (priv->usb_interface[i].apib->id) {
case USB_API_WINUSBX:
{
struct winusb_device_priv *priv = _device_priv(dev_handle->dev);
+ UNUSED(sub_api);
CHECK_SUPPORTED_API(priv->usb_interface[iface].apib, claim_interface);
return priv->usb_interface[iface].apib->
{
struct winusb_device_priv *priv = _device_priv(dev_handle->dev);
+ UNUSED(sub_api);
CHECK_SUPPORTED_API(priv->usb_interface[iface].apib, set_interface_altsetting);
return priv->usb_interface[iface].apib->
{
struct winusb_device_priv *priv = _device_priv(dev_handle->dev);
+ UNUSED(sub_api);
CHECK_SUPPORTED_API(priv->usb_interface[iface].apib, release_interface);
return priv->usb_interface[iface].apib->
WINUSB_SETUP_PACKET *setup = (WINUSB_SETUP_PACKET *)transfer->buffer;
int iface, pass, r;
+ UNUSED(sub_api);
+
// Interface shouldn't matter for control, but it does in practice, with Windows'
// restrictions with regards to accessing HID keyboards and mice. Try to target
// a specific interface first, if possible.
struct winusb_device_priv *priv = _device_priv(transfer->dev_handle->dev);
int current_interface;
+ UNUSED(sub_api);
+
current_interface = interface_by_endpoint(priv, handle_priv, transfer->endpoint);
if (current_interface < 0) {
usbi_err(ctx, "unable to match endpoint to an open interface - cancelling transfer");
struct winusb_device_priv *priv = _device_priv(transfer->dev_handle->dev);
int current_interface;
+ UNUSED(sub_api);
+
current_interface = interface_by_endpoint(priv, handle_priv, transfer->endpoint);
if (current_interface < 0) {
usbi_err(ctx, "unable to match endpoint to an open interface - cancelling transfer");
struct winusb_device_priv *priv = _device_priv(dev_handle->dev);
int current_interface;
+ UNUSED(sub_api);
+
current_interface = interface_by_endpoint(priv, handle_priv, endpoint);
if (current_interface < 0) {
usbi_err(ctx, "unable to match endpoint to an open interface - cannot clear");
struct winusb_device_priv *priv = _device_priv(transfer->dev_handle->dev);
int current_interface = transfer_priv->interface_number;
+ UNUSED(sub_api);
+
if ((current_interface < 0) || (current_interface >= USB_MAXINTERFACES)) {
usbi_err(TRANSFER_CTX(transfer), "program assertion failed: invalid interface_number");
return LIBUSB_ERROR_NOT_FOUND;
struct winusb_device_priv *priv = _device_priv(transfer->dev_handle->dev);
int current_interface = transfer_priv->interface_number;
+ UNUSED(sub_api);
+
if ((current_interface < 0) || (current_interface >= USB_MAXINTERFACES)) {
usbi_err(TRANSFER_CTX(transfer), "program assertion failed: invalid interface_number");
return LIBUSB_ERROR_NOT_FOUND;
uint8_t i;
bool available[SUB_API_MAX];
+ UNUSED(sub_api);
+
for (i = 0; i < SUB_API_MAX; i++)
available[i] = false;
struct winusb_device_priv *priv = _device_priv(transfer->dev_handle->dev);
int current_interface = transfer_priv->interface_number;
+ UNUSED(sub_api);
CHECK_SUPPORTED_API(priv->usb_interface[current_interface].apib, copy_transfer_data);
return priv->usb_interface[current_interface].apib->
#if defined(_MSC_VER)
// disable /W4 MSVC warnings that are benign
-#pragma warning(disable:4100) // unreferenced formal parameter
-#pragma warning(disable:4127) // conditional expression is constant
#pragma warning(disable:4201) // nameless struct/union
#pragma warning(disable:4214) // bit field types other than int
-#pragma warning(disable:4996) // deprecated API calls
-#pragma warning(disable:28159) // more deprecated API calls
#endif
// Missing from MSVC6 setupapi.h
-#define LIBUSB_NANO 11446
+#define LIBUSB_NANO 11447
#define _TIMESPEC_DEFINED 1
#endif
+/* Disable: warning C4127: conditional expression is constant */
+#pragma warning(disable:4127)
/* Disable: warning C4200: nonstandard extension used : zero-sized array in struct/union */
#pragma warning(disable:4200)
/* Disable: warning C4324: structure was padded due to __declspec(align()) */
#pragma warning(disable:4324)
-/* Disable: warning C4996: 'GetVersionA': was declared deprecated */
+/* Disable: warning C4996: 'GetVersionExA': was declared deprecated */
#pragma warning(disable:4996)
#if defined(_PREFAST_)